Browse code

XJAB module - some bugs fixed - added a monitoring process for Jabber GW workers - confirmation message when someone leaves a conference or Jabber network

Daniel-Constantin Mierla authored on 08/11/2002 15:58:19
Showing 6 changed files
... ...
@@ -33,9 +33,11 @@
33 33
 #include <string.h>
34 34
 #include <stdlib.h>
35 35
 #include <sys/types.h>
36
+#include <sys/wait.h>
36 37
 #include <sys/ipc.h>
37 38
 #include <unistd.h>
38 39
 #include <fcntl.h>
40
+#include <errno.h>
39 41
 
40 42
 #include "../../sr_module.h"
41 43
 #include "../../error.h"
... ...
@@ -43,6 +45,7 @@
43 45
 #include "../../mem/shm_mem.h"
44 46
 #include "../../mem/mem.h"
45 47
 #include "../../globals.h"
48
+#include "../../timer.h"
46 49
 #include "../../parser/parse_uri.h"
47 50
 
48 51
 #include "../im/im_load.h"
... ...
@@ -52,6 +55,7 @@
52 55
 #include "xjab_util.h"
53 56
 #include "../../db/db.h"
54 57
 
58
+
55 59
 /** TM bind */
56 60
 struct tm_binds tmb;
57 61
 /** IM binds */
... ...
@@ -81,6 +85,7 @@ char *jdomain  = NULL;
81 85
 int delay_time = 90;
82 86
 int sleep_time = 20;
83 87
 int cache_time = 600;
88
+int check_time = 20;
84 89
 
85 90
 int **pipes = NULL;
86 91
 
... ...
@@ -88,6 +93,7 @@ static int mod_init(void);
88 93
 static int child_init(int rank);
89 94
 
90 95
 int xjab_manage_sipmsg(struct sip_msg *msg, int type);
96
+void xjab_check_workers(int mpid);
91 97
 
92 98
 static int jab_send_message(struct sip_msg*, char*, char*);
93 99
 static int jab_send_bye(struct sip_msg*, char*, char*);
... ...
@@ -135,7 +141,8 @@ struct module_exports exports= {
135 141
 		"max_jobs",
136 142
 		"cache_time",
137 143
 		"delay_time",
138
-		"sleep_time"
144
+		"sleep_time",
145
+		"check_time"
139 146
 	},
