int main(int argc, char *argv[]) { int ret = 1, error; Config config; const char *argv0; avahi_init_i18n(); setlocale(LC_ALL, ""); if ((argv0 = strrchr(argv[0], '/'))) argv0++; else argv0 = argv[0]; if (parse_command_line(&config, argv0, argc, argv) < 0) goto fail; switch (config.command) { case COMMAND_UNSPEC: ret = 1; fprintf(stderr, _("No command specified.\n")); break; case COMMAND_HELP: help(stdout, argv0); ret = 0; break; case COMMAND_VERSION: printf("%s "PACKAGE_VERSION"\n", argv0); ret = 0; break; case COMMAND_RESOLVE_HOST_NAME: case COMMAND_RESOLVE_ADDRESS: { int i; if (!(simple_poll = avahi_simple_poll_new())) { fprintf(stderr, _("Failed to create simple poll object.\n")); goto fail; } if (sigint_install(simple_poll) < 0) goto fail; if (!(client = avahi_client_new(avahi_simple_poll_get(simple_poll), 0, client_callback, NULL, &error))) { fprintf(stderr, _("Failed to create client object: %s\n"), avahi_strerror(error)); goto fail; } if (config.verbose) { 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))); goto fail; } if (!(hn = avahi_client_get_host_name_fqdn(client))) { fprintf(stderr, _("Failed to query host name: %s\n"), avahi_strerror(avahi_client_errno(client))); goto fail; } fprintf(stderr, _("Server version: %s; Host name: %s\n"), version, hn); } n_resolving = 0; for (i = optind; i < argc; i++) { if (config.command == COMMAND_RESOLVE_HOST_NAME) { if (!(avahi_host_name_resolver_new(client, AVAHI_IF_UNSPEC, AVAHI_PROTO_UNSPEC, argv[i], config.proto, 0, host_name_resolver_callback, NULL))) { fprintf(stderr, _("Failed to create host name resolver: %s\n"), avahi_strerror(avahi_client_errno(client))); goto fail; } } else { AvahiAddress a; assert(config.command == COMMAND_RESOLVE_ADDRESS); if (!avahi_address_parse(argv[i], AVAHI_PROTO_UNSPEC, &a)) { fprintf(stderr, _("Failed to parse address '%s'\n"), argv[i]); goto fail; } if (!(avahi_address_resolver_new(client, AVAHI_IF_UNSPEC, AVAHI_PROTO_UNSPEC, &a, 0, address_resolver_callback, NULL))) { fprintf(stderr, _("Failed to create address resolver: %s\n"), avahi_strerror(avahi_client_errno(client))); goto fail; } } n_resolving++; } avahi_simple_poll_loop(simple_poll); ret = 0; break; } } fail: if (client) avahi_client_free(client); sigint_uninstall(); if (simple_poll) avahi_simple_poll_free(simple_poll); return ret; }
AvahiClient *avahi_client_new(const AvahiPoll *poll_api, AvahiClientFlags flags, AvahiClientCallback callback, void *userdata, int *ret_error) { AvahiClient *client = NULL; DBusError error; DBusMessage *message = NULL, *reply = NULL; avahi_init_i18n(); dbus_error_init(&error); if (!(client = avahi_new(AvahiClient, 1))) { if (ret_error) *ret_error = AVAHI_ERR_NO_MEMORY; goto fail; } client->poll_api = poll_api; client->error = AVAHI_OK; client->callback = callback; client->userdata = userdata; client->state = (AvahiClientState) -1; client->flags = flags; client->host_name = NULL; client->host_name_fqdn = NULL; client->domain_name = NULL; client->version_string = NULL; client->local_service_cookie_valid = 0; AVAHI_LLIST_HEAD_INIT(AvahiEntryGroup, client->groups); AVAHI_LLIST_HEAD_INIT(AvahiDomainBrowser, client->domain_browsers); AVAHI_LLIST_HEAD_INIT(AvahiServiceBrowser, client->service_browsers); AVAHI_LLIST_HEAD_INIT(AvahiServiceTypeBrowser, client->service_type_browsers); AVAHI_LLIST_HEAD_INIT(AvahiServiceResolver, client->service_resolvers); AVAHI_LLIST_HEAD_INIT(AvahiHostNameResolver, client->host_name_resolvers); AVAHI_LLIST_HEAD_INIT(AvahiAddressResolver, client->address_resolvers); AVAHI_LLIST_HEAD_INIT(AvahiRecordBrowser, client->record_browsers); if (!(client->bus = avahi_dbus_bus_get(&error)) || dbus_error_is_set(&error)) { if (ret_error) *ret_error = AVAHI_ERR_DBUS_ERROR; goto fail; } if (avahi_dbus_connection_glue(client->bus, poll_api) < 0) { if (ret_error) *ret_error = AVAHI_ERR_NO_MEMORY; /* Not optimal */ goto fail; } if (!dbus_connection_add_filter(client->bus, filter_func, client, NULL)) { if (ret_error) *ret_error = AVAHI_ERR_NO_MEMORY; goto fail; } dbus_bus_add_match( client->bus, "type='signal', " "interface='" AVAHI_DBUS_INTERFACE_SERVER "', " "sender='" AVAHI_DBUS_NAME "', " "path='" AVAHI_DBUS_PATH_SERVER "'", &error); if (dbus_error_is_set(&error)) goto fail; dbus_bus_add_match ( client->bus, "type='signal', " "interface='" DBUS_INTERFACE_DBUS "', " "sender='" DBUS_SERVICE_DBUS "', " "path='" DBUS_PATH_DBUS "'", &error); if (dbus_error_is_set(&error)) goto fail; dbus_bus_add_match( client->bus, "type='signal', " "interface='" DBUS_INTERFACE_LOCAL "'", &error); if (dbus_error_is_set(&error)) goto fail; if (!(message = dbus_message_new_method_call(AVAHI_DBUS_NAME, AVAHI_DBUS_PATH_SERVER, "org.freedesktop.DBus.Peer", "Ping"))) goto fail; reply = dbus_connection_send_with_reply_and_block (client->bus, message, -1, &error); if (!reply || dbus_error_is_set (&error)) { /* We free the error so its not set, that way the fail target * will return the NO_DAEMON error rather than a DBUS error */ dbus_error_free(&error); if (!(flags & AVAHI_CLIENT_NO_FAIL)) { if (ret_error) *ret_error = AVAHI_ERR_NO_DAEMON; goto fail; } /* The user doesn't want this call to fail if the daemon is not * available, so let's return succesfully */ client_set_state(client, AVAHI_CLIENT_CONNECTING); } else { if (init_server(client, ret_error) < 0) goto fail; } dbus_message_unref(message); if (reply) dbus_message_unref(reply); return client; fail: if (message) dbus_message_unref(message); if (reply) dbus_message_unref(reply); if (client) avahi_client_free(client); if (dbus_error_is_set(&error)) { if (ret_error) { if (strcmp(error.name, DBUS_ERROR_FILE_NOT_FOUND) == 0) /* DBUS returns this error when the DBUS daemon is not running */ *ret_error = AVAHI_ERR_NO_DAEMON; else *ret_error = avahi_error_dbus_to_number(error.name); } dbus_error_free(&error); } return NULL; }
const char *avahi_strerror(int error) { const char * const msg[- AVAHI_ERR_MAX] = { N_("OK"), N_("Operation failed"), N_("Bad state"), N_("Invalid host name"), N_("Invalid domain name"), N_("No suitable network protocol available"), N_("Invalid DNS TTL"), N_("Resource record key is pattern"), N_("Local name collision"), N_("Invalid record"), N_("Invalid service name"), N_("Invalid service type"), N_("Invalid port number"), N_("Invalid record key"), N_("Invalid address"), N_("Timeout reached"), N_("Too many clients"), N_("Too many objects"), N_("Too many entries"), N_("OS Error"), N_("Access denied"), N_("Invalid operation"), N_("An unexpected D-Bus error occured"), N_("Daemon connection failed"), N_("Memory exhausted"), N_("The object passed in was not valid"), N_("Daemon not running"), N_("Invalid interface index"), N_("Invalid protocol specification"), N_("Invalid flags"), N_("Not found"), N_("Invalid configuration"), N_("Version mismatch"), N_("Invalid service subtype"), N_("Invalid packet"), N_("Invalid DNS return code"), N_("DNS failure: FORMERR"), N_("DNS failure: SERVFAIL"), N_("DNS failure: NXDOMAIN"), N_("DNS failure: NOTIMP"), N_("DNS failure: REFUSED"), N_("DNS failure: YXDOMAIN"), N_("DNS failure: YXRRSET"), N_("DNS failure: NXRRSET"), N_("DNS failure: NOTAUTH"), N_("DNS failure: NOTZONE"), N_("Invalid RDATA"), N_("Invalid DNS type"), N_("Invalid DNS class"), N_("Not supported"), N_("Not permitted"), N_("Invalid argument"), N_("Is empty"), N_("The requested operation is invalid because redundant"), N_("New entry is requested to be published with invalid group") }; avahi_init_i18n(); if (-error < 0 || -error >= -AVAHI_ERR_MAX) return _("Invalid Error Code"); return _(msg[-error]); }