~ubuntu-branches/ubuntu/natty/bluefish/natty-proposed

« back to all changes in this revision

Viewing changes to src/msg_queue.c

  • Committer: Bazaar Package Importer
  • Author(s): Davide Puricelli (evo)
  • Date: 2005-04-23 17:05:18 UTC
  • mfrom: (1.2.1 upstream) (2.1.1 warty)
  • Revision ID: james.westby@ubuntu.com-20050423170518-pb8zi3vg32cm6g04
Tags: 1.0-1
* Acknowledge NMU, thanks Leo; closes: #291222.
* Updated debian/ files, thanks Daniel Leidert. 

Show diffs side-by-side

added added

removed removed

Lines of Context:
 
1
/* Bluefish HTML Editor
 
2
 * msg_queue.c - message queue handling
 
3
 *
 
4
 * Copyright (C) 2003 Olivier Sessink
 
5
 *
 
6
 * This program is free software; you can redistribute it and/or modify
 
7
 * it under the terms of the GNU General Public License as published by
 
8
 * the Free Software Foundation; either version 2 of the License, or
 
9
 * (at your option) any later version.
 
10
 *
 
11
 * This program is distributed in the hope that it will be useful,
 
12
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 
13
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 
14
 * GNU General Public License for more details.
 
15
 *
 
16
 * You should have received a copy of the GNU General Public License
 
17
 * along with this program; if not, write to the Free Software
 
18
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
 
19
 */
 
20
#include <gtk/gtk.h>
 
21
 
 
22
/* #define DEBUG */
 
23
 
 
24
#include "bluefish.h"
 
25
 
 
26
#ifdef WITH_MSG_QUEUE
 
27
 
 
28
#include <sys/types.h>
 
29
#include <sys/ipc.h>                    /* msgsnd() */
 
30
#include <sys/msg.h>                    /* msgsnd() */
 
31
#include <time.h>
 
32
#include <errno.h>                              /* errno */
 
33
#include <unistd.h> /* getpid, getuid */
 
34
#include <string.h> /* strncpy */
 
35
#include <stdlib.h> /* exit() */
 
36
 
 
37
#include "stringlist.h"
 
38
#include "gtk_easy.h" /* *_dialog */
 
39
#include "gui.h" /* notebook_changed() */
 
40
#include "document.h"
 
41
#include "project.h"
 
42
 
 
43
#define BLUEFISH_MSG_QUEUE 9723475
 
44
#define MSQ_QUEUE_SIZE 1024
 
45
#define MSQ_QUEUE_SMALL_SIZE 7
 
46
#define MSQ_QUEUE_CHECK_TIME 300        /* miliseconds for gtk_timeout*/
 
47
 
 
48
/* send alive must have the highest number, because it is the only type that 
 
49
 * should not be read by the master process. The sending processes reads this
 
50
 * to check if the queue is alive
 
51
 */
 
52
#define MSG_QUEUE_SEND_ALIVE 46064
 
53
#define MSG_QUEUE_OPENFILE 46063
 
54
#define MSG_QUEUE_OPENPROJECT 46062
 
55
#define MSG_QUEUE_OPENNEWWIN 46061
 
56
/* from man msgrcv: 'the first message on the queue with the lowest type less 
 
57
 * than or equal to the absolute value of msgtyp will be read'
 
58
 * that means the requestalive should have the lowest number, because
 
59
 * it has the highest priority
 
60
 */
 
61
#define MSG_QUEUE_ASK_ALIVE 46010
 
62
 
 
63
#define MSG_QUEUE_PER_DOCUMENT_TIMEOUT 20000000 /* nanoseconds */
 
64
 
 
65
/* 
 
66
the message queue system is quite easy:
 
67
 
 
68
if there is no queue --> open it and start listening
 
69
on a MSG_QUEUE_OPENFILE, open the file, on a MSG_QUEUE_ASK_ALIVE return
 
70
the same data with type MSG_QUEUE_SEND_ALIVE (which we are not
 
71
listening for)
 
72
 
 
73
if there is a queue and there are files loaded on the commandline --> 
 
74
check the server (send a keepalive containing the pid) and send the 
 
75
files to the queue, after sending the files check if a 
 
76
MSG_QUEUE_SEND_ALIVE is received contaning the pid. If so, there is
 
77
a server and we can quit. If not, we continue starting and load them
 
78
 
 
79
if there is a queue and we do not have files loaded on the commandline
 
80
we just start, but we don't listen to the queue!
 
81
*/
 