140 147
 	(modparam_t[]) {   /* Module parameter types */
141 148
 		STR_PARAM,
... ...
@@ -161,9 +168,10 @@ struct module_exports exports= {
161 168
 		&max_jobs,
162 169
 		&cache_time,
163 170
 		&delay_time,
164
-		&sleep_time
171
+		&sleep_time,
172
+		&check_time
165 173
 	},
166
-	11,      /* Number of module paramers */
174
+	12,      /* Number of module paramers */
167 175
 	
168 176
 	mod_init,   /* module initialization function */
169 177
 	(response_function) 0,
... ...
@@ -289,41 +297,49 @@ static int mod_init(void)
289 297
  */
290 298
 static int child_init(int rank)
291 299
 {
292
-	int i;
293
-	int *pids = NULL;
300
+	int i, j, mpid, cpid;
294 301
 	
295 302
 	DBG("XJAB:child_init: initializing child <%d>\n", rank);
296 303
 	if(rank == 0)
297 304
 	{
298
-		pids = (int*)pkg_malloc(nrw*sizeof(int));
299
-		if (pids == NULL)
305
+		if((mpid=fork())<0 )
300 306
 		{
301
-			DBG("XJAB:child_init: error while allocating pid's\n");
302
-			return -1;
307
+			DBG("XJAB:child_init: error - cannot launch worker's manager\n");
308
+				return -1;
303 309
 		}
304
-		/** launching the workers */
305
-		for(i=0;i<nrw;i++)
310
+		if(mpid == 0)
306 311
 		{
307
-			if ( (pids[i]=fork())<0 )
312
+			/** launching the workers */
313
+			for(i=0;i<nrw;i++)
308 314
 			{
309
-				DBG("XJAB:child_init: error - cannot launch worker\n");
310
-				return -1;
315
+				if ( (cpid=fork())<0 )
316
+				{
317
+					DBG("XJAB:child_init: error - cannot launch worker\n");
318
+					return -1;
319
+				}
320
+				if (cpid == 0)
321
+				{
322
+					for(j=0;j<nrw;j++)
323
+						if(j!=i) close(pipes[j][0]);
324
+					close(pipes[i][1]);
325
+					if(xj_wlist_set_pid(jwl, getpid(), i) < 0)
326
+					{
327
+						DBG("XJAB:child_init: error setting worker's pid\n");
328
+						return -1;
329
+					}
330
+					xj_worker_process(jwl,jaddress,jport,i,db_con[i]);
331
+					exit(0);
332
+				}
311 333
 			}
312
-			if (pids[i] == 0)
334
+
335
+			mpid = getpid();
336
+			while(1)
313 337
 			{
314
-				close(pipes[i][1]);
315
-				xj_worker_process(jwl,jaddress,jport,pipes[i][0],db_con[i]);
316
-				exit(0);
338
+				sleep(check_time);
339
+				xjab_check_workers(mpid);
317 340
 			}
341
+			exit(0);
318 342
 		}
319
-	
320
-		if(xj_wlist_set_pids(jwl, pids, nrw) < 0)
321
-		{
322
-			DBG("XJAB:child_init: error setting pid's\n");
323
-			return -1;
324
-		}
325
-		if(pids)
326
-			pkg_free(pids);
327 343
 	}
328 344
 	
329 345
 	if(pipes)
... ...
@@ -581,12 +597,13 @@ int xjab_manage_sipmsg(struct sip_msg *msg, int type)
581 597
 
582 598
 	jsmsg->jkey = p;
583 599
 	jsmsg->type = type;
584
-	jsmsg->jkey->hash = jkey.hash;
600
+	//jsmsg->jkey->hash = jkey.hash;
585 601
 
586 602
 	DBG("XJAB:xjab_manage_sipmsg:%d: sending <%p> to worker through <%d>\n",
587 603
 			getpid(), jsmsg, pipe);
588 604
 	// sending the SHM pointer of SIP message to the worker
589
-	if(write(pipe, &jsmsg, sizeof(jsmsg)) != sizeof(jsmsg))
605
+	fl = write(pipe, &jsmsg, sizeof(jsmsg));
606
+	if(fl != sizeof(jsmsg))
590 607
 	{
591 608
 		DBG("XJAB:xjab_manage_sipmsg: error when writting to worker pipe!\n");
592 609
 		if(type == XJ_SEND_MESSAGE)
... ...
@@ -630,3 +647,50 @@ void destroy(void)
630 647
 	DBG("XJAB: Unloaded\n");
631 648
 }
632 649
 
650
+void xjab_check_workers(int mpid)
651
+{
652
+	int i, n, stat;
653
+	DBG("XJAB:%d:xjab_check_workers: time=%d\n", mpid, get_ticks());
654
+	if(!jwl || jwl->len <= 0)
655
+		return;
656
+	for(i=0; i < jwl->len; i++)
657
+	{
658
+		if(jwl->workers[i].pid <= 0)
659
+			continue;
660
+				stat = 0;
661
+		n = waitpid(jwl->workers[i].pid, &stat, WNOHANG);
662
+		if(n == 0)
663
+			continue;
664
+		
665
+		DBG("XJAB:xjab_check_workers: worker[%d][pid=%d] has exited"
666
+			" - status %d err=%d errno=%d\n", i, 
667
+			jwl->workers[i].pid, stat, n, errno);
668
+		if(n==jwl->workers[i].pid)
669
+		{
670
+			DBG("XJAB:%d:xjab_check_workers: create a new worker\n", mpid);
671
+			xj_wlist_set_pid(jwl, -1, i);
672
+			if ( (stat=fork())<0 )
673
+			{
674
+				DBG("XJAB:xjab_check_workers: error - cannot launch worker\n");
675
+				return;
676
+			}
677
+			if (stat == 0)
678
+			{
679
+				if(xj_wlist_set_pid(jwl, getpid(), i) < 0)
680
+				{
681
+					DBG("XJAB:xjab_check_workers: error setting worker's pid\n");
682
+					return;
683
+				}
684
+				xj_worker_process(jwl,jaddress,jport,i,db_con[i]);
685
+				exit(0);
686
+			}
687
+		}
688
+		else
689
+		{
690
+			LOG(L_ERR, "XJAB:xjab_check_workers: error - worker[%d][pid=%d] lost"
691
+				" forever\n", i, jwl->workers[i].pid);
692
+			xj_wlist_set_pid(jwl, -1, i);
693
+		}
694
+	}			
695
+}
696
+
... ...
@@ -46,6 +46,7 @@
46 46
 typedef struct _xj_jkey
47 47
 {
48 48
 	int hash;
49
+	int flag;
49 50
 	str *id;
50 51
 } t_xj_jkey, *xj_jkey;
51 52
 
... ...
@@ -80,14 +80,6 @@ xj_jcon xj_jcon_init(char *hostname, int port)
80 80
 		_M_FREE(jbc);
81 81
 		return NULL;
82 82
 	}
83
-	if((jbc->close = (int*)_M_SHM_MALLOC(sizeof(int)))==NULL)
84
-	{
85
-		_M_FREE(jbc->hostname);
86
-		_M_FREE(jbc);
87
-		return NULL;
88
-
89
-	}
90
-	*jbc->close = 0;
91 83
     strcpy(jbc->hostname, hostname);
92 84
 	jbc->allowed = jbc->ready = XJ_NET_NUL;
93 85
 	jbc->jconf = NULL;
... ...
@@ -474,11 +466,7 @@ int xj_jcon_free(xj_jcon jbc)
474 466
 		_M_FREE(jbc->hostname);
475 467
 	if(jbc->stream_id != NULL)
476 468
 		_M_FREE(jbc->stream_id);
477
-	if(jbc->close != NULL)
478
-	{
479
-		_M_SHM_FREE(jbc->close);
480
-		jbc->close = NULL;
481
-	}
469
+	
482 470
 	if(jbc->resource != NULL)
483 471
 		_M_FREE(jbc->resource);
484 472
 	DBG("XJAB:xj_jcon_free: %d conferences\n", jbc->nrjconf);
... ...
@@ -545,7 +533,7 @@ int xj_jcon_is_ready(xj_jcon jbc, char *to, int tol)
545 533
 		DBG("XJAB: xj_jcon_is_ready: destination=conference\n");
546 534
 		
547 535
 		if((jcf=xj_jcon_get_jconf(jbc, &sto))!=NULL)
548
-			return (jcf->status & XJ_JCONF_READY)?0:1;
536
+			return (jcf->status & XJ_JCONF_READY)?0:3;
549 537
 		
550 538
 		DBG("XJAB: xj_jcon_is_ready: conference does not exist\n");
551 539
 		return -1;
... ...
@@ -75,7 +75,6 @@ typedef struct _xj_jcon
75 75
 	int allowed;	// allowed IM networks
76 76
 	int ready;		// time when the connection is ready for sending messages
77 77
 
78
-	int *close;		// t_uac callback parameter
79 78
 	int nrjconf;	// number of open conferences
80 79
 	tree234 *jconf; // open conferences
81 80
 } t_xj_jcon, *xj_jcon;
