Explorar o código

ims_dialog: Add support for database backend

Morten Tryfoss hai 1 ano
pai
achega
cd54fdde05

+ 8 - 1
src/modules/ims_dialog/dlg_db_handler.c

@@ -643,6 +643,13 @@ static int load_dialog_info_from_db(int dlg_hash_size, int fetch_num_rows)
 
 
 	} while(nr_rows > 0);
 	} while(nr_rows > 0);
 
 
+	if(dlg_db_mode == DB_MODE_SHUTDOWN) {
+		if(dialog_dbf.delete(dialog_db_handle, 0, 0, 0, 0) < 0) {
+			LM_ERR("failed to clear dialog in table\n");
+			goto error;
+		}
+	}
+
 	if(dlg != NULL) {
 	if(dlg != NULL) {
 		d_entry = &(d_table->entries[dlg->h_entry]);
 		d_entry = &(d_table->entries[dlg->h_entry]);
 		dlg = d_entry->first;
 		dlg = d_entry->first;
@@ -655,7 +662,7 @@ static int load_dialog_info_from_db(int dlg_hash_size, int fetch_num_rows)
 
 
 	if(dlg_db_mode == DB_MODE_SHUTDOWN) {
 	if(dlg_db_mode == DB_MODE_SHUTDOWN) {
 		if(dialog_dbf.delete(dialog_db_handle, 0, 0, 0, 0) < 0) {
 		if(dialog_dbf.delete(dialog_db_handle, 0, 0, 0, 0) < 0) {
-			LM_ERR("failed to clear dialog table\n");
+			LM_ERR("failed to clear dialog out table\n");
 			goto error;
 			goto error;
 		}
 		}
 	}
 	}

+ 43 - 9
src/modules/ims_dialog/dlg_handlers.c

@@ -93,12 +93,10 @@ void destroy_dlg_handlers(void)
  * \param id dialog hash id
  * \param id dialog hash id
  * \return 0 on success, -1 on failure
  * \return 0 on success, -1 on failure
  */
  */
-static inline int add_dlg_rr_param(
-		struct sip_msg *req, unsigned int entry, unsigned int id)
+static inline int add_dlg_rr_param(struct sip_msg *req, str did)
 {
 {
 	static char buf[RR_DLG_PARAM_SIZE];
 	static char buf[RR_DLG_PARAM_SIZE];
 	str s;
 	str s;
-	int n;
 	char *p;
 	char *p;
 
 
 	s.s = p = buf;
 	s.s = p = buf;
@@ -108,22 +106,56 @@ static inline int add_dlg_rr_param(
 	p += rr_param.len;
 	p += rr_param.len;
 	*(p++) = '=';
 	*(p++) = '=';
 
 
+	memcpy(p, did.s, did.len);
+	p += did.len;
+	s.len = p - buf;
+
+	if(s.len > RR_DLG_PARAM_SIZE) {
+		return -1;
+	}
+
+	if(d_rrb.add_rr_param(req, &s) < 0) {
+		LM_ERR("failed to add rr param\n");
+		return -1;
+	}
+
+	return 0;
+}
+
+/*!
+ * \brief Generate dialog id for dialog
+ * \param dlg dialog
+ * \return 0 on success, -1 on failure
+ */
+static inline int generate_did(struct dlg_cell *dlg)
+{
+	static char buf[RR_DLG_PARAM_SIZE];
+	str s;
+	int n;
+	char *p;
+
+	s.s = p = buf;
+
 	n = RR_DLG_PARAM_SIZE - (p - buf);
 	n = RR_DLG_PARAM_SIZE - (p - buf);
-	if(int2reverse_hex(&p, &n, entry) == -1)
+	if(int2reverse_hex(&p, &n, dlg->h_entry) == -1)
 		return -1;
 		return -1;
 
 
 	*(p++) = DLG_SEPARATOR;
 	*(p++) = DLG_SEPARATOR;
 
 
 	n = RR_DLG_PARAM_SIZE - (p - buf);
 	n = RR_DLG_PARAM_SIZE - (p - buf);
-	if(int2reverse_hex(&p, &n, id) == -1)
+	if(int2reverse_hex(&p, &n, dlg->h_id) == -1)
 		return -1;
 		return -1;
 
 
 	s.len = p - buf;
 	s.len = p - buf;
 
 
-	if(d_rrb.add_rr_param(req, &s) < 0) {
-		LM_ERR("failed to add rr param\n");
+	dlg->did.s = (char *)shm_malloc(s.len);
+	if(!dlg->did.s) {
+		LM_ERR("no more shm_mem\n");
 		return -1;
 		return -1;
 	}
 	}
+	memset(dlg->did.s, 0, s.len);
+	memcpy(dlg->did.s, s.s, s.len);
+	dlg->did.len = s.len;
 
 
 	return 0;
 	return 0;
 }
 }
@@ -1668,7 +1700,7 @@ int dlg_new_dialog(
 
 
 				//Add did to rr header for all spiralled requested INVITEs
 				//Add did to rr header for all spiralled requested INVITEs
 				if(req->first_line.u.request.method_value == METHOD_INVITE) {
 				if(req->first_line.u.request.method_value == METHOD_INVITE) {
-					if(add_dlg_rr_param(req, dlg->h_entry, dlg->h_id) < 0) {
+					if(add_dlg_rr_param(req, dlg->did) < 0) {
 						LM_ERR("failed to add RR param\n");
 						LM_ERR("failed to add RR param\n");
 					}
 					}
 				}
 				}
@@ -1735,6 +1767,8 @@ int dlg_new_dialog(
 	//    if (dlg_send_bye != 0 || _dlg_ctx.to_bye != 0)
 	//    if (dlg_send_bye != 0 || _dlg_ctx.to_bye != 0)
 	//        dlg->iflags |= DLG_IFLAG_TIMEOUTBYE;
 	//        dlg->iflags |= DLG_IFLAG_TIMEOUTBYE;
 
 
+	generate_did(dlg);
+
 	if(run_initial_cbs)
 	if(run_initial_cbs)
 		run_create_callbacks(dlg, req);
 		run_create_callbacks(dlg, req);
 
 
@@ -1742,7 +1776,7 @@ int dlg_new_dialog(
 
 
 	/* first INVITE seen (dialog created, unconfirmed) */
 	/* first INVITE seen (dialog created, unconfirmed) */
 	if(seq_match_mode != SEQ_MATCH_NO_ID
 	if(seq_match_mode != SEQ_MATCH_NO_ID
-			&& add_dlg_rr_param(req, dlg->h_entry, dlg->h_id) < 0) {
+			&& add_dlg_rr_param(req, dlg->did) < 0) {
 		LM_ERR("failed to add RR param\n");
 		LM_ERR("failed to add RR param\n");
 		goto error;
 		goto error;
 	}
 	}

+ 3 - 2
src/modules/ims_dialog/dlg_hash.c

@@ -513,8 +513,9 @@ struct dlg_cell_out *build_new_dlg_out(
 	int len;
 	int len;
 	char *p;
 	char *p;
 
 
-	//len = sizeof (struct dlg_cell_out) +dlg->did.len + to_tag->len + to_uri->len;
-	len = sizeof(struct dlg_cell_out) + to_tag->len + to_uri->len + branch->len;
+	//branch might be unset, according to code in dlg_onreply()
+	len = sizeof(struct dlg_cell_out) + to_tag->len + to_uri->len
+		  + (branch ? branch->len : 0);
 
 
 	dlg_out = (struct dlg_cell_out *)shm_malloc(len);
 	dlg_out = (struct dlg_cell_out *)shm_malloc(len);
 	if(dlg_out == 0) {
 	if(dlg_out == 0) {

+ 82 - 11
src/modules/ims_dialog/doc/ims_dialog_admin.xml

@@ -351,8 +351,22 @@ modparam("ims_dialog", "detect_spirals", 1)
                 <varname>db_url</varname> (string)
                 <varname>db_url</varname> (string)
             </title>
             </title>
             <para>
             <para>
-		Db storage not yet supported by ims_dialog - this to be done in future.
+            In order to store information about dialogs in a database,
+            a database URL must be specified.
             </para>
             </para>
+            <para>
+            <emphasis>
+                Default value is <quote>&defaultdb;</quote>.
+            </emphasis>
+            </para>
+            <example>
+            <title>Set <varname>db_url</varname> parameter</title>
+            <programlisting format="linespecific">
+    ...
+    modparam("ims_dialog", "db_url", "&exampledb;")
+    ...
+    </programlisting>
+            </example>
         </section>
         </section>
 
 
         <section>
         <section>
@@ -360,8 +374,40 @@ modparam("ims_dialog", "detect_spirals", 1)
                 <varname>db_mode</varname> (integer)
                 <varname>db_mode</varname> (integer)
             </title>
             </title>
             <para>
             <para>
-		Db storage not yet supported by ims_dialog - this to be done in future.
+            This is the database mode to be used for dialog persistent storage.
             </para>
             </para>
+            <itemizedlist>
+                <listitem><para>
+                    <emphasis>0 - NO_DB</emphasis> - the memory content is not
+                    flushed into DB;
+                </para></listitem>
+                <listitem><para>
+                    <emphasis>1 - REALTIME</emphasis> - any dialog information
+                    changes will be reflected into the database immediately.
+                </para></listitem>
+                <listitem><para>
+                    <emphasis>2 - DELAYED</emphasis> - the dialog information
+                    changes will be flushed into DB periodically, based on a
+                    timer routine.
+                </para></listitem>
+                <listitem><para>
+                    <emphasis>3 - SHUTDOWN</emphasis> - the dialog information
+                    will be flushed into DB only at shutdown - no runtime updates.
+                </para></listitem>
+            </itemizedlist>
+            <para>
+            <emphasis>
+                Default value is <quote>0</quote>.
+            </emphasis>
+            </para>
+            <example>
+            <title>Set <varname>db_mode</varname> parameter</title>
+            <programlisting format="linespecific">
+    ...
+    modparam("ims_dialog", "db_mode", 1)
+    ...
+    </programlisting>
+            </example>
         </section>
         </section>
 
 
         <section>
         <section>
@@ -369,8 +415,24 @@ modparam("ims_dialog", "detect_spirals", 1)
                 <varname>db_update_period</varname> (integer)
                 <varname>db_update_period</varname> (integer)
             </title>
             </title>
             <para>
             <para>
-		Db storage not yet supported by ims_dialog - this to be done in future.
+            The interval (seconds) at which to update dialogs' information,
+            if the server is configured to store the dialog information at a given interval.
+            A too short interval will generate intensive database operations,
+            while an excessively long one will miss dialogs with a short lifetime.
             </para>
             </para>
+            <para>
+            <emphasis>
+                Default value is <quote>60</quote> seconds.
+            </emphasis>
+            </para>
+            <example>
+            <title>Set <varname>db_update_period</varname> parameter</title>
+            <programlisting format="linespecific">
+    ...
+    modparam("ims_dialog", "db_update_period", 120)
+    ...
+    </programlisting>
+            </example>
         </section>
         </section>
 
 
         <section>
         <section>
@@ -378,17 +440,26 @@ modparam("ims_dialog", "detect_spirals", 1)
                 <varname>db_fetch_rows</varname> (integer)
                 <varname>db_fetch_rows</varname> (integer)
             </title>
             </title>
             <para>
             <para>
-		Db storage not yet supported by ims_dialog - this to be done in future.
+                The number of the rows to be fetched at once from database
+                when loading the dialog records at startup from the database.
+                This value can be used to tune the load time at startup.
+                For 1MB of private memory (default), it should be below 400.
+                The database driver must support the fetch_result() capability.
+                A value of 0 means the database fetch is not limited.
             </para>
             </para>
-        </section>
-
-        <section>
-            <title>
-                <varname>table_name</varname> (string)
-            </title>
             <para>
             <para>
-		Db storage not yet supported by ims_dialog - this to be done in future.
+            <emphasis>
+                Default value is <quote>200</quote>.
+            </emphasis>
             </para>
             </para>
+            <example>
+            <title>Set <varname>db_fetch_rows</varname> parameter</title>
+            <programlisting format="linespecific">
+    ...
+    modparam("ims_dialog", "db_fetch_rows", 500)
+    ...
+    </programlisting>
+            </example>
         </section>
         </section>
 
 
         <section>
         <section>