82
 
 
83
typedef struct {
 
84
        gboolean functional;
 
85
        gboolean server;
 
86
        int msgid;
 
87
        GList *file_error_list;
 
88
} Tmsg_queue;
 
89
 
 
90
/******************************/
 
91
/* global var for this module */
 
92
/******************************/
 
93
Tmsg_queue msg_queue = { TRUE, FALSE, -1, NULL};
 
94
 
 
95
/**
 
96
 * msg_queue_check_alive:
 
97
 *
 
98
 * checks the message queue for messages of type MSG_QUEUE_SEND_ALIVE
 
99
 * if we receive such a message, there must be another process 
 
100
 * active on this message queue
 
101
 */
 
102
static gboolean msg_queue_check_alive(gboolean wait_first)
 
103
{
 
104
        struct small_msgbuf {
 
105
                long mtype;
 
106
                char mtext[MSQ_QUEUE_SMALL_SIZE];
 
107
        } small_msgp;
 
108
        gchar *pid_string = g_strdup_printf("%d", (int) getpid());
 
109
 
 
110
        if (wait_first) {
 
111
                static struct timespec const req = { 0, MSQ_QUEUE_CHECK_TIME * 1000000};
 
112
                static struct timespec rem;
 
113
                nanosleep(&req, &rem);
 
114
        }
 
115
 
 
116
        while (msgrcv
 
117
                   (msg_queue.msgid, &small_msgp, MSQ_QUEUE_SMALL_SIZE * sizeof(char), MSG_QUEUE_SEND_ALIVE,
 
118
                        IPC_NOWAIT) != -1) {
 
119
                DEBUG_MSG("msg_queue_check_alive, received a keepalive, mtext=%s!\n", small_msgp.mtext);
 
120
                if (strncmp(pid_string, small_msgp.mtext, MSQ_QUEUE_SMALL_SIZE - 1) == 0) {
 
121
                        DEBUG_MSG("msg_queue_check_alive, keepalive matches request!\n");
 
122
                        /* we did receive a keepalive on our request !! */
 
123
                        g_free(pid_string);
 
124
                        return TRUE;
 
125
                } else {
 
126
                        DEBUG_MSG("msg_queue_check_alive, keepalive does NOT match request %s\n", pid_string);
 
127
                }
 
128
        }
 
129
        DEBUG_MSG("msg_queue_check_alive, errno=%d, error=%s\n", errno, g_strerror(errno));
 
130
        g_free(pid_string);
 
131
        return FALSE;
 
132
}
 
133
 
 
134
/**
 
135
 * msg_queue_open:
 
136
 *
 
137
 *  returns 1 if another process has the queue open already
 
138
 *  returns 0 if we opened the queue
 
139
 */
 
140
static gboolean msg_queue_open(void)
 