... ...
@@ -65,6 +65,10 @@ extern struct tm_binds tmb;
65 65
 int _xj_pid = 0;
66 66
 int main_loop = 1;
67 67
 
68
+/** **/
69
+
70
+static str jab_gw_name = {"sip_to_jabber_gateway", 21};
71
+
68 72
 /**
69 73
  * init a workers list
70 74
  * - pipes : communication pipes
... ...
@@ -106,7 +110,9 @@ xj_wlist xj_wlist_init(int **pipes, int size, int max, int cache_time,
106 110
 	for(i = 0; i < size; i++)
107 111
 	{
108 112
 		jwl->workers[i].nr = 0;
109
-		jwl->workers[i].pipe = pipes[i][1];
113
+		jwl->workers[i].pid = 0;
114
+		jwl->workers[i].wpipe = pipes[i][1];
115
+		jwl->workers[i].rpipe = pipes[i][0];
110 116
 		if((jwl->workers[i].sip_ids = newtree234(xj_jkey_cmp)) == NULL)
111 117
 			goto clean;
112 118
 	}	
... ...
@@ -182,14 +188,13 @@ int xj_wlist_init_contact(xj_wlist jwl, char *ch)
182 188
  * - size : number of pids
183 189
  * #return : 0 on success or <0 on error
184 190
  */
185
-int xj_wlist_set_pids(xj_wlist jwl, int *pids, int size)
191
+int xj_wlist_set_pid(xj_wlist jwl, int pid, int idx)
186 192
 {
187
-	int i;
188
-
189
-	if(jwl == NULL || pids == NULL || size <= 0)
193
+	if(jwl == NULL || pid <= 0 || idx < 0 || idx >= jwl->len)
190 194
 		return -1;
191
-	for(i = 0; i < size; i++)
192
-		jwl->workers[i].pid = pids[i];
195
+	s_lock_at(jwl->sems, idx);
196
+	jwl->workers[idx].pid = pid;
197
+	s_unlock_at(jwl->sems, idx);
193 198
 	return 0;
194 199
 }
195 200
 
... ...
@@ -259,13 +264,19 @@ int xj_wlist_check(xj_wlist jwl, xj_jkey jkey, xj_jkey *p)
259 264
 	while(i < jwl->len)
