diff options
author | Dr. David Alan Gilbert <dave@treblig.org> | 2017-03-26 20:13:57 +0100 |
---|---|---|
committer | Dr. David Alan Gilbert <dave@treblig.org> | 2018-02-25 02:08:49 +0000 |
commit | 437f18c038134fc2f8541e2d55728b72d2392103 (patch) | |
tree | 40454e23d6aeb856cbf3c887747bdc07745c5b6a | |
parent | 9fb00bdd6244e31852e913d5fe2720daab52d6d4 (diff) | |
download | purple-matrix-437f18c038134fc2f8541e2d55728b72d2392103.tar.gz |
e2e: Route decrypted messages back up
Parse the decrypted JSON and route it back up to the room code.
Signed-off-by: Dr. David Alan Gilbert <dave@treblig.org>
-rw-r--r-- | matrix-e2e.c | 35 | ||||
-rw-r--r-- | matrix-e2e.h | 2 | ||||
-rw-r--r-- | matrix-room.c | 27 |
3 files changed, 52 insertions, 12 deletions
diff --git a/matrix-e2e.c b/matrix-e2e.c index cad7d30..c43a360 100644 --- a/matrix-e2e.c +++ b/matrix-e2e.c @@ -1139,8 +1139,11 @@ out: return; } -void matrix_e2e_decrypt_room(PurpleConversation *conv, - struct _JsonObject *cevent) +/* + * If succesful returns a JsonParser on the decrypted event. + */ +JsonParser *matrix_e2e_decrypt_room(PurpleConversation *conv, + struct _JsonObject *cevent) { JsonObject *cevent_content; const gchar *cevent_sender, *cevent_sender_key, *cevent_session_id; @@ -1148,6 +1151,7 @@ void matrix_e2e_decrypt_room(PurpleConversation *conv, gchar *dupe_ciphertext = NULL; gchar *plaintext = NULL; size_t maxlen = 0; + JsonParser *plaintext_parser = NULL; cevent_sender = matrix_json_object_get_string_member(cevent, "sender"); cevent_content = matrix_json_object_get_object_member(cevent, "content"); @@ -1165,7 +1169,7 @@ void matrix_e2e_decrypt_room(PurpleConversation *conv, if (!algorithm || strcmp(algorithm, "m.megolm.v1.aes-sha2")) { purple_debug_info("matrixprpl", "%s: Bad algorithm %s\n", __func__, algorithm); - return; + goto out; } if (!cevent_sender || !cevent_content || !cevent_sender_key || @@ -1177,7 +1181,7 @@ void matrix_e2e_decrypt_room(PurpleConversation *conv, __func__, cevent_sender, cevent_content, cevent_sender_key, cevent_session_id, cevent_device_id, cevent_ciphertext); - return; + goto out; } OlmInboundGroupSession *oigs = get_inbound_megolm_session(conv, @@ -1191,7 +1195,7 @@ void matrix_e2e_decrypt_room(PurpleConversation *conv, "%s: No Megolm session for %s/%s/%s/%s\n", __func__, cevent_device_id, cevent_sender, cevent_sender_key, cevent_session_id); - return; + goto out; } purple_debug_info("matrixprpl", "%s: have Megolm session %p for %s/%s/%s/%s\n", @@ -1232,12 +1236,22 @@ void matrix_e2e_decrypt_room(PurpleConversation *conv, __func__, decrypt_len, maxlen); goto out; } + // TODO: Stash index somewhere - supposed to check it for validity plaintext[decrypt_len] = '\0'; purple_debug_info("matrixprpl", "%s: Decrypted megolm event as '%s' index=%zd\n", __func__, plaintext, (size_t)index); - // TODO: Stash index somewhere - supposed to check it for validity - // TODO: JSON parse it and then send it back to matrix_room_handle_timeline_event + + plaintext_parser = json_parser_new(); + GError *err = NULL; + if (!json_parser_load_from_data(plaintext_parser, + plaintext, strlen(plaintext), &err)) { + purple_debug_info("matrixprpl", + "%s: Failed to json parse decrypted plain text: %s\n", + __func__, plaintext); + g_object_unref(plaintext_parser); + goto out; + } out: g_free(dupe_ciphertext); @@ -1245,6 +1259,8 @@ out: clear_mem(plaintext, maxlen); } g_free(plaintext); + + return plaintext_parser; } #else @@ -1253,9 +1269,10 @@ void matrix_e2e_decrypt_d2d(PurpleConnection *pc, JsonObject *cevent) { } -void matrix_e2e_decrypt_room(PurpleConversation *conv, - struct _JsonObject *cevent) +JsonParser *matrix_e2e_decrypt_room(PurpleConversation *conv, + struct _JsonObject *cevent) { + return NULL; } int matrix_e2e_get_device_keys(MatrixConnectionData *conn, const gchar *device_id) diff --git a/matrix-e2e.h b/matrix-e2e.h index 9483b4e..a3d953f 100644 --- a/matrix-e2e.h +++ b/matrix-e2e.h @@ -28,7 +28,7 @@ typedef struct _PurpleConversation PurpleConversation; int matrix_e2e_get_device_keys(MatrixConnectionData *conn, const gchar *device_id); void matrix_e2e_cleanup_connection(MatrixConnectionData *conn); void matrix_e2e_decrypt_d2d(struct _PurpleConnection *pc, struct _JsonObject *event); -void matrix_e2e_decrypt_room(struct _PurpleConversation *conv, struct _JsonObject *event); +JsonParser *matrix_e2e_decrypt_room(struct _PurpleConversation *conv, struct _JsonObject *event); void matrix_e2e_handle_sync_key_counts(struct _PurpleConnection *pc, struct _JsonObject *count_object, gboolean force_send); #endif diff --git a/matrix-room.c b/matrix-room.c index 6acaf0b..60ab229 100644 --- a/matrix-room.c +++ b/matrix-room.c @@ -932,6 +932,7 @@ void matrix_room_handle_timeline_event(PurpleConversation *conv, gchar *tmp_body = NULL; gchar *escaped_body = NULL; PurpleMessageFlags flags; + JsonParser *decrypted_parser = NULL; const gchar *sender_display_name; MatrixRoomMember *sender = NULL; @@ -953,8 +954,27 @@ void matrix_room_handle_timeline_event(PurpleConversation *conv, if(!strcmp(event_type, "m.room.encrypted")) { purple_debug_info("matrixprpl", "Got an m.room.encrypted!\n"); - matrix_e2e_decrypt_room(conv, json_event_obj); - return; + decrypted_parser = matrix_e2e_decrypt_room(conv, json_event_obj); + if (!decrypted_parser) { + purple_debug_warning("matrixprpl", + "Failed to decrypt m.room.encrypted"); + return; + } + JsonNode *decrypted_node = json_parser_get_root(decrypted_parser); + JsonObject *decrypted_body; + decrypted_body = matrix_json_node_get_object(decrypted_node); + event_type = matrix_json_object_get_string_member(decrypted_body, + "type"); + json_content_obj = matrix_json_object_get_object_member(decrypted_body, + "content"); + // TODO: Check room_id matches + // TODO: Add some info about device trust etc + if (!event_type || !json_content_obj) { + purple_debug_warning("matrixprpl", + "Failed to find members of decrypted json"); + g_object_unref(decrypted_parser); + return; + } } if(strcmp(event_type, "m.room.message") != 0) { @@ -1023,6 +1043,9 @@ void matrix_room_handle_timeline_event(PurpleConversation *conv, serv_got_chat_in(conv->account->gc, g_str_hash(room_id), sender_display_name, flags, escaped_body, timestamp / 1000); g_free(escaped_body); + if (decrypted_parser) { + g_object_unref(decrypted_parser); + } } |