141
{
 
142
        DEBUG_MSG("msg_queue_open, started\n");
 
143
        msg_queue.msgid = msgget((key_t) BLUEFISH_MSG_QUEUE + getuid(), 0666 | IPC_CREAT | IPC_EXCL);
 
144
#ifdef DEBUG
 
145
        if (msg_queue.msgid == -1) {
 
146
                DEBUG_MSG("msg_queue_open, errno=%d, error=%s\n", errno, g_strerror(errno));
 
147
        }
 
148
#endif
 
149
        /* if msg_queue.msgid == -1 the message queue was already opened by another process */
 
150
        DEBUG_MSG("msg_queue_open, msg_queue.msgid=%d\n", msg_queue.msgid);
 
151
        if (msg_queue.msgid == -1) {
 
152
                msg_queue.msgid = msgget((key_t) BLUEFISH_MSG_QUEUE + getuid(), 0666);
 
153
                DEBUG_MSG("msg_queue_open, connected to existing message queue, id=%d\n", msg_queue.msgid);
 
154
                
 
155
                /* now we want to avoid the situation where the message queue is full (because the server died)
 
156
                so we cannot send a keepalive, so we check if the queue is filled (assume when there are >5 messages)
 
157
                and the last completed msgrcv() call was > 5 seconds ago */
 
158
                {
 
159
                        struct msqid_ds msg_stat;
 
160
                        gint timediff;
 
161
                        /* check if there are messages on the queue, if so, check when the last msgrcv() call was on this queue */
 
162
                        msgctl(msg_queue.msgid, IPC_STAT, &msg_stat);
 
163
                        if (msg_stat.msg_qnum > 5) {
 
164
                                timediff = time(NULL) - msg_stat.msg_ctime;
 
165
                                if (timediff > 2) {
 
166
                                        DEBUG_MSG("msg_queue_request_alive, more then 2 seconds no reads on message_queue, timediff=%d, deleting queue\n", timediff);
 
167
                                        msgctl(msg_queue.msgid, IPC_RMID, NULL);
 
168
                                        msg_queue.msgid = msgget((key_t) BLUEFISH_MSG_QUEUE + getuid(), 0666 | IPC_CREAT | IPC_EXCL);
 
169
                                        return FALSE;
 
170
                                }
 
171
                        }
 
172
                }
 
173
                if (msg_queue.msgid == -1) {
 
174
                        DEBUG_MSG("msg_queue_open, errno=%d, error=%s\n", errno, g_strerror(errno));
 
175
                        msg_queue.functional = FALSE;
 
176
                }
 
177
                return TRUE;
 
178
        }
 
179
        return FALSE;
 
180
}
 
181
/**
 
182
 * msg_queue_check:
 
183
 *
 
184
 * checks the queue for any messages
 
185
 * this is called by the master program, usually by gtk_timeout_add()
 
186
 * the messages it will listen to are the types:
 
187
 * - MSG_QUEUE_ASK_ALIVE - we should respond with a type MSG_QUEUE_SEND_ALIVE
 
188
 * - MSG_QUEUE_OPENFILE - open a filename
 
189
 * - MSG_QUEUE_OPENPROJECT - open a filename as project
 
190
 * - MSG_QUEUE_OPENNEWWIN - open a new window
 
191
 */
 
192
static gboolean msg_queue_check(gint started_by_gtk_timeout)
 