260 265
 	{
261 266
 		s_lock_at(jwl->sems, i);
267
+		if(jwl->workers[i].pid <= 0)
268
+		{
269
+			s_unlock_at(jwl->sems, i);
270
+			i++;
271
+			continue;
272
+		}
262 273
 		if((*p = find234(jwl->workers[i].sip_ids, (void*)jkey, NULL)) != NULL)
263 274
 		{
264 275
 			s_unlock_at(jwl->sems, i);
265 276
 			DBG("XJAB:xj_wlist_check: entry exists for <%.*s> in the"
266 277
 				" pool of <%d> [%d]\n",jkey->id->len, jkey->id->s,
267 278
 				jwl->workers[i].pid,i);
268
-			return jwl->workers[i].pipe;
279
+			return jwl->workers[i].wpipe;
269 280
 		}
270 281
 		s_unlock_at(jwl->sems, i);
271 282
 		i++;
... ...
@@ -295,6 +306,12 @@ int xj_wlist_get(xj_wlist jwl, xj_jkey jkey, xj_jkey *p)
295 306
 	while(i < jwl->len)
296 307
 	{
297 308
 		s_lock_at(jwl->sems, i);
309
+		if(jwl->workers[i].pid <= 0)
310
+		{
311
+			s_unlock_at(jwl->sems, i);
312
+			i++;
313
+			continue;
314
+		}
298 315
 		if((*p = find234(jwl->workers[i].sip_ids, (void*)jkey, NULL))!=NULL)
299 316
 		{
300 317
 			if(pos >= 0)
... ...
@@ -303,7 +320,7 @@ int xj_wlist_get(xj_wlist jwl, xj_jkey jkey, xj_jkey *p)
303 320
 			DBG("XJAB:xj_wlist_get: entry already exists for <%.*s> in the"
304 321
 				" pool of <%d> [%d]\n",jkey->id->len, jkey->id->s,
305 322
 				jwl->workers[i].pid,i);
306
-			return jwl->workers[i].pipe;
323
+			return jwl->workers[i].wpipe;
307 324
 		}
308 325
 		if(min > jwl->workers[i].nr)
309 326
 		{
... ...
@@ -343,11 +360,12 @@ int xj_wlist_get(xj_wlist jwl, xj_jkey jkey, xj_jkey *p)
343 360
 			msid->id->len = jkey->id->len;
344 361
 			memcpy(msid->id->s, jkey->id->s, jkey->id->len);
345 362
 			msid->hash = jkey->hash;
346
-						s_unlock_at(jwl->sems, pos);
363
+			msid->flag = 0;
364
+			s_unlock_at(jwl->sems, pos);
347 365
 			DBG("XJAB:xj_wlist_get: new entry for <%.*s> in the pool of"
348 366
 				" <%d> - [%d]\n", jkey->id->len, jkey->id->s,
349 367
 				jwl->workers[pos].pid, pos);
350
-			return jwl->workers[pos].pipe;
368
+			return jwl->workers[pos].wpipe;
351 369
 		}
352 370
 		_M_SHM_FREE(msid->id->s);
353 371
 		_M_SHM_FREE(msid->id);
... ...
@@ -639,19 +657,19 @@ done:
639 657
  * - db_con : connection to database
640 658
  * #return : 0 on success or <0 on error
641 659
  */
642
-int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
660
+int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int rank,
643 661
 		db_con_t* db_con)
644 662
 {
645
-	int ret, i, pos, maxfd, flag;
663
+	int pipe, ret, i, pos, maxfd, flag;
646 664
 	xj_jcon_pool jcp;
647 665
 	struct timeval tmv;
648 666
 	fd_set set, mset;
649 667
 	xj_sipmsg jsmsg;
650
-	xj_jcon jbc;
651
-	xj_jconf jcf;
668
+	str sto;
669
+	xj_jcon jbc = NULL;
670
+	xj_jconf jcf = NULL;
652 671
 	char *p, buff[1024], recv_buff[4096];
653 672
 	int flags, nr, ltime = 0;
654
-	str sto;
655 673
 	
656 674
 	db_key_t keys[] = {"sip_id", "type"};
657 675
 	db_val_t vals[] = { {DB_STRING, 0, {.string_val = buff}},
... ...
@@ -664,9 +682,19 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
664 682
 	signal(SIGTERM, xj_sig_handler);
665 683
 	signal(SIGINT, xj_sig_handler);
666 684
 	signal(SIGQUIT, xj_sig_handler);
667
-	
668
-	DBG("XJAB:xj_worker:%d: started - pipe=<%d> : 1st message delay"
669
-		" <%d>\n", _xj_pid, pipe, jwl->delayt);
685
+	signal(SIGSEGV, xj_sig_handler);
686
+
687
+	if(!jwl || !jaddress || rank >= jwl->len)
688
+	{
689
+		DBG("XJAB:xj_worker[%d]:%d: exiting - wrong parameters\n",
690
+				rank, _xj_pid);
691
+		return -1;
692
+	}
693
+
694
+	pipe = jwl->workers[rank].rpipe;
695
+
696
+	DBG("XJAB:xj_worker[%d]:%d: started - pipe=<%d> : 1st message delay"
697
+		" <%d>\n", rank, _xj_pid, pipe, jwl->delayt);
670 698
 
671 699
 	if((jcp=xj_jcon_pool_init(jwl->maxj,XJ_POOL_SIZE,jwl->delayt))==NULL)
672 700
 	{
... ...
@@ -685,8 +713,8 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
685 713
 		mset = set;
686 714
 
687 715
 		tmv.tv_sec = (jcp->jmqueue.size == 0)?jwl->sleept:1;
688
-		DBG("XJAB:xj_worker:%d: select waiting %ds - queue=%d\n",_xj_pid,
689
-				(int)tmv.tv_sec, jcp->jmqueue.size);
716
+		DBG("XJAB:xj_worker[%d]:%d: select waiting %ds - queue=%d\n",rank,
717
+				_xj_pid, (int)tmv.tv_sec, jcp->jmqueue.size);
690 718
 		tmv.tv_usec = 0;
691 719
 
692 720
 		ret = select(maxfd+1, &mset, NULL, NULL, &tmv);
... ...
@@ -713,7 +741,7 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
713 741
 				xj_send_sip_msgz(jcp->jmqueue.jsm[i]->jkey->id, 
714 742
 						&jcp->jmqueue.jsm[i]->to, jwl->contact_h, 
715 743
 						"ERROR: Your message was not sent. Conection to IM"
716
-						" network failed.", jcp->jmqueue.ojc[i]->close);
744
+						" network failed.", &jcp->jmqueue.ojc[i]->jkey->flag);
717 745
 				if(jcp->jmqueue.jsm[i]!=NULL)
718 746
 				{
719 747
 					xj_sipmsg_free(jcp->jmqueue.jsm[i]);
... ...
@@ -724,6 +752,14 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
724 752
 				continue;
725 753
 			}
726 754
 
755
+			DBG("XJAB:xj_worker:%d:%d: QUEUE: message[%d] from [%.*s]/to [%.*s]/"
756
+					"body[%.*s] expires at %d\n",
757
+					_xj_pid, get_ticks(), i, 
758
+					jcp->jmqueue.jsm[i]->jkey->id->len,
759
+					jcp->jmqueue.jsm[i]->jkey->id->s,
760
+					jcp->jmqueue.jsm[i]->to.len,jcp->jmqueue.jsm[i]->to.s,
761
+					jcp->jmqueue.jsm[i]->msg.len,jcp->jmqueue.jsm[i]->msg.s,
762
+					jcp->jmqueue.expire[i]);
727 763
 			if(xj_jcon_is_ready(jcp->jmqueue.ojc[i], 
728 764
 					jcp->jmqueue.jsm[i]->to.s, jcp->jmqueue.jsm[i]->to.len))
729 765
 				continue;
... ...
@@ -740,8 +776,8 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
740 776
 			{
741 777
 		
742 778
 				/** send message from queue */
743
-				DBG("XJAB:xj_worker:%d: SENDING AS JABBER MESSAGE FROM "
744
-					" LOCAL QUEUE ...\n", _xj_pid);
779
+				DBG("XJAB:xj_worker:%d: SENDING THE MESSAGE FROM "
780
+					" LOCAL QUEUE TO JABBER NETWORK ...\n", _xj_pid);
745 781
 				xj_jcon_send_msg(jcp->jmqueue.ojc[i],
746 782
 					sto.s, sto.len,
747 783
 					jcp->jmqueue.jsm[i]->msg.s,
... ...
@@ -749,8 +785,8 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
749 785
 					(flag&XJ_ADDRTR_CON)?XJ_JMSG_GROUPCHAT:XJ_JMSG_CHAT);
750 786
 			}
751 787
 			else
752
-				DBG("XJAB:xj_worker:%d: ERROR SENDING AS JABBER MESSAGE FROM "
753
-				" LOCAL QUEUE ...\n", _xj_pid);
788
+				DBG("XJAB:xj_worker:%d: ERROR SENDING THE MESSAGE FROM "
789
+				" LOCAL QUEUE TO JABBER NETWORK ...\n", _xj_pid);
754 790
 				
755 791
 			if(jcp->jmqueue.jsm[i]!=NULL)
756 792
 			{
... ...
@@ -787,6 +823,16 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
787 823
 		switch(jsmsg->type)
788 824
 		{
789 825
 			case XJ_SEND_MESSAGE:
826
+				if(!xj_jconf_check_addr(&jsmsg->to) &&
827
+					(!jbc || !xj_jcon_get_jconf(jbc, &jsmsg->to) ) )
828
+				{
829
+					xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
830
+						jwl->contact_h, "ERROR: Your message was not"
831
+						" sent. You are not joined in the conference.",
832
+						NULL);
833
+					goto step_w;
834
+				}
835
+				break;
790 836
 			case XJ_JOIN_JCONF:
791 837
 			case XJ_GO_ONLINE:
792 838
 				break;
... ...
@@ -798,10 +844,13 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
798 844
 					goto step_w;
799 845
 				if(!xj_jconf_check_addr(&jsmsg->to))
800 846
 					xj_jcon_del_jconf(jbc, &jsmsg->to, XJ_JCMD_UNSUBSCRIBE);
847
+				xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
848
+					jwl->contact_h, "INFO: Your have just left"
849
+					" the conference.", NULL);
801 850
 				goto step_w;
802 851
 			case XJ_GO_OFFLINE:
803 852
 				if(jbc != NULL)
804
-					jbc->expire = ltime = 0;
853
+					jbc->expire = ltime = -1;
805 854
 				goto step_w;
806 855
 			case XJ_SEND_SUBSCRIBE:
807 856
 			case XJ_SEND_BYE:
... ...
@@ -842,7 +891,7 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
842 891
 			xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to, 
843 892
 				jwl->contact_h, "ERROR: Your message was"
844 893
 				" not sent. Cannot connect to the Jabber"
845
-				" server.", jbc->close);
894
+				" server.", &jbc->jkey->flag);
846 895
 
847 896
 			goto step_v;
848 897
 		}
