+ case AVAHI_BROWSER_CACHE_EXHAUSTED:
+ n_cache_exhausted --;
+ check_terminate(c);
+ break;
+
+ case AVAHI_BROWSER_ALL_FOR_NOW:
+ n_all_for_now --;
+ check_terminate(c);
+ break;
+ }
+}
+
+static void browse_domains(Config *c) {
+ AvahiDomainBrowser *b;
+
+ assert(c);
+
+ if (!(b = avahi_domain_browser_new(
+ client,
+ AVAHI_IF_UNSPEC,
+ AVAHI_PROTO_UNSPEC,
+ c->domain,
+ AVAHI_DOMAIN_BROWSER_BROWSE,
+ 0,
+ domain_browser_callback,
+ c))) {
+
+ fprintf(stderr, _("avahi_domain_browser_new() failed: %s\n"), avahi_strerror(avahi_client_errno(client)));
+ avahi_simple_poll_quit(simple_poll);
+ }
+
+ n_cache_exhausted++;
+ n_all_for_now++;
+}
+
+static int start(Config *config) {
+
+ assert(!browsing);
+
+ if (config->verbose && !config->parsable) {
+ const char *version, *hn;
+
+ if (!(version = avahi_client_get_version_string(client))) {
+ fprintf(stderr, _("Failed to query version string: %s\n"), avahi_strerror(avahi_client_errno(client)));
+ return -1;
+ }
+
+ if (!(hn = avahi_client_get_host_name_fqdn(client))) {
+ fprintf(stderr, _("Failed to query host name: %s\n"), avahi_strerror(avahi_client_errno(client)));
+ return -1;
+ }
+
+ fprintf(stderr, _("Server version: %s; Host name: %s\n"), version, hn);
+
+ if (config->command == COMMAND_BROWSE_DOMAINS) {
+ /* Translators: This is a column heading with abbreviations for
+ * Event (+/-), Network Interface, Protocol (IPv4/v6), Domain */
+ fprintf(stderr, _("E Ifce Prot Domain\n"));
+ } else {
+ /* Translators: This is a column heading with abbreviations for
+ * Event (+/-), Network Interface, Protocol (IPv4/v6), Domain */
+ fprintf(stderr, _("E Ifce Prot %-*s %-20s Domain\n"), n_columns-35, _("Name"), _("Type"));
+ }
+ }
+
+ if (config->command == COMMAND_BROWSE_SERVICES)
+ browse_service_type(config, config->stype, config->domain);
+ else if (config->command == COMMAND_BROWSE_ALL_SERVICES)
+ browse_all(config);
+ else {
+ assert(config->command == COMMAND_BROWSE_DOMAINS);
+ browse_domains(config);
+ }
+
+ browsing = 1;
+ return 0;
+}
+
+static void client_callback(AvahiClient *c, AvahiClientState state, AVAHI_GCC_UNUSED void * userdata) {
+ Config *config = userdata;
+
+ /* This function might be called when avahi_client_new() has not
+ * returned yet.*/
+ client = c;
+
+ switch (state) {
+ case AVAHI_CLIENT_FAILURE:
+
+ if (config->no_fail && avahi_client_errno(c) == AVAHI_ERR_DISCONNECTED) {
+ int error;
+
+ /* We have been disconnected, so let reconnect */
+
+ fprintf(stderr, _("Disconnected, reconnecting ...\n"));
+
+ avahi_client_free(client);
+ client = NULL;
+
+ avahi_string_list_free(browsed_types);
+ browsed_types = NULL;
+
+ while (services)
+ remove_service(config, services);
+
+ browsing = 0;
+
+ if (!(client = avahi_client_new(avahi_simple_poll_get(simple_poll), AVAHI_CLIENT_NO_FAIL, client_callback, config, &error))) {
+ fprintf(stderr, _("Failed to create client object: %s\n"), avahi_strerror(error));
+ avahi_simple_poll_quit(simple_poll);
+ }
+
+ } else {
+ fprintf(stderr, _("Client failure, exiting: %s\n"), avahi_strerror(avahi_client_errno(c)));
+ avahi_simple_poll_quit(simple_poll);
+ }
+
+ break;
+