193
{
 
194
        struct msgbuf {
 
195
                long mtype;
 
196
                char mtext[MSQ_QUEUE_SIZE];
 
197
        } msgp;
 
198
        gint retval;
 
199
        if (main_v->bfwinlist == NULL || BFWIN(main_v->bfwinlist->data)->documentlist == NULL) {
 
200
                DEBUG_MSG("msg_queue_check, no documentlist yet, so we do not continue\n");
 
201
                return TRUE;
 
202
        }
 
203
 
 
204
        if (msg_queue.msgid == -1) {
 
205
                return FALSE;
 
206
        }
 
207
        retval =        msgrcv(msg_queue.msgid, &msgp, MSQ_QUEUE_SIZE, -MSG_QUEUE_OPENFILE, IPC_NOWAIT);
 
208
        if (retval != -1) {
 
209
                DEBUG_MSG("msg_queue_check, found type %ld\n", msgp.mtype);
 
210
                if (msgp.mtype == MSG_QUEUE_ASK_ALIVE) {
 
211
                        struct small_msgbuf {
 
212
                                long mtype;
 
213
                                char mtext[MSQ_QUEUE_SMALL_SIZE];
 
214
                        } small_msgp;
 
215
                        DEBUG_MSG("msg_queue_check, a keepalive is asked from %s, sending!\n", msgp.mtext);
 
216
                        small_msgp.mtype = MSG_QUEUE_SEND_ALIVE;
 
217
                        strncpy(small_msgp.mtext, msgp.mtext, MSQ_QUEUE_SMALL_SIZE - 1);
 
218
                        msgsnd(msg_queue.msgid, (void *) &small_msgp, MSQ_QUEUE_SMALL_SIZE * sizeof(char),
 
219
                                   IPC_NOWAIT);
 
220
                } else if (msgp.mtype == MSG_QUEUE_OPENFILE) {
 
221
                        GList *lastlist = g_list_last(main_v->bfwinlist);
 
222
                        DEBUG_MSG("msg_queue_check, a filename %s is received\n", msgp.mtext);
 
223
                        if (!doc_new_with_file(BFWIN(lastlist->data),msgp.mtext, TRUE, FALSE)) {
 
224
                                msg_queue.file_error_list = g_list_append(msg_queue.file_error_list, g_strdup(msgp.mtext));
 
225
                        }
 
226
                        msg_queue_check(0);     /* call myself again, there may have been multiple files */
 
227
                        if (started_by_gtk_timeout) {
 
228
                                if (msg_queue.file_error_list) {
 
229
                                        gchar *message, *tmp;
 
230
                                        tmp = stringlist_to_string(msg_queue.file_error_list, "\n");
 
231
                                        free_stringlist(msg_queue.file_error_list);
 
232
                                        msg_queue.file_error_list = NULL;
 
233
                                        message = g_strconcat(_("These files were not opened:\n"), tmp, NULL);
 
234
                                        g_free(tmp);
 
235
                                        warning_dialog(BFWIN(main_v->bfwinlist->data)->main_window,_("Unable to open file(s)\n"), message);
 
236
                                        g_free(message);
 
237
                                }
 
238
/*                              gtk_notebook_set_page(GTK_NOTEBOOK(main_v->notebook),g_list_length(main_v->documentlist) - 1);
 
239
                                notebook_changed(-1);*/
 
240
                        }
 
241
                } else if (msgp.mtype == MSG_QUEUE_OPENPROJECT) {
 
242
                        GList *lastlist = g_list_last(main_v->bfwinlist);
 
243
                        DEBUG_MSG("msg_queue_check, a project %s is received\n", msgp.mtext);
 
244
                        project_open_from_file(BFWIN(lastlist->data), msgp.mtext);
 
245
                        msg_queue_check(0);     /* call myself again, there may have been multiple projects */
 
246
                } else if (msgp.mtype == MSG_QUEUE_OPENNEWWIN) {
 
247
                        /* now check if this is indeed send by another process
 
248
                        if the message queue was dead during the startup of this process,
 
249
                        it might be started by this very process */
 
250
                        int otherpid = atoi(msgp.mtext);
 
251
                        DEBUG_MSG("msg_queue_check, a new window is requested by PID=%d\n",otherpid);
 
252
                        if (otherpid != (int) getpid()) {
 
253
                                DEBUG_MSG("msg_queue_check, the PID is not ours, opening new window\n");
 
254
                                gui_new_window(NULL, NULL);
 
255
                        }
 
256
                }
 
257
#ifdef DEBUG
 
258
                 else {
 
259
                        DEBUG_MSG("msg_queue_check, unknown message queue type %ld\n", msgp.mtype);
 
260
                 }
 
261
#endif
 
262
                
 
263
        } else {
 
264
#ifdef MSG_QUEUE_DEBUG
 
265
                DEBUG_MSG("msg_queue_check, found errno(%d)=%s\n", errno, g_strerror(errno));
 
266
#endif
 
267
        /*
 
268
        43 = Identifier removed
 
269
        */
 
270
                if (errno == 22 || errno == 43) {
 
271
                        DEBUG_MSG("msg_queue_check, re-opening message queue ?!?!?\n");
 
272
                        /* the msg_queue was removed !?!?! */
 
273
                        if (msg_queue_open()) {
 
274
                                DEBUG_MSG("msg_queue_check, another process has opened the message_queue, stopping server\n");
 
275
                                msg_queue.server = FALSE;
 
276
                                return FALSE;
 
277
                        }
 
278
                }
 
279
        }
 
280
        return TRUE;
 
281
}
 
282
 
 
283
/**
 
284
 * msg_queue_send_names:
 
285
 *
 
286
 *
 
287
 * returns FALSE if we never received a keepalive, so the server process seems to be non-responsive
 
288
 */
 
