]>
Commit | Line | Data |
---|---|---|
c5571a1d | 1 | /* |
61515785 | 2 | * "$Id: dbus.c 11500 2014-01-06 22:21:15Z msweet $" |
c5571a1d | 3 | * |
61515785 | 4 | * D-Bus notifier for CUPS. |
c5571a1d | 5 | * |
61515785 MS |
6 | * Copyright 2008-2014 by Apple Inc. |
7 | * Copyright (C) 2011, 2013 Red Hat, Inc. | |
8 | * Copyright (C) 2007 Tim Waugh <twaugh@redhat.com> | |
9 | * Copyright 1997-2005 by Easy Software Products. | |
c5571a1d | 10 | * |
61515785 MS |
11 | * These coded instructions, statements, and computer programs are the |
12 | * property of Apple Inc. and are protected by Federal copyright | |
13 | * law. Distribution and use rights are outlined in the file "LICENSE.txt" | |
14 | * which should have been included with this file. If this file is | |
15 | * file is missing or damaged, see the license at "http://www.cups.org/". | |
c5571a1d MS |
16 | */ |
17 | ||
18 | /* | |
19 | * Include necessary headers... | |
20 | */ | |
21 | ||
22 | #include <cups/cups.h> | |
71e16022 | 23 | #include <cups/string-private.h> |
c5571a1d MS |
24 | #include <fcntl.h> |
25 | #include <signal.h> | |
26 | #include <sys/stat.h> | |
27 | #include <sys/types.h> | |
28 | #include <unistd.h> | |
29 | ||
12f89d24 MS |
30 | #ifdef HAVE_DBUS |
31 | # include <dbus/dbus.h> | |
32 | # ifdef HAVE_DBUS_MESSAGE_ITER_INIT_APPEND | |
33 | # define dbus_message_append_iter_init dbus_message_iter_init_append | |
34 | # define dbus_message_iter_append_string(i,v) dbus_message_iter_append_basic(i, DBUS_TYPE_STRING, v) | |
35 | # define dbus_message_iter_append_uint32(i,v) dbus_message_iter_append_basic(i, DBUS_TYPE_UINT32, v) | |
36 | # define dbus_message_iter_append_boolean(i,v) dbus_message_iter_append_basic(i, DBUS_TYPE_BOOLEAN, v) | |
37 | # endif /* HAVE_DBUS_MESSAGE_ITER_INIT_APPEND */ | |
c5571a1d MS |
38 | |
39 | ||
40 | /* | |
41 | * D-Bus object: org.cups.cupsd.Notifier | |
42 | * D-Bus object path: /org/cups/cupsd/Notifier | |
43 | * | |
44 | * D-Bus interface name: org.cups.cupsd.Notifier | |
45 | * | |
46 | * Signals: | |
47 | * | |
48 | * ServerRestarted(STRING text) | |
49 | * Server has restarted. | |
50 | * | |
51 | * ServerStarted(STRING text) | |
52 | * Server has started. | |
53 | * | |
54 | * ServerStopped(STRING text) | |
55 | * Server has stopped. | |
56 | * | |
57 | * ServerAudit(STRING text) | |
58 | * Security-related event. | |
59 | * | |
60 | * PrinterRestarted(STRING text, | |
61 | * STRING printer-uri, | |
62 | * STRING printer-name, | |
63 | * UINT32 printer-state, | |
64 | * STRING printer-state-reasons, | |
65 | * BOOLEAN printer-is-accepting-jobs) | |
66 | * Printer has restarted. | |
67 | * | |
68 | * PrinterShutdown(STRING text, | |
69 | * STRING printer-uri, | |
70 | * STRING printer-name, | |
71 | * UINT32 printer-state, | |
72 | * STRING printer-state-reasons, | |
73 | * BOOLEAN printer-is-accepting-jobs) | |
74 | * Printer has shutdown. | |
75 | * | |
76 | * PrinterStopped(STRING text, | |
77 | * STRING printer-uri, | |
78 | * STRING printer-name, | |
79 | * UINT32 printer-state, | |
80 | * STRING printer-state-reasons, | |
81 | * BOOLEAN printer-is-accepting-jobs) | |
82 | * Printer has stopped. | |
83 | * | |
84 | * PrinterStateChanged(STRING text, | |
85 | * STRING printer-uri, | |
86 | * STRING printer-name, | |
87 | * UINT32 printer-state, | |
88 | * STRING printer-state-reasons, | |
89 | * BOOLEAN printer-is-accepting-jobs) | |
90 | * Printer state has changed. | |
91 | * | |
92 | * PrinterFinishingsChanged(STRING text, | |
93 | * STRING printer-uri, | |
94 | * STRING printer-name, | |
95 | * UINT32 printer-state, | |
96 | * STRING printer-state-reasons, | |
97 | * BOOLEAN printer-is-accepting-jobs) | |
98 | * Printer's finishings-supported attribute has changed. | |
99 | * | |
100 | * PrinterMediaChanged(STRING text, | |
101 | * STRING printer-uri, | |
102 | * STRING printer-name, | |
103 | * UINT32 printer-state, | |
104 | * STRING printer-state-reasons, | |
105 | * BOOLEAN printer-is-accepting-jobs) | |
106 | * Printer's media-supported attribute has changed. | |
107 | * | |
108 | * PrinterAdded(STRING text, | |
109 | * STRING printer-uri, | |
110 | * STRING printer-name, | |
111 | * UINT32 printer-state, | |
112 | * STRING printer-state-reasons, | |
113 | * BOOLEAN printer-is-accepting-jobs) | |
114 | * Printer has been added. | |
115 | * | |
116 | * PrinterDeleted(STRING text, | |
117 | * STRING printer-uri, | |
118 | * STRING printer-name, | |
119 | * UINT32 printer-state, | |
120 | * STRING printer-state-reasons, | |
121 | * BOOLEAN printer-is-accepting-jobs) | |
122 | * Printer has been deleted. | |
123 | * | |
124 | * PrinterModified(STRING text, | |
125 | * STRING printer-uri, | |
126 | * STRING printer-name, | |
127 | * UINT32 printer-state, | |
128 | * STRING printer-state-reasons, | |
129 | * BOOLEAN printer-is-accepting-jobs) | |
130 | * Printer has been modified. | |
131 | * | |
132 | * text describes the event. | |
133 | * printer-state-reasons is a comma-separated list. | |
134 | * If printer-uri is "" in a Job* signal, the other printer-* parameters | |
135 | * must be ignored. | |
136 | * If the job name is not know, job-name will be "". | |
137 | */ | |
138 | ||
139 | /* | |
140 | * Constants... | |
141 | */ | |
142 | ||
143 | enum | |
144 | { | |
145 | PARAMS_NONE, | |
146 | PARAMS_PRINTER, | |
147 | PARAMS_JOB | |
148 | }; | |
149 | ||
150 | ||
61515785 MS |
151 | /* |
152 | * Global variables... | |
153 | */ | |
154 | ||
155 | static char lock_filename[1024]; /* Lock filename */ | |
156 | ||
157 | ||
c5571a1d MS |
158 | /* |
159 | * Local functions... | |
160 | */ | |
161 | ||
49d87452 | 162 | static int acquire_lock(int *fd, char *lockfile, size_t locksize); |
61515785 | 163 | static void release_lock(void); |
c5571a1d MS |
164 | |
165 | ||
166 | /* | |
167 | * 'main()' - Read events and send DBUS notifications. | |
168 | */ | |
169 | ||
170 | int /* O - Exit status */ | |
171 | main(int argc, /* I - Number of command-line args */ | |
172 | char *argv[]) /* I - Command-line arguments */ | |
173 | { | |
174 | ipp_t *msg; /* Event message from scheduler */ | |
175 | ipp_state_t state; /* IPP event state */ | |
176 | struct sigaction action; /* POSIX sigaction data */ | |
177 | DBusConnection *con = NULL; /* Connection to DBUS server */ | |
178 | DBusError error; /* Error, if any */ | |
179 | DBusMessage *message; /* Message to send */ | |
180 | DBusMessageIter iter; /* Iterator for message data */ | |
181 | int lock_fd = -1; /* Lock file descriptor */ | |
c5571a1d MS |
182 | |
183 | ||
184 | /* | |
185 | * Don't buffer stderr... | |
186 | */ | |
187 | ||
188 | setbuf(stderr, NULL); | |
189 | ||
190 | /* | |
191 | * Ignore SIGPIPE signals... | |
192 | */ | |
193 | ||
194 | memset(&action, 0, sizeof(action)); | |
195 | action.sa_handler = SIG_IGN; | |
196 | sigaction(SIGPIPE, &action, NULL); | |
197 | ||
198 | /* | |
199 | * Validate command-line options... | |
200 | */ | |
201 | ||
202 | if (argc != 3) | |
203 | { | |
204 | fputs("Usage: dbus dbus:/// notify-user-data\n", stderr); | |
205 | return (1); | |
206 | } | |
207 | ||
49d87452 | 208 | if (strncmp(argv[1], "dbus:", 5)) |
c5571a1d MS |
209 | { |
210 | fprintf(stderr, "ERROR: Bad URI \"%s\"!\n", argv[1]); | |
211 | return (1); | |
212 | } | |
213 | ||
214 | /* | |
215 | * Loop forever until we run out of events... | |
216 | */ | |
217 | ||
218 | for (;;) | |
219 | { | |
220 | ipp_attribute_t *attr; /* Current attribute */ | |
221 | const char *event; /* Event name */ | |
222 | const char *signame = NULL;/* DBUS signal name */ | |
223 | char *printer_reasons = NULL; | |
224 | /* Printer reasons string */ | |
dcb445bc MS |
225 | char *job_reasons = NULL; |
226 | /* Job reasons string */ | |
c5571a1d MS |
227 | const char *nul = ""; /* Empty string value */ |
228 | int no = 0; /* Boolean "no" value */ | |
229 | int params = PARAMS_NONE; | |
230 | /* What parameters to include? */ | |
231 | ||
232 | ||
233 | /* | |
234 | * Get the next event... | |
235 | */ | |
236 | ||
237 | msg = ippNew(); | |
238 | while ((state = ippReadFile(0, msg)) != IPP_DATA) | |
239 | { | |
240 | if (state <= IPP_IDLE) | |
241 | break; | |
242 | } | |
243 | ||
244 | fprintf(stderr, "DEBUG: state=%d\n", state); | |
245 | ||
246 | if (state == IPP_ERROR) | |
247 | fputs("DEBUG: ippReadFile() returned IPP_ERROR!\n", stderr); | |
248 | ||
249 | if (state <= IPP_IDLE) | |
250 | { | |
251 | /* | |
252 | * Out of messages, free memory and then exit... | |
253 | */ | |
254 | ||
255 | ippDelete(msg); | |
256 | break; | |
257 | } | |
258 | ||
259 | /* | |
260 | * Verify connection to DBUS server... | |
261 | */ | |
262 | ||
263 | if (con && !dbus_connection_get_is_connected(con)) | |
264 | { | |
265 | dbus_connection_unref(con); | |
266 | con = NULL; | |
267 | } | |
268 | ||
269 | if (!con) | |
270 | { | |
271 | dbus_error_init(&error); | |
272 | ||
273 | con = dbus_bus_get(DBUS_BUS_SYSTEM, &error); | |
274 | if (!con) | |
275 | dbus_error_free(&error); | |
276 | else | |
277 | fputs("DEBUG: Connected to D-BUS\n", stderr); | |
278 | } | |
279 | ||
280 | if (!con) | |
281 | continue; | |
282 | ||
283 | if (lock_fd == -1 && | |
284 | acquire_lock(&lock_fd, lock_filename, sizeof(lock_filename))) | |
285 | continue; | |
286 | ||
287 | attr = ippFindAttribute(msg, "notify-subscribed-event", | |
dcb445bc | 288 | IPP_TAG_KEYWORD); |
c5571a1d MS |
289 | if (!attr) |
290 | continue; | |
291 | ||
dcb445bc | 292 | event = ippGetString(attr, 0, NULL); |
c5571a1d MS |
293 | if (!strncmp(event, "server-", 7)) |
294 | { | |
295 | const char *word2 = event + 7; /* Second word */ | |
296 | ||
297 | if (!strcmp(word2, "restarted")) | |
298 | signame = "ServerRestarted"; | |
299 | else if (!strcmp(word2, "started")) | |
300 | signame = "ServerStarted"; | |
301 | else if (!strcmp(word2, "stopped")) | |
302 | signame = "ServerStopped"; | |
303 | else if (!strcmp(word2, "audit")) | |
304 | signame = "ServerAudit"; | |
305 | else | |
306 | continue; | |
307 | } | |
308 | else if (!strncmp(event, "printer-", 8)) | |
309 | { | |
310 | const char *word2 = event + 8; /* Second word */ | |
311 | ||
312 | params = PARAMS_PRINTER; | |
313 | if (!strcmp(word2, "restarted")) | |
314 | signame = "PrinterRestarted"; | |
315 | else if (!strcmp(word2, "shutdown")) | |
316 | signame = "PrinterShutdown"; | |
317 | else if (!strcmp(word2, "stopped")) | |
318 | signame = "PrinterStopped"; | |
319 | else if (!strcmp(word2, "state-changed")) | |
320 | signame = "PrinterStateChanged"; | |
321 | else if (!strcmp(word2, "finishings-changed")) | |
322 | signame = "PrinterFinishingsChanged"; | |
323 | else if (!strcmp(word2, "media-changed")) | |
324 | signame = "PrinterMediaChanged"; | |
325 | else if (!strcmp(word2, "added")) | |
326 | signame = "PrinterAdded"; | |
327 | else if (!strcmp(word2, "deleted")) | |
328 | signame = "PrinterDeleted"; | |
329 | else if (!strcmp(word2, "modified")) | |
330 | signame = "PrinterModified"; | |
331 | else | |
332 | continue; | |
333 | } | |
334 | else if (!strncmp(event, "job-", 4)) | |
335 | { | |
336 | const char *word2 = event + 4; /* Second word */ | |
337 | ||
338 | params = PARAMS_JOB; | |
f14324a7 | 339 | if (!strcmp(word2, "state-changed")) |
c5571a1d MS |
340 | signame = "JobState"; |
341 | else if (!strcmp(word2, "created")) | |
342 | signame = "JobCreated"; | |
343 | else if (!strcmp(word2, "completed")) | |
344 | signame = "JobCompleted"; | |
345 | else if (!strcmp(word2, "stopped")) | |
346 | signame = "JobStopped"; | |
347 | else if (!strcmp(word2, "config-changed")) | |
348 | signame = "JobConfigChanged"; | |
349 | else if (!strcmp(word2, "progress")) | |
350 | signame = "JobProgress"; | |
351 | else | |
352 | continue; | |
353 | } | |
354 | else | |
355 | continue; | |
356 | ||
357 | /* | |
358 | * Create and send the new message... | |
359 | */ | |
d7225fc2 | 360 | |
c5571a1d MS |
361 | fprintf(stderr, "DEBUG: %s\n", signame); |
362 | message = dbus_message_new_signal("/org/cups/cupsd/Notifier", | |
363 | "org.cups.cupsd.Notifier", | |
364 | signame); | |
365 | ||
366 | dbus_message_append_iter_init(message, &iter); | |
367 | attr = ippFindAttribute(msg, "notify-text", IPP_TAG_TEXT); | |
dcb445bc MS |
368 | if (attr) |
369 | { | |
370 | const char *val = ippGetString(attr, 0, NULL); | |
371 | if (!dbus_message_iter_append_string(&iter, &val)) | |
372 | goto bail; | |
373 | } | |
374 | else | |
c5571a1d | 375 | goto bail; |
c5571a1d MS |
376 | |
377 | if (params >= PARAMS_PRINTER) | |
378 | { | |
379 | char *p; /* Pointer into printer_reasons */ | |
380 | size_t reasons_length; /* Required size of printer_reasons */ | |
381 | int i; /* Looping var */ | |
382 | int have_printer_params = 1;/* Do we have printer URI? */ | |
383 | ||
384 | /* STRING printer-uri or "" */ | |
385 | attr = ippFindAttribute(msg, "notify-printer-uri", IPP_TAG_URI); | |
386 | if (attr) | |
dcb445bc MS |
387 | { |
388 | const char *val = ippGetString(attr, 0, NULL); | |
389 | if (!dbus_message_iter_append_string(&iter, &val)) | |
390 | goto bail; | |
391 | } | |
c5571a1d MS |
392 | else |
393 | { | |
394 | have_printer_params = 0; | |
395 | dbus_message_iter_append_string(&iter, &nul); | |
396 | } | |
397 | ||
398 | /* STRING printer-name */ | |
399 | if (have_printer_params) | |
400 | { | |
401 | attr = ippFindAttribute(msg, "printer-name", IPP_TAG_NAME); | |
dcb445bc MS |
402 | if (attr) |
403 | { | |
404 | const char *val = ippGetString(attr, 0, NULL); | |
405 | if (!dbus_message_iter_append_string(&iter, &val)) | |
406 | goto bail; | |
407 | } | |
408 | else | |
409 | goto bail; | |
c5571a1d MS |
410 | } |
411 | else | |
412 | dbus_message_iter_append_string(&iter, &nul); | |
413 | ||
414 | /* UINT32 printer-state */ | |
415 | if (have_printer_params) | |
416 | { | |
417 | attr = ippFindAttribute(msg, "printer-state", IPP_TAG_ENUM); | |
418 | if (attr) | |
dcb445bc MS |
419 | { |
420 | dbus_uint32_t val = ippGetInteger(attr, 0); | |
421 | dbus_message_iter_append_uint32(&iter, &val); | |
422 | } | |
c5571a1d MS |
423 | else |
424 | goto bail; | |
425 | } | |
426 | else | |
427 | dbus_message_iter_append_uint32(&iter, &no); | |
428 | ||
429 | /* STRING printer-state-reasons */ | |
430 | if (have_printer_params) | |
431 | { | |
432 | attr = ippFindAttribute(msg, "printer-state-reasons", | |
433 | IPP_TAG_KEYWORD); | |
434 | if (attr) | |
435 | { | |
dcb445bc MS |
436 | int num_values = ippGetCount(attr); |
437 | for (reasons_length = 0, i = 0; i < num_values; i++) | |
c5571a1d | 438 | /* All need commas except the last, which needs a nul byte. */ |
dcb445bc | 439 | reasons_length += 1 + strlen(ippGetString(attr, i, NULL)); |
c5571a1d MS |
440 | printer_reasons = malloc(reasons_length); |
441 | if (!printer_reasons) | |
442 | goto bail; | |
443 | p = printer_reasons; | |
dcb445bc | 444 | for (i = 0; i < num_values; i++) |
c5571a1d | 445 | { |
c5571a1d MS |
446 | if (i) |
447 | *p++ = ','; | |
d7225fc2 | 448 | |
5a9febac MS |
449 | strlcpy(p, ippGetString(attr, i, NULL), |
450 | reasons_length - (p - printer_reasons)); | |
d7225fc2 | 451 | p += strlen(p); |
c5571a1d | 452 | } |
dcb445bc MS |
453 | if (!dbus_message_iter_append_string(&iter, &printer_reasons)) |
454 | goto bail; | |
c5571a1d MS |
455 | } |
456 | else | |
457 | goto bail; | |
458 | } | |
459 | else | |
460 | dbus_message_iter_append_string(&iter, &nul); | |
461 | ||
462 | /* BOOL printer-is-accepting-jobs */ | |
463 | if (have_printer_params) | |
464 | { | |
465 | attr = ippFindAttribute(msg, "printer-is-accepting-jobs", | |
466 | IPP_TAG_BOOLEAN); | |
467 | if (attr) | |
dcb445bc MS |
468 | { |
469 | dbus_bool_t val = ippGetBoolean(attr, 0); | |
470 | dbus_message_iter_append_boolean(&iter, &val); | |
471 | } | |
c5571a1d MS |
472 | else |
473 | goto bail; | |
474 | } | |
475 | else | |
476 | dbus_message_iter_append_boolean(&iter, &no); | |
477 | } | |
478 | ||
479 | if (params >= PARAMS_JOB) | |
480 | { | |
dcb445bc MS |
481 | char *p; /* Pointer into job_reasons */ |
482 | size_t reasons_length; /* Required size of job_reasons */ | |
483 | int i; /* Looping var */ | |
484 | ||
c5571a1d MS |
485 | /* UINT32 job-id */ |
486 | attr = ippFindAttribute(msg, "notify-job-id", IPP_TAG_INTEGER); | |
dcb445bc MS |
487 | if (attr) |
488 | { | |
489 | dbus_uint32_t val = ippGetInteger(attr, 0); | |
490 | dbus_message_iter_append_uint32(&iter, &val); | |
491 | } | |
492 | else | |
c5571a1d | 493 | goto bail; |
c5571a1d MS |
494 | |
495 | /* UINT32 job-state */ | |
496 | attr = ippFindAttribute(msg, "job-state", IPP_TAG_ENUM); | |
dcb445bc MS |
497 | if (attr) |
498 | { | |
499 | dbus_uint32_t val = ippGetInteger(attr, 0); | |
500 | dbus_message_iter_append_uint32(&iter, &val); | |
501 | } | |
502 | else | |
c5571a1d | 503 | goto bail; |
c5571a1d MS |
504 | |
505 | /* STRING job-state-reasons */ | |
506 | attr = ippFindAttribute(msg, "job-state-reasons", IPP_TAG_KEYWORD); | |
dcb445bc MS |
507 | if (attr) |
508 | { | |
509 | int num_values = ippGetCount(attr); | |
510 | for (reasons_length = 0, i = 0; i < num_values; i++) | |
511 | /* All need commas except the last, which needs a nul byte. */ | |
512 | reasons_length += 1 + strlen(ippGetString(attr, i, NULL)); | |
513 | job_reasons = malloc(reasons_length); | |
514 | if (!job_reasons) | |
515 | goto bail; | |
516 | p = job_reasons; | |
517 | for (i = 0; i < num_values; i++) | |
518 | { | |
519 | if (i) | |
520 | *p++ = ','; | |
521 | ||
5a9febac MS |
522 | strlcpy(p, ippGetString(attr, i, NULL), |
523 | reasons_length - (p - job_reasons)); | |
dcb445bc MS |
524 | p += strlen(p); |
525 | } | |
526 | if (!dbus_message_iter_append_string(&iter, &job_reasons)) | |
527 | goto bail; | |
528 | } | |
529 | else | |
c5571a1d | 530 | goto bail; |
c5571a1d MS |
531 | |
532 | /* STRING job-name or "" */ | |
533 | attr = ippFindAttribute(msg, "job-name", IPP_TAG_NAME); | |
534 | if (attr) | |
dcb445bc MS |
535 | { |
536 | const char *val = ippGetString(attr, 0, NULL); | |
537 | if (!dbus_message_iter_append_string(&iter, &val)) | |
538 | goto bail; | |
539 | } | |
c5571a1d MS |
540 | else |
541 | dbus_message_iter_append_string(&iter, &nul); | |
542 | ||
543 | /* UINT32 job-impressions-completed */ | |
544 | attr = ippFindAttribute(msg, "job-impressions-completed", | |
545 | IPP_TAG_INTEGER); | |
dcb445bc MS |
546 | if (attr) |
547 | { | |
548 | dbus_uint32_t val = ippGetInteger(attr, 0); | |
549 | dbus_message_iter_append_uint32(&iter, &val); | |
550 | } | |
551 | else | |
c5571a1d | 552 | goto bail; |
c5571a1d MS |
553 | } |
554 | ||
555 | dbus_connection_send(con, message, NULL); | |
556 | dbus_connection_flush(con); | |
557 | ||
558 | /* | |
559 | * Cleanup... | |
560 | */ | |
561 | ||
562 | bail: | |
563 | ||
dcb445bc MS |
564 | dbus_message_unref(message); |
565 | ||
c5571a1d MS |
566 | if (printer_reasons) |
567 | free(printer_reasons); | |
568 | ||
dcb445bc MS |
569 | if (job_reasons) |
570 | free(job_reasons); | |
571 | ||
c5571a1d MS |
572 | ippDelete(msg); |
573 | } | |
574 | ||
575 | /* | |
576 | * Remove lock file... | |
577 | */ | |
578 | ||
579 | if (lock_fd >= 0) | |
580 | { | |
581 | close(lock_fd); | |
61515785 | 582 | release_lock(); |
c5571a1d MS |
583 | } |
584 | ||
585 | return (0); | |
586 | } | |
587 | ||
588 | ||
61515785 MS |
589 | /* |
590 | * 'release_lock()' - Release the singleton lock. | |
591 | */ | |
592 | ||
593 | static void | |
594 | release_lock(void) | |
595 | { | |
596 | unlink(lock_filename); | |
597 | } | |
598 | ||
599 | ||
600 | /* | |
601 | * 'handle_sigterm()' - Handle SIGTERM signal. | |
602 | */ | |
603 | static void | |
604 | handle_sigterm(int signum) | |
605 | { | |
606 | release_lock(); | |
607 | _exit(0); | |
608 | } | |
609 | ||
c5571a1d MS |
610 | /* |
611 | * 'acquire_lock()' - Acquire a lock so we only have a single notifier running. | |
612 | */ | |
613 | ||
614 | static int /* O - 0 on success, -1 on failure */ | |
615 | acquire_lock(int *fd, /* O - Lock file descriptor */ | |
616 | char *lockfile, /* I - Lock filename buffer */ | |
617 | size_t locksize) /* I - Size of filename buffer */ | |
618 | { | |
61515785 MS |
619 | const char *tmpdir; /* Temporary directory */ |
620 | struct sigaction action; /* POSIX sigaction data */ | |
c5571a1d MS |
621 | |
622 | ||
623 | /* | |
624 | * Figure out where to put the lock file... | |
625 | */ | |
626 | ||
627 | if ((tmpdir = getenv("TMPDIR")) == NULL) | |
628 | tmpdir = "/tmp"; | |
629 | ||
630 | snprintf(lockfile, locksize, "%s/cups-dbus-notifier-lockfile", tmpdir); | |
631 | ||
632 | /* | |
633 | * Create the lock file and fail if it already exists... | |
634 | */ | |
635 | ||
636 | if ((*fd = open(lockfile, O_RDWR | O_CREAT | O_EXCL, S_IRUSR | S_IWUSR)) < 0) | |
637 | return (-1); | |
61515785 MS |
638 | |
639 | /* | |
640 | * Set a SIGTERM handler to make sure we release the lock if the | |
641 | * scheduler decides to stop us. | |
642 | */ | |
643 | memset(&action, 0, sizeof(action)); | |
644 | action.sa_handler = handle_sigterm; | |
645 | sigaction(SIGTERM, &action, NULL); | |
646 | ||
647 | return (0); | |
c5571a1d | 648 | } |
12f89d24 MS |
649 | #else /* !HAVE_DBUS */ |
650 | int | |
651 | main(void) | |
652 | { | |
653 | return (1); | |
654 | } | |
655 | #endif /* HAVE_DBUS */ | |
c5571a1d MS |
656 | |
657 | ||
658 | /* | |
61515785 | 659 | * End of "$Id: dbus.c 11500 2014-01-06 22:21:15Z msweet $". |
c5571a1d | 660 | */ |