Home | History | Annotate | Download | only in patches
      1 --- /usr/tmp/clean/avahi-0.6.12/avahi-core/resolve-host-name.c	2006-03-02 01:30:17.000000000 +0000
      2 +++ avahi-0.6.12/avahi-core/resolve-host-name.c	2006-08-28 14:38:21.577853000 +0100
      3 @@ -24,6 +24,7 @@
      4  #endif
      5  
      6  #include <stdlib.h>
      7 +#include <stdio.h>
      8  
      9  #include <avahi-common/domain.h>
     10  #include <avahi-common/timeval.h>
     11 @@ -52,6 +53,15 @@
     12  
     13      AvahiTimeEvent *time_event;
     14  
     15 +#ifdef HAVE_BONJOUR
     16 +    AvahiTimeEvent *defer_time_event;
     17 +    AvahiWatch *watch_a;
     18 +    AvahiWatch *watch_a6;
     19 +    AvahiLookupFlags lookup_flags;
     20 +    DNSServiceRef client_a;
     21 +    DNSServiceRef client_a6;
     22 +#endif
     23 +
     24      AVAHI_LLIST_FIELDS(AvahiSHostNameResolver, resolver);
     25  };
     26  
     27 @@ -96,6 +106,168 @@
     28      }
     29  }
     30  
     31 +#ifdef HAVE_BONJOUR 
     32 +static void resolve_socket_event(AvahiWatch *w, int fd, AvahiWatchEvent events,
     33 +void *userdata) {
     34 +    AvahiSHostNameResolver *r = userdata;
     35 +    DNSServiceErrorType ret;
     36 +    DNSServiceRef client;
     37 +
     38 +    assert(w);
     39 +    assert(fd >= 0);
     40 +    assert(events & AVAHI_WATCH_IN);
     41 +
     42 +    if (fd == DNSServiceRefSockFD(r->client_a))
     43 +        client = r->client_a;
     44 +    else if (fd == DNSServiceRefSockFD(r->client_a6))
     45 +        client = r->client_a6;
     46 +    else
     47 +        assert (0);
     48 +
     49 +    ret = DNSServiceProcessResult(client);
     50 +    if (ret != kDNSServiceErr_NoError) {
     51 +        if (client == r->client_a) {
     52 +            if (r->watch_a) {
     53 +                r->server->poll_api->watch_free(r->watch_a);
     54 +                r->watch_a = NULL;
     55 +            }
     56 +            DNSServiceRefDeallocate(r->client_a);
     57 +            r->client_a = NULL;
     58 +        } else if (client == r->client_a6) {
     59 +            if (r->watch_a6) {
     60 +                r->server->poll_api->watch_free(r->watch_a6);
     61 +                r->watch_a6 = NULL;
     62 +            }
     63 +            DNSServiceRefDeallocate(r->client_a6);
     64 +            r->client_a6 = NULL;
     65 +        }
     66 +        avahi_server_set_errno(r->server, AVAHI_ERR_DISCONNECTED);
     67 +        finish(r, AVAHI_RESOLVER_FAILURE);
     68 +    }
     69 +}
     70 +
     71 +static void resolve_reply(DNSServiceRef client, DNSServiceFlags flags, uint32_t IfIndex, DNSServiceErrorType errorCode, const char *fullname, uint16_t rrtype, uint16_t rrclass, uint16_t rdlen, const void* rdata, uint32_t ttl, void *context) {
     72 +    AvahiSHostNameResolver *r = context;
     73 +    const unsigned char *rd = rdata;
     74 +    AvahiAddress a;
     75 +
     76 +    assert(rrtype == kDNSServiceType_A || rrtype == kDNSServiceType_A6);
     77 +    if (!flags & kDNSServiceFlagsAdd)
     78 +        /* this is a remove event  so ignore*/
     79 +        return;
     80 +
     81 +    if (r->interface > 0  && IfIndex != r->interface)
     82 +        return;
     83 +    if (r->interface <= 0)
     84 +       r->interface = IfIndex;
     85 +
     86 +    /* 
     87 +     * Using Bonjour we cannot determine whether result was obtained from
     88 +     * multicast ot unicast query
     89 +     */
     90 +    r->flags = 0;
     91 +
     92 +    switch (rrtype) {
     93 +        case kDNSServiceType_A:
     94 +            if (r->protocol == AVAHI_PROTO_UNSPEC)
     95 +                r->protocol = AVAHI_PROTO_INET;
     96 +            else if (r->protocol != AVAHI_PROTO_INET)
     97 +                return;
     98 +
     99 +            if (!r->address_record) {
    100 +                if (!(r->address_record = avahi_record_new_full(r->host_name, AVAHI_DNS_CLASS_IN, AVAHI_DNS_TYPE_A, ttl))) {
    101 +                    avahi_server_set_errno(r->server, AVAHI_ERR_NO_MEMORY);
    102 +                    finish(r, AVAHI_RESOLVER_FAILURE);
    103 +                    return;
    104 +                }
    105 +                if (avahi_rdata_parse(r->address_record, rdata, rdlen) != 0) {
    106 +                    avahi_server_set_errno(r->server, AVAHI_ERR_INVALID_PACKET);
    107 +                    finish(r, AVAHI_RESOLVER_FAILURE);
    108 +                }
    109 +            }
    110 +            break;
    111 +        case kDNSServiceType_A6:
    112 +            if (r->protocol == AVAHI_PROTO_UNSPEC)
    113 +                r->protocol = AVAHI_PROTO_INET6;
    114 +            else if (r->protocol != AVAHI_PROTO_INET6)
    115 +                return;
    116 +            if (!r->address_record) {
    117 +                if (!(r->address_record = avahi_record_new_full(r->host_name, AVAHI_DNS_CLASS_IN, AVAHI_DNS_TYPE_AAAA, ttl))) {
    118 +                    avahi_server_set_errno(r->server, AVAHI_ERR_NO_MEMORY);
    119 +                    finish(r, AVAHI_RESOLVER_FAILURE);
    120 +                    return;
    121 +                }
    122 +                if (avahi_rdata_parse(r->address_record, rdata, rdlen) != 0) {
    123 +                    avahi_server_set_errno(r->server, AVAHI_ERR_INVALID_PACKET);
    124 +                    finish(r, AVAHI_RESOLVER_FAILURE);
    125 +                    return;
    126 +                }
    127 +            }
    128 +            break;
    129 +        default:
    130 +            abort();
    131 +    }
    132 +    finish(r, AVAHI_RESOLVER_FOUND);
    133 +}
    134 +
    135 +static void resolve_error_callback(AvahiTimeEvent *e, void *userdata) {
    136 +    AvahiSHostNameResolver *r = userdata;
    137 +
    138 +    if (r->defer_time_event) {
    139 +        avahi_time_event_free(r->defer_time_event);
    140 +        r->defer_time_event = NULL;
    141 +    }
    142 +    avahi_server_set_errno(r->server, AVAHI_ERR_FAILURE);
    143 +    finish(r, AVAHI_RESOLVER_FAILURE);
    144 +}
    145 +
    146 +static void avahi_resolve_host_name_start(AvahiSHostNameResolver *r, AvahiProtocol aprotocol)
    147 +{
    148 +    DNSServiceErrorType ret;
    149 +    DNSServiceFlags flags;
    150 +
    151 +    if (r->flags == AVAHI_LOOKUP_USE_MULTICAST)
    152 +        flags = kDNSServiceFlagsForceMulticast;
    153 +
    154 +    if (aprotocol == AVAHI_PROTO_INET || aprotocol == AVAHI_PROTO_UNSPEC) {
    155 +        ret = DNSServiceQueryRecord(&r->client_a,
    156 +                                    flags,
    157 +                                    r->interface == AVAHI_IF_UNSPEC ?
    158 +                                        kDNSServiceInterfaceIndexAny :
    159 +                                        r->interface,
    160 +                                    r->host_name,
    161 +                                    kDNSServiceType_A,
    162 +                                    kDNSServiceClass_IN,
    163 +                                    resolve_reply,
    164 +                                    r);
    165 +        if (ret != kDNSServiceErr_NoError || !r->client_a) {
    166 +            r->defer_time_event = avahi_time_event_new(r->server->time_event_queue, NULL, resolve_error_callback, r);
    167 +           return;
    168 +        } else {
    169 +            r->watch_a = r->server->poll_api->watch_new(r->server->poll_api, DNSServiceRefSockFD(r->client_a), AVAHI_WATCH_IN, resolve_socket_event, r);
    170 +        }
    171 +    }
    172 +    if (aprotocol == AVAHI_PROTO_INET6 || aprotocol == AVAHI_PROTO_UNSPEC) {
    173 +        ret = DNSServiceQueryRecord(&r->client_a6,
    174 +                                    flags,
    175 +                                    r->interface == AVAHI_IF_UNSPEC ?
    176 +                                        kDNSServiceInterfaceIndexAny :
    177 +                                        r->interface,
    178 +                                    r->host_name,
    179 +                                    kDNSServiceType_AAAA,
    180 +                                    kDNSServiceClass_IN,
    181 +                                    resolve_reply,
    182 +                                    r);
    183 +        if (ret != kDNSServiceErr_NoError || !r->client_a6) {
    184 +            r->defer_time_event = avahi_time_event_new(r->server->time_event_queue, NULL, resolve_error_callback, r);
    185 +           return;
    186 +        } else {
    187 +            r->watch_a6 = r->server->poll_api->watch_new(r->server->poll_api, DNSServiceRefSockFD(r->client_a6), AVAHI_WATCH_IN, resolve_socket_event, r);
    188 +        }
    189 +    }
    190 +}
    191 +#endif
    192 +
    193  static void time_event_callback(AvahiTimeEvent *e, void *userdata) {
    194      AvahiSHostNameResolver *r = userdata;
    195      
    196 @@ -118,6 +290,7 @@
    197      r->time_event = avahi_time_event_new(r->server->time_event_queue, &tv, time_event_callback, r);
    198  }
    199  
    200 +#ifndef HAVE_BONJOUR
    201  static void record_browser_callback(
    202      AvahiSRecordBrowser*rr,
    203      AvahiIfIndex interface,
    204 @@ -202,6 +375,7 @@
    205              break;
    206      }
    207  }
    208 +#endif
    209  
    210  AvahiSHostNameResolver *avahi_s_host_name_resolver_new(
    211      AvahiServer *server,
    212 @@ -248,6 +422,15 @@
    213  
    214      r->record_browser_aaaa = r->record_browser_a = NULL;
    215  
    216 +#ifdef HAVE_BONJOUR
    217 +    r->defer_time_event = NULL;
    218 +    r->watch_a = NULL;
    219 +    r->watch_a6 = NULL;
    220 +    r->client_a = NULL;
    221 +    r->client_a6 = NULL;
    222 +    r->lookup_flags = flags;
    223 +    avahi_resolve_host_name_start (r, aprotocol);
    224 +#else
    225      if (aprotocol == AVAHI_PROTO_INET || aprotocol == AVAHI_PROTO_UNSPEC) {
    226          k = avahi_key_new(host_name, AVAHI_DNS_CLASS_IN, AVAHI_DNS_TYPE_A);
    227          r->record_browser_a = avahi_s_record_browser_new(server, interface, protocol, k, flags, record_browser_callback, r);
    228 @@ -267,6 +450,7 @@
    229      }
    230  
    231      assert(r->record_browser_aaaa || r->record_browser_a);
    232 +#endif
    233  
    234      start_timeout(r);
    235      
    236 @@ -294,6 +478,23 @@
    237      if (r->address_record)
    238          avahi_record_unref(r->address_record);
    239      
    240 +#ifdef HAVE_BONJOUR
    241 +    if (r->defer_time_event) {
    242 +        avahi_time_event_free(r->defer_time_event);
    243 +        r->defer_time_event = NULL;
    244 +    }
    245 +
    246 +    if (r->watch_a)
    247 +       r->server->poll_api->watch_free(r->watch_a);
    248 +    if (r->watch_a6)
    249 +       r->server->poll_api->watch_free(r->watch_a6);
    250 +
    251 +    if (r->client_a)
    252 +        DNSServiceRefDeallocate(r->client_a);
    253 +    if (r->client_a6)
    254 +        DNSServiceRefDeallocate(r->client_a6);
    255 +#endif
    256 +
    257      avahi_free(r->host_name);
    258      avahi_free(r);
    259  }
    260