289
static gboolean msg_queue_send_names(gint send_with_id, GList * names, gboolean received_keepalive)
 
290
{
 
291
        struct msgbuf {
 
292
                long mtype;
 
293
                char mtext[MSQ_QUEUE_SIZE];
 
294
        } msgp;
 
295
        gint success = 1, check_keepalive_cnt = 0, send_failure_cnt = 0;
 
296
        GList *tmplist;
 
297
 
 
298
        /* we have a message queue now, opened by another bluefish process */
 
299
        msgp.mtype = send_with_id;
 
300
        tmplist = g_list_first(names);
 
301
        while (tmplist && success) {
 
302
                gint retval;
 
303
                gint len = strlen((gchar *) tmplist->data);
 
304
                
 
305
                /* we start with checking for keepalives */
 
306
                if (!received_keepalive) {
 
307
                        if (msg_queue_check_alive(TRUE)) {
 
308
                                received_keepalive = TRUE;
 
309
                                DEBUG_MSG("msg_queue_send_files, received keepalive\n");
 
310
                        } else {
 
311
                                check_keepalive_cnt++;
 
312
                                DEBUG_MSG("msg_queue_send_files, no keepalive (try %d)\n", check_keepalive_cnt);
 
313
                        }
 
314
                }
 
315
                
 
316
                if (len < MSQ_QUEUE_SIZE - 1) {
 
317
                        strncpy(msgp.mtext, (gchar *) tmplist->data, MSQ_QUEUE_SIZE - 1);
 
318
                        retval =        msgsnd(msg_queue.msgid, (void *) &msgp, MSQ_QUEUE_SIZE * sizeof(char), IPC_NOWAIT);
 
319
                        if (retval == -1) {
 
320
                                DEBUG_MSG("msg_queue_send_files, failed sending, errno=%d\n", errno);
 
321
                                if (errno == EAGAIN) { /* EAGAIN = 11 */
 
322
                                        static struct timespec const req = { 0, MSG_QUEUE_PER_DOCUMENT_TIMEOUT};
 
323
                                        static struct timespec rem;
 
324
                                        nanosleep(&req, &rem);
 
325
                                        send_failure_cnt++;
 
326
                                } else {
 
327
                                        DEBUG_MSG("msg_queue_send_files, failing to send, errno=%d, aborting\n", errno);
 
328
                                        success = 0;
 
329
                                }
 
330
                        } else {
 
331
                                if (!received_keepalive) {
 
332
                                        /* if we fill the message queue with loads of data, the server 
 
333
                                           process doesn't even get a chance of reply-ing. So as long as we 
 
334
                                           don't know a thing about it, we give it some time and check for
 
335
                                           a reply often */
 
336
                                        if (msg_queue_check_alive(TRUE)) {
 
337
                                                received_keepalive = TRUE;
 
338
                                                DEBUG_MSG("msg_queue_send_files, received keepalive\n");
 
339
                                        } else {
 
340
                                                check_keepalive_cnt++;
 
341
                                                DEBUG_MSG("msg_queue_send_files, no keepalive (try %d)\n", check_keepalive_cnt);
 
342
                                        }
 
343
                                }
 
344
                                DEBUG_MSG("msg_queue_send_files, sending %s succeeded\n", (gchar *) tmplist->data);
 
345
                                send_failure_cnt = 0;
 
346
                                tmplist = g_list_next(tmplist);
 
347
                        }
 
348
                } else {
 
349
                        DEBUG_MSG("msg_queue_send_files, failed sending, length increased message size\n");
 
350
                        success = 0;
 
351
                }
 
352
                if ((check_keepalive_cnt > 5) || (send_failure_cnt > 60)) {
 
353
                        DEBUG_MSG
 
354
                                ("msg_queue_send_files, to many tries, check_keepalive_cnt=%d, send_failure_cnt=%d\n",
 
355
                                 check_keepalive_cnt, send_failure_cnt);
 
356
                        success = 0;
 
357
                }
 
358
        }
 
359
        if (success) {
 
360
                DEBUG_MSG
 
361
                        ("msg_queue_send_files, sending filenames complete and successfull, received_keepalive=%d\n",
 
362
                         received_keepalive);
 
363
/*              / * all filenames send to other process, test if it is alive * /
 
364
                if (received_keepalive) {
 
365
                        exit(0);
 
366
                } else {
 
367
                        / * the other process should have enough time to check the queue * /
 
368
                        / * the macro is in milliseconds, usleep is microseconds * /
 
369
                        if (msg_queue_check_alive(TRUE)) {
 
370
                                / * we did receive a keep alive message! * /
 
371
                                exit(0);
 
372
                        }
 
373
                }*/
 
374
                return received_keepalive;
 
375
        }
 
376
        return FALSE;
 
377
}
 
