aboutsummaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/account.cpp14
-rw-r--r--src/base64.cpp33
-rw-r--r--src/cipher.cpp89
-rw-r--r--src/crypto.cpp22
-rw-r--r--src/memory.cpp6
-rw-r--r--src/olm.cpp77
-rw-r--r--src/pickle.cpp35
-rw-r--r--src/ratchet.cpp60
-rw-r--r--src/session.cpp45
-rw-r--r--src/utility.cpp14
10 files changed, 240 insertions, 155 deletions
diff --git a/src/account.cpp b/src/account.cpp
index e5cbfab..c8e6e40 100644
--- a/src/account.cpp
+++ b/src/account.cpp
@@ -19,7 +19,7 @@
olm::Account::Account(
) : next_one_time_key_id(0),
- last_error(olm::ErrorCode::SUCCESS) {
+ last_error(OlmErrorCode::OLM_SUCCESS) {
}
@@ -56,7 +56,7 @@ std::size_t olm::Account::new_account(
uint8_t const * random, std::size_t random_length
) {
if (random_length < new_account_random_length()) {
- last_error = olm::ErrorCode::NOT_ENOUGH_RANDOM;
+ last_error = OlmErrorCode::OLM_NOT_ENOUGH_RANDOM;
return std::size_t(-1);
}
@@ -110,7 +110,7 @@ std::size_t olm::Account::get_identity_json(
size_t expected_length = get_identity_json_length();
if (identity_json_length < expected_length) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
@@ -146,7 +146,7 @@ std::size_t olm::Account::sign(
std::uint8_t * signature, std::size_t signature_length
) {
if (signature_length < this->signature_length()) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
olm::ed25519_sign(
@@ -185,7 +185,7 @@ std::size_t olm::Account::get_one_time_keys_json(
) {
std::uint8_t * pos = one_time_json;
if (one_time_json_length < get_one_time_keys_json_length()) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
*(pos++) = '{';
@@ -246,7 +246,7 @@ std::size_t olm::Account::generate_one_time_keys(
std::uint8_t const * random, std::size_t random_length
) {
if (random_length < generate_one_time_keys_random_length(number_of_keys)) {
- last_error = olm::ErrorCode::NOT_ENOUGH_RANDOM;
+ last_error = OlmErrorCode::OLM_NOT_ENOUGH_RANDOM;
return std::size_t(-1);
}
for (unsigned i = 0; i < number_of_keys; ++i) {
@@ -361,7 +361,7 @@ std::uint8_t const * olm::unpickle(
uint32_t pickle_version;
pos = olm::unpickle(pos, end, pickle_version);
if (pickle_version != ACCOUNT_PICKLE_VERSION) {
- value.last_error = olm::ErrorCode::UNKNOWN_PICKLE_VERSION;
+ value.last_error = OlmErrorCode::OLM_UNKNOWN_PICKLE_VERSION;
return end;
}
pos = olm::unpickle(pos, end, value.identity_keys);
diff --git a/src/base64.cpp b/src/base64.cpp
index 66f512b..bbfb210 100644
--- a/src/base64.cpp
+++ b/src/base64.cpp
@@ -12,9 +12,9 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
+#include "olm/base64.h"
#include "olm/base64.hh"
-
namespace {
static const std::uint8_t ENCODE_BASE64[64] = {
@@ -134,3 +134,34 @@ std::uint8_t const * olm::decode_base64(
}
return input + input_length;
}
+
+
+// implementations of base64.h
+
+size_t _olm_encode_base64_length(
+ size_t input_length
+) {
+ return olm::encode_base64_length(input_length);
+}
+
+size_t _olm_encode_base64(
+ uint8_t const * input, size_t input_length,
+ uint8_t * output
+) {
+ uint8_t * r = olm::encode_base64(input, input_length, output);
+ return r - output;
+}
+
+size_t _olm_decode_base64_length(
+ size_t input_length
+) {
+ return olm::decode_base64_length(input_length);
+}
+
+size_t _olm_decode_base64(
+ uint8_t const * input, size_t input_length,
+ uint8_t * output
+) {
+ olm::decode_base64(input, input_length, output);
+ return olm::decode_base64_length(input_length);
+}
diff --git a/src/cipher.cpp b/src/cipher.cpp
index 7bb11b8..8c3de92 100644
--- a/src/cipher.cpp
+++ b/src/cipher.cpp
@@ -12,15 +12,11 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-#include "olm/cipher.hh"
+#include "olm/cipher.h"
#include "olm/crypto.hh"
#include "olm/memory.hh"
#include <cstring>
-olm::Cipher::~Cipher() {
-
-}
-
namespace {
struct DerivedKeys {
@@ -36,7 +32,7 @@ static void derive_keys(
DerivedKeys & keys
) {
std::uint8_t derived_secrets[2 * olm::KEY_LENGTH + olm::IV_LENGTH];
- olm::hkdf_sha256(
+ _olm_crypto_hkdf_sha256(
key, key_length,
nullptr, 0,
kdf_info, kdf_info_length,
@@ -51,47 +47,40 @@ static void derive_keys(
static const std::size_t MAC_LENGTH = 8;
-} // namespace
-
-
-olm::CipherAesSha256::CipherAesSha256(
- std::uint8_t const * kdf_info, std::size_t kdf_info_length
-) : kdf_info(kdf_info), kdf_info_length(kdf_info_length) {
-
-}
-
-
-std::size_t olm::CipherAesSha256::mac_length() const {
+size_t aes_sha_256_cipher_mac_length(const struct _olm_cipher *cipher) {
return MAC_LENGTH;
}
-
-std::size_t olm::CipherAesSha256::encrypt_ciphertext_length(
- std::size_t plaintext_length
-) const {
+size_t aes_sha_256_cipher_encrypt_ciphertext_length(
+ const struct _olm_cipher *cipher, size_t plaintext_length
+) {
return olm::aes_encrypt_cbc_length(plaintext_length);
}
+size_t aes_sha_256_cipher_encrypt(
+ const struct _olm_cipher *cipher,
+ uint8_t const * key, size_t key_length,
+ uint8_t const * plaintext, size_t plaintext_length,
+ uint8_t * ciphertext, size_t ciphertext_length,
+ uint8_t * output, size_t output_length
+) {
+ auto *c = reinterpret_cast<const _olm_cipher_aes_sha_256 *>(cipher);
-std::size_t olm::CipherAesSha256::encrypt(
- std::uint8_t const * key, std::size_t key_length,
- std::uint8_t const * plaintext, std::size_t plaintext_length,
- std::uint8_t * ciphertext, std::size_t ciphertext_length,
- std::uint8_t * output, std::size_t output_length
-) const {
- if (encrypt_ciphertext_length(plaintext_length) < ciphertext_length) {
+ if (aes_sha_256_cipher_encrypt_ciphertext_length(cipher, plaintext_length)
+ < ciphertext_length) {
return std::size_t(-1);
}
+
struct DerivedKeys keys;
- std::uint8_t mac[olm::SHA256_OUTPUT_LENGTH];
+ std::uint8_t mac[SHA256_OUTPUT_LENGTH];
- derive_keys(kdf_info, kdf_info_length, key, key_length, keys);
+ derive_keys(c->kdf_info, c->kdf_info_length, key, key_length, keys);
olm::aes_encrypt_cbc(
keys.aes_key, keys.aes_iv, plaintext, plaintext_length, ciphertext
);
- olm::hmac_sha256(
+ _olm_crypto_hmac_sha256(
keys.mac_key, olm::KEY_LENGTH, output, output_length - MAC_LENGTH, mac
);
@@ -102,24 +91,28 @@ std::size_t olm::CipherAesSha256::encrypt(
}
-std::size_t olm::CipherAesSha256::decrypt_max_plaintext_length(
- std::size_t ciphertext_length
-) const {
+size_t aes_sha_256_cipher_decrypt_max_plaintext_length(
+ const struct _olm_cipher *cipher,
+ size_t ciphertext_length
+) {
return ciphertext_length;
}
-std::size_t olm::CipherAesSha256::decrypt(
- std::uint8_t const * key, std::size_t key_length,
- std::uint8_t const * input, std::size_t input_length,
- std::uint8_t const * ciphertext, std::size_t ciphertext_length,
- std::uint8_t * plaintext, std::size_t max_plaintext_length
-) const {
+size_t aes_sha_256_cipher_decrypt(
+ const struct _olm_cipher *cipher,
+ uint8_t const * key, size_t key_length,
+ uint8_t const * input, size_t input_length,
+ uint8_t const * ciphertext, size_t ciphertext_length,
+ uint8_t * plaintext, size_t max_plaintext_length
+) {
+ auto *c = reinterpret_cast<const _olm_cipher_aes_sha_256 *>(cipher);
+
DerivedKeys keys;
- std::uint8_t mac[olm::SHA256_OUTPUT_LENGTH];
+ std::uint8_t mac[SHA256_OUTPUT_LENGTH];
- derive_keys(kdf_info, kdf_info_length, key, key_length, keys);
+ derive_keys(c->kdf_info, c->kdf_info_length, key, key_length, keys);
- olm::hmac_sha256(
+ _olm_crypto_hmac_sha256(
keys.mac_key, olm::KEY_LENGTH, input, input_length - MAC_LENGTH, mac
);
@@ -136,3 +129,13 @@ std::size_t olm::CipherAesSha256::decrypt(
olm::unset(keys);
return plaintext_length;
}
+
+} // namespace
+
+const struct _olm_cipher_ops _olm_cipher_aes_sha_256_ops = {
+ aes_sha_256_cipher_mac_length,
+ aes_sha_256_cipher_encrypt_ciphertext_length,
+ aes_sha_256_cipher_encrypt,
+ aes_sha_256_cipher_decrypt_max_plaintext_length,
+ aes_sha_256_cipher_decrypt,
+};
diff --git a/src/crypto.cpp b/src/crypto.cpp
index ffe2661..4fa92f1 100644
--- a/src/crypto.cpp
+++ b/src/crypto.cpp
@@ -85,7 +85,7 @@ inline static void hmac_sha256_final(
std::uint8_t const * hmac_key,
std::uint8_t * output
) {
- std::uint8_t o_pad[SHA256_BLOCK_LENGTH + olm::SHA256_OUTPUT_LENGTH];
+ std::uint8_t o_pad[SHA256_BLOCK_LENGTH + SHA256_OUTPUT_LENGTH];
std::memcpy(o_pad, hmac_key, SHA256_BLOCK_LENGTH);
for (std::size_t i = 0; i < SHA256_BLOCK_LENGTH; ++i) {
o_pad[i] ^= 0x5C;
@@ -255,7 +255,7 @@ std::size_t olm::aes_decrypt_cbc(
}
-void olm::sha256(
+void _olm_crypto_sha256(
std::uint8_t const * input, std::size_t input_length,
std::uint8_t * output
) {
@@ -267,7 +267,7 @@ void olm::sha256(
}
-void olm::hmac_sha256(
+void _olm_crypto_hmac_sha256(
std::uint8_t const * key, std::size_t key_length,
std::uint8_t const * input, std::size_t input_length,
std::uint8_t * output
@@ -283,7 +283,7 @@ void olm::hmac_sha256(
}
-void olm::hkdf_sha256(
+void _olm_crypto_hkdf_sha256(
std::uint8_t const * input, std::size_t input_length,
std::uint8_t const * salt, std::size_t salt_length,
std::uint8_t const * info, std::size_t info_length,
@@ -291,7 +291,7 @@ void olm::hkdf_sha256(
) {
::SHA256_CTX context;
std::uint8_t hmac_key[SHA256_BLOCK_LENGTH];
- std::uint8_t step_result[olm::SHA256_OUTPUT_LENGTH];
+ std::uint8_t step_result[SHA256_OUTPUT_LENGTH];
std::size_t bytes_remaining = output_length;
std::uint8_t iteration = 1;
if (!salt) {
@@ -303,20 +303,20 @@ void olm::hkdf_sha256(
hmac_sha256_init(&context, hmac_key);
::sha256_update(&context, input, input_length);
hmac_sha256_final(&context, hmac_key, step_result);
- hmac_sha256_key(step_result, olm::SHA256_OUTPUT_LENGTH, hmac_key);
+ hmac_sha256_key(step_result, SHA256_OUTPUT_LENGTH, hmac_key);
/* Expand */
hmac_sha256_init(&context, hmac_key);
::sha256_update(&context, info, info_length);
::sha256_update(&context, &iteration, 1);
hmac_sha256_final(&context, hmac_key, step_result);
- while (bytes_remaining > olm::SHA256_OUTPUT_LENGTH) {
- std::memcpy(output, step_result, olm::SHA256_OUTPUT_LENGTH);
- output += olm::SHA256_OUTPUT_LENGTH;
- bytes_remaining -= olm::SHA256_OUTPUT_LENGTH;
+ while (bytes_remaining > SHA256_OUTPUT_LENGTH) {
+ std::memcpy(output, step_result, SHA256_OUTPUT_LENGTH);
+ output += SHA256_OUTPUT_LENGTH;
+ bytes_remaining -= SHA256_OUTPUT_LENGTH;
iteration ++;
hmac_sha256_init(&context, hmac_key);
- ::sha256_update(&context, step_result, olm::SHA256_OUTPUT_LENGTH);
+ ::sha256_update(&context, step_result, SHA256_OUTPUT_LENGTH);
::sha256_update(&context, info, info_length);
::sha256_update(&context, &iteration, 1);
hmac_sha256_final(&context, hmac_key, step_result);
diff --git a/src/memory.cpp b/src/memory.cpp
index 16a4683..20e0683 100644
--- a/src/memory.cpp
+++ b/src/memory.cpp
@@ -13,7 +13,13 @@
* limitations under the License.
*/
#include "olm/memory.hh"
+#include "olm/memory.h"
+void _olm_unset(
+ void volatile * buffer, size_t buffer_length
+) {
+ olm::unset(buffer, buffer_length);
+}
void olm::unset(
void volatile * buffer, std::size_t buffer_length
diff --git a/src/olm.cpp b/src/olm.cpp
index 4e5f215..fcd033a 100644
--- a/src/olm.cpp
+++ b/src/olm.cpp
@@ -12,12 +12,12 @@
* See the License for the specific language governing permissions and
* limitations under the License.
*/
-#include "olm/olm.hh"
+#include "olm/olm.h"
#include "olm/session.hh"
#include "olm/account.hh"
+#include "olm/cipher.h"
#include "olm/utility.hh"
#include "olm/base64.hh"
-#include "olm/cipher.hh"
#include "olm/memory.hh"
#include <new>
@@ -57,17 +57,15 @@ static std::uint8_t const * from_c(void const * bytes) {
return reinterpret_cast<std::uint8_t const *>(bytes);
}
-static const std::uint8_t CIPHER_KDF_INFO[] = "Pickle";
-
-static const olm::CipherAesSha256 PICKLE_CIPHER(
- CIPHER_KDF_INFO, sizeof(CIPHER_KDF_INFO) -1
-);
+static const struct _olm_cipher_aes_sha_256 PICKLE_CIPHER =
+ OLM_CIPHER_INIT_AES_SHA_256("Pickle");
std::size_t enc_output_length(
size_t raw_length
) {
- std::size_t length = PICKLE_CIPHER.encrypt_ciphertext_length(raw_length);
- length += PICKLE_CIPHER.mac_length();
+ auto *cipher = OLM_CIPHER_BASE(&PICKLE_CIPHER);
+ std::size_t length = cipher->ops->encrypt_ciphertext_length(cipher, raw_length);
+ length += cipher->ops->mac_length(cipher);
return olm::encode_base64_length(length);
}
@@ -76,8 +74,9 @@ std::uint8_t * enc_output_pos(
std::uint8_t * output,
size_t raw_length
) {
- std::size_t length = PICKLE_CIPHER.encrypt_ciphertext_length(raw_length);
- length += PICKLE_CIPHER.mac_length();
+ auto *cipher = OLM_CIPHER_BASE(&PICKLE_CIPHER);
+ std::size_t length = cipher->ops->encrypt_ciphertext_length(cipher, raw_length);
+ length += cipher->ops->mac_length(cipher);
return output + olm::encode_base64_length(length) - length;
}
@@ -85,13 +84,15 @@ std::size_t enc_output(
std::uint8_t const * key, std::size_t key_length,
std::uint8_t * output, size_t raw_length
) {
- std::size_t ciphertext_length = PICKLE_CIPHER.encrypt_ciphertext_length(
- raw_length
+ auto *cipher = OLM_CIPHER_BASE(&PICKLE_CIPHER);
+ std::size_t ciphertext_length = cipher->ops->encrypt_ciphertext_length(
+ cipher, raw_length
);
- std::size_t length = ciphertext_length + PICKLE_CIPHER.mac_length();
+ std::size_t length = ciphertext_length + cipher->ops->mac_length(cipher);
std::size_t base64_length = olm::encode_base64_length(length);
std::uint8_t * raw_output = output + base64_length - length;
- PICKLE_CIPHER.encrypt(
+ cipher->ops->encrypt(
+ cipher,
key, key_length,
raw_output, raw_length,
raw_output, ciphertext_length,
@@ -104,23 +105,25 @@ std::size_t enc_output(
std::size_t enc_input(
std::uint8_t const * key, std::size_t key_length,
std::uint8_t * input, size_t b64_length,
- olm::ErrorCode & last_error
+ OlmErrorCode & last_error
) {
std::size_t enc_length = olm::decode_base64_length(b64_length);
if (enc_length == std::size_t(-1)) {
- last_error = olm::ErrorCode::INVALID_BASE64;
+ last_error = OlmErrorCode::OLM_INVALID_BASE64;
return std::size_t(-1);
}
olm::decode_base64(input, b64_length, input);
- std::size_t raw_length = enc_length - PICKLE_CIPHER.mac_length();
- std::size_t result = PICKLE_CIPHER.decrypt(
+ auto *cipher = OLM_CIPHER_BASE(&PICKLE_CIPHER);
+ std::size_t raw_length = enc_length - cipher->ops->mac_length(cipher);
+ std::size_t result = cipher->ops->decrypt(
+ cipher,
key, key_length,
input, enc_length,
input, raw_length,
input, raw_length
);
if (result == std::size_t(-1)) {
- last_error = olm::ErrorCode::BAD_ACCOUNT_KEY;
+ last_error = OlmErrorCode::OLM_BAD_ACCOUNT_KEY;
}
return result;
}
@@ -150,11 +153,11 @@ std::size_t b64_output(
std::size_t b64_input(
std::uint8_t * input, size_t b64_length,
- olm::ErrorCode & last_error
+ OlmErrorCode & last_error
) {
std::size_t raw_length = olm::decode_base64_length(b64_length);
if (raw_length == std::size_t(-1)) {
- last_error = olm::ErrorCode::INVALID_BASE64;
+ last_error = OlmErrorCode::OLM_INVALID_BASE64;
return std::size_t(-1);
}
olm::decode_base64(input, b64_length, input);
@@ -312,7 +315,7 @@ size_t olm_pickle_account(
olm::Account & object = *from_c(account);
std::size_t raw_length = pickle_length(object);
if (pickled_length < enc_output_length(raw_length)) {
- object.last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ object.last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return size_t(-1);
}
pickle(enc_output_pos(from_c(pickled), raw_length), object);
@@ -328,7 +331,7 @@ size_t olm_pickle_session(
olm::Session & object = *from_c(session);
std::size_t raw_length = pickle_length(object);
if (pickled_length < enc_output_length(raw_length)) {
- object.last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ object.last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return size_t(-1);
}
pickle(enc_output_pos(from_c(pickled), raw_length), object);
@@ -355,8 +358,8 @@ size_t olm_unpickle_account(
* (pos + raw_length). On error unpickle will return (pos + raw_length + 1).
*/
if (end != unpickle(pos, end + 1, object)) {
- if (object.last_error == olm::ErrorCode::SUCCESS) {
- object.last_error = olm::ErrorCode::CORRUPTED_PICKLE;
+ if (object.last_error == OlmErrorCode::OLM_SUCCESS) {
+ object.last_error = OlmErrorCode::OLM_CORRUPTED_PICKLE;
}
return std::size_t(-1);
}
@@ -384,8 +387,8 @@ size_t olm_unpickle_session(
* (pos + raw_length). On error unpickle will return (pos + raw_length + 1).
*/
if (end != unpickle(pos, end + 1, object)) {
- if (object.last_error == olm::ErrorCode::SUCCESS) {
- object.last_error = olm::ErrorCode::CORRUPTED_PICKLE;
+ if (object.last_error == OlmErrorCode::OLM_SUCCESS) {
+ object.last_error = OlmErrorCode::OLM_CORRUPTED_PICKLE;
}
return std::size_t(-1);
}
@@ -442,7 +445,7 @@ size_t olm_account_sign(
std::size_t raw_length = from_c(account)->signature_length();
if (signature_length < b64_output_length(raw_length)) {
from_c(account)->last_error =
- olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
from_c(account)->sign(
@@ -528,7 +531,7 @@ size_t olm_create_outbound_session(
if (olm::decode_base64_length(id_key_length) != olm::KEY_LENGTH
|| olm::decode_base64_length(ot_key_length) != olm::KEY_LENGTH
) {
- from_c(session)->last_error = olm::ErrorCode::INVALID_BASE64;
+ from_c(session)->last_error = OlmErrorCode::OLM_INVALID_BASE64;
return std::size_t(-1);
}
olm::Curve25519PublicKey identity_key;
@@ -573,7 +576,7 @@ size_t olm_create_inbound_session_from(
std::size_t id_key_length = their_identity_key_length;
if (olm::decode_base64_length(id_key_length) != olm::KEY_LENGTH) {
- from_c(session)->last_error = olm::ErrorCode::INVALID_BASE64;
+ from_c(session)->last_error = OlmErrorCode::OLM_INVALID_BASE64;
return std::size_t(-1);
}
olm::Curve25519PublicKey identity_key;
@@ -605,7 +608,7 @@ size_t olm_session_id(
std::size_t raw_length = from_c(session)->session_id_length();
if (id_length < b64_output_length(raw_length)) {
from_c(session)->last_error =
- olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
std::size_t result = from_c(session)->session_id(
@@ -644,7 +647,7 @@ size_t olm_matches_inbound_session_from(
std::size_t id_key_length = their_identity_key_length;
if (olm::decode_base64_length(id_key_length) != olm::KEY_LENGTH) {
- from_c(session)->last_error = olm::ErrorCode::INVALID_BASE64;
+ from_c(session)->last_error = OlmErrorCode::OLM_INVALID_BASE64;
return std::size_t(-1);
}
olm::Curve25519PublicKey identity_key;
@@ -671,7 +674,7 @@ size_t olm_remove_one_time_keys(
from_c(session)->bob_one_time_key
);
if (result == std::size_t(-1)) {
- from_c(account)->last_error = olm::ErrorCode::BAD_MESSAGE_KEY_ID;
+ from_c(account)->last_error = OlmErrorCode::OLM_BAD_MESSAGE_KEY_ID;
}
return result;
}
@@ -712,7 +715,7 @@ size_t olm_encrypt(
);
if (message_length < b64_output_length(raw_length)) {
from_c(session)->last_error =
- olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
std::size_t result = from_c(session)->encrypt(
@@ -779,7 +782,7 @@ size_t olm_sha256(
std::size_t raw_length = from_c(utility)->sha256_length();
if (output_length < b64_output_length(raw_length)) {
from_c(utility)->last_error =
- olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
std::size_t result = from_c(utility)->sha256(
@@ -800,7 +803,7 @@ size_t olm_ed25519_verify(
void * signature, size_t signature_length
) {
if (olm::decode_base64_length(key_length) != olm::KEY_LENGTH) {
- from_c(utility)->last_error = olm::ErrorCode::INVALID_BASE64;
+ from_c(utility)->last_error = OlmErrorCode::OLM_INVALID_BASE64;
return std::size_t(-1);
}
olm::Ed25519PublicKey verify_key;
diff --git a/src/pickle.cpp b/src/pickle.cpp
index 00f7cd4..fc3e2b4 100644
--- a/src/pickle.cpp
+++ b/src/pickle.cpp
@@ -13,6 +13,7 @@
* limitations under the License.
*/
#include "olm/pickle.hh"
+#include "olm/pickle.h"
std::uint8_t * olm::pickle(
std::uint8_t * pos,
@@ -196,3 +197,37 @@ std::uint8_t const * olm::unpickle(
);
return pos;
}
+
+////// pickle.h implementations
+
+uint8_t * _olm_pickle_uint32(uint8_t * pos, uint32_t value) {
+ return olm::pickle(pos, value);
+}
+
+uint8_t const * _olm_unpickle_uint32(
+ uint8_t const * pos, uint8_t const * end,
+ uint32_t *value
+) {
+ return olm::unpickle(pos, end, *value);
+}
+
+uint8_t * _olm_pickle_bool(uint8_t * pos, int value) {
+ return olm::pickle(pos, (bool)value);
+}
+
+uint8_t const * _olm_unpickle_bool(
+ uint8_t const * pos, uint8_t const * end,
+ int *value
+) {
+ return olm::unpickle(pos, end, *reinterpret_cast<bool *>(value));
+}
+
+uint8_t * _olm_pickle_bytes(uint8_t * pos, uint8_t const * bytes,
+ size_t bytes_length) {
+ return olm::pickle_bytes(pos, bytes, bytes_length);
+}
+
+uint8_t const * _olm_unpickle_bytes(uint8_t const * pos, uint8_t const * end,
+ uint8_t * bytes, size_t bytes_length) {
+ return olm::unpickle_bytes(pos, end, bytes, bytes_length);
+}
diff --git a/src/ratchet.cpp b/src/ratchet.cpp
index b04099f..abcc8a1 100644
--- a/src/ratchet.cpp
+++ b/src/ratchet.cpp
@@ -15,7 +15,7 @@
#include "olm/ratchet.hh"
#include "olm/message.hh"
#include "olm/memory.hh"
-#include "olm/cipher.hh"
+#include "olm/cipher.h"
#include "olm/pickle.hh"
#include <cstring>
@@ -50,7 +50,7 @@ static void create_chain_key(
olm::SharedKey secret;
olm::curve25519_shared_secret(our_key, their_key, secret);
std::uint8_t derived_secrets[2 * olm::KEY_LENGTH];
- olm::hkdf_sha256(
+ _olm_crypto_hkdf_sha256(
secret, sizeof(secret),
root_key, sizeof(root_key),
info.ratchet_info, info.ratchet_info_length,
@@ -70,7 +70,7 @@ static void advance_chain_key(
olm::ChainKey const & chain_key,
olm::ChainKey & new_chain_key
) {
- olm::hmac_sha256(
+ _olm_crypto_hmac_sha256(
chain_key.key, sizeof(chain_key.key),
CHAIN_KEY_SEED, sizeof(CHAIN_KEY_SEED),
new_chain_key.key
@@ -84,7 +84,7 @@ static void create_message_keys(
olm::ChainKey const & chain_key,
olm::KdfInfo const & info,
olm::MessageKey & message_key) {
- olm::hmac_sha256(
+ _olm_crypto_hmac_sha256(
chain_key.key, sizeof(chain_key.key),
MESSAGE_KEY_SEED, sizeof(MESSAGE_KEY_SEED),
message_key.key
@@ -94,12 +94,13 @@ static void create_message_keys(
static std::size_t verify_mac_and_decrypt(
- olm::Cipher const & cipher,
+ _olm_cipher const *cipher,
olm::MessageKey const & message_key,
olm::MessageReader const & reader,
std::uint8_t * plaintext, std::size_t max_plaintext_length
) {
- return cipher.decrypt(
+ return cipher->ops->decrypt(
+ cipher,
message_key.key, sizeof(message_key.key),
reader.input, reader.input_length,
reader.ciphertext, reader.ciphertext_length,
@@ -183,10 +184,10 @@ static std::size_t verify_mac_and_decrypt_for_new_chain(
olm::Ratchet::Ratchet(
olm::KdfInfo const & kdf_info,
- Cipher const & ratchet_cipher
+ _olm_cipher const * ratchet_cipher
) : kdf_info(kdf_info),
ratchet_cipher(ratchet_cipher),
- last_error(olm::ErrorCode::SUCCESS) {
+ last_error(OlmErrorCode::OLM_SUCCESS) {
}
@@ -195,7 +196,7 @@ void olm::Ratchet::initialise_as_bob(
olm::Curve25519PublicKey const & their_ratchet_key
) {
std::uint8_t derived_secrets[2 * olm::KEY_LENGTH];
- olm::hkdf_sha256(
+ _olm_crypto_hkdf_sha256(
shared_secret, shared_secret_length,
nullptr, 0,
kdf_info.root_info, kdf_info.root_info_length,
@@ -217,7 +218,7 @@ void olm::Ratchet::initialise_as_alice(
olm::Curve25519KeyPair const & our_ratchet_key
) {
std::uint8_t derived_secrets[2 * olm::KEY_LENGTH];
- olm::hkdf_sha256(
+ _olm_crypto_hkdf_sha256(
shared_secret, shared_secret_length,
nullptr, 0,
kdf_info.root_info, kdf_info.root_info_length,
@@ -405,11 +406,12 @@ std::size_t olm::Ratchet::encrypt_output_length(
if (!sender_chain.empty()) {
counter = sender_chain[0].chain_key.index;
}
- std::size_t padded = ratchet_cipher.encrypt_ciphertext_length(
+ std::size_t padded = ratchet_cipher->ops->encrypt_ciphertext_length(
+ ratchet_cipher,
plaintext_length
);
return olm::encode_message_length(
- counter, olm::KEY_LENGTH, padded, ratchet_cipher.mac_length()
+ counter, olm::KEY_LENGTH, padded, ratchet_cipher->ops->mac_length(ratchet_cipher)
);
}
@@ -427,11 +429,11 @@ std::size_t olm::Ratchet::encrypt(
std::size_t output_length = encrypt_output_length(plaintext_length);
if (random_length < encrypt_random_length()) {
- last_error = olm::ErrorCode::NOT_ENOUGH_RANDOM;
+ last_error = OlmErrorCode::OLM_NOT_ENOUGH_RANDOM;
return std::size_t(-1);
}
if (max_output_length < output_length) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
@@ -452,7 +454,8 @@ std::size_t olm::Ratchet::encrypt(
create_message_keys(chain_index, sender_chain[0].chain_key, kdf_info, keys);
advance_chain_key(chain_index, sender_chain[0].chain_key, sender_chain[0].chain_key);
- std::size_t ciphertext_length = ratchet_cipher.encrypt_ciphertext_length(
+ std::size_t ciphertext_length = ratchet_cipher->ops->encrypt_ciphertext_length(
+ ratchet_cipher,
plaintext_length
);
std::uint32_t counter = keys.index;
@@ -467,7 +470,8 @@ std::size_t olm::Ratchet::encrypt(
olm::store_array(writer.ratchet_key, ratchet_key.public_key);
- ratchet_cipher.encrypt(
+ ratchet_cipher->ops->encrypt(
+ ratchet_cipher,
keys.key, sizeof(keys.key),
plaintext, plaintext_length,
writer.ciphertext, ciphertext_length,
@@ -484,15 +488,17 @@ std::size_t olm::Ratchet::decrypt_max_plaintext_length(
) {
olm::MessageReader reader;
olm::decode_message(
- reader, input, input_length, ratchet_cipher.mac_length()
+ reader, input, input_length,
+ ratchet_cipher->ops->mac_length(ratchet_cipher)
);
if (!reader.ciphertext) {
- last_error = olm::ErrorCode::BAD_MESSAGE_FORMAT;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_FORMAT;
return std::size_t(-1);
}
- return ratchet_cipher.decrypt_max_plaintext_length(reader.ciphertext_length);
+ return ratchet_cipher->ops->decrypt_max_plaintext_length(
+ ratchet_cipher, reader.ciphertext_length);
}
@@ -502,30 +508,32 @@ std::size_t olm::Ratchet::decrypt(
) {
olm::MessageReader reader;
olm::decode_message(
- reader, input, input_length, ratchet_cipher.mac_length()
+ reader, input, input_length,
+ ratchet_cipher->ops->mac_length(ratchet_cipher)
);
if (reader.version != PROTOCOL_VERSION) {
- last_error = olm::ErrorCode::BAD_MESSAGE_VERSION;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_VERSION;
return std::size_t(-1);
}
if (!reader.has_counter || !reader.ratchet_key || !reader.ciphertext) {
- last_error = olm::ErrorCode::BAD_MESSAGE_FORMAT;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_FORMAT;
return std::size_t(-1);
}
- std::size_t max_length = ratchet_cipher.decrypt_max_plaintext_length(
+ std::size_t max_length = ratchet_cipher->ops->decrypt_max_plaintext_length(
+ ratchet_cipher,
reader.ciphertext_length
);
if (max_plaintext_length < max_length) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
if (reader.ratchet_key_length != olm::KEY_LENGTH) {
- last_error = olm::ErrorCode::BAD_MESSAGE_FORMAT;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_FORMAT;
return std::size_t(-1);
}
@@ -588,7 +596,7 @@ std::size_t olm::Ratchet::decrypt(
}
if (result == std::size_t(-1)) {
- last_error = olm::ErrorCode::BAD_MESSAGE_MAC;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_MAC;
return std::size_t(-1);
}
diff --git a/src/session.cpp b/src/session.cpp
index 86ba63b..c148c97 100644
--- a/src/session.cpp
+++ b/src/session.cpp
@@ -13,7 +13,7 @@
* limitations under the License.
*/
#include "olm/session.hh"
-#include "olm/cipher.hh"
+#include "olm/cipher.h"
#include "olm/crypto.hh"
#include "olm/account.hh"
#include "olm/memory.hh"
@@ -30,20 +30,19 @@ static const std::uint8_t ROOT_KDF_INFO[] = "OLM_ROOT";
static const std::uint8_t RATCHET_KDF_INFO[] = "OLM_RATCHET";
static const std::uint8_t CIPHER_KDF_INFO[] = "OLM_KEYS";
-static const olm::CipherAesSha256 OLM_CIPHER(
- CIPHER_KDF_INFO, sizeof(CIPHER_KDF_INFO) -1
-);
-
static const olm::KdfInfo OLM_KDF_INFO = {
ROOT_KDF_INFO, sizeof(ROOT_KDF_INFO) - 1,
RATCHET_KDF_INFO, sizeof(RATCHET_KDF_INFO) - 1
};
+static const struct _olm_cipher_aes_sha_256 OLM_CIPHER =
+ OLM_CIPHER_INIT_AES_SHA_256(CIPHER_KDF_INFO);
+
} // namespace
olm::Session::Session(
-) : ratchet(OLM_KDF_INFO, OLM_CIPHER),
- last_error(olm::ErrorCode::SUCCESS),
+) : ratchet(OLM_KDF_INFO, OLM_CIPHER_BASE(&OLM_CIPHER)),
+ last_error(OlmErrorCode::OLM_SUCCESS),
received_message(false) {
}
@@ -61,7 +60,7 @@ std::size_t olm::Session::new_outbound_session(
std::uint8_t const * random, std::size_t random_length
) {
if (random_length < new_outbound_session_random_length()) {
- last_error = olm::ErrorCode::NOT_ENOUGH_RANDOM;
+ last_error = OlmErrorCode::OLM_NOT_ENOUGH_RANDOM;
return std::size_t(-1);
}
@@ -128,7 +127,7 @@ std::size_t olm::Session::new_inbound_session(
decode_one_time_key_message(reader, one_time_key_message, message_length);
if (!check_message_fields(reader, their_identity_key)) {
- last_error = olm::ErrorCode::BAD_MESSAGE_FORMAT;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_FORMAT;
return std::size_t(-1);
}
@@ -137,7 +136,7 @@ std::size_t olm::Session::new_inbound_session(
their_identity_key->public_key, reader.identity_key, olm::KEY_LENGTH
);
if (!same) {
- last_error = olm::ErrorCode::BAD_MESSAGE_KEY_ID;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_KEY_ID;
return std::size_t(-1);
}
}
@@ -149,12 +148,12 @@ std::size_t olm::Session::new_inbound_session(
olm::MessageReader message_reader;
decode_message(
message_reader, reader.message, reader.message_length,
- ratchet.ratchet_cipher.mac_length()
+ ratchet.ratchet_cipher->ops->mac_length(ratchet.ratchet_cipher)
);
if (!message_reader.ratchet_key
|| message_reader.ratchet_key_length != olm::KEY_LENGTH) {
- last_error = olm::ErrorCode::BAD_MESSAGE_FORMAT;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_FORMAT;
return std::size_t(-1);
}
@@ -166,7 +165,7 @@ std::size_t olm::Session::new_inbound_session(
);
if (!our_one_time_key) {
- last_error = olm::ErrorCode::BAD_MESSAGE_KEY_ID;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_KEY_ID;
return std::size_t(-1);
}
@@ -192,7 +191,7 @@ std::size_t olm::Session::new_inbound_session(
std::size_t olm::Session::session_id_length() {
- return olm::SHA256_OUTPUT_LENGTH;
+ return SHA256_OUTPUT_LENGTH;
}
@@ -200,7 +199,7 @@ std::size_t olm::Session::session_id(
std::uint8_t * id, std::size_t id_length
) {
if (id_length < session_id_length()) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
std::uint8_t tmp[olm::KEY_LENGTH * 3];
@@ -208,7 +207,7 @@ std::size_t olm::Session::session_id(
pos = olm::store_array(pos, alice_identity_key.public_key);
pos = olm::store_array(pos, alice_base_key.public_key);
pos = olm::store_array(pos, bob_one_time_key.public_key);
- olm::sha256(tmp, sizeof(tmp), id);
+ _olm_crypto_sha256(tmp, sizeof(tmp), id);
return session_id_length();
}
@@ -286,7 +285,7 @@ std::size_t olm::Session::encrypt(
std::uint8_t * message, std::size_t message_length
) {
if (message_length < encrypt_message_length(plaintext_length)) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
std::uint8_t * message_body;
@@ -321,7 +320,7 @@ std::size_t olm::Session::encrypt(
if (result == std::size_t(-1)) {
last_error = ratchet.last_error;
- ratchet.last_error = olm::ErrorCode::SUCCESS;
+ ratchet.last_error = OlmErrorCode::OLM_SUCCESS;
return result;
}
@@ -342,7 +341,7 @@ std::size_t olm::Session::decrypt_max_plaintext_length(
olm::PreKeyMessageReader reader;
decode_one_time_key_message(reader, message, message_length);
if (!reader.message) {
- last_error = olm::ErrorCode::BAD_MESSAGE_FORMAT;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_FORMAT;
return std::size_t(-1);
}
message_body = reader.message;
@@ -355,7 +354,7 @@ std::size_t olm::Session::decrypt_max_plaintext_length(
if (result == std::size_t(-1)) {
last_error = ratchet.last_error;
- ratchet.last_error = olm::ErrorCode::SUCCESS;
+ ratchet.last_error = OlmErrorCode::OLM_SUCCESS;
}
return result;
}
@@ -375,7 +374,7 @@ std::size_t olm::Session::decrypt(
olm::PreKeyMessageReader reader;
decode_one_time_key_message(reader, message, message_length);
if (!reader.message) {
- last_error = olm::ErrorCode::BAD_MESSAGE_FORMAT;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_FORMAT;
return std::size_t(-1);
}
message_body = reader.message;
@@ -388,7 +387,7 @@ std::size_t olm::Session::decrypt(
if (result == std::size_t(-1)) {
last_error = ratchet.last_error;
- ratchet.last_error = olm::ErrorCode::SUCCESS;
+ ratchet.last_error = OlmErrorCode::OLM_SUCCESS;
return result;
}
@@ -435,7 +434,7 @@ std::uint8_t const * olm::unpickle(
uint32_t pickle_version;
pos = olm::unpickle(pos, end, pickle_version);
if (pickle_version != SESSION_PICKLE_VERSION) {
- value.last_error = olm::ErrorCode::UNKNOWN_PICKLE_VERSION;
+ value.last_error = OlmErrorCode::OLM_UNKNOWN_PICKLE_VERSION;
return end;
}
pos = olm::unpickle(pos, end, value.received_message);
diff --git a/src/utility.cpp b/src/utility.cpp
index bc51cff..67029c9 100644
--- a/src/utility.cpp
+++ b/src/utility.cpp
@@ -18,12 +18,12 @@
olm::Utility::Utility(
-) : last_error(olm::ErrorCode::SUCCESS) {
+) : last_error(OlmErrorCode::OLM_SUCCESS) {
}
size_t olm::Utility::sha256_length() {
- return olm::SHA256_OUTPUT_LENGTH;
+ return SHA256_OUTPUT_LENGTH;
}
@@ -32,11 +32,11 @@ size_t olm::Utility::sha256(
std::uint8_t * output, std::size_t output_length
) {
if (output_length < sha256_length()) {
- last_error = olm::ErrorCode::OUTPUT_BUFFER_TOO_SMALL;
+ last_error = OlmErrorCode::OLM_OUTPUT_BUFFER_TOO_SMALL;
return std::size_t(-1);
}
- olm::sha256(input, input_length, output);
- return olm::SHA256_OUTPUT_LENGTH;
+ _olm_crypto_sha256(input, input_length, output);
+ return SHA256_OUTPUT_LENGTH;
}
@@ -46,11 +46,11 @@ size_t olm::Utility::ed25519_verify(
std::uint8_t const * signature, std::size_t signature_length
) {
if (signature_length < olm::SIGNATURE_LENGTH) {
- last_error = olm::ErrorCode::BAD_MESSAGE_MAC;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_MAC;
return std::size_t(-1);
}
if (!olm::ed25519_verify(key, message, message_length, signature)) {
- last_error = olm::ErrorCode::BAD_MESSAGE_MAC;
+ last_error = OlmErrorCode::OLM_BAD_MESSAGE_MAC;
return std::size_t(-1);
}
return std::size_t(0);