about summary refs log tree commit diff stats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/xmpp/message.c34
-rw-r--r--src/xmpp/stanza.c15
-rw-r--r--src/xmpp/stanza.h5
3 files changed, 52 insertions, 2 deletions
diff --git a/src/xmpp/message.c b/src/xmpp/message.c
index 064e7b29..54be543c 100644
--- a/src/xmpp/message.c
+++ b/src/xmpp/message.c
@@ -64,6 +64,7 @@
 #include "xmpp/stanza.h"
 #include "xmpp/connection.h"
 #include "xmpp/xmpp.h"
+#include "xmpp/form.h"
 
 #ifdef HAVE_OMEMO
 #include "xmpp/omemo.h"
@@ -91,6 +92,7 @@ static xmpp_stanza_t* _handle_carbons(xmpp_stanza_t* const stanza);
 static void _send_message_stanza(xmpp_stanza_t* const stanza);
 static gboolean _handle_mam(xmpp_stanza_t* const stanza);
 static void _handle_pubsub(xmpp_stanza_t* const stanza, xmpp_stanza_t* const event);
+static gboolean _handle_form(xmpp_stanza_t* const stanza);
 
 #ifdef HAVE_LIBGPGME
 static xmpp_stanza_t* _openpgp_signcrypt(xmpp_ctx_t* ctx, const char* const to, const char* const text);
@@ -170,6 +172,11 @@ _message_handler(xmpp_conn_t* const conn, xmpp_stanza_t* const stanza, void* con
     } else if (type == NULL || g_strcmp0(type, STANZA_TYPE_CHAT) != 0 || g_strcmp0(type, STANZA_TYPE_NORMAL) != 0) {
         // type: chat, normal (==NULL)
 
+        // XEP-0045: Multi-User Chat 8.6 Voice Requests
+        if (_handle_form(stanza)) {
+            return 1;
+        }
+
         // XEP-0313: Message Archive Management
         if (_handle_mam(stanza)) {
             return 1;
@@ -249,6 +256,33 @@ _message_handler(xmpp_conn_t* const conn, xmpp_stanza_t* const stanza, void* con
 }
 
 void
+message_muc_submit_voice_approve(ProfConfWin* confwin)
+{
+    xmpp_ctx_t* const ctx = connection_get_ctx();
+    xmpp_stanza_t* message = stanza_create_approve_voice(ctx, NULL, confwin->roomjid, NULL, confwin->form);
+
+    _send_message_stanza(message);
+    xmpp_stanza_release(message);
+}
+
+static gboolean
+_handle_form(xmpp_stanza_t* const stanza)
+{
+    xmpp_stanza_t* result = xmpp_stanza_get_child_by_name_and_ns(stanza, STANZA_NAME_X, STANZA_NS_DATA);
+    if (!result) {
+        return FALSE;
+    }
+
+    const char* const stanza_from = xmpp_stanza_get_from(stanza);
+
+    DataForm* form = form_create(result);
+    ProfConfWin* confwin = (ProfConfWin*)wins_new_config(stanza_from, form, message_muc_submit_voice_approve, NULL, NULL);
+    confwin_handle_configuration(confwin, form);
+
+    return TRUE;
+}
+
+void
 message_handlers_init(void)
 {
     xmpp_conn_t* const conn = connection_get_conn();
diff --git a/src/xmpp/stanza.c b/src/xmpp/stanza.c
index 3ce2c88a..32892311 100644
--- a/src/xmpp/stanza.c
+++ b/src/xmpp/stanza.c
@@ -2813,3 +2813,18 @@ stanza_request_voice(xmpp_ctx_t* ctx, const char* const room)
 
     return message;
 }
+
+xmpp_stanza_t*
+stanza_create_approve_voice(xmpp_ctx_t* ctx, const char* const id, const char* const jid, const char* const node, DataForm* form)
+{
+    char* stid = connection_create_stanza_id();
+    xmpp_stanza_t* message = xmpp_message_new(ctx, NULL, jid, stid);
+    free(stid);
+
+    xmpp_stanza_t* x = form_create_submission(form);
+
+    xmpp_stanza_add_child(message, x);
+    xmpp_stanza_release(x);
+
+    return message;
+}
diff --git a/src/xmpp/stanza.h b/src/xmpp/stanza.h
index 3600fb0b..0115942a 100644
--- a/src/xmpp/stanza.h
+++ b/src/xmpp/stanza.h
@@ -398,7 +398,8 @@ xmpp_stanza_t* stanza_create_mam_iq(xmpp_ctx_t* ctx, const char* const jid, cons
 
 xmpp_stanza_t* stanza_change_password(xmpp_ctx_t* ctx, const char* const user, const char* const password);
 
-xmpp_stanza_t*
-stanza_request_voice(xmpp_ctx_t* ctx, const char* const room);
+xmpp_stanza_t* stanza_request_voice(xmpp_ctx_t* ctx, const char* const room);
+
+xmpp_stanza_t* stanza_create_approve_voice(xmpp_ctx_t* ctx, const char* const id, const char* const jid, const char* const node, DataForm* form);
 
 #endif