... ...
@@ -863,7 +912,7 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
863 912
 			xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
864 913
 				jwl->contact_h, "ERROR: Your message"
865 914
 				" was not sent. Authentication to the"
866
-				" Jabber server failed.", jbc->close);
915
+				" Jabber server failed.", &jbc->jkey->flag);
867 916
 			
868 917
 			xj_jcon_free(jbc);
869 918
 			goto step_v;
... ...
@@ -877,7 +926,7 @@ int xj_worker_process(xj_wlist jwl, char* jaddress, int jport, int pipe,
877 926
 			xj_jcon_disconnect(jbc);
878 927
 			xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to, jwl->contact_h,	
879 928
 				"ERROR:Your message was	not sent. SIP-2-JABBER"
880
-				" gateway is full.", jbc->close);
929
+				" gateway is full.", &jbc->jkey->flag);
881 930
 			xj_jcon_free(jbc);
882 931
 			goto step_v;
883 932
 		}
... ...
@@ -912,7 +961,8 @@ step_z:
912 961
 		{
913 962
 			if((jcf = xj_jcon_get_jconf(jbc, &jsmsg->to)) != NULL)
914 963
 			{
915
-				if(!(jcf->status & XJ_JCONF_READY || 
964
+				if((jsmsg->type == XJ_JOIN_JCONF) &&
965
+					!(jcf->status & XJ_JCONF_READY || 
916 966
 						jcf->status & XJ_JCONF_WAITING))
917 967
 				{
918 968
 					if(!xj_jcon_jconf_presence(jbc,jcf,NULL,"online"))
... ...
@@ -923,7 +973,7 @@ step_z:
923 973
 						// --- send back to SIP user a msg
924 974
 						xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to, 
925 975
 							jwl->contact_h,"ERROR:Cannot join the"
926
-							" conference room.", jbc->close);
976
+							" conference room.", &jbc->jkey->flag);
927 977
 						goto step_w;
928 978
 					}
929 979
 				}
... ...
@@ -935,7 +985,7 @@ step_z:
935 985
 				// --- send back to SIP user a msg
936 986
 				xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to, 
937 987
 					jwl->contact_h,"ERROR:Cannot create a new"
938
-					" conference session.", jbc->close);
988
+					" conference session.", &jbc->jkey->flag);
939 989
 				goto step_w;
