mirror of
https://git.jabber.space/devs/cproof.git
synced 2026-07-27 14:56:21 +00:00
Merge pull request #2137 from profanity-im/omemo-prekey
fix(omemo): standardize PreKey management to prevent decryption failures
This commit is contained in:
@@ -78,6 +78,7 @@ typedef struct omemo_context
|
|||||||
ratchet_identity_key_pair* identity_key_pair;
|
ratchet_identity_key_pair* identity_key_pair;
|
||||||
uint32_t registration_id;
|
uint32_t registration_id;
|
||||||
uint32_t signed_pre_key_id;
|
uint32_t signed_pre_key_id;
|
||||||
|
uint32_t max_pre_key_id;
|
||||||
signal_protocol_store_context* store;
|
signal_protocol_store_context* store;
|
||||||
GHashTable* session_store;
|
GHashTable* session_store;
|
||||||
GHashTable* pre_key_store;
|
GHashTable* pre_key_store;
|
||||||
@@ -323,6 +324,7 @@ omemo_generate_crypto_materials(ProfAccount* account)
|
|||||||
g_key_file_set_uint64(omemo_ctx.identity.keyfile, OMEMO_STORE_GROUP_IDENTITY, OMEMO_STORE_KEY_REGISTRATION_ID, omemo_ctx.registration_id);
|
g_key_file_set_uint64(omemo_ctx.identity.keyfile, OMEMO_STORE_GROUP_IDENTITY, OMEMO_STORE_KEY_REGISTRATION_ID, omemo_ctx.registration_id);
|
||||||
|
|
||||||
/* Pre keys */
|
/* Pre keys */
|
||||||
|
omemo_ctx.max_pre_key_id = 0;
|
||||||
_generate_pre_keys(100);
|
_generate_pre_keys(100);
|
||||||
|
|
||||||
/* Signed pre key */
|
/* Signed pre key */
|
||||||
@@ -1095,16 +1097,17 @@ omemo_on_message_recv(const char* const from_jid, uint32_t sid,
|
|||||||
signal_buffer_len(identity_buffer), &omemo_ctx.identity_key_store);
|
signal_buffer_len(identity_buffer), &omemo_ctx.identity_key_store);
|
||||||
signal_buffer_free(identity_buffer);
|
signal_buffer_free(identity_buffer);
|
||||||
|
|
||||||
/* Replace used pre_key in bundle */
|
/* Remove used pre_key from store */
|
||||||
uint32_t pre_key_id = pre_key_signal_message_get_pre_key_id(message);
|
uint32_t pre_key_id = pre_key_signal_message_get_pre_key_id(message);
|
||||||
ec_key_pair* ec_pair;
|
signal_protocol_pre_key_remove_key(omemo_ctx.store, pre_key_id);
|
||||||
session_pre_key* new_pre_key;
|
|
||||||
curve_generate_key_pair(omemo_ctx.signal, &ec_pair);
|
/* If we have few pre_keys left, generate more */
|
||||||
session_pre_key_create(&new_pre_key, pre_key_id, ec_pair);
|
if (g_hash_table_size(omemo_ctx.pre_key_store) < 10) {
|
||||||
signal_protocol_pre_key_store_key(omemo_ctx.store, new_pre_key);
|
log_debug("[OMEMO] Few pre keys left, generating more");
|
||||||
SIGNAL_UNREF(new_pre_key);
|
_generate_pre_keys(100);
|
||||||
|
}
|
||||||
|
|
||||||
SIGNAL_UNREF(message);
|
SIGNAL_UNREF(message);
|
||||||
SIGNAL_UNREF(ec_pair);
|
|
||||||
omemo_bundle_publish(TRUE);
|
omemo_bundle_publish(TRUE);
|
||||||
|
|
||||||
if (res == 0) {
|
if (res == 0) {
|
||||||
@@ -1784,14 +1787,19 @@ _load_identity(void)
|
|||||||
int i;
|
int i;
|
||||||
/* Pre keys */
|
/* Pre keys */
|
||||||
i = 0;
|
i = 0;
|
||||||
|
omemo_ctx.max_pre_key_id = 0;
|
||||||
keys = g_key_file_get_keys(omemo_ctx.identity.keyfile, OMEMO_STORE_GROUP_PREKEYS, NULL, NULL);
|
keys = g_key_file_get_keys(omemo_ctx.identity.keyfile, OMEMO_STORE_GROUP_PREKEYS, NULL, NULL);
|
||||||
if (keys) {
|
if (keys) {
|
||||||
for (i = 0; keys[i] != NULL; i++) {
|
for (i = 0; keys[i] != NULL; i++) {
|
||||||
|
uint32_t id = strtoul(keys[i], NULL, 10);
|
||||||
|
if (id > omemo_ctx.max_pre_key_id) {
|
||||||
|
omemo_ctx.max_pre_key_id = id;
|
||||||
|
}
|
||||||
auto_gchar gchar* pre_key_b64 = g_key_file_get_string(omemo_ctx.identity.keyfile, OMEMO_STORE_GROUP_PREKEYS, keys[i], NULL);
|
auto_gchar gchar* pre_key_b64 = g_key_file_get_string(omemo_ctx.identity.keyfile, OMEMO_STORE_GROUP_PREKEYS, keys[i], NULL);
|
||||||
size_t pre_key_len;
|
size_t pre_key_len;
|
||||||
auto_guchar guchar* pre_key = g_base64_decode(pre_key_b64, &pre_key_len);
|
auto_guchar guchar* pre_key = g_base64_decode(pre_key_b64, &pre_key_len);
|
||||||
signal_buffer* buffer = signal_buffer_create(pre_key, pre_key_len);
|
signal_buffer* buffer = signal_buffer_create(pre_key, pre_key_len);
|
||||||
g_hash_table_insert(omemo_ctx.pre_key_store, GINT_TO_POINTER(strtoul(keys[i], NULL, 10)), buffer);
|
g_hash_table_insert(omemo_ctx.pre_key_store, GINT_TO_POINTER(id), buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
g_strfreev(keys);
|
g_strfreev(keys);
|
||||||
@@ -1980,8 +1988,7 @@ _cache_device_identity(const char* const jid, uint32_t device_id, ec_public_key*
|
|||||||
static void
|
static void
|
||||||
_generate_pre_keys(int count)
|
_generate_pre_keys(int count)
|
||||||
{
|
{
|
||||||
unsigned int start;
|
uint32_t start = omemo_ctx.max_pre_key_id + 1;
|
||||||
gcry_randomize(&start, sizeof(unsigned int), GCRY_VERY_STRONG_RANDOM);
|
|
||||||
signal_protocol_key_helper_pre_key_list_node* pre_keys_head;
|
signal_protocol_key_helper_pre_key_list_node* pre_keys_head;
|
||||||
signal_protocol_key_helper_generate_pre_keys(&pre_keys_head, start, count, omemo_ctx.signal);
|
signal_protocol_key_helper_generate_pre_keys(&pre_keys_head, start, count, omemo_ctx.signal);
|
||||||
|
|
||||||
@@ -1991,6 +1998,8 @@ _generate_pre_keys(int count)
|
|||||||
signal_protocol_pre_key_store_key(omemo_ctx.store, prekey);
|
signal_protocol_pre_key_store_key(omemo_ctx.store, prekey);
|
||||||
}
|
}
|
||||||
signal_protocol_key_helper_key_list_free(pre_keys_head);
|
signal_protocol_key_helper_key_list_free(pre_keys_head);
|
||||||
|
|
||||||
|
omemo_ctx.max_pre_key_id += count;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void
|
static void
|
||||||
|
|||||||
Reference in New Issue
Block a user