378
 
 
379
static gboolean msg_queue_send_files(GList * filenames, gboolean received_keepalive) {
 
380
        return msg_queue_send_names(MSG_QUEUE_OPENFILE, filenames, received_keepalive);
 
381
}
 
382
 
 
383
static gboolean msg_queue_send_projects(GList * filenames, gboolean received_keepalive) {
 
384
        return msg_queue_send_names(MSG_QUEUE_OPENPROJECT, filenames, received_keepalive);
 
385
}
 
386
 
 
387
/**
 
388
 * msg_queue_request_alive:
 
389
 *
 
390
 * sends a message of type MSG_QUEUE_ASK_ALIVE to the already existing queue
 
391
 * to check if the queue is alive
 
392
 */
 
393
static void msg_queue_request_alive(void)
 
394
{
 
395
        gboolean ask_alive;
 
396
        struct small_msgbuf {
 
397
                long mtype;
 
398
                char mtext[MSQ_QUEUE_SMALL_SIZE];
 
399
        } small_msgp;
 
400
        gchar *pid_string = g_strdup_printf("%d", (int) getpid());
 
401
 
 
402
        DEBUG_MSG("msg_queue_request_alive, asking for keepalive, string %s\n", pid_string);
 
403
        small_msgp.mtype = MSG_QUEUE_ASK_ALIVE;
 
404
        strncpy(small_msgp.mtext, pid_string, MSQ_QUEUE_SMALL_SIZE - 1);
 
405
        ask_alive =
 
406
                msgsnd(msg_queue.msgid, (void *) &small_msgp, MSQ_QUEUE_SMALL_SIZE * sizeof(char),
 
407
                           IPC_NOWAIT);
 
408
        g_free(pid_string);
 
409
        if (ask_alive == -1) {
 
410
                if (errno == 11) {
 
411
                        /* the resource is temporary unavailable - perhaps the queue is full, this could mean a very busy
 
412
                        message queue or a dead server */
 
413
                        struct msqid_ds msg_stat;
 
414
                        gint timediff;
 
415
 
 
416
                        /* check the last time a process listened to the queue */
 
417
                        msgctl(msg_queue.msgid, IPC_STAT, &msg_stat);
 
418
                        timediff = time(NULL) - msg_stat.msg_rtime;
 
419
                        if (timediff > 2) {
 
420
                                DEBUG_MSG("msg_queue_request_alive, more then 2 seconds no reads on message_queue, timediff=%d, deleting queue\n", timediff);
 
421
                                
 
422
                        }
 
423
                }
 
424
                DEBUG_MSG("msg_queue_request_alive, errno=%d, error=%s\n", errno, g_strerror(errno));
 
425
                msg_queue.functional = FALSE;
 
426
        }
 
427
}
 
428
 
 
429
static void msg_queue_send_new_window(void) {
 
430
        int retval;
 
431
        struct msgbuf {
 
432
                long mtype;
 
433
                char mtext[MSQ_QUEUE_SMALL_SIZE];
 
434
        } small_msgp;
 
435
        /* perhaps we should first check if the queue is alive */
 
436
        gchar *pid_string = g_strdup_printf("%d", (int) getpid());
 
437
        DEBUG_MSG("msg_queue_send_new_window, requesting new window using our PID %s!\n",pid_string);
 
438
        small_msgp.mtype = MSG_QUEUE_OPENNEWWIN;
 
439
        strncpy(small_msgp.mtext, pid_string, MSQ_QUEUE_SMALL_SIZE - 1);
 
440
        retval = msgsnd(msg_queue.msgid,(void *) &small_msgp, MSQ_QUEUE_SMALL_SIZE * sizeof(char),IPC_NOWAIT);
 
441
        if (retval == -1) {
 
442
                /* hmm an error, we have to do some error handling here */
 
443
        }
 
444
}
 