940 990
 			}
941 991
 		}
... ...
@@ -946,8 +996,8 @@ step_z:
946 996
 		switch(xj_jcon_is_ready(jbc, jsmsg->to.s, jsmsg->to.len))
947 997
 		{
948 998
 			case 0:
949
-				DBG("XJAB:xj_worker:%d: SENDING AS JABBER"
950
-					" MESSAGE ...\n", _xj_pid);
999
+				DBG("XJAB:xj_worker:%d: SENDING THE MESSAGE TO JABBER"
1000
+					" NETWORK ...\n", _xj_pid);
951 1001
 				/*** address corection ***/
952 1002
 				sto.s = buff; 
953 1003
 				sto.len = 0;
... ...
@@ -962,7 +1012,7 @@ step_z:
962 1012
 						xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
963 1013
 							jwl->contact_h, "ERROR: Your message was not"
964 1014
 							" sent. Something wrong during transmition to"
965
-							" Jabber.", jbc->close);
1015
+							" Jabber.", &jbc->jkey->flag);
966 1016
 				}
967 1017
 				else
968 1018
 					DBG("XJAB:xj_worker:%d: ERROR SENDING AS JABBER"
... ...
@@ -977,6 +1027,10 @@ step_z:
977 1027
 				{
978 1028
 					DBG("XJAB:xj_worker:%d: SCHEDULING THE"
979 1029
 						" MESSAGE FAILED. Message was droped.\n",_xj_pid);
1030
+					xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
1031
+						jwl->contact_h, "ERROR: Your message was not"
1032
+						" sent. Something wrong during transmition to"
1033
+						" Jabber!", &jbc->jkey->flag);
980 1034
 					goto step_w;
981 1035
 				}
982 1036
 				else // skip freeing the SIP message - now is in queue
... ...
@@ -986,14 +1040,20 @@ step_z:
986 1040
 				xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
987 1041
 						jwl->contact_h, "ERROR: Your message was not"
