#include <sys/stat.h>
#include <fcntl.h>
+#include <ifaddrs.h>
#include <time.h>
#include <stdio.h>
#include <unistd.h>
}
void
-dns_send_question(struct interface *iface, const char *question, int type, int unicast)
+dns_send_question(struct interface *iface, const char *question, int type, int multicast)
{
static struct dns_header h;
static struct dns_question q;
int len;
h.questions = cpu_to_be16(1);
- q.class = cpu_to_be16(((unicast) ? (CLASS_UNICAST) : (0)) | 1);
+ q.class = cpu_to_be16((multicast ? 0 : CLASS_UNICAST) | 1);
q.type = cpu_to_be16(type);
len = dn_comp(question, (void *) dns_buffer, sizeof(dns_buffer), NULL, NULL);
fprintf(stderr, "failed to send question\n");
}
+void
+dns_reply_a(struct interface *iface, int ttl)
+{
+ struct ifaddrs *ifap, *ifa;
+ struct sockaddr_in *sa;
+ struct sockaddr_in6 *sa6;
+
+ getifaddrs(&ifap);
+
+ dns_init_answer();
+ for (ifa = ifap; ifa; ifa = ifa->ifa_next) {
+ if (strcmp(ifa->ifa_name, iface->name))
+ continue;
+ if (ifa->ifa_addr->sa_family == AF_INET) {
+ sa = (struct sockaddr_in *) ifa->ifa_addr;
+ dns_add_answer(TYPE_A, (uint8_t *) &sa->sin_addr, 4, ttl);
+ }
+ if (ifa->ifa_addr->sa_family == AF_INET6) {
+ uint8_t ll_prefix[] = {0xfe, 0x80 };
+ sa6 = (struct sockaddr_in6 *) ifa->ifa_addr;
+ if (!memcmp(&sa6->sin6_addr, &ll_prefix, 2))
+ dns_add_answer(TYPE_AAAA, (uint8_t *) &sa6->sin6_addr, 16, ttl);
+ }
+ }
+ dns_send_answer(iface, mdns_hostname_local);
+
+ freeifaddrs(ifap);
+}
+
static int
scan_name(const uint8_t *buffer, int len)
{
switch (q->type) {
case TYPE_ANY:
- if (!strcmp(name, mdns_hostname_local))
+ if (!strcmp(name, mdns_hostname_local)) {
service_reply(iface, NULL, announce_ttl);
+ dns_reply_a(iface, announce_ttl);
+ }
break;
case TYPE_PTR:
- service_announce_services(iface, name, announce_ttl);
+ if (!strcmp(name, sdudp))
+ service_announce_services(iface, announce_ttl);
service_reply(iface, name, announce_ttl);
break;
if (host)
*host = '\0';
if (!strcmp(mdns_hostname, name))
- service_reply_a(iface, announce_ttl);
+ dns_reply_a(iface, announce_ttl);
break;
};
}
}
if (h->questions && !iface->multicast && port != 5353)
- // silently drop unicast questions that dont originate from port 5353
+ /* silently drop unicast questions that dont originate from port 5353 */
return;
while (h->questions-- > 0) {