445
 
 
446
/*
 
447
        static struct timespec const req = { 0, 200000000};
 
448
        static struct timespec rem;
 
449
        nanosleep(&req, &rem);
 
450
*/
 
451
void msg_queue_start(GList * filenames, GList *projectfiles, gboolean open_new_window) {
 
452
        gboolean received_keepalive = FALSE;
 
453
        gboolean queue_already_open;
 
454
 
 
455
        DEBUG_MSG("msg_queue_start, open message queue\n");
 
456
        queue_already_open = msg_queue_open();
 
457
        if (queue_already_open && msg_queue.functional) {
 
458
                msg_queue_request_alive();
 
459
                if (open_new_window) {
 
460
                        msg_queue_send_new_window();
 
461
                }
 
462
                /* if we have filenames to open, we start sending them now, else we just check if we have to be master or not */
 
463
                if (filenames || projectfiles) {
 
464
                        if (filenames) {
 
465
                                received_keepalive = msg_queue_send_files(filenames, received_keepalive);
 
466
                        }
 
467
                        if (projectfiles) {
 
468
                                received_keepalive = msg_queue_send_projects(projectfiles, received_keepalive);
 
469
                        }
 
470
                        DEBUG_MSG("msg_queue_start, after sending files and projects, keepalive=%d\n",received_keepalive);
 
471
                }
 
472
                
 
473
                if (!received_keepalive) {
 
474
                        gint check_keepalive_cnt = 0;
 
475
                        /* if the message queue is still open and the process listening is killed
 
476
                           we should be the server process --> we have to check if the process is still running */
 
477
                        while (!received_keepalive && check_keepalive_cnt < 10) {
 
478
                                DEBUG_MSG("msg_queue_start, no keepalive yet, check_keepalive_cnt=%d\n", check_keepalive_cnt);
 
479
                                if (msg_queue_check_alive(TRUE)) {
 
480
                                        received_keepalive = TRUE;
 
481
                                }
 
482
                                check_keepalive_cnt++;
 
483
                        }
 
484
                        if ((filenames || projectfiles || open_new_window) && received_keepalive) {
 
485
                                DEBUG_MSG("msg_queue_start, we did send all our messages to an active queue, exiting!\n");
 
486
                                exit(0);
 
487
                        }
 
488
                } else {
 
489
                        DEBUG_MSG("msg_queue_start, we did send all our messages to an active queue, exiting!\n");
 
490
                        exit(0);
 
491
                }
 
492
        }
 
493
 
 
494
        /* if (queue_already_open) */
 
495
        /* if we opened the queue, or we did not get a keepalive */
 
496
        if (msg_queue.functional
 
497
                && (!queue_already_open || (queue_already_open && !received_keepalive))) {
 
498
                msg_queue.server = TRUE;
 
499
                DEBUG_MSG
 
500
                        ("msg_queue_start, we opened the queue, or we didn't get a keepalive, we will be server!\n");
 
501
                gtk_timeout_add(MSQ_QUEUE_CHECK_TIME, (GtkFunction)msg_queue_check, GINT_TO_POINTER(1));
 
502
        } else {
 
503
                DEBUG_MSG("msg_queue_start, we didn't open the queue, and we received a keepalive, further ignoring the mssage queue\n");
 
504
        }
 
505
}
 
506
 
 
507
void msg_queue_cleanup(void)
 
508
{
 
509
        if (msg_queue.functional && msg_queue.server) {
 
510
                DEBUG_MSG("msg_queue_cleanup, removing msg_queue()\n");
 
511
                msgctl(msg_queue.msgid, IPC_RMID, NULL);
 
512
        }
 
513
}
 
514
 
 
515
#endif                                                  /* WITH_MSG_QUEUE */