988 1042
 						" sent. You are not registered with this transport.",
989
-						jbc->close);
1043
+						&jbc->jkey->flag);
990 1044
 				goto step_w;
991
-			
1045
+			case 3:
1046
+				xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
1047
+						jwl->contact_h, "ERROR: Your message was not"
1048
+						" sent. You are not joined in the conference.",
1049
+						&jbc->jkey->flag);
1050
+				goto step_w;
1051
+				
992 1052
 			default:
993 1053
 				xj_send_sip_msgz(jsmsg->jkey->id, &jsmsg->to,
994 1054
 						jwl->contact_h, "ERROR: Your message was not"
995 1055
 						" sent. Something wrong during transmition to"
996
-						" Jabber.", jbc->close);
1056
+						" Jabber.", &jbc->jkey->flag);
997 1057
 				goto step_w;
998 1058
 		}
999 1059
 
... ...
@@ -1057,9 +1117,13 @@ step_y:
1057 1117
 					DBG("XJAB:xj_worker:%d: ERROR -"
1058 1118
 						" connection to jabber lost on socket <%d> ...\n",
1059 1119
 						_xj_pid, jcp->ojc[i]->sock);
1060
-					jcp->ojc[i]->sock = -1;
1061
-					jcp->ojc[i]->expire = ltime = 0;
1062
-					break;
1120
+					xj_send_sip_msgz(jcp->ojc[i]->jkey->id, &jab_gw_name, 
1121
+						jwl->contact_h,"ERROR:Connection to Jabber server"
1122
+						" lost. You have to re-login.", &jbc->jkey->flag);
1123
+					// make sure that will ckeck expired connections
1124
+					ltime = jcp->ojc[i]->expire = -1;
1125
+					FD_CLR(jcp->ojc[i]->sock, &set);
1126
+					goto step_xx;
1063 1127
 				}
1064 1128
 				DBG("XJAB:xj_worker:%d: received: %dbytes Err:%d/EA:%d\n", 
1065 1129
 						_xj_pid, nr, errno, EAGAIN);		
... ...
@@ -1109,8 +1173,8 @@ step_x:
1109 1173
 				}
1110 1174
 			}
1111 1175
 		}
1112
-
1113
-		if(ltime + jwl->sleept <= get_ticks())
1176
+step_xx:
1177
+		if(ltime < 0 || ltime + jwl->sleept <= get_ticks())
1114 1178
 		{
1115 1179
 			ltime = get_ticks();
1116 1180
 			DBG("XJAB:xj_worker:%d: scanning for expired connection\n",
... ...
@@ -1119,16 +1183,20 @@ step_x:
1119 1183
 			{
1120 1184
 				if(jcp->ojc[i] == NULL)
1121 1185
 					continue;
1122
-				if((jcp->ojc[i]->close == NULL || *(jcp->ojc[i]->close)==0) &&
1186
+				if(jcp->ojc[i]->jkey->flag==0 &&
1123 1187
 					jcp->ojc[i]->expire > ltime)
1124 1188
 					continue;
1125 1189
 				
1126 1190
 				DBG("XJAB:xj_worker:%d: connection expired for"
1127 1191
 					" <%.*s> \n", _xj_pid, jcp->ojc[i]->jkey->id->len,
1128 1192
 					jcp->ojc[i]->jkey->id->s);
1129
-				if(jcp->ojc[i]->close != NULL)
1130
-					DBG("XJAB:xj_worker:%d: connection's close flag [%p=%d]\n",
1131
-						_xj_pid, jcp->ojc[i]->close, *(jcp->ojc[i]->close));
1193
+
1194
+				xj_send_sip_msgz(jcp->ojc[i]->jkey->id,  &jab_gw_name,
1195
+					jwl->contact_h, "INFO: Your are now offline in"
1196
+					" Jabber network.", NULL);
1197
+
1198
+				DBG("XJAB:xj_worker:%d: connection's close flag =%d\n",
1199
+						_xj_pid, jcp->ojc[i]->jkey->flag);
1132 1200
 				// CLEAN JAB_WLIST
1133 1201
 				xj_wlist_del(jwl, jcp->ojc[i]->jkey, _xj_pid);
1134 1202
 
... ...
@@ -1152,10 +1220,10 @@ step_x:
1152 1220
 				jcp->ojc[i] = NULL;
1153 1221
 			}
1154 1222
 		}
1155
-
1156 1223
 	} // END while
1157 1224
 
1158 1225
 	DBG("XJAB:xj_worker:%d: cleaning procedure\n", _xj_pid);
1226
+
1159 1227
 	return 0;
1160 1228
 } // end xj_worker_process
1161 1229
 
