]>
Commit | Line | Data |
---|---|---|
b737a6ac JR |
1 | diff --git a/cgi-bin/admin.c b/cgi-bin/admin.c |
2 | index 99b8e7b..2688eff 100644 | |
3 | --- a/cgi-bin/admin.c | |
4 | +++ b/cgi-bin/admin.c | |
5 | @@ -1643,7 +1643,7 @@ do_config_server(http_t *http) /* I - HTTP connection */ | |
6 | else | |
7 | local_protocols[0] = '\0'; | |
8 | ||
9 | -#ifdef HAVE_DNSSD | |
10 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
11 | if (cgiGetVariable("BROWSE_LOCAL_DNSSD")) | |
12 | { | |
13 | if (local_protocols[0]) | |
14 | @@ -1651,7 +1651,7 @@ do_config_server(http_t *http) /* I - HTTP connection */ | |
15 | else | |
16 | strcat(local_protocols, "dnssd"); | |
17 | } | |
18 | -#endif /* HAVE_DNSSD */ | |
19 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
20 | ||
21 | #ifdef HAVE_LDAP | |
22 | if (cgiGetVariable("BROWSE_LOCAL_LDAP")) | |
23 | @@ -2718,9 +2718,9 @@ do_menu(http_t *http) /* I - HTTP connection */ | |
24 | #endif /* HAVE_GSSAPI */ | |
25 | cgiSetVariable("KERBEROS", ""); | |
26 | ||
27 | -#ifdef HAVE_DNSSD | |
28 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
29 | cgiSetVariable("HAVE_DNSSD", "1"); | |
30 | -#endif /* HAVE_DNSSD */ | |
31 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
32 | ||
33 | #ifdef HAVE_LDAP | |
34 | cgiSetVariable("HAVE_LDAP", "1"); | |
d07e62b1 ER |
35 | diff --git a/scheduler/client.c b/scheduler/client.c |
36 | index e4c9b01..984dcc5 100644 | |
37 | --- a/scheduler/client.c | |
38 | +++ b/scheduler/client.c | |
39 | @@ -4987,7 +4987,7 @@ valid_host(cupsd_client_t *con) /* I - Client connection */ | |
40 | !strncmp(host, "[::1]:", 6)); | |
41 | } | |
42 | ||
43 | -#ifdef HAVE_DNSSD | |
44 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
45 | /* | |
46 | * Check if the hostname is something.local (Bonjour); if so, allow it. | |
47 | */ | |
48 | @@ -4996,7 +4996,7 @@ valid_host(cupsd_client_t *con) /* I - Client connection */ | |
49 | (!_cups_strcasecmp(end, ".local") || !_cups_strncasecmp(end, ".local:", 7) || | |
50 | !_cups_strcasecmp(end, ".local.") || !_cups_strncasecmp(end, ".local.:", 8))) | |
51 | return (1); | |
52 | -#endif /* HAVE_DNSSD */ | |
53 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
54 | ||
55 | /* | |
56 | * Check if the hostname is an IP address... | |
57 | diff --git a/scheduler/conf.c b/scheduler/conf.c | |
58 | index badc630..c1edd39 100644 | |
59 | --- a/scheduler/conf.c | |
60 | +++ b/scheduler/conf.c | |
61 | @@ -648,7 +648,7 @@ cupsdReadConfiguration(void) | |
62 | Browsing = CUPS_DEFAULT_BROWSING; | |
63 | DefaultShared = CUPS_DEFAULT_DEFAULT_SHARED; | |
64 | ||
65 | -#ifdef HAVE_DNSSD | |
66 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
67 | cupsdSetString(&DNSSDRegType, "_ipp._tcp,_cups"); | |
68 | #endif /* HAVE_DNSSD */ | |
69 | ||
70 | diff --git a/scheduler/dirsvc.c b/scheduler/dirsvc.c | |
71 | index eb3c862..48dcef9 100644 | |
72 | --- a/scheduler/dirsvc.c | |
73 | +++ b/scheduler/dirsvc.c | |
74 | @@ -27,6 +27,7 @@ | |
b737a6ac JR |
75 | * ldap_connect() - Start new LDAP connection |
76 | * ldap_reconnect() - Reconnect to LDAP Server | |
77 | * ldap_disconnect() - Disconnect from LDAP Server | |
d07e62b1 | 78 | + * cupsdStartAvahiClient() - Start an Avahi client if needed |
b737a6ac JR |
79 | * cupsdStartBrowsing() - Start sending and receiving broadcast |
80 | * information. | |
81 | * cupsdStartPolling() - Start polling servers as needed. | |
d07e62b1 | 82 | @@ -45,6 +46,8 @@ |
b737a6ac JR |
83 | * printer. |
84 | * dnssdPackTxtRecord() - Pack an array of key/value pairs into the TXT | |
85 | * record format. | |
d07e62b1 ER |
86 | + * avahiPackTxtRecord() - Pack an array of key/value pairs into an |
87 | + * AvahiStringList. | |
b737a6ac JR |
88 | * dnssdRegisterCallback() - DNSServiceRegister callback. |
89 | * dnssdRegisterPrinter() - Start sending broadcast information for a | |
90 | * printer or update the broadcast contents. | |
d07e62b1 ER |
91 | @@ -83,6 +86,7 @@ |
92 | */ | |
93 | ||
94 | #include "cupsd.h" | |
95 | +#include <assert.h> | |
96 | #include <grp.h> | |
97 | ||
98 | #ifdef HAVE_DNSSD | |
99 | @@ -97,6 +101,17 @@ | |
100 | # endif /* HAVE_SYSTEMCONFIGURATION */ | |
101 | # endif /* __APPLE__ */ | |
102 | #endif /* HAVE_DNSSD */ | |
103 | +#ifdef HAVE_AVAHI | |
104 | +# include <avahi-common/domain.h> | |
105 | +#endif /* HAVE_AVAHI */ | |
106 | + | |
107 | + | |
108 | +#ifdef HAVE_DNSSD | |
109 | +typedef char *cupsd_txt_record_t; | |
110 | +#endif /* HAVE_DNSSD */ | |
111 | +#ifdef HAVE_AVAHI | |
112 | +typedef AvahiStringList *cupsd_txt_record_t; | |
113 | +#endif /* HAVE_AVAHI */ | |
114 | ||
115 | ||
116 | /* | |
b737a6ac | 117 | @@ -159,27 +174,39 @@ static void update_polling(void); |
d07e62b1 ER |
118 | static void update_smb(int onoff); |
119 | ||
120 | ||
121 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
122 | +static cupsd_txt_record_t dnssdBuildTxtRecord(int *txt_len, cupsd_printer_t *p, | |
123 | + int for_lpd); | |
124 | +static int dnssdComparePrinters(cupsd_printer_t *a, cupsd_printer_t *b); | |
125 | +static void dnssdDeregisterPrinter(cupsd_printer_t *p); | |
126 | +static void dnssdRegisterPrinter(cupsd_printer_t *p); | |
127 | +static void dnssdStop(void); | |
128 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
129 | + | |
130 | #ifdef HAVE_DNSSD | |
131 | # ifdef HAVE_COREFOUNDATION | |
132 | static void dnssdAddAlias(const void *key, const void *value, | |
133 | void *context); | |
134 | # endif /* HAVE_COREFOUNDATION */ | |
135 | -static char *dnssdBuildTxtRecord(int *txt_len, cupsd_printer_t *p, | |
136 | - int for_lpd); | |
b737a6ac | 137 | -static int dnssdComparePrinters(cupsd_printer_t *a, cupsd_printer_t *b); |
d07e62b1 ER |
138 | -static void dnssdDeregisterPrinter(cupsd_printer_t *p); |
139 | -static char *dnssdPackTxtRecord(int *txt_len, char *keyvalue[][2], | |
140 | - int count); | |
141 | static void dnssdRegisterCallback(DNSServiceRef sdRef, | |
142 | DNSServiceFlags flags, | |
143 | DNSServiceErrorType errorCode, | |
144 | const char *name, const char *regtype, | |
145 | const char *domain, void *context); | |
146 | -static void dnssdRegisterPrinter(cupsd_printer_t *p); | |
147 | -static void dnssdStop(void); | |
148 | static void dnssdUpdate(void); | |
149 | #endif /* HAVE_DNSSD */ | |
150 | ||
151 | +#ifdef HAVE_AVAHI | |
152 | +static AvahiStringList *avahiPackTxtRecord(char *keyvalue[][2], | |
153 | + int count); | |
154 | +static void avahi_entry_group_cb (AvahiEntryGroup *group, | |
155 | + AvahiEntryGroupState state, | |
156 | + void *userdata); | |
157 | +static void avahi_client_cb (AvahiClient *client, | |
158 | + AvahiClientState state, | |
159 | + void *userdata); | |
160 | +#endif /* HAVE_AVAHI */ | |
161 | + | |
b737a6ac JR |
162 | #ifdef HAVE_LDAP |
163 | static const char * const ldap_attrs[] =/* CUPS LDAP attributes */ | |
164 | { | |
d07e62b1 ER |
165 | @@ -283,10 +310,10 @@ cupsdDeregisterPrinter( |
166 | ldap_dereg_printer(p); | |
167 | #endif /* HAVE_LDAP */ | |
168 | ||
169 | -#ifdef HAVE_DNSSD | |
170 | - if (removeit && (BrowseLocalProtocols & BROWSE_DNSSD) && DNSSDRef) | |
171 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
172 | + if (removeit && (BrowseLocalProtocols & BROWSE_DNSSD)) | |
173 | dnssdDeregisterPrinter(p); | |
174 | -#endif /* HAVE_DNSSD */ | |
175 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
176 | } | |
177 | ||
178 | ||
179 | @@ -702,10 +729,10 @@ cupsdRegisterPrinter(cupsd_printer_t *p)/* I - Printer */ | |
180 | slpRegisterPrinter(p); */ | |
181 | #endif /* HAVE_LIBSLP */ | |
182 | ||
183 | -#ifdef HAVE_DNSSD | |
184 | - if ((BrowseLocalProtocols & BROWSE_DNSSD) && DNSSDRef) | |
185 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
186 | + if ((BrowseLocalProtocols & BROWSE_DNSSD)) | |
187 | dnssdRegisterPrinter(p); | |
188 | -#endif /* HAVE_DNSSD */ | |
189 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
190 | } | |
191 | ||
192 | ||
193 | @@ -1419,6 +1446,27 @@ ldap_disconnect(LDAP *ld) /* I - LDAP handle */ | |
194 | #endif /* HAVE_LDAP */ | |
195 | ||
196 | ||
197 | +#ifdef HAVE_AVAHI | |
198 | +/* | |
199 | + * 'cupsdStartAvahiClient()' - Start an Avahi client if needed | |
200 | + */ | |
201 | + | |
202 | +void | |
203 | +cupsdStartAvahiClient(void) | |
204 | +{ | |
205 | + if (!AvahiCupsClient && !AvahiCupsClientConnecting) | |
206 | + { | |
207 | + if (!AvahiCupsPollHandle) | |
208 | + AvahiCupsPollHandle = avahi_cups_poll_new (); | |
209 | + | |
210 | + if (AvahiCupsPollHandle) | |
211 | + avahi_client_new (avahi_cups_poll_get (AvahiCupsPollHandle), | |
212 | + AVAHI_CLIENT_NO_FAIL, avahi_client_cb, NULL, NULL); | |
213 | + } | |
214 | +} | |
215 | +#endif /* HAVE_AVAHI */ | |
216 | + | |
217 | + | |
218 | /* | |
219 | * 'cupsdStartBrowsing()' - Start sending and receiving broadcast information. | |
220 | */ | |
221 | @@ -1542,13 +1590,16 @@ cupsdStartBrowsing(void) | |
222 | else | |
223 | BrowseSocket = -1; | |
224 | ||
225 | -#ifdef HAVE_DNSSD | |
226 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
b737a6ac | 227 | if ((BrowseLocalProtocols | BrowseRemoteProtocols) & BROWSE_DNSSD) |
d07e62b1 ER |
228 | { |
229 | +#ifdef HAVE_DNSSD | |
230 | DNSServiceErrorType error; /* Error from service creation */ | |
231 | +#endif /* HAVE_DNSSD */ | |
232 | cupsd_listener_t *lis; /* Current listening socket */ | |
233 | ||
234 | ||
235 | +#ifdef HAVE_DNSSD | |
236 | /* | |
237 | * First create a "master" connection for all registrations... | |
238 | */ | |
239 | @@ -1573,6 +1624,7 @@ cupsdStartBrowsing(void) | |
240 | fcntl(fd, F_SETFD, fcntl(fd, F_GETFD) | FD_CLOEXEC); | |
241 | ||
242 | cupsdAddSelect(fd, (cupsd_selfunc_t)dnssdUpdate, NULL, NULL); | |
243 | +#endif /* HAVE_DNSSD */ | |
244 | ||
245 | /* | |
246 | * Then get the port we use for registrations. If we are not listening | |
247 | @@ -1606,9 +1658,16 @@ cupsdStartBrowsing(void) | |
248 | */ | |
249 | ||
250 | cupsdUpdateDNSSDName(); | |
251 | + | |
252 | +#ifdef HAVE_AVAHI | |
253 | + cupsdStartAvahiClient (); | |
254 | +#endif /* HAVE_AVAHI */ | |
255 | + | |
256 | +#ifdef HAVE_DNSSD | |
257 | } | |
258 | - } | |
259 | #endif /* HAVE_DNSSD */ | |
260 | + } | |
261 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
262 | ||
b737a6ac JR |
263 | #ifdef HAVE_LIBSLP |
264 | if ((BrowseLocalProtocols | BrowseRemoteProtocols) & BROWSE_SLP) | |
d07e62b1 ER |
265 | @@ -1834,10 +1893,10 @@ cupsdStopBrowsing(void) |
266 | BrowseSocket = -1; | |
267 | } | |
268 | ||
269 | -#ifdef HAVE_DNSSD | |
270 | - if ((BrowseLocalProtocols & BROWSE_DNSSD) && DNSSDRef) | |
271 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
272 | + if ((BrowseLocalProtocols & BROWSE_DNSSD)) | |
273 | dnssdStop(); | |
274 | -#endif /* HAVE_DNSSD */ | |
275 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
276 | ||
277 | #ifdef HAVE_LIBSLP | |
278 | if (((BrowseLocalProtocols | BrowseRemoteProtocols) & BROWSE_SLP) && | |
279 | @@ -1902,7 +1961,7 @@ cupsdStopPolling(void) | |
280 | } | |
281 | ||
282 | ||
283 | -#ifdef HAVE_DNSSD | |
284 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
285 | /* | |
286 | * 'cupsdUpdateDNSSDName()' - Update the computer name we use for browsing... | |
287 | */ | |
288 | @@ -1910,8 +1969,14 @@ cupsdStopPolling(void) | |
289 | void | |
290 | cupsdUpdateDNSSDName(void) | |
291 | { | |
292 | +#ifdef HAVE_DNSSD | |
293 | DNSServiceErrorType error; /* Error from service creation */ | |
294 | char webif[1024]; /* Web interface share name */ | |
295 | +#endif /* HAVE_DNSSD */ | |
296 | +#ifdef HAVE_AVAHI | |
297 | + int ret; /* Error from service creation */ | |
298 | + char webif[AVAHI_LABEL_MAX]; /* Web interface share name */ | |
299 | +#endif /* HAVE_AVAHI */ | |
300 | # ifdef HAVE_SYSTEMCONFIGURATION | |
301 | SCDynamicStoreRef sc; /* Context for dynamic store */ | |
302 | CFDictionaryRef btmm; /* Back-to-My-Mac domains */ | |
303 | @@ -2042,6 +2107,7 @@ cupsdUpdateDNSSDName(void) | |
304 | else | |
305 | strlcpy(webif, "CUPS Web Interface", sizeof(webif)); | |
306 | ||
307 | +#ifdef HAVE_DNSSD | |
308 | if (WebIFRef) | |
309 | DNSServiceRefDeallocate(WebIFRef); | |
310 | ||
311 | @@ -2054,9 +2120,45 @@ cupsdUpdateDNSSDName(void) | |
312 | NULL)) != kDNSServiceErr_NoError) | |
313 | cupsdLogMessage(CUPSD_LOG_ERROR, | |
314 | "DNS-SD web interface registration failed: %d", error); | |
315 | +#endif /* HAVE_DNSSD */ | |
316 | + | |
317 | +#ifdef HAVE_AVAHI | |
318 | + if (!AvahiCupsClient) | |
319 | + /* | |
320 | + * Client not yet running. | |
321 | + */ | |
322 | + return; | |
323 | + | |
324 | + if (AvahiWebIFGroup) | |
325 | + avahi_entry_group_reset (AvahiWebIFGroup); | |
326 | + else | |
327 | + AvahiWebIFGroup = avahi_entry_group_new (AvahiCupsClient, | |
328 | + avahi_entry_group_cb, | |
329 | + NULL); | |
330 | + | |
331 | + if (AvahiWebIFGroup) | |
332 | + { | |
333 | + ret = avahi_entry_group_add_service (AvahiWebIFGroup, | |
334 | + AVAHI_IF_UNSPEC, | |
335 | + AVAHI_PROTO_UNSPEC, | |
336 | + 0, /* flags */ | |
337 | + webif, /* name */ | |
338 | + "_http._tcp", /* type */ | |
339 | + NULL, /* domain */ | |
340 | + NULL, /* host */ | |
341 | + DNSSDPort, /* port */ | |
342 | + "path=/", NULL); | |
343 | + if (ret == 0) | |
344 | + ret = avahi_entry_group_commit (AvahiWebIFGroup); | |
345 | + | |
346 | + if (ret != 0) | |
347 | + cupsdLogMessage (CUPSD_LOG_ERROR, | |
348 | + "Avahi web interface registration failed: %d", ret); | |
349 | + } | |
350 | +#endif /* HAVE_AVAHI */ | |
351 | } | |
352 | } | |
353 | -#endif /* HAVE_DNSSD */ | |
354 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
355 | ||
356 | ||
357 | #ifdef HAVE_LDAP | |
358 | @@ -2334,13 +2436,15 @@ dnssdAddAlias(const void *key, /* I - Key */ | |
359 | "Bad Back to My Mac domain in dynamic store!"); | |
360 | } | |
361 | # endif /* HAVE_COREFOUNDATION */ | |
362 | +#endif /* HAVE_DNSSD */ | |
363 | ||
364 | ||
365 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
366 | /* | |
367 | * 'dnssdBuildTxtRecord()' - Build a TXT record from printer info. | |
368 | */ | |
369 | ||
370 | -static char * /* O - TXT record */ | |
371 | +static cupsd_txt_record_t /* O - TXT record */ | |
372 | dnssdBuildTxtRecord( | |
373 | int *txt_len, /* O - TXT record length */ | |
374 | cupsd_printer_t *p, /* I - Printer information */ | |
375 | @@ -2379,7 +2483,12 @@ dnssdBuildTxtRecord( | |
376 | keyvalue[i ][0] = "ty"; | |
377 | keyvalue[i++][1] = p->make_model ? p->make_model : "Unknown"; | |
378 | ||
379 | - snprintf(admin_hostname, sizeof(admin_hostname), "%s.local.", DNSSDHostName); | |
380 | + snprintf(admin_hostname, sizeof(admin_hostname), | |
381 | + "%s.local" | |
382 | +#ifdef HAVE_DNSSD | |
383 | + "." /* terminating dot no good for Avahi */ | |
384 | +#endif /* HAVE_DNSSD */ | |
385 | + , DNSSDHostName); | |
386 | httpAssembleURIf(HTTP_URI_CODING_ALL, adminurl_str, sizeof(adminurl_str), | |
387 | "http", NULL, admin_hostname, DNSSDPort, "/%s/%s", | |
388 | (p->type & CUPS_PRINTER_CLASS) ? "classes" : "printers", | |
389 | @@ -2462,7 +2571,12 @@ dnssdBuildTxtRecord( | |
390 | * Then pack them into a proper txt record... | |
391 | */ | |
392 | ||
393 | +#ifdef HAVE_DNSSD | |
394 | return (dnssdPackTxtRecord(txt_len, keyvalue, i)); | |
395 | +#endif /* HAVE_DNSSD */ | |
396 | +#ifdef HAVE_AVAHI | |
397 | + return (avahiPackTxtRecord(keyvalue, i)); | |
398 | +#endif /* HAVE_AVAHI */ | |
399 | } | |
400 | ||
401 | ||
b737a6ac JR |
402 | @@ -2474,7 +2588,16 @@ static int /* O - Result of comparison */ |
403 | dnssdComparePrinters(cupsd_printer_t *a,/* I - First printer */ | |
404 | cupsd_printer_t *b)/* I - Second printer */ | |
405 | { | |
406 | - return (_cups_strcasecmp(a->reg_name, b->reg_name)); | |
407 | + if (!a->reg_name) | |
408 | + if (!b->reg_name) | |
409 | + return 0; | |
410 | + else | |
411 | + return -1; | |
412 | + else | |
413 | + if (!b->reg_name) | |
414 | + return 1; | |
415 | + else | |
416 | + return (_cups_strcasecmp(a->reg_name, b->reg_name)); | |
417 | } | |
418 | ||
419 | ||
d07e62b1 ER |
420 | @@ -2489,6 +2612,10 @@ dnssdDeregisterPrinter( |
421 | { | |
422 | cupsdLogMessage(CUPSD_LOG_DEBUG2, "dnssdDeregisterPrinter(%s)", p->name); | |
423 | ||
424 | +#ifdef HAVE_DNSSD | |
425 | + if (!DNSSDRef) | |
426 | + return; | |
427 | + | |
428 | /* | |
429 | * Closing the socket deregisters the service | |
430 | */ | |
431 | @@ -2524,6 +2651,24 @@ dnssdDeregisterPrinter( | |
432 | free(p->printer_txt); | |
433 | p->printer_txt = NULL; | |
434 | } | |
435 | +#endif /* HAVE_DNSSD */ | |
436 | + | |
437 | +#ifdef HAVE_AVAHI | |
438 | + if (p->avahi_group) | |
439 | + { | |
440 | + avahi_entry_group_reset (p->avahi_group); | |
441 | + avahi_entry_group_free (p->avahi_group); | |
442 | + p->avahi_group = NULL; | |
443 | + | |
444 | + if (p->ipp_txt) | |
445 | + avahi_string_list_free (p->ipp_txt); | |
446 | + | |
447 | + if (p->printer_txt) | |
448 | + avahi_string_list_free (p->printer_txt); | |
449 | + | |
450 | + p->ipp_txt = p->printer_txt = NULL; | |
451 | + } | |
452 | +#endif /* HAVE_AVAHI */ | |
453 | ||
454 | /* | |
455 | * Remove the printer from the array of DNS-SD printers, then clear the | |
456 | @@ -2533,8 +2678,10 @@ dnssdDeregisterPrinter( | |
457 | cupsArrayRemove(DNSSDPrinters, p); | |
458 | cupsdClearString(&p->reg_name); | |
459 | } | |
460 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
461 | ||
462 | ||
463 | +#ifdef HAVE_DNSSD | |
464 | /* | |
465 | * 'dnssdPackTxtRecord()' - Pack an array of key/value pairs into the | |
466 | * TXT record format. | |
467 | @@ -2644,8 +2791,10 @@ dnssdRegisterCallback( | |
468 | LastEvent |= CUPSD_EVENT_PRINTER_MODIFIED; | |
469 | } | |
470 | } | |
471 | +#endif /* HAVE_DNSSD */ | |
472 | ||
473 | ||
474 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
475 | /* | |
476 | * 'dnssdRegisterPrinter()' - Start sending broadcast information for a printer | |
477 | * or update the broadcast contents. | |
478 | @@ -2654,20 +2803,40 @@ dnssdRegisterCallback( | |
479 | static void | |
480 | dnssdRegisterPrinter(cupsd_printer_t *p)/* I - Printer */ | |
481 | { | |
482 | +#ifdef HAVE_DNSSD | |
483 | DNSServiceErrorType se; /* dnssd errors */ | |
484 | char *ipp_txt, /* IPP TXT record buffer */ | |
485 | *printer_txt, /* LPD TXT record buffer */ | |
486 | - name[1024], /* Service name */ | |
487 | - *nameptr; /* Pointer into name */ | |
488 | + name[1024]; /* Service name */ | |
489 | int ipp_len, /* IPP TXT record length */ | |
490 | printer_len, /* LPD TXT record length */ | |
491 | printer_port; /* LPD port number */ | |
492 | +#endif /* HAVE_DNSSD */ | |
493 | +#ifdef HAVE_AVAHI | |
494 | + int ret; /* Error code */ | |
495 | + AvahiStringList *ipp_txt, /* IPP TXT record */ | |
496 | + *printer_txt; /* LPD TXT record */ | |
497 | + char name[AVAHI_LABEL_MAX], /* Service name */ | |
498 | + fullsubtype[AVAHI_LABEL_MAX]; /* Full subtype */ | |
499 | + char *regtype_copy, /* Writeable copy of reg type */ | |
500 | + *subtype, /* Current service sub type */ | |
501 | + *nextsubtype; /* Next service sub type */ | |
502 | +#endif /* HAVE_AVAHI */ | |
503 | + char *nameptr; /* Pointer into name */ | |
504 | const char *regtype; /* Registration type */ | |
505 | ||
506 | ||
507 | +#ifdef HAVE_DNSSD | |
508 | + if (!DNSSDRef) | |
509 | + return; | |
510 | + | |
511 | cupsdLogMessage(CUPSD_LOG_DEBUG2, "dnssdRegisterPrinter(%s) %s", p->name, | |
512 | !p->ipp_ref ? "new" : "update"); | |
513 | - | |
514 | +#endif /* HAVE_DNSSD */ | |
515 | +#ifdef HAVE_AVAHI | |
516 | + cupsdLogMessage(CUPSD_LOG_DEBUG2, "dnssdRegisterPrinter(%s) %s", p->name, | |
517 | + !p->avahi_group ? "new" : "update"); | |
518 | +#endif /* HAVE_AVAHI */ | |
519 | /* | |
520 | * If per-printer sharing was just disabled make sure we're not | |
521 | * registered before returning. | |
522 | @@ -2686,12 +2855,36 @@ dnssdRegisterPrinter(cupsd_printer_t *p)/* I - Printer */ | |
523 | if (p->info && strlen(p->info) > 0) | |
524 | { | |
525 | if (DNSSDComputerName) | |
526 | - snprintf(name, sizeof(name), "%s @ %s", p->info, DNSSDComputerName); | |
527 | + { | |
528 | + /* | |
529 | + * Make sure there is room for at least 15 characters of | |
530 | + * DNSSDComputerName. | |
531 | + */ | |
532 | + | |
533 | + assert(sizeof(name) >= 15 + 4); | |
534 | + nameptr = name + strlcpy(name, p->info, | |
535 | + sizeof(name) - 4 - | |
536 | + strnlen(DNSSDComputerName, 15)); | |
537 | + nameptr += strlcpy(nameptr, " @ ", sizeof(name) - (nameptr - name)); | |
538 | + strlcpy(nameptr, DNSSDComputerName, sizeof(name) - (nameptr - name)); | |
539 | + } | |
540 | else | |
541 | strlcpy(name, p->info, sizeof(name)); | |
542 | } | |
543 | else if (DNSSDComputerName) | |
544 | - snprintf(name, sizeof(name), "%s @ %s", p->name, DNSSDComputerName); | |
545 | + { | |
546 | + /* | |
547 | + * Make sure there is room for at least 15 characters of | |
548 | + * DNSSDComputerName. | |
549 | + */ | |
550 | + | |
551 | + assert(sizeof(name) >= 15 + 4); | |
552 | + nameptr = name + strlcpy(name, p->info, | |
553 | + sizeof(name) - 4 - | |
554 | + strnlen(DNSSDComputerName, 15)); | |
555 | + nameptr += strlcpy(nameptr, " @ ", sizeof(name) - (nameptr - name)); | |
556 | + strlcpy(nameptr, DNSSDComputerName, sizeof(name) - (nameptr - name)); | |
557 | + } | |
558 | else | |
559 | strlcpy(name, p->name, sizeof(name)); | |
560 | ||
561 | @@ -2712,6 +2905,7 @@ dnssdRegisterPrinter(cupsd_printer_t *p)/* I - Printer */ | |
562 | * Register IPP and (optionally) LPD... | |
563 | */ | |
564 | ||
565 | +#ifdef HAVE_DNSSD | |
566 | ipp_len = 0; /* anti-compiler-warning-code */ | |
567 | ipp_txt = dnssdBuildTxtRecord(&ipp_len, p, 0); | |
568 | ||
569 | @@ -2884,6 +3078,209 @@ dnssdRegisterPrinter(cupsd_printer_t *p)/* I - Printer */ | |
570 | ||
571 | if (printer_txt) | |
572 | free(printer_txt); | |
573 | +#endif /* HAVE_DNSSD */ | |
574 | +#ifdef HAVE_AVAHI | |
575 | + if (!AvahiCupsClient) | |
576 | + /* | |
577 | + * Client not running yet. The client callback will call us again later. | |
578 | + */ | |
579 | + return; | |
580 | + | |
581 | + ipp_txt = dnssdBuildTxtRecord(NULL, p, 0); | |
582 | + printer_txt = dnssdBuildTxtRecord(NULL, p, 1); | |
583 | + regtype = (p->type & CUPS_PRINTER_FAX) ? "_fax-ipp._tcp" : DNSSDRegType; | |
584 | + | |
585 | + if (p->avahi_group && p->ipp_txt && ipp_txt && | |
586 | + !avahi_string_list_equal (p->ipp_txt, ipp_txt)) | |
587 | + { | |
588 | + /* | |
589 | + * Update the existing registration... | |
590 | + */ | |
591 | + | |
592 | + avahi_string_list_free (p->ipp_txt); | |
593 | + | |
594 | + if (p->printer_txt) | |
595 | + avahi_string_list_free (p->printer_txt); | |
596 | + | |
597 | + /* | |
598 | + * Update the service group entry. | |
599 | + */ | |
600 | + | |
601 | + regtype_copy = strdup (regtype); | |
602 | + subtype = strchr (regtype_copy, ','); | |
603 | + if (subtype) | |
604 | + *subtype = '\0'; | |
605 | + | |
606 | + cupsdLogMessage (CUPSD_LOG_DEBUG, | |
607 | + "Updating TXT record for %s (%s)", name, regtype_copy); | |
608 | + ret = avahi_entry_group_update_service_txt_strlst (p->avahi_group, | |
609 | + AVAHI_IF_UNSPEC, | |
610 | + AVAHI_PROTO_UNSPEC, | |
611 | + 0, name, | |
612 | + regtype_copy, | |
613 | + NULL, ipp_txt); | |
614 | + free (regtype_copy); | |
615 | + | |
616 | + if (ret < 0) | |
617 | + goto update_failed; | |
618 | + | |
619 | + p->ipp_txt = ipp_txt; | |
620 | + ipp_txt = NULL; | |
621 | + | |
622 | + if (BrowseLocalProtocols & BROWSE_LPD) | |
623 | + { | |
624 | + ret = avahi_entry_group_update_service_txt_strlst (p->avahi_group, | |
625 | + AVAHI_IF_UNSPEC, | |
626 | + AVAHI_PROTO_UNSPEC, | |
627 | + 0, name, | |
628 | + "_printer._tcp", NULL, | |
629 | + printer_txt); | |
630 | + if (ret < 0) | |
631 | + goto update_failed; | |
632 | + | |
633 | + p->printer_txt = printer_txt; | |
634 | + printer_txt = NULL; | |
635 | + } | |
636 | + | |
637 | + ret = avahi_entry_group_commit (p->avahi_group); | |
638 | + if (ret < 0) | |
639 | + { | |
640 | + update_failed: | |
641 | + cupsdLogMessage (CUPSD_LOG_ERROR, | |
642 | + "Failed to update TXT record for %s: %d", | |
643 | + name, ret); | |
644 | + avahi_entry_group_reset (p->avahi_group); | |
645 | + avahi_entry_group_free (p->avahi_group); | |
646 | + p->avahi_group = NULL; | |
647 | + ipp_txt = p->ipp_txt; | |
648 | + p->ipp_txt = NULL; | |
649 | + } | |
650 | + } | |
651 | + | |
652 | + if (!p->avahi_group) | |
653 | + { | |
654 | + /* | |
655 | + * Initial registration. Use the _fax subtype for fax queues... | |
656 | + */ | |
657 | + | |
658 | + p->avahi_group = avahi_entry_group_new (AvahiCupsClient, | |
659 | + avahi_entry_group_cb, | |
660 | + p); | |
661 | + | |
662 | + cupsdLogMessage(CUPSD_LOG_DEBUG, | |
663 | + "Registering Avahi printer %s with name \"%s\" and " | |
664 | + "type \"%s\"", p->name, name, regtype); | |
665 | + | |
666 | + if (!p->avahi_group) | |
667 | + { | |
668 | + ret = 0; | |
669 | + goto add_failed; | |
670 | + } | |
671 | + | |
672 | + /* | |
673 | + * Add each service type (DNSSDRegType may contain several, | |
674 | + * separated by commas). | |
675 | + */ | |
676 | + | |
677 | + subtype = regtype_copy = strdup (regtype); | |
678 | + while (subtype && *subtype) | |
679 | + { | |
680 | + nextsubtype = strchr (subtype, ','); | |
681 | + if (nextsubtype) | |
682 | + *nextsubtype++ = '\0'; | |
683 | + | |
684 | + if (subtype == regtype_copy) | |
685 | + { | |
686 | + /* | |
687 | + * Main type entry. | |
688 | + */ | |
689 | + | |
690 | + cupsdLogMessage (CUPSD_LOG_DEBUG, | |
691 | + "Adding TXT record for %s (%s)", name, regtype_copy); | |
692 | + ret = avahi_entry_group_add_service_strlst (p->avahi_group, | |
693 | + AVAHI_IF_UNSPEC, | |
694 | + AVAHI_PROTO_UNSPEC, | |
695 | + 0, name, regtype_copy, | |
696 | + NULL, NULL, | |
697 | + DNSSDPort, | |
698 | + ipp_txt); | |
699 | + } | |
700 | + else | |
701 | + { | |
702 | + /* | |
703 | + * Sub-type entry. | |
704 | + */ | |
705 | + | |
706 | + snprintf (fullsubtype, sizeof(fullsubtype), | |
707 | + "%s._sub.%s", subtype, regtype_copy); | |
708 | + cupsdLogMessage (CUPSD_LOG_DEBUG, | |
709 | + "Adding TXT record for %s (%s)", name, fullsubtype); | |
710 | + ret = avahi_entry_group_add_service_subtype (p->avahi_group, | |
711 | + AVAHI_IF_UNSPEC, | |
712 | + AVAHI_PROTO_UNSPEC, | |
713 | + 0, name, | |
714 | + regtype_copy, | |
715 | + NULL, fullsubtype); | |
716 | + } | |
717 | + | |
718 | + if (ret < 0) | |
719 | + { | |
720 | + free (regtype_copy); | |
721 | + goto add_failed; | |
722 | + } | |
723 | + | |
724 | + subtype = nextsubtype; | |
725 | + } | |
726 | + | |
727 | + free (regtype_copy); | |
728 | + p->ipp_txt = ipp_txt; | |
729 | + ipp_txt = NULL; | |
730 | + | |
731 | + if (BrowseLocalProtocols & BROWSE_LPD) | |
732 | + { | |
733 | + cupsdLogMessage(CUPSD_LOG_DEBUG, | |
734 | + "Registering Avahi printer %s with name \"%s\" and " | |
735 | + "type \"_printer._tcp\"", p->name, name); | |
736 | + | |
737 | + ret = avahi_entry_group_add_service_strlst (p->avahi_group, | |
738 | + AVAHI_IF_UNSPEC, | |
739 | + AVAHI_PROTO_UNSPEC, | |
740 | + 0, name, | |
741 | + "_printer._tcp", NULL, NULL, | |
742 | + 515, | |
743 | + printer_txt); | |
744 | + if (ret < 0) | |
745 | + goto add_failed; | |
746 | + | |
747 | + p->printer_txt = printer_txt; | |
748 | + printer_txt = NULL; | |
749 | + } | |
750 | + | |
751 | + ret = avahi_entry_group_commit (p->avahi_group); | |
752 | + | |
753 | + if (ret < 0) | |
754 | + { | |
755 | + add_failed: | |
756 | + cupsdLogMessage (CUPSD_LOG_ERROR, | |
757 | + "Failed to add Avahi entry for %s: %d", | |
758 | + name, ret); | |
759 | + if (p->avahi_group) | |
760 | + { | |
761 | + avahi_entry_group_reset (p->avahi_group); | |
762 | + avahi_entry_group_free (p->avahi_group); | |
763 | + p->avahi_group = NULL; | |
764 | + } | |
765 | + ipp_txt = p->ipp_txt; | |
766 | + p->ipp_txt = NULL; | |
767 | + } | |
768 | + } | |
769 | + | |
770 | + if (ipp_txt) | |
771 | + avahi_string_list_free (ipp_txt); | |
772 | + | |
773 | + if (printer_txt) | |
774 | + avahi_string_list_free (printer_txt); | |
775 | +#endif /* HAVE_AVAHI */ | |
776 | } | |
777 | ||
778 | ||
779 | @@ -2896,6 +3293,10 @@ dnssdStop(void) | |
780 | { | |
781 | cupsd_printer_t *p; /* Current printer */ | |
782 | ||
783 | +#ifdef HAVE_DNSSD | |
784 | + if (!DNSSDRef) | |
785 | + return; | |
786 | +#endif /* HAVE_DNSSD */ | |
787 | ||
788 | /* | |
789 | * De-register the individual printers | |
790 | @@ -2906,6 +3307,7 @@ dnssdStop(void) | |
791 | p = (cupsd_printer_t *)cupsArrayNext(Printers)) | |
792 | dnssdDeregisterPrinter(p); | |
793 | ||
794 | +#ifdef HAVE_DNSSD | |
795 | /* | |
796 | * Shutdown the rest of the service refs... | |
797 | */ | |
798 | @@ -2926,14 +3328,17 @@ dnssdStop(void) | |
799 | ||
800 | DNSServiceRefDeallocate(DNSSDRef); | |
801 | DNSSDRef = NULL; | |
802 | +#endif /* HAVE_DNSSD */ | |
803 | ||
804 | cupsArrayDelete(DNSSDPrinters); | |
805 | DNSSDPrinters = NULL; | |
806 | ||
807 | DNSSDPort = 0; | |
808 | } | |
809 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
810 | ||
811 | ||
812 | +#ifdef HAVE_DNSSD | |
813 | /* | |
814 | * 'dnssdUpdate()' - Handle DNS-SD queries. | |
815 | */ | |
816 | @@ -2955,6 +3360,147 @@ dnssdUpdate(void) | |
817 | #endif /* HAVE_DNSSD */ | |
818 | ||
819 | ||
820 | +#ifdef HAVE_AVAHI | |
821 | +/* | |
822 | + * 'avahiPackTxtRecord()' - Pack an array of key/value pairs into an | |
823 | + * AvahiStringList. | |
824 | + */ | |
825 | + | |
826 | +static AvahiStringList * /* O - new string list */ | |
827 | +avahiPackTxtRecord(char *keyvalue[][2], /* I - Table of key value pairs */ | |
828 | + int count) /* I - Number of items in table */ | |
829 | +{ | |
830 | + AvahiStringList *strlst = NULL; | |
831 | + char **elements; | |
832 | + size_t len; | |
833 | + int i = 0; | |
834 | + | |
835 | + elements = malloc ((1 + count) * sizeof (char *)); | |
836 | + if (!elements) | |
837 | + goto cleanup; | |
838 | + | |
839 | + for (i = 0; i < count; i++) | |
840 | + { | |
841 | + len = (1 + strlen (keyvalue[i][0]) + | |
842 | + (keyvalue[i][1] ? 1 + strlen (keyvalue[i][1]) : 1)); | |
843 | + elements[i] = malloc (len * sizeof (char)); | |
844 | + if (!elements[i]) | |
845 | + goto cleanup; | |
846 | + | |
847 | + snprintf (elements[i], len, "%s=%s", keyvalue[i][0], keyvalue[i][1]); | |
848 | + } | |
849 | + | |
850 | + strlst = avahi_string_list_new_from_array ((const char **) elements, count); | |
851 | + | |
852 | +cleanup: | |
853 | + while (--i >= 0) | |
854 | + free (elements[i]); | |
855 | + | |
856 | + free (elements); | |
857 | + return (strlst); | |
858 | +} | |
859 | + | |
860 | + | |
861 | +/* | |
862 | + * 'avahi_entry_group_cb()' - Avahi entry group callback function. | |
863 | + */ | |
864 | +static void | |
865 | +avahi_entry_group_cb (AvahiEntryGroup *group, | |
866 | + AvahiEntryGroupState state, | |
867 | + void *userdata) | |
868 | +{ | |
869 | + char *name; | |
870 | + | |
871 | + if (userdata) | |
872 | + name = ((cupsd_printer_t *) userdata)->reg_name; | |
873 | + else | |
874 | + name = "CUPS web interface"; | |
875 | + | |
876 | + switch (state) | |
877 | + { | |
878 | + case AVAHI_ENTRY_GROUP_UNCOMMITED: | |
879 | + case AVAHI_ENTRY_GROUP_REGISTERING: | |
880 | + break; | |
881 | + | |
882 | + case AVAHI_ENTRY_GROUP_ESTABLISHED: | |
883 | + cupsdLogMessage (CUPSD_LOG_DEBUG, | |
884 | + "Avahi entry group established for %s", name); | |
885 | + break; | |
886 | + | |
887 | + default: | |
888 | + cupsdLogMessage (CUPSD_LOG_DEBUG, | |
889 | + "Avahi entry group %s has state %d", | |
890 | + name, state); | |
891 | + break; | |
892 | + } | |
893 | +} | |
894 | + | |
895 | + | |
896 | +/* | |
897 | + * 'avahi_client_cb()' - Avahi client callback function. | |
898 | + */ | |
899 | +static void | |
900 | +avahi_client_cb (AvahiClient *client, | |
901 | + AvahiClientState state, | |
902 | + void *userdata) | |
903 | +{ | |
904 | + cupsd_printer_t *printer; | |
905 | + switch (state) | |
906 | + { | |
907 | + case AVAHI_CLIENT_S_RUNNING: | |
908 | + /* | |
909 | + * Avahi client started successfully. | |
910 | + */ | |
911 | + AvahiCupsClient = client; | |
912 | + AvahiCupsClientConnecting = 0; | |
913 | + cupsdLogMessage (CUPSD_LOG_DEBUG, "Avahi client started"); | |
914 | + | |
915 | + cupsdUpdateDNSSDName (); | |
916 | + | |
917 | + for (printer = (cupsd_printer_t *)cupsArrayFirst(Printers); | |
918 | + printer; | |
919 | + printer = (cupsd_printer_t *)cupsArrayNext(Printers)) | |
920 | + if (Browsing && (BrowseLocalProtocols & BROWSE_DNSSD) && | |
921 | + (!(printer->type & (CUPS_PRINTER_REMOTE | CUPS_PRINTER_IMPLICIT | | |
922 | + CUPS_PRINTER_SCANNER))) && printer->shared) | |
923 | + dnssdRegisterPrinter (printer); | |
924 | + | |
925 | + break; | |
926 | + | |
927 | + case AVAHI_CLIENT_CONNECTING: | |
928 | + /* | |
929 | + * No Avahi daemon, client is waiting. | |
930 | + */ | |
931 | + AvahiCupsClientConnecting = 1; | |
932 | + cupsdLogMessage (CUPSD_LOG_DEBUG, "Avahi client connecting"); | |
933 | + break; | |
934 | + | |
935 | + case AVAHI_CLIENT_FAILURE: | |
936 | + /* | |
937 | + * Avahi client failed, close it to allow a clean restart. | |
938 | + */ | |
939 | + cupsdLogMessage (CUPSD_LOG_ERROR, | |
940 | + "Avahi client failed, " | |
941 | + "closing client to allow a clean restart"); | |
942 | + | |
943 | + for (printer = (cupsd_printer_t *)cupsArrayFirst(Printers); | |
944 | + printer; | |
945 | + printer = (cupsd_printer_t *)cupsArrayNext(Printers)) | |
946 | + dnssdDeregisterPrinter (printer); | |
947 | + | |
948 | + avahi_client_free(client); | |
949 | + AvahiCupsClientConnecting = 0; | |
950 | + AvahiCupsClient = NULL; | |
951 | + | |
952 | + break; | |
953 | + | |
954 | + default: | |
955 | + cupsdLogMessage (CUPSD_LOG_DEBUG, "Avahi client state: %d", state); | |
956 | + } | |
957 | +} | |
958 | +#endif /* HAVE_AVAHI */ | |
959 | + | |
960 | + | |
961 | /* | |
962 | * 'get_auth_info_required()' - Get the auth-info-required value to advertise. | |
963 | */ | |
964 | diff --git a/scheduler/dirsvc.h b/scheduler/dirsvc.h | |
965 | index 99079bd..d53a179 100644 | |
966 | --- a/scheduler/dirsvc.h | |
967 | +++ b/scheduler/dirsvc.h | |
968 | @@ -31,6 +31,10 @@ | |
b737a6ac JR |
969 | # endif /* HAVE_LDAP_SSL_H */ |
970 | #endif /* HAVE_LDAP */ | |
d07e62b1 ER |
971 | |
972 | +#ifdef HAVE_AVAHI | |
973 | +# include <avahi-client/publish.h> | |
974 | +#endif /* HAVE_AVAHI */ | |
975 | + | |
976 | /* | |
977 | * Browse protocols... | |
978 | */ | |
979 | @@ -131,19 +135,22 @@ VAR int PollPipe VALUE(0); | |
b737a6ac JR |
980 | VAR cupsd_statbuf_t *PollStatusBuffer VALUE(NULL); |
981 | /* Status buffer for pollers */ | |
982 | ||
d07e62b1 ER |
983 | -#ifdef HAVE_DNSSD |
984 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
985 | VAR char *DNSSDComputerName VALUE(NULL), | |
986 | /* Computer/server name */ | |
987 | *DNSSDHostName VALUE(NULL), | |
988 | /* Hostname */ | |
989 | *DNSSDRegType VALUE(NULL); | |
990 | /* Bonjour registration type */ | |
991 | -VAR cups_array_t *DNSSDAlias VALUE(NULL); | |
992 | - /* List of dynamic ServerAlias's */ | |
993 | VAR int DNSSDPort VALUE(0); | |
994 | /* Port number to register */ | |
995 | VAR cups_array_t *DNSSDPrinters VALUE(NULL); | |
996 | /* Printers we have registered */ | |
997 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
998 | + | |
999 | +#ifdef HAVE_DNSSD | |
1000 | +VAR cups_array_t *DNSSDAlias VALUE(NULL); | |
1001 | + /* List of dynamic ServerAlias's */ | |
1002 | VAR DNSServiceRef DNSSDRef VALUE(NULL), | |
1003 | /* Master DNS-SD service reference */ | |
b737a6ac | 1004 | WebIFRef VALUE(NULL), |
d07e62b1 ER |
1005 | @@ -152,6 +159,17 @@ VAR DNSServiceRef DNSSDRef VALUE(NULL), |
1006 | /* Remote printer browse reference */ | |
1007 | #endif /* HAVE_DNSSD */ | |
1008 | ||
1009 | +#ifdef HAVE_AVAHI | |
1010 | +VAR AvahiCupsPoll *AvahiCupsPollHandle VALUE(NULL); | |
1011 | + /* AvahiCupsPoll object */ | |
1012 | +VAR AvahiClient *AvahiCupsClient VALUE(NULL); | |
1013 | + /* AvahiClient object */ | |
1014 | +VAR int AvahiCupsClientConnecting VALUE(0); | |
1015 | + /* Is AvahiClient object connecting? */ | |
1016 | +VAR AvahiEntryGroup *AvahiWebIFGroup VALUE(NULL); | |
1017 | + /* Web interface entry group */ | |
1018 | +#endif /* HAVE_AVAHI */ | |
1019 | + | |
b737a6ac JR |
1020 | #ifdef HAVE_LIBSLP |
1021 | VAR SLPHandle BrowseSLPHandle VALUE(NULL); | |
1022 | /* SLP API handle */ | |
1023 | @@ -195,13 +213,14 @@ extern void cupsdRegisterPrinter(cupsd_printer_t *p); | |
1024 | extern void cupsdRestartPolling(void); | |
1025 | extern void cupsdSaveRemoteCache(void); | |
1026 | extern void cupsdSendBrowseList(void); | |
d07e62b1 ER |
1027 | +extern void cupsdStartAvahiClient(void); |
1028 | extern void cupsdStartBrowsing(void); | |
b737a6ac | 1029 | extern void cupsdStartPolling(void); |
d07e62b1 | 1030 | extern void cupsdStopBrowsing(void); |
b737a6ac | 1031 | extern void cupsdStopPolling(void); |
d07e62b1 ER |
1032 | -#ifdef HAVE_DNSSD |
1033 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
1034 | extern void cupsdUpdateDNSSDName(void); | |
1035 | -#endif /* HAVE_DNSSD */ | |
1036 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
b737a6ac JR |
1037 | #ifdef HAVE_LDAP |
1038 | extern void cupsdUpdateLDAPBrowse(void); | |
1039 | #endif /* HAVE_LDAP */ | |
d07e62b1 ER |
1040 | diff --git a/scheduler/ipp.c b/scheduler/ipp.c |
1041 | index a048baa..9a3ab11 100644 | |
1042 | --- a/scheduler/ipp.c | |
1043 | +++ b/scheduler/ipp.c | |
1044 | @@ -6087,7 +6087,7 @@ copy_printer_attrs( | |
1045 | ippAddDate(con->response, IPP_TAG_PRINTER, "printer-current-time", | |
1046 | ippTimeToDate(curtime)); | |
1047 | ||
1048 | -#ifdef HAVE_DNSSD | |
1049 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
1050 | if (!ra || cupsArrayFind(ra, "printer-dns-sd-name")) | |
1051 | { | |
1052 | if (printer->reg_name) | |
1053 | @@ -6097,7 +6097,7 @@ copy_printer_attrs( | |
1054 | ippAddInteger(con->response, IPP_TAG_PRINTER, IPP_TAG_NOVALUE, | |
1055 | "printer-dns-sd-name", 0); | |
1056 | } | |
1057 | -#endif /* HAVE_DNSSD */ | |
1058 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
1059 | ||
1060 | if (!ra || cupsArrayFind(ra, "printer-error-policy")) | |
1061 | ippAddString(con->response, IPP_TAG_PRINTER, IPP_TAG_NAME, | |
1062 | diff --git a/scheduler/main.c b/scheduler/main.c | |
1063 | index 1e60572..6c210e6 100644 | |
1064 | --- a/scheduler/main.c | |
1065 | +++ b/scheduler/main.c | |
1066 | @@ -120,6 +120,10 @@ main(int argc, /* I - Number of command-line args */ | |
1067 | cupsd_listener_t *lis; /* Current listener */ | |
1068 | time_t current_time, /* Current time */ | |
1069 | activity, /* Client activity timer */ | |
1070 | +#ifdef HAVE_AVAHI | |
1071 | + avahi_client_time, /* Time for next Avahi client | |
1072 | + check */ | |
1073 | +#endif /* HAVE_AVAHI */ | |
b737a6ac | 1074 | browse_time, /* Next browse send time */ |
d07e62b1 ER |
1075 | senddoc_time, /* Send-Document time */ |
1076 | expire_time, /* Subscription expire time */ | |
1077 | @@ -662,6 +666,9 @@ main(int argc, /* I - Number of command-line args */ | |
1078 | */ | |
1079 | ||
1080 | current_time = time(NULL); | |
1081 | +#ifdef HAVE_AVAHI | |
1082 | + avahi_client_time = current_time; | |
1083 | +#endif /* HAVE_AVAHI */ | |
b737a6ac | 1084 | browse_time = current_time; |
d07e62b1 ER |
1085 | event_time = current_time; |
1086 | expire_time = current_time; | |
1087 | @@ -884,6 +891,16 @@ main(int argc, /* I - Number of command-line args */ | |
1088 | tmo = cupsdNextTimeout (&tmo_delay); | |
1089 | if (tmo && tmo_delay == 0) | |
1090 | cupsdRunTimeout (tmo); | |
1091 | + | |
1092 | + /* | |
1093 | + * Try to restart the Avahi client every 10 seconds if needed... | |
1094 | + */ | |
1095 | + | |
1096 | + if ((current_time - avahi_client_time) >= 10) | |
1097 | + { | |
1098 | + avahi_client_time = current_time; | |
1099 | + cupsdStartAvahiClient(); | |
1100 | + } | |
1101 | #endif /* HAVE_AVAHI */ | |
1102 | ||
1103 | #ifndef __APPLE__ | |
1104 | diff --git a/scheduler/printers.c b/scheduler/printers.c | |
1105 | index 4686c4c..fac7bbc 100644 | |
1106 | --- a/scheduler/printers.c | |
1107 | +++ b/scheduler/printers.c | |
1108 | @@ -883,9 +883,9 @@ cupsdDeletePrinter( | |
1109 | cupsdClearString(&p->alert); | |
1110 | cupsdClearString(&p->alert_description); | |
1111 | ||
1112 | -#ifdef HAVE_DNSSD | |
1113 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
1114 | cupsdClearString(&p->pdl); | |
1115 | -#endif /* HAVE_DNSSD */ | |
1116 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
1117 | ||
1118 | cupsArrayDelete(p->filetypes); | |
1119 | ||
1120 | @@ -3765,7 +3765,7 @@ add_printer_formats(cupsd_printer_t *p) /* I - Printer */ | |
1121 | attr->values[i].string.text = _cupsStrAlloc(mimetype); | |
1122 | } | |
1123 | ||
1124 | -#ifdef HAVE_DNSSD | |
1125 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
1126 | { | |
1127 | char pdl[1024]; /* Buffer to build pdl list */ | |
1128 | mime_filter_t *filter; /* MIME filter looping var */ | |
1129 | @@ -3821,7 +3821,7 @@ add_printer_formats(cupsd_printer_t *p) /* I - Printer */ | |
1130 | ||
1131 | cupsdSetString(&p->pdl, pdl); | |
1132 | } | |
1133 | -#endif /* HAVE_DNSSD */ | |
1134 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
1135 | } | |
1136 | ||
1137 | ||
1138 | diff --git a/scheduler/printers.h b/scheduler/printers.h | |
1139 | index 1751578..fb04651 100644 | |
1140 | --- a/scheduler/printers.h | |
1141 | +++ b/scheduler/printers.h | |
1142 | @@ -16,6 +16,9 @@ | |
1143 | #ifdef HAVE_DNSSD | |
1144 | # include <dns_sd.h> | |
1145 | #endif /* HAVE_DNSSD */ | |
1146 | +#ifdef HAVE_AVAHI | |
1147 | +# include "avahi.h" | |
1148 | +#endif /* HAVE_AVAHI */ | |
1149 | #include <cups/pwg-private.h> | |
1150 | ||
1151 | ||
1152 | @@ -95,16 +98,23 @@ struct cupsd_printer_s | |
1153 | time_t marker_time; /* Last time marker attributes were updated */ | |
1154 | _ppd_cache_t *pc; /* PPD cache and mapping data */ | |
1155 | ||
1156 | -#ifdef HAVE_DNSSD | |
1157 | +#if defined(HAVE_DNSSD) || defined(HAVE_AVAHI) | |
1158 | char *reg_name, /* Name used for service registration */ | |
1159 | - *pdl, /* pdl value for TXT record */ | |
1160 | - *ipp_txt, /* IPP TXT record contents */ | |
1161 | + *pdl; /* pdl value for TXT record */ | |
1162 | +#endif /* defined(HAVE_DNSSD) || defined(HAVE_AVAHI) */ | |
1163 | +#ifdef HAVE_DNSSD | |
1164 | + char *ipp_txt, /* IPP TXT record contents */ | |
1165 | *printer_txt; /* LPD TXT record contents */ | |
1166 | int ipp_len, /* IPP TXT record length */ | |
1167 | printer_len; /* LPD TXT record length */ | |
1168 | DNSServiceRef ipp_ref, /* Reference for _ipp._tcp,_cups */ | |
1169 | printer_ref; /* Reference for _printer._tcp */ | |
1170 | #endif /* HAVE_DNSSD */ | |
1171 | +#ifdef HAVE_AVAHI | |
1172 | + AvahiStringList *ipp_txt, /* IPP TXT record */ | |
1173 | + *printer_txt; /* LPD TXT record */ | |
1174 | + AvahiEntryGroup *avahi_group; /* Avahi entry group */ | |
1175 | +#endif /* HAVE_AVAHI */ | |
1176 | }; | |
1177 | ||
1178 |