mirror of
http://thekelleys.org.uk/git/dnsmasq.git
synced 2026-11-06 15:51:41 +00:00
Compare commits
24
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
9e4cf47ee8 | ||
|
|
fdc97e1383 | ||
|
|
a18bf3149a | ||
|
|
1566bacb2c | ||
|
|
e6e751b066 | ||
|
|
8de875f0fb | ||
|
|
4ace25c5d6 | ||
|
|
1e5051228d | ||
|
|
926332a764 | ||
|
|
d05dd58de1 | ||
|
|
f7443d76f7 | ||
|
|
f344dbc622 | ||
|
|
f4d0c660ca | ||
|
|
1801a29226 | ||
|
|
92be34a407 | ||
|
|
bb58f63ce5 | ||
|
|
367341f745 | ||
|
|
eddf365284 | ||
|
|
a63b8b89e6 | ||
|
|
5757371d43 | ||
|
|
b633de9413 | ||
|
|
c49778df4a | ||
|
|
53a9173fc0 | ||
|
|
d917275e48 |
No files matched your search
@@ -18,6 +18,36 @@ version 2.76
|
|||||||
that the same name is empty. Thanks to Edwin Török for
|
that the same name is empty. Thanks to Edwin Török for
|
||||||
the patch.
|
the patch.
|
||||||
|
|
||||||
|
Fix failure to correctly calculate cache-size when
|
||||||
|
reading a hosts-file fails. Thanks to André Glüpker
|
||||||
|
for the patch.
|
||||||
|
|
||||||
|
Fix wrong answer to simple name query when --domain-needed
|
||||||
|
set, but no upstream servers configured. Dnsmasq returned
|
||||||
|
REFUSED, in this case, when it should be the same as when
|
||||||
|
upstream servers are configured - NOERROR. Thanks to
|
||||||
|
Allain Legacy for spotting the problem.
|
||||||
|
|
||||||
|
Return REFUSED when running out of forwarding table slots,
|
||||||
|
not SERVFAIL.
|
||||||
|
|
||||||
|
Add --max-port configuration. Thanks to Hans Dedecker for
|
||||||
|
the patch.
|
||||||
|
|
||||||
|
Add --script-arp and two new functions for the dhcp-script.
|
||||||
|
These are "arp" and "arp-old" which announce the arrival and
|
||||||
|
removal of entries in the ARP or nieghbour tables.
|
||||||
|
|
||||||
|
Extend --add-mac to allow a new encoding of the MAC address
|
||||||
|
as base64, by configurting --add-mac=base64
|
||||||
|
|
||||||
|
Add --add-cpe-id option.
|
||||||
|
|
||||||
|
Don't crash with divide-by-zero if an IPv6 dhcp-range
|
||||||
|
is declared as a whole /64.
|
||||||
|
(ie xx::0 to xx::ffff:ffff:ffff:ffff)
|
||||||
|
Thanks to Laurent Bendel for spotting this problem.
|
||||||
|
|
||||||
|
|
||||||
version 2.75
|
version 2.75
|
||||||
Fix reversion on 2.74 which caused 100% CPU use when a
|
Fix reversion on 2.74 which caused 100% CPU use when a
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
# dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
# dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
#
|
#
|
||||||
# This program is free software; you can redistribute it and/or modify
|
# This program is free software; you can redistribute it and/or modify
|
||||||
# it under the terms of the GNU General Public License as published by
|
# it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
Vendored
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
It was downloaded from: http://www.thekelleys.org.uk/dnsmasq/
|
It was downloaded from: http://www.thekelleys.org.uk/dnsmasq/
|
||||||
|
|
||||||
|
|||||||
+40
-6
@@ -174,6 +174,13 @@ queries. Dnsmasq picks random ports as source for outbound queries:
|
|||||||
when this option is given, the ports used will always to larger
|
when this option is given, the ports used will always to larger
|
||||||
than that specified. Useful for systems behind firewalls.
|
than that specified. Useful for systems behind firewalls.
|
||||||
.TP
|
.TP
|
||||||
|
.B --max-port=<port>
|
||||||
|
Use ports lower than that given as source for outbound DNS queries.
|
||||||
|
Dnsmasq picks random ports as source for outbound queries:
|
||||||
|
when this option is given, the ports used will always be lower
|
||||||
|
than that specified. Useful for systems behind firewalls.
|
||||||
|
.TP
|
||||||
|
|
||||||
.B \-i, --interface=<interface name>
|
.B \-i, --interface=<interface name>
|
||||||
Listen only on the specified interface(s). Dnsmasq automatically adds
|
Listen only on the specified interface(s). Dnsmasq automatically adds
|
||||||
the loopback (local) interface to the list of interfaces to use when
|
the loopback (local) interface to the list of interfaces to use when
|
||||||
@@ -405,7 +412,10 @@ xxx.internal.thekelleys.org.uk at 192.168.1.1 then giving the flag
|
|||||||
.B -S /internal.thekelleys.org.uk/192.168.1.1
|
.B -S /internal.thekelleys.org.uk/192.168.1.1
|
||||||
will send all queries for
|
will send all queries for
|
||||||
internal machines to that nameserver, everything else will go to the
|
internal machines to that nameserver, everything else will go to the
|
||||||
servers in /etc/resolv.conf. An empty domain specification,
|
servers in /etc/resolv.conf. DNSSEC validation is turned off for such
|
||||||
|
private nameservers, UNLESS a
|
||||||
|
.B --trust-anchor
|
||||||
|
is specified for the domain in question. An empty domain specification,
|
||||||
.B //
|
.B //
|
||||||
has the special meaning of "unqualified names only" ie names without any
|
has the special meaning of "unqualified names only" ie names without any
|
||||||
dots in them. A non-standard port may be specified as
|
dots in them. A non-standard port may be specified as
|
||||||
@@ -594,7 +604,7 @@ configured a zero is added in front of the label. ::1 becomes 0--1.
|
|||||||
The address range can be of the form
|
The address range can be of the form
|
||||||
<ip address>,<ip address> or <ip address>/<netmask>
|
<ip address>,<ip address> or <ip address>/<netmask>
|
||||||
.TP
|
.TP
|
||||||
.B --add-mac
|
.B --add-mac[=base64|text]
|
||||||
Add the MAC address of the requestor to DNS queries which are
|
Add the MAC address of the requestor to DNS queries which are
|
||||||
forwarded upstream. This may be used to DNS filtering by the upstream
|
forwarded upstream. This may be used to DNS filtering by the upstream
|
||||||
server. The MAC address can only be added if the requestor is on the same
|
server. The MAC address can only be added if the requestor is on the same
|
||||||
@@ -602,7 +612,12 @@ subnet as the dnsmasq server. Note that the mechanism used to achieve this (an E
|
|||||||
is not yet standardised, so this should be considered
|
is not yet standardised, so this should be considered
|
||||||
experimental. Also note that exposing MAC addresses in this way may
|
experimental. Also note that exposing MAC addresses in this way may
|
||||||
have security and privacy implications. The warning about caching
|
have security and privacy implications. The warning about caching
|
||||||
given for --add-subnet applies to --add-mac too.
|
given for --add-subnet applies to --add-mac too. An alternative encoding of the
|
||||||
|
MAC, as base64, is enabled by adding the "base64" parameter and a human-readable encoding of hex-and-colons is enabled by added the "text" parameter.
|
||||||
|
.TP
|
||||||
|
.B --add-cpe-id=<string>
|
||||||
|
Add a arbitrary identifying string to o DNS queries which are
|
||||||
|
forwarded upstream.
|
||||||
.TP
|
.TP
|
||||||
.B --add-subnet[[=[<IPv4 address>/]<IPv4 prefix length>][,[<IPv6 address>/]<IPv6 prefix length>]]
|
.B --add-subnet[[=[<IPv4 address>/]<IPv4 prefix length>][,[<IPv6 address>/]<IPv6 prefix length>]]
|
||||||
Add a subnet address to the DNS queries which are forwarded
|
Add a subnet address to the DNS queries which are forwarded
|
||||||
@@ -1533,11 +1548,11 @@ At dnsmasq startup, the script will be invoked for
|
|||||||
all existing leases as they are read from the lease file. Expired
|
all existing leases as they are read from the lease file. Expired
|
||||||
leases will be called with "del" and others with "old". When dnsmasq
|
leases will be called with "del" and others with "old". When dnsmasq
|
||||||
receives a HUP signal, the script will be invoked for existing leases
|
receives a HUP signal, the script will be invoked for existing leases
|
||||||
with an "old " event.
|
with an "old" event.
|
||||||
|
|
||||||
|
|
||||||
There are two further actions which may appear as the first argument
|
There are four further actions which may appear as the first argument
|
||||||
to the script, "init" and "tftp". More may be added in the future, so
|
to the script, "init", "arp-add", "arp-del" and "tftp". More may be added in the future, so
|
||||||
scripts should be written to ignore unknown actions. "init" is
|
scripts should be written to ignore unknown actions. "init" is
|
||||||
described below in
|
described below in
|
||||||
.B --leasefile-ro
|
.B --leasefile-ro
|
||||||
@@ -1545,6 +1560,11 @@ The "tftp" action is invoked when a TFTP file transfer completes: the
|
|||||||
arguments are the file size in bytes, the address to which the file
|
arguments are the file size in bytes, the address to which the file
|
||||||
was sent, and the complete pathname of the file.
|
was sent, and the complete pathname of the file.
|
||||||
|
|
||||||
|
The "arp-add" and "arp-del" actions are only called if enabled with
|
||||||
|
.B --script-arp
|
||||||
|
They are are supplied with a MAC address and IP address as arguments. "arp-add" indicates
|
||||||
|
the arrival of a new entry in the ARP or neighbour table, and "arp-del" indicates the deletion of same.
|
||||||
|
|
||||||
.TP
|
.TP
|
||||||
.B --dhcp-luascript=<path>
|
.B --dhcp-luascript=<path>
|
||||||
Specify a script written in Lua, to be run when leases are created,
|
Specify a script written in Lua, to be run when leases are created,
|
||||||
@@ -1591,10 +1611,24 @@ table holds the tags
|
|||||||
.B file_name
|
.B file_name
|
||||||
and
|
and
|
||||||
.B file_size.
|
.B file_size.
|
||||||
|
|
||||||
|
The
|
||||||
|
.B arp
|
||||||
|
and
|
||||||
|
.B arp-old
|
||||||
|
functions are called only when enabled with
|
||||||
|
.B --script-arp
|
||||||
|
and have a table which holds the tags
|
||||||
|
.B mac_addres
|
||||||
|
and
|
||||||
|
.B client_address.
|
||||||
.TP
|
.TP
|
||||||
.B --dhcp-scriptuser
|
.B --dhcp-scriptuser
|
||||||
Specify the user as which to run the lease-change script or Lua script. This defaults to root, but can be changed to another user using this flag.
|
Specify the user as which to run the lease-change script or Lua script. This defaults to root, but can be changed to another user using this flag.
|
||||||
.TP
|
.TP
|
||||||
|
.B --script-arp
|
||||||
|
Enable the "arp" and "arp-old" functions in the dhcp-script and dhcp-luascript.
|
||||||
|
.TP
|
||||||
.B \-9, --leasefile-ro
|
.B \-9, --leasefile-ro
|
||||||
Completely suppress use of the lease database file. The file will not
|
Completely suppress use of the lease database file. The file will not
|
||||||
be created, read, or written. Change the way the lease-change
|
be created, read, or written. Change the way the lease-change
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -44,6 +44,11 @@ static int filter_mac(int family, char *addrp, char *mac, size_t maclen, void *p
|
|||||||
if (maclen > DHCP_CHADDR_MAX)
|
if (maclen > DHCP_CHADDR_MAX)
|
||||||
return 1;
|
return 1;
|
||||||
|
|
||||||
|
#ifndef HAVE_IPV6
|
||||||
|
if (family != AF_INET)
|
||||||
|
return 1;
|
||||||
|
#endif
|
||||||
|
|
||||||
/* Look for existing entry */
|
/* Look for existing entry */
|
||||||
for (arp = arps; arp; arp = arp->next)
|
for (arp = arps; arp; arp = arp->next)
|
||||||
{
|
{
|
||||||
@@ -110,36 +115,42 @@ static int filter_mac(int family, char *addrp, char *mac, size_t maclen, void *p
|
|||||||
/* If in lazy mode, we cache absence of ARP entries. */
|
/* If in lazy mode, we cache absence of ARP entries. */
|
||||||
int find_mac(union mysockaddr *addr, unsigned char *mac, int lazy, time_t now)
|
int find_mac(union mysockaddr *addr, unsigned char *mac, int lazy, time_t now)
|
||||||
{
|
{
|
||||||
struct arp_record *arp, **up;
|
struct arp_record *arp, *tmp, **up;
|
||||||
int updated = 0;
|
int updated = 0;
|
||||||
|
|
||||||
again:
|
again:
|
||||||
|
|
||||||
/* If the database is less then INTERVAL old, look in there */
|
/* If the database is less then INTERVAL old, look in there */
|
||||||
if (difftime(now, last) < INTERVAL)
|
if (difftime(now, last) < INTERVAL)
|
||||||
for (arp = arps; arp; arp = arp->next)
|
{
|
||||||
{
|
/* addr == NULL -> just make cache up-to-date */
|
||||||
if (addr->sa.sa_family == arp->family)
|
if (!addr)
|
||||||
{
|
return 0;
|
||||||
if (arp->addr.addr.addr4.s_addr != addr->in.sin_addr.s_addr)
|
|
||||||
continue;
|
for (arp = arps; arp; arp = arp->next)
|
||||||
}
|
{
|
||||||
|
if (addr->sa.sa_family == arp->family)
|
||||||
|
{
|
||||||
|
if (arp->addr.addr.addr4.s_addr != addr->in.sin_addr.s_addr)
|
||||||
|
continue;
|
||||||
|
}
|
||||||
#ifdef HAVE_IPV6
|
#ifdef HAVE_IPV6
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (!IN6_ARE_ADDR_EQUAL(&arp->addr.addr.addr6, &addr->in6.sin6_addr))
|
if (!IN6_ARE_ADDR_EQUAL(&arp->addr.addr.addr6, &addr->in6.sin6_addr))
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
/* Only accept poitive entries unless in lazy mode. */
|
/* Only accept positive entries unless in lazy mode. */
|
||||||
if (arp->status != ARP_EMPTY || lazy || updated)
|
if (arp->status != ARP_EMPTY || lazy || updated)
|
||||||
{
|
{
|
||||||
if (mac && arp->hwlen != 0)
|
if (mac && arp->hwlen != 0)
|
||||||
memcpy(mac, arp->hwaddr, arp->hwlen);
|
memcpy(mac, arp->hwaddr, arp->hwlen);
|
||||||
return arp->hwlen;
|
return arp->hwlen;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
/* Not found, try the kernel */
|
/* Not found, try the kernel */
|
||||||
if (!updated)
|
if (!updated)
|
||||||
@@ -148,22 +159,26 @@ int find_mac(union mysockaddr *addr, unsigned char *mac, int lazy, time_t now)
|
|||||||
last = now;
|
last = now;
|
||||||
|
|
||||||
/* Mark all non-negative entries */
|
/* Mark all non-negative entries */
|
||||||
for (arp = arps, up = &arps; arp; arp = arp->next)
|
for (arp = arps; arp; arp = arp->next)
|
||||||
if (arp->status != ARP_EMPTY)
|
if (arp->status != ARP_EMPTY)
|
||||||
arp->status = ARP_MARK;
|
arp->status = ARP_MARK;
|
||||||
|
|
||||||
iface_enumerate(AF_UNSPEC, NULL, filter_mac);
|
iface_enumerate(AF_UNSPEC, NULL, filter_mac);
|
||||||
|
|
||||||
/* Remove all unconfirmed entries to old list. */
|
/* Remove all unconfirmed entries to old list. */
|
||||||
for (arp = arps, up = &arps; arp; arp = arp->next)
|
for (arp = arps, up = &arps; arp; arp = tmp)
|
||||||
if (arp->status == ARP_MARK)
|
{
|
||||||
{
|
tmp = arp->next;
|
||||||
*up = arp->next;
|
|
||||||
arp->next = old;
|
if (arp->status == ARP_MARK)
|
||||||
old = arp;
|
{
|
||||||
}
|
*up = arp->next;
|
||||||
else
|
arp->next = old;
|
||||||
up = &arp->next;
|
old = arp;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
up = &arp->next;
|
||||||
|
}
|
||||||
|
|
||||||
goto again;
|
goto again;
|
||||||
}
|
}
|
||||||
@@ -184,6 +199,7 @@ int find_mac(union mysockaddr *addr, unsigned char *mac, int lazy, time_t now)
|
|||||||
arps = arp;
|
arps = arp;
|
||||||
arp->status = ARP_EMPTY;
|
arp->status = ARP_EMPTY;
|
||||||
arp->family = addr->sa.sa_family;
|
arp->family = addr->sa.sa_family;
|
||||||
|
arp->hwlen = 0;
|
||||||
|
|
||||||
if (addr->sa.sa_family == AF_INET)
|
if (addr->sa.sa_family == AF_INET)
|
||||||
arp->addr.addr.addr4.s_addr = addr->in.sin_addr.s_addr;
|
arp->addr.addr.addr4.s_addr = addr->in.sin_addr.s_addr;
|
||||||
@@ -204,8 +220,8 @@ int do_arp_script_run(void)
|
|||||||
if (old)
|
if (old)
|
||||||
{
|
{
|
||||||
#ifdef HAVE_SCRIPT
|
#ifdef HAVE_SCRIPT
|
||||||
if (option_bool(OPT_DNS_CLIENT))
|
if (option_bool(OPT_SCRIPT_ARP))
|
||||||
queue_arp(ACTION_ARP_OLD, old->hwaddr, old->hwlen, old->family, &old->addr);
|
queue_arp(ACTION_ARP_DEL, old->hwaddr, old->hwlen, old->family, &old->addr);
|
||||||
#endif
|
#endif
|
||||||
arp = old;
|
arp = old;
|
||||||
old = arp->next;
|
old = arp->next;
|
||||||
@@ -218,7 +234,7 @@ int do_arp_script_run(void)
|
|||||||
if (arp->status == ARP_NEW)
|
if (arp->status == ARP_NEW)
|
||||||
{
|
{
|
||||||
#ifdef HAVE_SCRIPT
|
#ifdef HAVE_SCRIPT
|
||||||
if (option_bool(OPT_DNS_CLIENT))
|
if (option_bool(OPT_SCRIPT_ARP))
|
||||||
queue_arp(ACTION_ARP, arp->hwaddr, arp->hwlen, arp->family, &arp->addr);
|
queue_arp(ACTION_ARP, arp->hwaddr, arp->hwlen, arp->family, &arp->addr);
|
||||||
#endif
|
#endif
|
||||||
arp->status = ARP_FOUND;
|
arp->status = ARP_FOUND;
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -20,7 +20,9 @@
|
|||||||
#include <ifaddrs.h>
|
#include <ifaddrs.h>
|
||||||
|
|
||||||
#include <sys/param.h>
|
#include <sys/param.h>
|
||||||
|
#if defined(HAVE_BSD_NETWORK) && !defined(__APPLE__)
|
||||||
#include <sys/sysctl.h>
|
#include <sys/sysctl.h>
|
||||||
|
#endif
|
||||||
#include <net/if.h>
|
#include <net/if.h>
|
||||||
#include <net/route.h>
|
#include <net/route.h>
|
||||||
#include <net/if_dl.h>
|
#include <net/if_dl.h>
|
||||||
|
|||||||
+2
-2
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -919,7 +919,7 @@ int read_hostsfile(char *filename, unsigned int index, int cache_size, struct cr
|
|||||||
if (!f)
|
if (!f)
|
||||||
{
|
{
|
||||||
my_syslog(LOG_ERR, _("failed to load names from %s: %s"), filename, strerror(errno));
|
my_syslog(LOG_ERR, _("failed to load names from %s: %s"), filename, strerror(errno));
|
||||||
return 0;
|
return cache_size;
|
||||||
}
|
}
|
||||||
|
|
||||||
eatspace(f);
|
eatspace(f);
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+11
-2
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -434,7 +434,16 @@ struct dhcp_context *address6_allocate(struct dhcp_context *context, unsigned c
|
|||||||
/* seed is largest extant lease addr in this context */
|
/* seed is largest extant lease addr in this context */
|
||||||
start = lease_find_max_addr6(c) + serial;
|
start = lease_find_max_addr6(c) + serial;
|
||||||
else
|
else
|
||||||
start = addr6part(&c->start6) + ((j + c->addr_epoch) % (1 + addr6part(&c->end6) - addr6part(&c->start6)));
|
{
|
||||||
|
u64 range = 1 + addr6part(&c->end6) - addr6part(&c->start6);
|
||||||
|
u64 offset = j + c->addr_epoch;
|
||||||
|
|
||||||
|
/* don't divide by zero if range is whole 2^64 */
|
||||||
|
if (range != 0)
|
||||||
|
offset = offset % range;
|
||||||
|
|
||||||
|
start = addr6part(&c->start6) + offset;
|
||||||
|
}
|
||||||
|
|
||||||
/* iterate until we find a free address. */
|
/* iterate until we find a free address. */
|
||||||
addr = start;
|
addr = start;
|
||||||
|
|||||||
+2
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -16,6 +16,7 @@
|
|||||||
|
|
||||||
#define NAMESERVER_PORT 53
|
#define NAMESERVER_PORT 53
|
||||||
#define TFTP_PORT 69
|
#define TFTP_PORT 69
|
||||||
|
#define MAX_PORT 65535u
|
||||||
|
|
||||||
#define IN6ADDRSZ 16
|
#define IN6ADDRSZ 16
|
||||||
#define INADDRSZ 4
|
#define INADDRSZ 4
|
||||||
|
|||||||
+31
-8
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -169,8 +169,16 @@ int main (int argc, char **argv)
|
|||||||
if (option_bool(OPT_DNSSEC_VALID))
|
if (option_bool(OPT_DNSSEC_VALID))
|
||||||
{
|
{
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
if (!daemon->ds)
|
struct ds_config *ds;
|
||||||
die(_("no trust anchors provided for DNSSEC"), NULL, EC_BADCONF);
|
|
||||||
|
/* Must have at least a root trust anchor, or the DNSSEC code
|
||||||
|
can loop forever. */
|
||||||
|
for (ds = daemon->ds; ds; ds = ds->next)
|
||||||
|
if (ds->name[0] == 0)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (!ds)
|
||||||
|
die(_("no root trust anchor provided for DNSSEC"), NULL, EC_BADCONF);
|
||||||
|
|
||||||
if (daemon->cachesize < CACHESIZ)
|
if (daemon->cachesize < CACHESIZ)
|
||||||
die(_("cannot reduce cache size from default when DNSSEC enabled"), NULL, EC_BADCONF);
|
die(_("cannot reduce cache size from default when DNSSEC enabled"), NULL, EC_BADCONF);
|
||||||
@@ -212,6 +220,12 @@ int main (int argc, char **argv)
|
|||||||
die(_("loop detection not available: set HAVE_LOOP in src/config.h"), NULL, EC_BADCONF);
|
die(_("loop detection not available: set HAVE_LOOP in src/config.h"), NULL, EC_BADCONF);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
if (daemon->max_port != MAX_PORT && daemon->min_port == 0)
|
||||||
|
daemon->min_port = 1024u;
|
||||||
|
|
||||||
|
if (daemon->max_port < daemon->min_port)
|
||||||
|
die(_("max_port cannot be smaller than min_port"), NULL, EC_BADCONF);
|
||||||
|
|
||||||
now = dnsmasq_time();
|
now = dnsmasq_time();
|
||||||
|
|
||||||
/* Create a serial at startup if not configured. */
|
/* Create a serial at startup if not configured. */
|
||||||
@@ -246,10 +260,10 @@ int main (int argc, char **argv)
|
|||||||
creating any file descriptors which shouldn't be leaked
|
creating any file descriptors which shouldn't be leaked
|
||||||
to the lease-script init process. We need to call common_init
|
to the lease-script init process. We need to call common_init
|
||||||
before lease_init to allocate buffers it uses.
|
before lease_init to allocate buffers it uses.
|
||||||
The script subsystrm relies on DHCP buffers, hence the last two
|
The script subsystem relies on DHCP buffers, hence the last two
|
||||||
conditions below. */
|
conditions below. */
|
||||||
if (daemon->dhcp || daemon->doing_dhcp6 || daemon->relay4 ||
|
if (daemon->dhcp || daemon->doing_dhcp6 || daemon->relay4 ||
|
||||||
daemon->relay6 || option_bool(OPT_TFTP) || option_bool(OPT_DNS_CLIENT))
|
daemon->relay6 || option_bool(OPT_TFTP) || option_bool(OPT_SCRIPT_ARP))
|
||||||
{
|
{
|
||||||
dhcp_common_init();
|
dhcp_common_init();
|
||||||
if (daemon->dhcp || daemon->doing_dhcp6)
|
if (daemon->dhcp || daemon->doing_dhcp6)
|
||||||
@@ -556,7 +570,7 @@ int main (int argc, char **argv)
|
|||||||
/* if we are to run scripts, we need to fork a helper before dropping root. */
|
/* if we are to run scripts, we need to fork a helper before dropping root. */
|
||||||
daemon->helperfd = -1;
|
daemon->helperfd = -1;
|
||||||
#ifdef HAVE_SCRIPT
|
#ifdef HAVE_SCRIPT
|
||||||
if ((daemon->dhcp || daemon->dhcp6 || option_bool(OPT_TFTP) || option_bool(OPT_DNS_CLIENT)) &&
|
if ((daemon->dhcp || daemon->dhcp6 || option_bool(OPT_TFTP) || option_bool(OPT_SCRIPT_ARP)) &&
|
||||||
(daemon->lease_change_command || daemon->luascript))
|
(daemon->lease_change_command || daemon->luascript))
|
||||||
daemon->helperfd = create_helper(pipewrite, err_pipe[1], script_uid, script_gid, max_fd);
|
daemon->helperfd = create_helper(pipewrite, err_pipe[1], script_uid, script_gid, max_fd);
|
||||||
#endif
|
#endif
|
||||||
@@ -919,7 +933,13 @@ int main (int argc, char **argv)
|
|||||||
poll_listen(piperead, POLLIN);
|
poll_listen(piperead, POLLIN);
|
||||||
|
|
||||||
#ifdef HAVE_SCRIPT
|
#ifdef HAVE_SCRIPT
|
||||||
|
# ifdef HAVE_DHCP
|
||||||
while (helper_buf_empty() && do_script_run(now));
|
while (helper_buf_empty() && do_script_run(now));
|
||||||
|
# endif
|
||||||
|
|
||||||
|
/* Refresh cache */
|
||||||
|
if (option_bool(OPT_SCRIPT_ARP))
|
||||||
|
find_mac(NULL, NULL, 0, now);
|
||||||
while (helper_buf_empty() && do_arp_script_run());
|
while (helper_buf_empty() && do_arp_script_run());
|
||||||
|
|
||||||
# ifdef HAVE_TFTP
|
# ifdef HAVE_TFTP
|
||||||
@@ -930,8 +950,11 @@ int main (int argc, char **argv)
|
|||||||
poll_listen(daemon->helperfd, POLLOUT);
|
poll_listen(daemon->helperfd, POLLOUT);
|
||||||
#else
|
#else
|
||||||
/* need this for other side-effects */
|
/* need this for other side-effects */
|
||||||
|
# ifdef HAVE_DHCP
|
||||||
while (do_script_run(now));
|
while (do_script_run(now));
|
||||||
while (do_arp_script_run(now));
|
# endif
|
||||||
|
|
||||||
|
while (do_arp_script_run());
|
||||||
|
|
||||||
# ifdef HAVE_TFTP
|
# ifdef HAVE_TFTP
|
||||||
while (do_tftp_script_run());
|
while (do_tftp_script_run());
|
||||||
@@ -1312,7 +1335,7 @@ static void async_event(int pipe, time_t now)
|
|||||||
if (daemon->tcp_pids[i] != 0)
|
if (daemon->tcp_pids[i] != 0)
|
||||||
kill(daemon->tcp_pids[i], SIGALRM);
|
kill(daemon->tcp_pids[i], SIGALRM);
|
||||||
|
|
||||||
#if defined(HAVE_SCRIPT)
|
#if defined(HAVE_SCRIPT) && defined(HAVE_DHCP)
|
||||||
/* handle pending lease transitions */
|
/* handle pending lease transitions */
|
||||||
if (daemon->helperfd != -1)
|
if (daemon->helperfd != -1)
|
||||||
{
|
{
|
||||||
|
|||||||
+9
-6
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -14,7 +14,7 @@
|
|||||||
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#define COPYRIGHT "Copyright (c) 2000-2015 Simon Kelley"
|
#define COPYRIGHT "Copyright (c) 2000-2016 Simon Kelley"
|
||||||
|
|
||||||
#ifndef NO_LARGEFILE
|
#ifndef NO_LARGEFILE
|
||||||
/* Ensure we can use files >2GB (log files may grow this big) */
|
/* Ensure we can use files >2GB (log files may grow this big) */
|
||||||
@@ -235,8 +235,10 @@ struct event_desc {
|
|||||||
#define OPT_LOOP_DETECT 50
|
#define OPT_LOOP_DETECT 50
|
||||||
#define OPT_EXTRALOG 51
|
#define OPT_EXTRALOG 51
|
||||||
#define OPT_TFTP_NO_FAIL 52
|
#define OPT_TFTP_NO_FAIL 52
|
||||||
#define OPT_DNS_CLIENT 53
|
#define OPT_SCRIPT_ARP 53
|
||||||
#define OPT_LAST 54
|
#define OPT_MAC_B64 54
|
||||||
|
#define OPT_MAC_HEX 55
|
||||||
|
#define OPT_LAST 56
|
||||||
|
|
||||||
/* extra flags for my_syslog, we use a couple of facilities since they are known
|
/* extra flags for my_syslog, we use a couple of facilities since they are known
|
||||||
not to occupy the same bits as priorities, no matter how syslog.h is set up. */
|
not to occupy the same bits as priorities, no matter how syslog.h is set up. */
|
||||||
@@ -477,6 +479,7 @@ union mysockaddr {
|
|||||||
#define SERV_NO_REBIND 2048 /* inhibit dns-rebind protection */
|
#define SERV_NO_REBIND 2048 /* inhibit dns-rebind protection */
|
||||||
#define SERV_FROM_FILE 4096 /* read from --servers-file */
|
#define SERV_FROM_FILE 4096 /* read from --servers-file */
|
||||||
#define SERV_LOOP 8192 /* server causes forwarding loop */
|
#define SERV_LOOP 8192 /* server causes forwarding loop */
|
||||||
|
#define SERV_DO_DNSSEC 16384 /* Validate DNSSEC when using this server */
|
||||||
|
|
||||||
struct serverfd {
|
struct serverfd {
|
||||||
int fd;
|
int fd;
|
||||||
@@ -635,7 +638,7 @@ struct frec {
|
|||||||
#define ACTION_ADD 4
|
#define ACTION_ADD 4
|
||||||
#define ACTION_TFTP 5
|
#define ACTION_TFTP 5
|
||||||
#define ACTION_ARP 6
|
#define ACTION_ARP 6
|
||||||
#define ACTION_ARP_OLD 7
|
#define ACTION_ARP_DEL 7
|
||||||
|
|
||||||
#define LEASE_NEW 1 /* newly created */
|
#define LEASE_NEW 1 /* newly created */
|
||||||
#define LEASE_CHANGED 2 /* modified */
|
#define LEASE_CHANGED 2 /* modified */
|
||||||
@@ -949,7 +952,7 @@ extern struct daemon {
|
|||||||
char *log_file; /* optional log file */
|
char *log_file; /* optional log file */
|
||||||
int max_logs; /* queue limit */
|
int max_logs; /* queue limit */
|
||||||
int cachesize, ftabsize;
|
int cachesize, ftabsize;
|
||||||
int port, query_port, min_port;
|
int port, query_port, min_port, max_port;
|
||||||
unsigned long local_ttl, neg_ttl, max_ttl, min_cache_ttl, max_cache_ttl, auth_ttl;
|
unsigned long local_ttl, neg_ttl, max_ttl, min_cache_ttl, max_cache_ttl, auth_ttl;
|
||||||
char *dns_client_id;
|
char *dns_client_id;
|
||||||
struct hostsfile *addn_hosts;
|
struct hostsfile *addn_hosts;
|
||||||
|
|||||||
+19
-2
@@ -1,5 +1,5 @@
|
|||||||
/* dnssec.c is Copyright (c) 2012 Giovanni Bajo <rasky@develer.com>
|
/* dnssec.c is Copyright (c) 2012 Giovanni Bajo <rasky@develer.com>
|
||||||
and Copyright (c) 2012-2015 Simon Kelley
|
and Copyright (c) 2012-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -1873,10 +1873,27 @@ static int prove_non_existence(struct dns_header *header, size_t plen, char *key
|
|||||||
*/
|
*/
|
||||||
static int zone_status(char *name, int class, char *keyname, time_t now)
|
static int zone_status(char *name, int class, char *keyname, time_t now)
|
||||||
{
|
{
|
||||||
int name_start = strlen(name);
|
int name_start = strlen(name); /* for when TA is root */
|
||||||
struct crec *crecp;
|
struct crec *crecp;
|
||||||
char *p;
|
char *p;
|
||||||
|
|
||||||
|
/* First, work towards the root, looking for a trust anchor.
|
||||||
|
This can either be one configured, or one previously cached.
|
||||||
|
We can assume, if we don't find one first, that there is
|
||||||
|
a trust anchor at the root. */
|
||||||
|
for (p = name; p; p = strchr(p, '.'))
|
||||||
|
{
|
||||||
|
if (*p == '.')
|
||||||
|
p++;
|
||||||
|
|
||||||
|
if (cache_find_by_name(NULL, p, now, F_DS))
|
||||||
|
{
|
||||||
|
name_start = p - name;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* Now work away from the trust anchor */
|
||||||
while (1)
|
while (1)
|
||||||
{
|
{
|
||||||
strcpy(keyname, &name[name_start]);
|
strcpy(keyname, &name[name_start]);
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+16
-11
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -223,20 +223,21 @@ static size_t add_dns_client(struct dns_header *header, size_t plen, unsigned ch
|
|||||||
{
|
{
|
||||||
int maclen;
|
int maclen;
|
||||||
unsigned char mac[DHCP_CHADDR_MAX];
|
unsigned char mac[DHCP_CHADDR_MAX];
|
||||||
char encode[8]; /* handle 6 byte MACs */
|
char encode[18]; /* handle 6 byte MACs */
|
||||||
|
|
||||||
if ((maclen = find_mac(l3, mac, 1, now)) == 6)
|
if ((maclen = find_mac(l3, mac, 1, now)) == 6)
|
||||||
{
|
{
|
||||||
encoder(mac, encode);
|
if (option_bool(OPT_MAC_HEX))
|
||||||
encoder(mac+3, encode+4);
|
print_mac(encode, mac, maclen);
|
||||||
|
else
|
||||||
plen = add_pseudoheader(header, plen, limit, PACKETSZ, EDNS0_OPTION_NOMDEVICEID, (unsigned char *)encode, 8, 0);
|
{
|
||||||
|
encoder(mac, encode);
|
||||||
|
encoder(mac+3, encode+4);
|
||||||
|
encode[8] = 0;
|
||||||
|
}
|
||||||
|
plen = add_pseudoheader(header, plen, limit, PACKETSZ, EDNS0_OPTION_NOMDEVICEID, (unsigned char *)encode, strlen(encode), 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (daemon->dns_client_id)
|
|
||||||
plen = add_pseudoheader(header, plen, limit, PACKETSZ, EDNS0_OPTION_NOMCPEID,
|
|
||||||
(unsigned char *)daemon->dns_client_id, strlen(daemon->dns_client_id), 0);
|
|
||||||
|
|
||||||
return plen;
|
return plen;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -381,9 +382,13 @@ size_t add_edns0_config(struct dns_header *header, size_t plen, unsigned char *l
|
|||||||
if (option_bool(OPT_ADD_MAC))
|
if (option_bool(OPT_ADD_MAC))
|
||||||
plen = add_mac(header, plen, limit, source, now);
|
plen = add_mac(header, plen, limit, source, now);
|
||||||
|
|
||||||
if (option_bool(OPT_DNS_CLIENT))
|
if (option_bool(OPT_MAC_B64) || option_bool(OPT_MAC_HEX))
|
||||||
plen = add_dns_client(header, plen, limit, source, now);
|
plen = add_dns_client(header, plen, limit, source, now);
|
||||||
|
|
||||||
|
if (daemon->dns_client_id)
|
||||||
|
plen = add_pseudoheader(header, plen, limit, PACKETSZ, EDNS0_OPTION_NOMCPEID,
|
||||||
|
(unsigned char *)daemon->dns_client_id, strlen(daemon->dns_client_id), 0);
|
||||||
|
|
||||||
if (option_bool(OPT_CLIENT_SUBNET))
|
if (option_bool(OPT_CLIENT_SUBNET))
|
||||||
{
|
{
|
||||||
plen = add_source_addr(header, plen, limit, source);
|
plen = add_source_addr(header, plen, limit, source);
|
||||||
|
|||||||
+174
-43
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -106,8 +106,8 @@ int send_from(int fd, int nowild, char *packet, size_t len,
|
|||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
static unsigned int search_servers(time_t now, struct all_addr **addrpp,
|
static unsigned int search_servers(time_t now, struct all_addr **addrpp, unsigned int qtype,
|
||||||
unsigned int qtype, char *qdomain, int *type, char **domain, int *norebind)
|
char *qdomain, int *type, char **domain, int *norebind)
|
||||||
|
|
||||||
{
|
{
|
||||||
/* If the query ends in the domain in one of our servers, set
|
/* If the query ends in the domain in one of our servers, set
|
||||||
@@ -151,7 +151,7 @@ static unsigned int search_servers(time_t now, struct all_addr **addrpp,
|
|||||||
hostname_isequal(matchstart, serv->domain) &&
|
hostname_isequal(matchstart, serv->domain) &&
|
||||||
(domainlen == 0 || namelen == domainlen || *(matchstart-1) == '.' ))
|
(domainlen == 0 || namelen == domainlen || *(matchstart-1) == '.' ))
|
||||||
{
|
{
|
||||||
if (serv->flags & SERV_NO_REBIND)
|
if ((serv->flags & SERV_NO_REBIND) && norebind)
|
||||||
*norebind = 1;
|
*norebind = 1;
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -175,7 +175,7 @@ static unsigned int search_servers(time_t now, struct all_addr **addrpp,
|
|||||||
|
|
||||||
if (domainlen >= matchlen)
|
if (domainlen >= matchlen)
|
||||||
{
|
{
|
||||||
*type = serv->flags & (SERV_HAS_DOMAIN | SERV_USE_RESOLV | SERV_NO_REBIND);
|
*type = serv->flags & (SERV_HAS_DOMAIN | SERV_USE_RESOLV | SERV_NO_REBIND | SERV_DO_DNSSEC);
|
||||||
*domain = serv->domain;
|
*domain = serv->domain;
|
||||||
matchlen = domainlen;
|
matchlen = domainlen;
|
||||||
if (serv->flags & SERV_NO_ADDR)
|
if (serv->flags & SERV_NO_ADDR)
|
||||||
@@ -233,12 +233,13 @@ static int forward_query(int udpfd, union mysockaddr *udpaddr,
|
|||||||
struct frec *forward, int ad_reqd, int do_bit)
|
struct frec *forward, int ad_reqd, int do_bit)
|
||||||
{
|
{
|
||||||
char *domain = NULL;
|
char *domain = NULL;
|
||||||
int type = 0, norebind = 0;
|
int type = SERV_DO_DNSSEC, norebind = 0;
|
||||||
struct all_addr *addrp = NULL;
|
struct all_addr *addrp = NULL;
|
||||||
unsigned int flags = 0;
|
unsigned int flags = 0;
|
||||||
struct server *start = NULL;
|
struct server *start = NULL;
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
void *hash = hash_questions(header, plen, daemon->namebuff);
|
void *hash = hash_questions(header, plen, daemon->namebuff);
|
||||||
|
int do_dnssec = 0;
|
||||||
#else
|
#else
|
||||||
unsigned int crc = questions_crc(header, plen, daemon->namebuff);
|
unsigned int crc = questions_crc(header, plen, daemon->namebuff);
|
||||||
void *hash = &crc;
|
void *hash = &crc;
|
||||||
@@ -248,9 +249,7 @@ static int forward_query(int udpfd, union mysockaddr *udpaddr,
|
|||||||
(void)do_bit;
|
(void)do_bit;
|
||||||
|
|
||||||
/* may be no servers available. */
|
/* may be no servers available. */
|
||||||
if (!daemon->servers)
|
if (forward || (hash && (forward = lookup_frec_by_sender(ntohs(header->id), udpaddr, hash))))
|
||||||
forward = NULL;
|
|
||||||
else if (forward || (hash && (forward = lookup_frec_by_sender(ntohs(header->id), udpaddr, hash))))
|
|
||||||
{
|
{
|
||||||
/* If we didn't get an answer advertising a maximal packet in EDNS,
|
/* If we didn't get an answer advertising a maximal packet in EDNS,
|
||||||
fall back to 1280, which should work everywhere on IPv6.
|
fall back to 1280, which should work everywhere on IPv6.
|
||||||
@@ -315,6 +314,10 @@ static int forward_query(int udpfd, union mysockaddr *udpaddr,
|
|||||||
daemon->last_server = NULL;
|
daemon->last_server = NULL;
|
||||||
}
|
}
|
||||||
type = forward->sentto->flags & SERV_TYPE;
|
type = forward->sentto->flags & SERV_TYPE;
|
||||||
|
#ifdef HAVE_DNSSEC
|
||||||
|
do_dnssec = forward->sentto->flags & SERV_DO_DNSSEC;
|
||||||
|
#endif
|
||||||
|
|
||||||
if (!(start = forward->sentto->next))
|
if (!(start = forward->sentto->next))
|
||||||
start = daemon->servers; /* at end of list, recycle */
|
start = daemon->servers; /* at end of list, recycle */
|
||||||
header->id = htons(forward->new_id);
|
header->id = htons(forward->new_id);
|
||||||
@@ -324,9 +327,14 @@ static int forward_query(int udpfd, union mysockaddr *udpaddr,
|
|||||||
if (gotname)
|
if (gotname)
|
||||||
flags = search_servers(now, &addrp, gotname, daemon->namebuff, &type, &domain, &norebind);
|
flags = search_servers(now, &addrp, gotname, daemon->namebuff, &type, &domain, &norebind);
|
||||||
|
|
||||||
if (!flags && !(forward = get_new_frec(now, NULL, 0)))
|
#ifdef HAVE_DNSSEC
|
||||||
/* table full - server failure. */
|
do_dnssec = type & SERV_DO_DNSSEC;
|
||||||
flags = F_NEG;
|
#endif
|
||||||
|
type &= ~SERV_DO_DNSSEC;
|
||||||
|
|
||||||
|
if (daemon->servers && !flags)
|
||||||
|
forward = get_new_frec(now, NULL, 0);
|
||||||
|
/* table full - flags == 0, return REFUSED */
|
||||||
|
|
||||||
if (forward)
|
if (forward)
|
||||||
{
|
{
|
||||||
@@ -406,7 +414,7 @@ static int forward_query(int udpfd, union mysockaddr *udpaddr,
|
|||||||
}
|
}
|
||||||
|
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
if (option_bool(OPT_DNSSEC_VALID))
|
if (option_bool(OPT_DNSSEC_VALID) && do_dnssec)
|
||||||
{
|
{
|
||||||
size_t new = add_do_bit(header, plen, ((unsigned char *) header) + PACKETSZ);
|
size_t new = add_do_bit(header, plen, ((unsigned char *) header) + PACKETSZ);
|
||||||
|
|
||||||
@@ -634,7 +642,7 @@ static size_t process_reply(struct dns_header *header, time_t now, struct server
|
|||||||
return resize_packet(header, n, pheader, plen);
|
return resize_packet(header, n, pheader, plen);
|
||||||
|
|
||||||
/* Complain loudly if the upstream server is non-recursive. */
|
/* Complain loudly if the upstream server is non-recursive. */
|
||||||
if (!(header->hb4 & HB4_RA) && RCODE(header) == NOERROR && ntohs(header->ancount) == 0 &&
|
if (!(header->hb4 & HB4_RA) && RCODE(header) == NOERROR &&
|
||||||
server && !(server->flags & SERV_WARNED_RECURSIVE))
|
server && !(server->flags & SERV_WARNED_RECURSIVE))
|
||||||
{
|
{
|
||||||
prettyprint_addr(&server->addr, daemon->namebuff);
|
prettyprint_addr(&server->addr, daemon->namebuff);
|
||||||
@@ -800,9 +808,9 @@ void reply_query(int fd, int family, time_t now)
|
|||||||
{
|
{
|
||||||
header->hb3 &= ~(HB3_QR | HB3_AA | HB3_TC);
|
header->hb3 &= ~(HB3_QR | HB3_AA | HB3_TC);
|
||||||
header->hb4 &= ~(HB4_RA | HB4_RCODE | HB4_CD | HB4_AD);
|
header->hb4 &= ~(HB4_RA | HB4_RCODE | HB4_CD | HB4_AD);
|
||||||
if (forward->flags |= FREC_CHECKING_DISABLED)
|
if (forward->flags & FREC_CHECKING_DISABLED)
|
||||||
header->hb4 |= HB4_CD;
|
header->hb4 |= HB4_CD;
|
||||||
if (forward->flags |= FREC_AD_QUESTION)
|
if (forward->flags & FREC_AD_QUESTION)
|
||||||
header->hb4 |= HB4_AD;
|
header->hb4 |= HB4_AD;
|
||||||
if (forward->flags & FREC_DO_QUESTION)
|
if (forward->flags & FREC_DO_QUESTION)
|
||||||
add_do_bit(header, nn, (unsigned char *)pheader + plen);
|
add_do_bit(header, nn, (unsigned char *)pheader + plen);
|
||||||
@@ -845,7 +853,7 @@ void reply_query(int fd, int family, time_t now)
|
|||||||
we get a good reply from another server. Kill it when we've
|
we get a good reply from another server. Kill it when we've
|
||||||
had replies from all to avoid filling the forwarding table when
|
had replies from all to avoid filling the forwarding table when
|
||||||
everything is broken */
|
everything is broken */
|
||||||
if (forward->forwardall == 0 || --forward->forwardall == 1 || RCODE(header) != SERVFAIL)
|
if (forward->forwardall == 0 || --forward->forwardall == 1 || RCODE(header) != REFUSED)
|
||||||
{
|
{
|
||||||
int check_rebind = 0, no_cache_dnssec = 0, cache_secure = 0, bogusanswer = 0;
|
int check_rebind = 0, no_cache_dnssec = 0, cache_secure = 0, bogusanswer = 0;
|
||||||
|
|
||||||
@@ -858,7 +866,8 @@ void reply_query(int fd, int family, time_t now)
|
|||||||
no_cache_dnssec = 1;
|
no_cache_dnssec = 1;
|
||||||
|
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
if (server && option_bool(OPT_DNSSEC_VALID) && !(forward->flags & FREC_CHECKING_DISABLED))
|
if (server && (server->flags & SERV_DO_DNSSEC) &&
|
||||||
|
option_bool(OPT_DNSSEC_VALID) && !(forward->flags & FREC_CHECKING_DISABLED))
|
||||||
{
|
{
|
||||||
int status = 0;
|
int status = 0;
|
||||||
|
|
||||||
@@ -912,12 +921,48 @@ void reply_query(int fd, int family, time_t now)
|
|||||||
status = STAT_ABANDONED;
|
status = STAT_ABANDONED;
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
int fd;
|
int fd, type = SERV_DO_DNSSEC;
|
||||||
struct frec *next = new->next;
|
struct frec *next = new->next;
|
||||||
|
char *domain;
|
||||||
|
|
||||||
*new = *forward; /* copy everything, then overwrite */
|
*new = *forward; /* copy everything, then overwrite */
|
||||||
new->next = next;
|
new->next = next;
|
||||||
new->blocking_query = NULL;
|
new->blocking_query = NULL;
|
||||||
|
|
||||||
|
/* Find server to forward to. This will normally be the
|
||||||
|
same as for the original query, but may be another if
|
||||||
|
servers for domains are involved. */
|
||||||
|
if (search_servers(now, NULL, F_QUERY, daemon->keyname, &type, &domain, NULL) == 0)
|
||||||
|
{
|
||||||
|
struct server *start = server, *new_server = NULL;
|
||||||
|
type &= ~SERV_DO_DNSSEC;
|
||||||
|
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
if (type == (start->flags & SERV_TYPE) &&
|
||||||
|
(type != SERV_HAS_DOMAIN || hostname_isequal(domain, start->domain)) &&
|
||||||
|
!(start->flags & (SERV_LITERAL_ADDRESS | SERV_LOOP)))
|
||||||
|
{
|
||||||
|
new_server = start;
|
||||||
|
if (server == start)
|
||||||
|
{
|
||||||
|
new_server = NULL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(start = start->next))
|
||||||
|
start = daemon->servers;
|
||||||
|
if (start == server)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (new_server)
|
||||||
|
server = new_server;
|
||||||
|
}
|
||||||
|
|
||||||
new->sentto = server;
|
new->sentto = server;
|
||||||
|
|
||||||
new->rfd4 = NULL;
|
new->rfd4 = NULL;
|
||||||
#ifdef HAVE_IPV6
|
#ifdef HAVE_IPV6
|
||||||
new->rfd6 = NULL;
|
new->rfd6 = NULL;
|
||||||
@@ -971,6 +1016,15 @@ void reply_query(int fd, int family, time_t now)
|
|||||||
|
|
||||||
if (fd != -1)
|
if (fd != -1)
|
||||||
{
|
{
|
||||||
|
#ifdef HAVE_CONNTRACK
|
||||||
|
/* Copy connection mark of incoming query to outgoing connection. */
|
||||||
|
if (option_bool(OPT_CONNTRACK))
|
||||||
|
{
|
||||||
|
unsigned int mark;
|
||||||
|
if (get_incoming_mark(&orig->source, &orig->dest, 0, &mark))
|
||||||
|
setsockopt(fd, SOL_SOCKET, SO_MARK, &mark, sizeof(unsigned int));
|
||||||
|
}
|
||||||
|
#endif
|
||||||
while (retry_send(sendto(fd, (char *)header, nn, 0,
|
while (retry_send(sendto(fd, (char *)header, nn, 0,
|
||||||
&server->addr.sa,
|
&server->addr.sa,
|
||||||
sa_len(&server->addr))));
|
sa_len(&server->addr))));
|
||||||
@@ -1033,7 +1087,7 @@ void reply_query(int fd, int family, time_t now)
|
|||||||
else
|
else
|
||||||
header->hb4 &= ~HB4_CD;
|
header->hb4 &= ~HB4_CD;
|
||||||
|
|
||||||
if ((nn = process_reply(header, now, server, (size_t)n, check_rebind, no_cache_dnssec, cache_secure, bogusanswer,
|
if ((nn = process_reply(header, now, forward->sentto, (size_t)n, check_rebind, no_cache_dnssec, cache_secure, bogusanswer,
|
||||||
forward->flags & FREC_AD_QUESTION, forward->flags & FREC_DO_QUESTION,
|
forward->flags & FREC_AD_QUESTION, forward->flags & FREC_DO_QUESTION,
|
||||||
forward->flags & FREC_ADDED_PHEADER, forward->flags & FREC_HAS_SUBNET, &forward->source)))
|
forward->flags & FREC_ADDED_PHEADER, forward->flags & FREC_HAS_SUBNET, &forward->source)))
|
||||||
{
|
{
|
||||||
@@ -1394,20 +1448,24 @@ void receive_query(struct listener *listen, time_t now)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
|
/* Recurse up the key heirarchy */
|
||||||
static int tcp_key_recurse(time_t now, int status, struct dns_header *header, size_t n,
|
static int tcp_key_recurse(time_t now, int status, struct dns_header *header, size_t n,
|
||||||
int class, char *name, char *keyname, struct server *server, int *keycount)
|
int class, char *name, char *keyname, struct server *server,
|
||||||
|
int have_mark, unsigned int mark, int *keycount)
|
||||||
{
|
{
|
||||||
/* Recurse up the key heirarchy */
|
|
||||||
int new_status;
|
int new_status;
|
||||||
unsigned char *packet = NULL;
|
unsigned char *packet = NULL;
|
||||||
size_t m;
|
|
||||||
unsigned char *payload = NULL;
|
unsigned char *payload = NULL;
|
||||||
struct dns_header *new_header = NULL;
|
struct dns_header *new_header = NULL;
|
||||||
u16 *length = NULL;
|
u16 *length = NULL;
|
||||||
unsigned char c1, c2;
|
|
||||||
|
|
||||||
while (1)
|
while (1)
|
||||||
{
|
{
|
||||||
|
int type = SERV_DO_DNSSEC;
|
||||||
|
char *domain;
|
||||||
|
size_t m;
|
||||||
|
unsigned char c1, c2;
|
||||||
|
|
||||||
/* limit the amount of work we do, to avoid cycling forever on loops in the DNS */
|
/* limit the amount of work we do, to avoid cycling forever on loops in the DNS */
|
||||||
if (--(*keycount) == 0)
|
if (--(*keycount) == 0)
|
||||||
new_status = STAT_ABANDONED;
|
new_status = STAT_ABANDONED;
|
||||||
@@ -1442,6 +1500,67 @@ static int tcp_key_recurse(time_t now, int status, struct dns_header *header, si
|
|||||||
|
|
||||||
*length = htons(m);
|
*length = htons(m);
|
||||||
|
|
||||||
|
/* Find server to forward to. This will normally be the
|
||||||
|
same as for the original query, but may be another if
|
||||||
|
servers for domains are involved. */
|
||||||
|
if (search_servers(now, NULL, F_QUERY, keyname, &type, &domain, NULL) == 0)
|
||||||
|
{
|
||||||
|
struct server *start = server, *new_server = NULL;
|
||||||
|
type &= ~SERV_DO_DNSSEC;
|
||||||
|
|
||||||
|
while (1)
|
||||||
|
{
|
||||||
|
if (type == (start->flags & SERV_TYPE) &&
|
||||||
|
(type != SERV_HAS_DOMAIN || hostname_isequal(domain, start->domain)) &&
|
||||||
|
!(start->flags & (SERV_LITERAL_ADDRESS | SERV_LOOP)))
|
||||||
|
{
|
||||||
|
new_server = start;
|
||||||
|
if (server == start)
|
||||||
|
{
|
||||||
|
new_server = NULL;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(start = start->next))
|
||||||
|
start = daemon->servers;
|
||||||
|
if (start == server)
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if (new_server)
|
||||||
|
{
|
||||||
|
server = new_server;
|
||||||
|
/* may need to make new connection. */
|
||||||
|
if (server->tcpfd == -1)
|
||||||
|
{
|
||||||
|
if ((server->tcpfd = socket(server->addr.sa.sa_family, SOCK_STREAM, 0)) == -1)
|
||||||
|
{
|
||||||
|
new_status = STAT_ABANDONED;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
#ifdef HAVE_CONNTRACK
|
||||||
|
/* Copy connection mark of incoming query to outgoing connection. */
|
||||||
|
if (have_mark)
|
||||||
|
setsockopt(server->tcpfd, SOL_SOCKET, SO_MARK, &mark, sizeof(unsigned int));
|
||||||
|
#endif
|
||||||
|
|
||||||
|
if (!local_bind(server->tcpfd, &server->source_addr, server->interface, 1) ||
|
||||||
|
connect(server->tcpfd, &server->addr.sa, sa_len(&server->addr)) == -1)
|
||||||
|
{
|
||||||
|
close(server->tcpfd);
|
||||||
|
server->tcpfd = -1;
|
||||||
|
new_status = STAT_ABANDONED;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
if (!read_write(server->tcpfd, packet, m + sizeof(u16), 0) ||
|
if (!read_write(server->tcpfd, packet, m + sizeof(u16), 0) ||
|
||||||
!read_write(server->tcpfd, &c1, 1, 1) ||
|
!read_write(server->tcpfd, &c1, 1, 1) ||
|
||||||
!read_write(server->tcpfd, &c2, 1, 1) ||
|
!read_write(server->tcpfd, &c2, 1, 1) ||
|
||||||
@@ -1453,7 +1572,7 @@ static int tcp_key_recurse(time_t now, int status, struct dns_header *header, si
|
|||||||
|
|
||||||
m = (c1 << 8) | c2;
|
m = (c1 << 8) | c2;
|
||||||
|
|
||||||
new_status = tcp_key_recurse(now, new_status, new_header, m, class, name, keyname, server, keycount);
|
new_status = tcp_key_recurse(now, new_status, new_header, m, class, name, keyname, server, have_mark, mark, keycount);
|
||||||
|
|
||||||
if (new_status != STAT_OK)
|
if (new_status != STAT_OK)
|
||||||
break;
|
break;
|
||||||
@@ -1497,10 +1616,31 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
socklen_t peer_len = sizeof(union mysockaddr);
|
socklen_t peer_len = sizeof(union mysockaddr);
|
||||||
int query_count = 0;
|
int query_count = 0;
|
||||||
unsigned char *pheader;
|
unsigned char *pheader;
|
||||||
|
unsigned int mark = 0;
|
||||||
|
int have_mark = 0;
|
||||||
|
|
||||||
|
(void)mark;
|
||||||
|
(void)have_mark;
|
||||||
|
|
||||||
if (getpeername(confd, (struct sockaddr *)&peer_addr, &peer_len) == -1)
|
if (getpeername(confd, (struct sockaddr *)&peer_addr, &peer_len) == -1)
|
||||||
return packet;
|
return packet;
|
||||||
|
|
||||||
|
#ifdef HAVE_CONNTRACK
|
||||||
|
/* Get connection mark of incoming query to set on outgoing connections. */
|
||||||
|
if (option_bool(OPT_CONNTRACK))
|
||||||
|
{
|
||||||
|
struct all_addr local;
|
||||||
|
#ifdef HAVE_IPV6
|
||||||
|
if (local_addr->sa.sa_family == AF_INET6)
|
||||||
|
local.addr.addr6 = local_addr->in6.sin6_addr;
|
||||||
|
else
|
||||||
|
#endif
|
||||||
|
local.addr.addr4 = local_addr->in.sin_addr;
|
||||||
|
|
||||||
|
have_mark = get_incoming_mark(&peer_addr, &local, 1, &mark);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
/* We can be configured to only accept queries from at-most-one-hop-away addresses. */
|
/* We can be configured to only accept queries from at-most-one-hop-away addresses. */
|
||||||
if (option_bool(OPT_LOCAL_SERVICE))
|
if (option_bool(OPT_LOCAL_SERVICE))
|
||||||
{
|
{
|
||||||
@@ -1626,7 +1766,7 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
{
|
{
|
||||||
unsigned int flags = 0;
|
unsigned int flags = 0;
|
||||||
struct all_addr *addrp = NULL;
|
struct all_addr *addrp = NULL;
|
||||||
int type = 0;
|
int type = SERV_DO_DNSSEC;
|
||||||
char *domain = NULL;
|
char *domain = NULL;
|
||||||
size_t new_size = add_edns0_config(header, size, ((unsigned char *) header) + 65536, &peer_addr, now, &check_subnet);
|
size_t new_size = add_edns0_config(header, size, ((unsigned char *) header) + 65536, &peer_addr, now, &check_subnet);
|
||||||
|
|
||||||
@@ -1639,6 +1779,8 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
if (gotname)
|
if (gotname)
|
||||||
flags = search_servers(now, &addrp, gotname, daemon->namebuff, &type, &domain, &norebind);
|
flags = search_servers(now, &addrp, gotname, daemon->namebuff, &type, &domain, &norebind);
|
||||||
|
|
||||||
|
type &= ~SERV_DO_DNSSEC;
|
||||||
|
|
||||||
if (type != 0 || option_bool(OPT_ORDER) || !daemon->last_server)
|
if (type != 0 || option_bool(OPT_ORDER) || !daemon->last_server)
|
||||||
last_server = daemon->servers;
|
last_server = daemon->servers;
|
||||||
else
|
else
|
||||||
@@ -1685,20 +1827,8 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
|
|
||||||
#ifdef HAVE_CONNTRACK
|
#ifdef HAVE_CONNTRACK
|
||||||
/* Copy connection mark of incoming query to outgoing connection. */
|
/* Copy connection mark of incoming query to outgoing connection. */
|
||||||
if (option_bool(OPT_CONNTRACK))
|
if (have_mark)
|
||||||
{
|
setsockopt(last_server->tcpfd, SOL_SOCKET, SO_MARK, &mark, sizeof(unsigned int));
|
||||||
unsigned int mark;
|
|
||||||
struct all_addr local;
|
|
||||||
#ifdef HAVE_IPV6
|
|
||||||
if (local_addr->sa.sa_family == AF_INET6)
|
|
||||||
local.addr.addr6 = local_addr->in6.sin6_addr;
|
|
||||||
else
|
|
||||||
#endif
|
|
||||||
local.addr.addr4 = local_addr->in.sin_addr;
|
|
||||||
|
|
||||||
if (get_incoming_mark(&peer_addr, &local, 1, &mark))
|
|
||||||
setsockopt(last_server->tcpfd, SOL_SOCKET, SO_MARK, &mark, sizeof(unsigned int));
|
|
||||||
}
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if ((!local_bind(last_server->tcpfd, &last_server->source_addr, last_server->interface, 1) ||
|
if ((!local_bind(last_server->tcpfd, &last_server->source_addr, last_server->interface, 1) ||
|
||||||
@@ -1710,7 +1840,7 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
}
|
}
|
||||||
|
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
if (option_bool(OPT_DNSSEC_VALID))
|
if (option_bool(OPT_DNSSEC_VALID) && (last_server->flags & SERV_DO_DNSSEC))
|
||||||
{
|
{
|
||||||
new_size = add_do_bit(header, size, ((unsigned char *) header) + 65536);
|
new_size = add_do_bit(header, size, ((unsigned char *) header) + 65536);
|
||||||
|
|
||||||
@@ -1756,10 +1886,11 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
if (option_bool(OPT_DNSSEC_VALID) && !checking_disabled)
|
if (option_bool(OPT_DNSSEC_VALID) && !checking_disabled && (last_server->flags & SERV_DO_DNSSEC))
|
||||||
{
|
{
|
||||||
int keycount = DNSSEC_WORK; /* Limit to number of DNSSEC questions, to catch loops and avoid filling cache. */
|
int keycount = DNSSEC_WORK; /* Limit to number of DNSSEC questions, to catch loops and avoid filling cache. */
|
||||||
int status = tcp_key_recurse(now, STAT_OK, header, m, 0, daemon->namebuff, daemon->keyname, last_server, &keycount);
|
int status = tcp_key_recurse(now, STAT_OK, header, m, 0, daemon->namebuff, daemon->keyname,
|
||||||
|
last_server, have_mark, mark, &keycount);
|
||||||
char *result, *domain = "result";
|
char *result, *domain = "result";
|
||||||
|
|
||||||
if (status == STAT_ABANDONED)
|
if (status == STAT_ABANDONED)
|
||||||
|
|||||||
+5
-5
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -221,12 +221,12 @@ int create_helper(int event_fd, int err_fd, uid_t uid, gid_t gid, long max_fd)
|
|||||||
}
|
}
|
||||||
else if (data.action == ACTION_ARP)
|
else if (data.action == ACTION_ARP)
|
||||||
{
|
{
|
||||||
action_str = "arp";
|
action_str = "arp-add";
|
||||||
is6 = (data.flags != AF_INET);
|
is6 = (data.flags != AF_INET);
|
||||||
}
|
}
|
||||||
else if (data.action == ACTION_ARP_OLD)
|
else if (data.action == ACTION_ARP_DEL)
|
||||||
{
|
{
|
||||||
action_str = "arp-old";
|
action_str = "arp-del";
|
||||||
is6 = (data.flags != AF_INET);
|
is6 = (data.flags != AF_INET);
|
||||||
data.action = ACTION_ARP;
|
data.action = ACTION_ARP;
|
||||||
}
|
}
|
||||||
@@ -300,7 +300,7 @@ int create_helper(int event_fd, int err_fd, uid_t uid, gid_t gid, long max_fd)
|
|||||||
|
|
||||||
if (!is6)
|
if (!is6)
|
||||||
inet_ntop(AF_INET, &data.addr, daemon->addrbuff, ADDRSTRLEN);
|
inet_ntop(AF_INET, &data.addr, daemon->addrbuff, ADDRSTRLEN);
|
||||||
#ifdef HAVE_DHCP6
|
#ifdef HAVE_IPV6
|
||||||
else
|
else
|
||||||
inet_ntop(AF_INET6, &data.addr6, daemon->addrbuff, ADDRSTRLEN);
|
inet_ntop(AF_INET6, &data.addr6, daemon->addrbuff, ADDRSTRLEN);
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+42
-7
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -1119,7 +1119,7 @@ int random_sock(int family)
|
|||||||
if ((fd = socket(family, SOCK_DGRAM, 0)) != -1)
|
if ((fd = socket(family, SOCK_DGRAM, 0)) != -1)
|
||||||
{
|
{
|
||||||
union mysockaddr addr;
|
union mysockaddr addr;
|
||||||
unsigned int ports_avail = 65536u - (unsigned short)daemon->min_port;
|
unsigned int ports_avail = ((unsigned short)daemon->max_port - (unsigned short)daemon->min_port) + 1;
|
||||||
int tries = ports_avail < 30 ? 3 * ports_avail : 100;
|
int tries = ports_avail < 30 ? 3 * ports_avail : 100;
|
||||||
|
|
||||||
memset(&addr, 0, sizeof(addr));
|
memset(&addr, 0, sizeof(addr));
|
||||||
@@ -1132,8 +1132,8 @@ int random_sock(int family)
|
|||||||
{
|
{
|
||||||
unsigned short port = rand16();
|
unsigned short port = rand16();
|
||||||
|
|
||||||
if (daemon->min_port != 0)
|
if (daemon->min_port != 0 || daemon->max_port != MAX_PORT)
|
||||||
port = htons(daemon->min_port + (port % ((unsigned short)ports_avail)));
|
port = htons(daemon->min_port + (port % ((unsigned short)ports_avail)));
|
||||||
|
|
||||||
if (family == AF_INET)
|
if (family == AF_INET)
|
||||||
{
|
{
|
||||||
@@ -1430,10 +1430,41 @@ void check_servers(void)
|
|||||||
if (!option_bool(OPT_NOWILD))
|
if (!option_bool(OPT_NOWILD))
|
||||||
enumerate_interfaces(0);
|
enumerate_interfaces(0);
|
||||||
|
|
||||||
|
#ifdef HAVE_DNSSEC
|
||||||
|
/* Disable DNSSEC validation when using server=/domain/.... servers
|
||||||
|
unless there's a configured trust anchor. */
|
||||||
|
for (serv = daemon->servers; serv; serv = serv->next)
|
||||||
|
serv->flags |= SERV_DO_DNSSEC;
|
||||||
|
#endif
|
||||||
|
|
||||||
for (serv = daemon->servers; serv; serv = serv->next)
|
for (serv = daemon->servers; serv; serv = serv->next)
|
||||||
{
|
{
|
||||||
if (!(serv->flags & (SERV_LITERAL_ADDRESS | SERV_NO_ADDR | SERV_USE_RESOLV | SERV_NO_REBIND)))
|
if (!(serv->flags & (SERV_LITERAL_ADDRESS | SERV_NO_ADDR | SERV_USE_RESOLV | SERV_NO_REBIND)))
|
||||||
{
|
{
|
||||||
|
#ifdef HAVE_DNSSEC
|
||||||
|
if (option_bool(OPT_DNSSEC_VALID))
|
||||||
|
{
|
||||||
|
if (serv->flags & SERV_HAS_DOMAIN)
|
||||||
|
{
|
||||||
|
struct ds_config *ds;
|
||||||
|
char *domain = serv->domain;
|
||||||
|
|
||||||
|
/* .example.com is valid */
|
||||||
|
while (*domain == '.')
|
||||||
|
domain++;
|
||||||
|
|
||||||
|
for (ds = daemon->ds; ds; ds = ds->next)
|
||||||
|
if (ds->name[0] != 0 && hostname_isequal(domain, ds->name))
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (!ds)
|
||||||
|
serv->flags &= ~SERV_DO_DNSSEC;
|
||||||
|
}
|
||||||
|
else if (serv->flags & SERV_FOR_NODOTS)
|
||||||
|
serv->flags &= ~SERV_DO_DNSSEC;
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
port = prettyprint_addr(&serv->addr, daemon->namebuff);
|
port = prettyprint_addr(&serv->addr, daemon->namebuff);
|
||||||
|
|
||||||
/* 0.0.0.0 is nothing, the stack treats it like 127.0.0.1 */
|
/* 0.0.0.0 is nothing, the stack treats it like 127.0.0.1 */
|
||||||
@@ -1471,7 +1502,11 @@ void check_servers(void)
|
|||||||
{
|
{
|
||||||
if (serv->flags & (SERV_HAS_DOMAIN | SERV_FOR_NODOTS | SERV_USE_RESOLV))
|
if (serv->flags & (SERV_HAS_DOMAIN | SERV_FOR_NODOTS | SERV_USE_RESOLV))
|
||||||
{
|
{
|
||||||
char *s1, *s2;
|
char *s1, *s2, *s3 = "";
|
||||||
|
#ifdef HAVE_DNSSEC
|
||||||
|
if (option_bool(OPT_DNSSEC_VALID) && !(serv->flags & SERV_DO_DNSSEC))
|
||||||
|
s3 = _("(no DNSSEC)");
|
||||||
|
#endif
|
||||||
if (!(serv->flags & SERV_HAS_DOMAIN))
|
if (!(serv->flags & SERV_HAS_DOMAIN))
|
||||||
s1 = _("unqualified"), s2 = _("names");
|
s1 = _("unqualified"), s2 = _("names");
|
||||||
else if (strlen(serv->domain) == 0)
|
else if (strlen(serv->domain) == 0)
|
||||||
@@ -1484,7 +1519,7 @@ void check_servers(void)
|
|||||||
else if (serv->flags & SERV_USE_RESOLV)
|
else if (serv->flags & SERV_USE_RESOLV)
|
||||||
my_syslog(LOG_INFO, _("using standard nameservers for %s %s"), s1, s2);
|
my_syslog(LOG_INFO, _("using standard nameservers for %s %s"), s1, s2);
|
||||||
else
|
else
|
||||||
my_syslog(LOG_INFO, _("using nameserver %s#%d for %s %s"), daemon->namebuff, port, s1, s2);
|
my_syslog(LOG_INFO, _("using nameserver %s#%d for %s %s %s"), daemon->namebuff, port, s1, s2, s3);
|
||||||
}
|
}
|
||||||
#ifdef HAVE_LOOP
|
#ifdef HAVE_LOOP
|
||||||
else if (serv->flags & SERV_LOOP)
|
else if (serv->flags & SERV_LOOP)
|
||||||
|
|||||||
+34
-9
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -154,7 +154,9 @@ struct myoption {
|
|||||||
#define LOPT_HOST_INOTIFY 342
|
#define LOPT_HOST_INOTIFY 342
|
||||||
#define LOPT_DNSSEC_STAMP 343
|
#define LOPT_DNSSEC_STAMP 343
|
||||||
#define LOPT_TFTP_NO_FAIL 344
|
#define LOPT_TFTP_NO_FAIL 344
|
||||||
#define LOPT_DNS_CLIENT_ID 355
|
#define LOPT_MAXPORT 345
|
||||||
|
#define LOPT_CPE_ID 346
|
||||||
|
#define LOPT_SCRIPT_ARP 347
|
||||||
|
|
||||||
#ifdef HAVE_GETOPT_LONG
|
#ifdef HAVE_GETOPT_LONG
|
||||||
static const struct option opts[] =
|
static const struct option opts[] =
|
||||||
@@ -271,6 +273,7 @@ static const struct myoption opts[] =
|
|||||||
{ "dhcp-alternate-port", 2, 0, LOPT_ALTPORT },
|
{ "dhcp-alternate-port", 2, 0, LOPT_ALTPORT },
|
||||||
{ "dhcp-scriptuser", 1, 0, LOPT_SCRIPTUSR },
|
{ "dhcp-scriptuser", 1, 0, LOPT_SCRIPTUSR },
|
||||||
{ "min-port", 1, 0, LOPT_MINPORT },
|
{ "min-port", 1, 0, LOPT_MINPORT },
|
||||||
|
{ "max-port", 1, 0, LOPT_MAXPORT },
|
||||||
{ "dhcp-fqdn", 0, 0, LOPT_DHCP_FQDN },
|
{ "dhcp-fqdn", 0, 0, LOPT_DHCP_FQDN },
|
||||||
{ "cname", 1, 0, LOPT_CNAME },
|
{ "cname", 1, 0, LOPT_CNAME },
|
||||||
{ "pxe-prompt", 1, 0, LOPT_PXE_PROMT },
|
{ "pxe-prompt", 1, 0, LOPT_PXE_PROMT },
|
||||||
@@ -280,9 +283,9 @@ static const struct myoption opts[] =
|
|||||||
{ "dhcp-proxy", 2, 0, LOPT_PROXY },
|
{ "dhcp-proxy", 2, 0, LOPT_PROXY },
|
||||||
{ "dhcp-generate-names", 2, 0, LOPT_GEN_NAMES },
|
{ "dhcp-generate-names", 2, 0, LOPT_GEN_NAMES },
|
||||||
{ "rebind-localhost-ok", 0, 0, LOPT_LOC_REBND },
|
{ "rebind-localhost-ok", 0, 0, LOPT_LOC_REBND },
|
||||||
{ "add-mac", 0, 0, LOPT_ADD_MAC },
|
{ "add-mac", 2, 0, LOPT_ADD_MAC },
|
||||||
{ "add-subnet", 2, 0, LOPT_ADD_SBNET },
|
{ "add-subnet", 2, 0, LOPT_ADD_SBNET },
|
||||||
{ "add-dns-client", 2, 0 , LOPT_DNS_CLIENT_ID },
|
{ "add-cpe-id", 1, 0 , LOPT_CPE_ID },
|
||||||
{ "proxy-dnssec", 0, 0, LOPT_DNSSEC },
|
{ "proxy-dnssec", 0, 0, LOPT_DNSSEC },
|
||||||
{ "dhcp-sequential-ip", 0, 0, LOPT_INCR_ADDR },
|
{ "dhcp-sequential-ip", 0, 0, LOPT_INCR_ADDR },
|
||||||
{ "conntrack", 0, 0, LOPT_CONNTRACK },
|
{ "conntrack", 0, 0, LOPT_CONNTRACK },
|
||||||
@@ -315,6 +318,7 @@ static const struct myoption opts[] =
|
|||||||
{ "quiet-dhcp6", 0, 0, LOPT_QUIET_DHCP6 },
|
{ "quiet-dhcp6", 0, 0, LOPT_QUIET_DHCP6 },
|
||||||
{ "quiet-ra", 0, 0, LOPT_QUIET_RA },
|
{ "quiet-ra", 0, 0, LOPT_QUIET_RA },
|
||||||
{ "dns-loop-detect", 0, 0, LOPT_LOOP_DETECT },
|
{ "dns-loop-detect", 0, 0, LOPT_LOOP_DETECT },
|
||||||
|
{ "script-arp", 0, 0, LOPT_SCRIPT_ARP },
|
||||||
{ NULL, 0, 0, 0 }
|
{ NULL, 0, 0, 0 }
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -412,6 +416,7 @@ static struct {
|
|||||||
{ '6', ARG_ONE, "<path>", gettext_noop("Shell script to run on DHCP lease creation and destruction."), NULL },
|
{ '6', ARG_ONE, "<path>", gettext_noop("Shell script to run on DHCP lease creation and destruction."), NULL },
|
||||||
{ LOPT_LUASCRIPT, ARG_DUP, "path", gettext_noop("Lua script to run on DHCP lease creation and destruction."), NULL },
|
{ LOPT_LUASCRIPT, ARG_DUP, "path", gettext_noop("Lua script to run on DHCP lease creation and destruction."), NULL },
|
||||||
{ LOPT_SCRIPTUSR, ARG_ONE, "<username>", gettext_noop("Run lease-change scripts as this user."), NULL },
|
{ LOPT_SCRIPTUSR, ARG_ONE, "<username>", gettext_noop("Run lease-change scripts as this user."), NULL },
|
||||||
|
{ LOPT_SCRIPT_ARP, OPT_SCRIPT_ARP, NULL, gettext_noop("Call dhcp-script with changes to local ARP table."), NULL },
|
||||||
{ '7', ARG_DUP, "<path>", gettext_noop("Read configuration from all the files in this directory."), NULL },
|
{ '7', ARG_DUP, "<path>", gettext_noop("Read configuration from all the files in this directory."), NULL },
|
||||||
{ '8', ARG_ONE, "<facilty>|<file>", gettext_noop("Log to this syslog facility or file. (defaults to DAEMON)"), NULL },
|
{ '8', ARG_ONE, "<facilty>|<file>", gettext_noop("Log to this syslog facility or file. (defaults to DAEMON)"), NULL },
|
||||||
{ '9', OPT_LEASE_RO, NULL, gettext_noop("Do not use leasefile."), NULL },
|
{ '9', OPT_LEASE_RO, NULL, gettext_noop("Do not use leasefile."), NULL },
|
||||||
@@ -438,6 +443,7 @@ static struct {
|
|||||||
{ LOPT_ALTPORT, ARG_ONE, "[=<ports>]", gettext_noop("Use alternative ports for DHCP."), NULL },
|
{ LOPT_ALTPORT, ARG_ONE, "[=<ports>]", gettext_noop("Use alternative ports for DHCP."), NULL },
|
||||||
{ LOPT_NAPTR, ARG_DUP, "<name>,<naptr>", gettext_noop("Specify NAPTR DNS record."), NULL },
|
{ LOPT_NAPTR, ARG_DUP, "<name>,<naptr>", gettext_noop("Specify NAPTR DNS record."), NULL },
|
||||||
{ LOPT_MINPORT, ARG_ONE, "<port>", gettext_noop("Specify lowest port available for DNS query transmission."), NULL },
|
{ LOPT_MINPORT, ARG_ONE, "<port>", gettext_noop("Specify lowest port available for DNS query transmission."), NULL },
|
||||||
|
{ LOPT_MAXPORT, ARG_ONE, "<port>", gettext_noop("Specify highest port available for DNS query transmission."), NULL },
|
||||||
{ LOPT_DHCP_FQDN, OPT_DHCP_FQDN, NULL, gettext_noop("Use only fully qualified domain names for DHCP clients."), NULL },
|
{ LOPT_DHCP_FQDN, OPT_DHCP_FQDN, NULL, gettext_noop("Use only fully qualified domain names for DHCP clients."), NULL },
|
||||||
{ LOPT_GEN_NAMES, ARG_DUP, "[=tag:<tag>]", gettext_noop("Generate hostnames based on MAC address for nameless clients."), NULL},
|
{ LOPT_GEN_NAMES, ARG_DUP, "[=tag:<tag>]", gettext_noop("Generate hostnames based on MAC address for nameless clients."), NULL},
|
||||||
{ LOPT_PROXY, ARG_DUP, "[=<ipaddr>]...", gettext_noop("Use these DHCP relays as full proxies."), NULL },
|
{ LOPT_PROXY, ARG_DUP, "[=<ipaddr>]...", gettext_noop("Use these DHCP relays as full proxies."), NULL },
|
||||||
@@ -446,9 +452,9 @@ static struct {
|
|||||||
{ LOPT_PXE_PROMT, ARG_DUP, "<prompt>,[<timeout>]", gettext_noop("Prompt to send to PXE clients."), NULL },
|
{ LOPT_PXE_PROMT, ARG_DUP, "<prompt>,[<timeout>]", gettext_noop("Prompt to send to PXE clients."), NULL },
|
||||||
{ LOPT_PXE_SERV, ARG_DUP, "<service>", gettext_noop("Boot service for PXE menu."), NULL },
|
{ LOPT_PXE_SERV, ARG_DUP, "<service>", gettext_noop("Boot service for PXE menu."), NULL },
|
||||||
{ LOPT_TEST, 0, NULL, gettext_noop("Check configuration syntax."), NULL },
|
{ LOPT_TEST, 0, NULL, gettext_noop("Check configuration syntax."), NULL },
|
||||||
{ LOPT_ADD_MAC, OPT_ADD_MAC, NULL, gettext_noop("Add requestor's MAC address to forwarded DNS queries."), NULL },
|
{ LOPT_ADD_MAC, ARG_DUP, "[=base64]", gettext_noop("Add requestor's MAC address to forwarded DNS queries."), NULL },
|
||||||
{ LOPT_ADD_SBNET, ARG_ONE, "<v4 pref>[,<v6 pref>]", gettext_noop("Add specified IP subnet to forwarded DNS queries."), NULL },
|
{ LOPT_ADD_SBNET, ARG_ONE, "<v4 pref>[,<v6 pref>]", gettext_noop("Add specified IP subnet to forwarded DNS queries."), NULL },
|
||||||
{ LOPT_DNS_CLIENT_ID, ARG_ONE, "<proxyname>", gettext_noop("Add client identification to forwarded DNS queries."), NULL },
|
{ LOPT_CPE_ID, ARG_ONE, "<text>", gettext_noop("Add client identification to forwarded DNS queries."), NULL },
|
||||||
{ LOPT_DNSSEC, OPT_DNSSEC_PROXY, NULL, gettext_noop("Proxy DNSSEC validation results from upstream nameservers."), NULL },
|
{ LOPT_DNSSEC, OPT_DNSSEC_PROXY, NULL, gettext_noop("Proxy DNSSEC validation results from upstream nameservers."), NULL },
|
||||||
{ LOPT_INCR_ADDR, OPT_CONSEC_ADDR, NULL, gettext_noop("Attempt to allocate sequential IP addresses to DHCP clients."), NULL },
|
{ LOPT_INCR_ADDR, OPT_CONSEC_ADDR, NULL, gettext_noop("Attempt to allocate sequential IP addresses to DHCP clients."), NULL },
|
||||||
{ LOPT_CONNTRACK, OPT_CONNTRACK, NULL, gettext_noop("Copy connection-track mark from queries to upstream connections."), NULL },
|
{ LOPT_CONNTRACK, OPT_CONNTRACK, NULL, gettext_noop("Copy connection-track mark from queries to upstream connections."), NULL },
|
||||||
@@ -2153,12 +2159,25 @@ static int one_opt(int option, char *arg, char *errstr, char *gen_err, int comma
|
|||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
|
|
||||||
case LOPT_DNS_CLIENT_ID: /* --add-dns-client */
|
case LOPT_CPE_ID: /* --add-dns-client */
|
||||||
set_option_bool(OPT_DNS_CLIENT);
|
if (arg)
|
||||||
if (arg)
|
|
||||||
daemon->dns_client_id = opt_string_alloc(arg);
|
daemon->dns_client_id = opt_string_alloc(arg);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case LOPT_ADD_MAC:
|
||||||
|
if (!arg)
|
||||||
|
set_option_bool(OPT_ADD_MAC);
|
||||||
|
else
|
||||||
|
{
|
||||||
|
unhide_metas(arg);
|
||||||
|
if (strcmp(arg, "base64") == 0)
|
||||||
|
set_option_bool(OPT_MAC_B64);
|
||||||
|
else if (strcmp(arg, "text") == 0)
|
||||||
|
set_option_bool(OPT_MAC_HEX);
|
||||||
|
ret_err(gen_err);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
|
||||||
case 'u': /* --user */
|
case 'u': /* --user */
|
||||||
daemon->username = opt_string_alloc(arg);
|
daemon->username = opt_string_alloc(arg);
|
||||||
break;
|
break;
|
||||||
@@ -2512,6 +2531,11 @@ static int one_opt(int option, char *arg, char *errstr, char *gen_err, int comma
|
|||||||
ret_err(gen_err);
|
ret_err(gen_err);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case LOPT_MAXPORT: /* --max-port */
|
||||||
|
if (!atoi_check16(arg, &daemon->max_port))
|
||||||
|
ret_err(gen_err);
|
||||||
|
break;
|
||||||
|
|
||||||
case '0': /* --dns-forward-max */
|
case '0': /* --dns-forward-max */
|
||||||
if (!atoi_check(arg, &daemon->ftabsize))
|
if (!atoi_check(arg, &daemon->ftabsize))
|
||||||
ret_err(gen_err);
|
ret_err(gen_err);
|
||||||
@@ -4462,6 +4486,7 @@ void read_opts(int argc, char **argv, char *compile_opts)
|
|||||||
daemon->soa_refresh = SOA_REFRESH;
|
daemon->soa_refresh = SOA_REFRESH;
|
||||||
daemon->soa_retry = SOA_RETRY;
|
daemon->soa_retry = SOA_RETRY;
|
||||||
daemon->soa_expiry = SOA_EXPIRY;
|
daemon->soa_expiry = SOA_EXPIRY;
|
||||||
|
daemon->max_port = MAX_PORT;
|
||||||
|
|
||||||
add_txt("version.bind", "dnsmasq-" VERSION, 0 );
|
add_txt("version.bind", "dnsmasq-" VERSION, 0 );
|
||||||
add_txt("authors.bind", "Simon Kelley", 0);
|
add_txt("authors.bind", "Simon Kelley", 0);
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+13
-4
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -28,11 +28,12 @@
|
|||||||
|
|
||||||
struct ra_param {
|
struct ra_param {
|
||||||
time_t now;
|
time_t now;
|
||||||
int ind, managed, other, found_context, first, adv_router;
|
int ind, managed, other, first, adv_router;
|
||||||
char *if_name;
|
char *if_name;
|
||||||
struct dhcp_netid *tags;
|
struct dhcp_netid *tags;
|
||||||
struct in6_addr link_local, link_global, ula;
|
struct in6_addr link_local, link_global, ula;
|
||||||
unsigned int glob_pref_time, link_pref_time, ula_pref_time, adv_interval, prio;
|
unsigned int glob_pref_time, link_pref_time, ula_pref_time, adv_interval, prio;
|
||||||
|
struct dhcp_context *found_context;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct search_param {
|
struct search_param {
|
||||||
@@ -251,7 +252,7 @@ static void send_ra_alias(time_t now, int iface, char *iface_name, struct in6_ad
|
|||||||
parm.ind = iface;
|
parm.ind = iface;
|
||||||
parm.managed = 0;
|
parm.managed = 0;
|
||||||
parm.other = 0;
|
parm.other = 0;
|
||||||
parm.found_context = 0;
|
parm.found_context = NULL;
|
||||||
parm.adv_router = 0;
|
parm.adv_router = 0;
|
||||||
parm.if_name = iface_name;
|
parm.if_name = iface_name;
|
||||||
parm.first = 1;
|
parm.first = 1;
|
||||||
@@ -310,6 +311,12 @@ static void send_ra_alias(time_t now, int iface, char *iface_name, struct in6_ad
|
|||||||
if (old > context->saved_valid)
|
if (old > context->saved_valid)
|
||||||
{
|
{
|
||||||
/* We've advertised this enough, time to go */
|
/* We've advertised this enough, time to go */
|
||||||
|
|
||||||
|
/* If this context held the timeout, and there's another context in use
|
||||||
|
transfer the timeout there. */
|
||||||
|
if (context->ra_time != 0 && parm.found_context && parm.found_context->ra_time == 0)
|
||||||
|
new_timeout(parm.found_context, iface_name, now);
|
||||||
|
|
||||||
*up = context->next;
|
*up = context->next;
|
||||||
free(context);
|
free(context);
|
||||||
}
|
}
|
||||||
@@ -637,7 +644,9 @@ static int add_prefixes(struct in6_addr *local, int prefix,
|
|||||||
}
|
}
|
||||||
|
|
||||||
param->first = 0;
|
param->first = 0;
|
||||||
param->found_context = 1;
|
/* found_context is the _last_ one we found, so if there's
|
||||||
|
more than one, it's not the first. */
|
||||||
|
param->found_context = context;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* configured time is ceiling */
|
/* configured time is ceiling */
|
||||||
|
|||||||
+2
-4
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
@@ -896,9 +896,7 @@ size_t setup_reply(struct dns_header *header, size_t qlen,
|
|||||||
header->nscount = htons(0);
|
header->nscount = htons(0);
|
||||||
header->arcount = htons(0);
|
header->arcount = htons(0);
|
||||||
header->ancount = htons(0); /* no answers unless changed below */
|
header->ancount = htons(0); /* no answers unless changed below */
|
||||||
if (flags == F_NEG)
|
if (flags == F_NOERR)
|
||||||
SET_RCODE(header, SERVFAIL); /* couldn't get memory */
|
|
||||||
else if (flags == F_NOERR)
|
|
||||||
SET_RCODE(header, NOERROR); /* empty domain */
|
SET_RCODE(header, NOERROR); /* empty domain */
|
||||||
else if (flags == F_NXDOMAIN)
|
else if (flags == F_NXDOMAIN)
|
||||||
SET_RCODE(header, NXDOMAIN);
|
SET_RCODE(header, NXDOMAIN);
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
+1
-1
@@ -1,4 +1,4 @@
|
|||||||
/* dnsmasq is Copyright (c) 2000-2015 Simon Kelley
|
/* dnsmasq is Copyright (c) 2000-2016 Simon Kelley
|
||||||
|
|
||||||
This program is free software; you can redistribute it and/or modify
|
This program is free software; you can redistribute it and/or modify
|
||||||
it under the terms of the GNU General Public License as published by
|
it under the terms of the GNU General Public License as published by
|
||||||
|
|||||||
Reference in new issue
Block a user