... ...
@@ -1245,7 +1313,7 @@ int xj_manage_jab(char *buf, int len, int *pos, str *sid,
1245 1313
 			ts.s = lbuf;
1246 1314
 			ts.len = strlen(lbuf);
1247 1315
 	
1248
-			if(xj_send_sip_msg(sid, &jcf->uri, sct, &ts, jbc->close) < 0)
1316
+			if(xj_send_sip_msg(sid, &jcf->uri, sct, &ts, &jbc->jkey->flag)<0)
1249 1317
 				DBG("XJAB:xj_manage_jab: ERROR SIP MESSAGE was not sent!\n");
1250 1318
 			else
1251 1319
 				DBG("XJAB:xj_manage_jab: SIP MESSAGE was sent!\n");
... ...
@@ -1262,7 +1330,7 @@ int xj_manage_jab(char *buf, int len, int *pos, str *sid,
1262 1330
 			ts.s = lbuf;
1263 1331
 			ts.len = strlen(lbuf);
1264 1332
 	
1265
-			if(xj_send_sip_msg(sid, &tf, sct, &ts, jbc->close) < 0)
1333
+			if(xj_send_sip_msg(sid, &tf, sct, &ts, &jbc->jkey->flag) < 0)
1266 1334
 				DBG("XJAB:xj_manage_jab: ERROR SIP MESSAGE was not sent ...\n");
1267 1335
 			else
1268 1336
 				DBG("XJAB:xj_manage_jab: SIP MESSAGE was sent.\n");
... ...
@@ -1293,11 +1361,11 @@ int xj_manage_jab(char *buf, int len, int *pos, str *sid,
1293 1361
 				{
1294 1362
 					xj_send_sip_msgz(sid, &tf, sct, "ERROR: Your nickname"
1295 1363
 					" already exists in the room. Please choose a new one.",
1296
-					jbc->close);
1364
+					&jbc->jkey->flag);
1297 1365
 					goto ready;
1298 1366
 				}
1299 1367
 				xj_send_sip_msgz(sid, &tf, sct, "ERROR: Your participation"
1300
-					" to the conference room was refused.", jbc->close);
1368
+					" to the conference room was refused.", &jbc->jkey->flag);
1301 1369
 			}
1302 1370
 
1303 1371
 			goto ready;
... ...
@@ -1395,6 +1463,9 @@ ready:
1395 1463
 void xj_sig_handler(int s) 
1396 1464
 {
1397 1465
 	signal(SIGTERM, xj_sig_handler);
1466
+	signal(SIGINT, xj_sig_handler);
1467
+	signal(SIGQUIT, xj_sig_handler);
1468
+	signal(SIGSEGV, xj_sig_handler);
1398 1469
 	main_loop = 0;
1399 1470
 	DBG("XJAB:xj_worker:%d: SIGNAL received=%d\n", _xj_pid, s);
1400 1471
 }
... ...
@@ -1498,10 +1569,14 @@ void xj_tuac_callback( struct cell *t, struct sip_msg *msg,
1498 1569
 		DBG("XJAB: m_tuac_callback: parameter not received\n");
1499 1570
 		return;
1500 1571
 	}
1501
-	DBG("XJAB: xj_tuac_callback: parameter [%p == %d]\n", t->cbp,
1502
-					(t->cbp)?*(*((int**)t->cbp)):0);
1572
+	DBG("XJAB: xj_tuac_callback: parameter [%p : ex-value=%d]\n", t->cbp,
1573
+					*(*((int**)t->cbp)) );
1503 1574
 	if(code < 200 || code >= 300)
1575
+	{
1576
+		DBG("XJAB: xj_tuac_callback: no 2XX return code - connection set"
1577
+			" as expired \n");
1504 1578
 		*(*((int**)t->cbp)) = 1;	
1579
+	}
1505 1580
 }
1506 1581
 
1507 1582
 /*****************************     ****************************************/
... ...
@@ -50,7 +50,8 @@ typedef struct _xj_jalias
50 50
 typedef struct _xj_worker
51 51
 {
52 52
 	int pid;			// process id
53
-	int pipe;			// communication pipe
53
+	int wpipe;			// communication pipe - write
54
+	int rpipe;			// communication pipe - read
54 55
 	int nr;				// number of jobs
55 56
 	tree234 *sip_ids;   // sip ids allocated for the worker
56 57
 } t_xj_worker, *xj_worker;
... ...
@@ -72,7 +73,7 @@ typedef struct _xj_wlist
72 73
 
73 74
 xj_wlist xj_wlist_init(int **, int, int, int, int, int);
74 75
 int  xj_wlist_init_contact(xj_wlist, char *);
75
-int  xj_wlist_set_pids(xj_wlist, int *, int);
76
+int  xj_wlist_set_pid(xj_wlist, int, int);
76 77
 int  xj_wlist_get(xj_wlist, xj_jkey, xj_jkey*);
77 78
 int  xj_wlist_check(xj_wlist, xj_jkey, xj_jkey*);
78 79
 void xj_wlist_del(xj_wlist, xj_jkey, int);