mirror of
http://thekelleys.org.uk/git/dnsmasq.git
synced 2026-11-06 15:51:41 +00:00
Compare commits
8
Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
5f4dc5c6ca | ||
|
|
2ae195f5a7 | ||
|
|
393415597c | ||
|
|
ae4624bf46 | ||
|
|
5e321739db | ||
|
|
9f79ee4ae3 | ||
|
|
28de38768e | ||
|
|
25cf5e373e |
No files matched your search
@@ -40,6 +40,25 @@ version 2.73
|
|||||||
nameservers in the unsigned parts of the DNS tree
|
nameservers in the unsigned parts of the DNS tree
|
||||||
which don't respond well to DNSSEC queries.
|
which don't respond well to DNSSEC queries.
|
||||||
|
|
||||||
|
Add --log-queries=extra option, which makes logs easier
|
||||||
|
to search automatically.
|
||||||
|
|
||||||
|
Add --min-cache-ttl option. I've resisted this for a long
|
||||||
|
time, on the grounds that disbelieving TTLs is never a
|
||||||
|
good idea, but I've been persuaded that there are
|
||||||
|
sometimes reasons to do it. (Step forward, GFW).
|
||||||
|
To avoid misuse, there's a hard limit on the TTL
|
||||||
|
floor of one hour. Thansk to RinSatsuki for the patch.
|
||||||
|
|
||||||
|
Cope with multiple interfaces with the same link-local
|
||||||
|
address. (IPv6 addresses are scoped, so this is allowed.)
|
||||||
|
Thanks to Cory Benfield for help with this.
|
||||||
|
|
||||||
|
Add --dhcp-hostsdir. This allows addition of new host
|
||||||
|
configurations to a running dnsmasq instance much more
|
||||||
|
cheaply than having dnsmasq re-read all its existing
|
||||||
|
configuration each time.
|
||||||
|
|
||||||
|
|
||||||
version 2.72
|
version 2.72
|
||||||
Add ra-advrouter mode, for RFC-3775 mobile IPv6 support.
|
Add ra-advrouter mode, for RFC-3775 mobile IPv6 support.
|
||||||
|
|||||||
+19
-1
@@ -81,6 +81,12 @@ the upstream DNS servers.
|
|||||||
.B --max-cache-ttl=<time>
|
.B --max-cache-ttl=<time>
|
||||||
Set a maximum TTL value for entries in the cache.
|
Set a maximum TTL value for entries in the cache.
|
||||||
.TP
|
.TP
|
||||||
|
.B --min-cache-ttl=<time>
|
||||||
|
Extend short TTL values to the time given when caching them. Note that
|
||||||
|
artificially extending TTL values is in general a bad idea, do not do it
|
||||||
|
unless you have a good reason, and understand what you are doing.
|
||||||
|
Dnsmasq limits the value of this option to one hour, unless recompiled.
|
||||||
|
.TP
|
||||||
.B --auth-ttl=<time>
|
.B --auth-ttl=<time>
|
||||||
Set the TTL value returned in answers from the authoritative server.
|
Set the TTL value returned in answers from the authoritative server.
|
||||||
.TP
|
.TP
|
||||||
@@ -98,7 +104,10 @@ only, to stop dnsmasq daemonising in production, use
|
|||||||
.B -k.
|
.B -k.
|
||||||
.TP
|
.TP
|
||||||
.B \-q, --log-queries
|
.B \-q, --log-queries
|
||||||
Log the results of DNS queries handled by dnsmasq. Enable a full cache dump on receipt of SIGUSR1.
|
Log the results of DNS queries handled by dnsmasq. Enable a full cache dump on receipt of SIGUSR1. If the argument "extra" is supplied, ie
|
||||||
|
.B --log-queries=extra
|
||||||
|
then the log has extra information at the start of each line.
|
||||||
|
This consists of a serial number which ties together the log lines associated with an individual query, and the IP address of the requestor.
|
||||||
.TP
|
.TP
|
||||||
.B \-8, --log-facility=<facility>
|
.B \-8, --log-facility=<facility>
|
||||||
Set the facility to which dnsmasq will send syslog entries, this
|
Set the facility to which dnsmasq will send syslog entries, this
|
||||||
@@ -968,6 +977,15 @@ is given, then read all the files contained in that directory. The advantage of
|
|||||||
using this option is the same as for --dhcp-hostsfile: the
|
using this option is the same as for --dhcp-hostsfile: the
|
||||||
dhcp-optsfile will be re-read when dnsmasq receives SIGHUP. Note that
|
dhcp-optsfile will be re-read when dnsmasq receives SIGHUP. Note that
|
||||||
it is possible to encode the information in a
|
it is possible to encode the information in a
|
||||||
|
.TP
|
||||||
|
.B --dhcp-hostsdir=<path>
|
||||||
|
This is exactly equivalent to dhcp-hostfile, except for the following. The path MUST be a
|
||||||
|
directory, and not an individual file. Changed or new files within
|
||||||
|
the directory are read automatically, without the need to send SIGHUP.
|
||||||
|
If a file is deleted for changed after it has been read by dnsmasq, then the
|
||||||
|
host record it contained will remain until dnsmasq recieves a SIGHUP, or
|
||||||
|
is restarted; ie host records are only added dynamically.
|
||||||
|
.TP
|
||||||
.B --dhcp-boot
|
.B --dhcp-boot
|
||||||
flag as DHCP options, using the options names bootfile-name,
|
flag as DHCP options, using the options names bootfile-name,
|
||||||
server-ip-address and tftp-server. This allows these to be included
|
server-ip-address and tftp-server. This allows these to be included
|
||||||
|
|||||||
+4
-1
@@ -413,7 +413,10 @@ size_t answer_auth(struct dns_header *header, char *limit, size_t qlen, time_t n
|
|||||||
peer_addr->in.sin_port = 0;
|
peer_addr->in.sin_port = 0;
|
||||||
#ifdef HAVE_IPV6
|
#ifdef HAVE_IPV6
|
||||||
else
|
else
|
||||||
peer_addr->in6.sin6_port = 0;
|
{
|
||||||
|
peer_addr->in6.sin6_port = 0;
|
||||||
|
peer_addr->in6.sin6_scope_id = 0;
|
||||||
|
}
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
for (peers = daemon->auth_peers; peers; peers = peers->next)
|
for (peers = daemon->auth_peers; peers; peers = peers->next)
|
||||||
|
|||||||
+13
-2
@@ -461,9 +461,11 @@ struct crec *cache_insert(char *name, struct all_addr *addr,
|
|||||||
if (flags & (F_IPV4 | F_IPV6 | F_CNAME))
|
if (flags & (F_IPV4 | F_IPV6 | F_CNAME))
|
||||||
{
|
{
|
||||||
log_query(flags | F_UPSTREAM, name, addr, NULL);
|
log_query(flags | F_UPSTREAM, name, addr, NULL);
|
||||||
/* Don;t mess with TTL for DNSSEC records. */
|
/* Don't mess with TTL for DNSSEC records. */
|
||||||
if (daemon->max_cache_ttl != 0 && daemon->max_cache_ttl < ttl)
|
if (daemon->max_cache_ttl != 0 && daemon->max_cache_ttl < ttl)
|
||||||
ttl = daemon->max_cache_ttl;
|
ttl = daemon->max_cache_ttl;
|
||||||
|
if (daemon->min_cache_ttl != 0 && daemon->min_cache_ttl > ttl)
|
||||||
|
ttl = daemon->min_cache_ttl;
|
||||||
}
|
}
|
||||||
|
|
||||||
/* if previous insertion failed give up now. */
|
/* if previous insertion failed give up now. */
|
||||||
@@ -1638,7 +1640,16 @@ void log_query(unsigned int flags, char *name, struct all_addr *addr, char *arg)
|
|||||||
if (strlen(name) == 0)
|
if (strlen(name) == 0)
|
||||||
name = ".";
|
name = ".";
|
||||||
|
|
||||||
my_syslog(LOG_INFO, "%s %s %s %s", source, name, verb, dest);
|
if (option_bool(OPT_EXTRALOG))
|
||||||
|
{
|
||||||
|
int port = prettyprint_addr(daemon->log_source_addr, daemon->addrbuff2);
|
||||||
|
if (flags & F_NOEXTRA)
|
||||||
|
my_syslog(LOG_INFO, "* %s/%u %s %s %s %s", daemon->addrbuff2, port, source, name, verb, dest);
|
||||||
|
else
|
||||||
|
my_syslog(LOG_INFO, "%u %s/%u %s %s %s %s", daemon->log_display_id, daemon->addrbuff2, port, source, name, verb, dest);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
my_syslog(LOG_INFO, "%s %s %s %s", source, name, verb, dest);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@@ -17,6 +17,7 @@
|
|||||||
#define FTABSIZ 150 /* max number of outstanding requests (default) */
|
#define FTABSIZ 150 /* max number of outstanding requests (default) */
|
||||||
#define MAX_PROCS 20 /* max no children for TCP requests */
|
#define MAX_PROCS 20 /* max no children for TCP requests */
|
||||||
#define CHILD_LIFETIME 150 /* secs 'till terminated (RFC1035 suggests > 120s) */
|
#define CHILD_LIFETIME 150 /* secs 'till terminated (RFC1035 suggests > 120s) */
|
||||||
|
#define TCP_MAX_QUERIES 100 /* Maximum number of queries per incoming TCP connection */
|
||||||
#define EDNS_PKTSZ 4096 /* default max EDNS.0 UDP packet from RFC5625 */
|
#define EDNS_PKTSZ 4096 /* default max EDNS.0 UDP packet from RFC5625 */
|
||||||
#define KEYBLOCK_LEN 40 /* choose to mininise fragmentation when storing DNSSEC keys */
|
#define KEYBLOCK_LEN 40 /* choose to mininise fragmentation when storing DNSSEC keys */
|
||||||
#define DNSSEC_WORK 50 /* Max number of queries to validate one question */
|
#define DNSSEC_WORK 50 /* Max number of queries to validate one question */
|
||||||
@@ -26,6 +27,7 @@
|
|||||||
#define RANDOM_SOCKS 64 /* max simultaneous random ports */
|
#define RANDOM_SOCKS 64 /* max simultaneous random ports */
|
||||||
#define LEASE_RETRY 60 /* on error, retry writing leasefile after LEASE_RETRY seconds */
|
#define LEASE_RETRY 60 /* on error, retry writing leasefile after LEASE_RETRY seconds */
|
||||||
#define CACHESIZ 150 /* default cache size */
|
#define CACHESIZ 150 /* default cache size */
|
||||||
|
#define TTL_FLOOR_LIMIT 3600 /* don't allow --min-cache-ttl to raise TTL above this under any circumstances */
|
||||||
#define MAXLEASES 1000 /* maximum number of DHCP leases */
|
#define MAXLEASES 1000 /* maximum number of DHCP leases */
|
||||||
#define PING_WAIT 3 /* wait for ping address-in-use test */
|
#define PING_WAIT 3 /* wait for ping address-in-use test */
|
||||||
#define PING_CACHE_TIME 30 /* Ping test assumed to be valid this long. */
|
#define PING_CACHE_TIME 30 /* Ping test assumed to be valid this long. */
|
||||||
|
|||||||
+24
-7
@@ -93,6 +93,8 @@ int main (int argc, char **argv)
|
|||||||
daemon->packet = safe_malloc(daemon->packet_buff_sz);
|
daemon->packet = safe_malloc(daemon->packet_buff_sz);
|
||||||
|
|
||||||
daemon->addrbuff = safe_malloc(ADDRSTRLEN);
|
daemon->addrbuff = safe_malloc(ADDRSTRLEN);
|
||||||
|
if (option_bool(OPT_EXTRALOG))
|
||||||
|
daemon->addrbuff2 = safe_malloc(ADDRSTRLEN);
|
||||||
|
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
if (option_bool(OPT_DNSSEC_VALID))
|
if (option_bool(OPT_DNSSEC_VALID))
|
||||||
@@ -140,6 +142,9 @@ int main (int argc, char **argv)
|
|||||||
set_option_bool(OPT_NOWILD);
|
set_option_bool(OPT_NOWILD);
|
||||||
reset_option_bool(OPT_CLEVERBIND);
|
reset_option_bool(OPT_CLEVERBIND);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (daemon->inotify_hosts)
|
||||||
|
die(_("dhcp-hostsdir not supported on this platform"), NULL, EC_BADCONF);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (option_bool(OPT_DNSSEC_VALID))
|
if (option_bool(OPT_DNSSEC_VALID))
|
||||||
@@ -314,12 +319,15 @@ int main (int argc, char **argv)
|
|||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
blockdata_init();
|
blockdata_init();
|
||||||
#endif
|
#endif
|
||||||
|
}
|
||||||
|
|
||||||
#ifdef HAVE_LINUX_NETWORK
|
#ifdef HAVE_LINUX_NETWORK
|
||||||
if (!option_bool(OPT_NO_POLL))
|
if ((!option_bool(OPT_NO_POLL) && daemon->port != 0) ||
|
||||||
inotify_dnsmasq_init();
|
daemon->dhcp || daemon->doing_dhcp6)
|
||||||
|
inotify_dnsmasq_init();
|
||||||
|
else
|
||||||
|
daemon->inotifyfd = -1;
|
||||||
#endif
|
#endif
|
||||||
}
|
|
||||||
|
|
||||||
if (option_bool(OPT_DBUS))
|
if (option_bool(OPT_DBUS))
|
||||||
#ifdef HAVE_DBUS
|
#ifdef HAVE_DBUS
|
||||||
@@ -743,7 +751,7 @@ int main (int argc, char **argv)
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef HAVE_TFTP
|
#ifdef HAVE_TFTP
|
||||||
if (option_bool(OPT_TFTP))
|
if (option_bool(OPT_TFTP))
|
||||||
{
|
{
|
||||||
#ifdef FD_SETSIZE
|
#ifdef FD_SETSIZE
|
||||||
if (FD_SETSIZE < (unsigned)max_fd)
|
if (FD_SETSIZE < (unsigned)max_fd)
|
||||||
@@ -868,7 +876,7 @@ int main (int argc, char **argv)
|
|||||||
#if defined(HAVE_LINUX_NETWORK)
|
#if defined(HAVE_LINUX_NETWORK)
|
||||||
FD_SET(daemon->netlinkfd, &rset);
|
FD_SET(daemon->netlinkfd, &rset);
|
||||||
bump_maxfd(daemon->netlinkfd, &maxfd);
|
bump_maxfd(daemon->netlinkfd, &maxfd);
|
||||||
if (daemon->port != 0 && !option_bool(OPT_NO_POLL))
|
if (daemon->inotifyfd != -1)
|
||||||
{
|
{
|
||||||
FD_SET(daemon->inotifyfd, &rset);
|
FD_SET(daemon->inotifyfd, &rset);
|
||||||
bump_maxfd(daemon->inotifyfd, &maxfd);
|
bump_maxfd(daemon->inotifyfd, &maxfd);
|
||||||
@@ -941,8 +949,11 @@ int main (int argc, char **argv)
|
|||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef HAVE_LINUX_NETWORK
|
#ifdef HAVE_LINUX_NETWORK
|
||||||
if (daemon->port != 0 && !option_bool(OPT_NO_POLL) && FD_ISSET(daemon->inotifyfd, &rset) && inotify_check())
|
if (daemon->inotifyfd != -1 && FD_ISSET(daemon->inotifyfd, &rset) && inotify_check(now))
|
||||||
poll_resolv(1, 1, now);
|
{
|
||||||
|
if (daemon->port != 0 && !option_bool(OPT_NO_POLL))
|
||||||
|
poll_resolv(1, 1, now);
|
||||||
|
}
|
||||||
#else
|
#else
|
||||||
/* Check for changes to resolv files once per second max. */
|
/* Check for changes to resolv files once per second max. */
|
||||||
/* Don't go silent for long periods if the clock goes backwards. */
|
/* Don't go silent for long periods if the clock goes backwards. */
|
||||||
@@ -1383,6 +1394,9 @@ void clear_cache_and_reload(time_t now)
|
|||||||
if (option_bool(OPT_ETHERS))
|
if (option_bool(OPT_ETHERS))
|
||||||
dhcp_read_ethers();
|
dhcp_read_ethers();
|
||||||
reread_dhcp();
|
reread_dhcp();
|
||||||
|
#ifdef HAVE_LINUX_NETWORK
|
||||||
|
set_dhcp_inotify();
|
||||||
|
#endif
|
||||||
dhcp_update_configs(daemon->dhcp_conf);
|
dhcp_update_configs(daemon->dhcp_conf);
|
||||||
lease_update_from_configs();
|
lease_update_from_configs();
|
||||||
lease_update_file(now);
|
lease_update_file(now);
|
||||||
@@ -1587,6 +1601,9 @@ static void check_dns_listeners(fd_set *set, time_t now)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
close(confd);
|
close(confd);
|
||||||
|
|
||||||
|
/* The child can use up to TCP_MAX_QUERIES ids, so skip that many. */
|
||||||
|
daemon->log_id += TCP_MAX_QUERIES;
|
||||||
}
|
}
|
||||||
#endif
|
#endif
|
||||||
else
|
else
|
||||||
|
|||||||
+19
-7
@@ -238,7 +238,8 @@ struct event_desc {
|
|||||||
#define OPT_DNSSEC_NO_SIGN 48
|
#define OPT_DNSSEC_NO_SIGN 48
|
||||||
#define OPT_LOCAL_SERVICE 49
|
#define OPT_LOCAL_SERVICE 49
|
||||||
#define OPT_LOOP_DETECT 50
|
#define OPT_LOOP_DETECT 50
|
||||||
#define OPT_LAST 51
|
#define OPT_EXTRALOG 51
|
||||||
|
#define OPT_LAST 52
|
||||||
|
|
||||||
/* 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. */
|
||||||
@@ -442,6 +443,7 @@ struct crec {
|
|||||||
#define F_NO_RR (1u<<25)
|
#define F_NO_RR (1u<<25)
|
||||||
#define F_IPSET (1u<<26)
|
#define F_IPSET (1u<<26)
|
||||||
#define F_NSIGMATCH (1u<<27)
|
#define F_NSIGMATCH (1u<<27)
|
||||||
|
#define F_NOEXTRA (1u<<28)
|
||||||
|
|
||||||
/* Values of uid in crecs with F_CONFIG bit set. */
|
/* Values of uid in crecs with F_CONFIG bit set. */
|
||||||
#define SRC_INTERFACE 0
|
#define SRC_INTERFACE 0
|
||||||
@@ -548,13 +550,17 @@ struct resolvc {
|
|||||||
#endif
|
#endif
|
||||||
};
|
};
|
||||||
|
|
||||||
/* adn-hosts parms from command-line (also dhcp-hostsfile and dhcp-optsfile */
|
/* adn-hosts parms from command-line (also dhcp-hostsfile and dhcp-optsfile and dhcp-hostsdir*/
|
||||||
#define AH_DIR 1
|
#define AH_DIR 1
|
||||||
#define AH_INACTIVE 2
|
#define AH_INACTIVE 2
|
||||||
|
#define AH_WD_DONE 4
|
||||||
struct hostsfile {
|
struct hostsfile {
|
||||||
struct hostsfile *next;
|
struct hostsfile *next;
|
||||||
int flags;
|
int flags;
|
||||||
char *fname;
|
char *fname;
|
||||||
|
#ifdef HAVE_LINUX_NETWORK
|
||||||
|
int wd; /* inotify watch descriptor */
|
||||||
|
#endif
|
||||||
unsigned int index; /* matches to cache entries for logging */
|
unsigned int index; /* matches to cache entries for logging */
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -599,7 +605,7 @@ struct frec {
|
|||||||
#endif
|
#endif
|
||||||
unsigned int iface;
|
unsigned int iface;
|
||||||
unsigned short orig_id, new_id;
|
unsigned short orig_id, new_id;
|
||||||
int fd, forwardall, flags;
|
int log_id, fd, forwardall, flags;
|
||||||
time_t time;
|
time_t time;
|
||||||
unsigned char *hash[HASH_SIZE];
|
unsigned char *hash[HASH_SIZE];
|
||||||
#ifdef HAVE_DNSSEC
|
#ifdef HAVE_DNSSEC
|
||||||
@@ -941,7 +947,7 @@ extern struct daemon {
|
|||||||
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;
|
||||||
unsigned long local_ttl, neg_ttl, max_ttl, max_cache_ttl, auth_ttl;
|
unsigned long local_ttl, neg_ttl, max_ttl, min_cache_ttl, max_cache_ttl, auth_ttl;
|
||||||
struct hostsfile *addn_hosts;
|
struct hostsfile *addn_hosts;
|
||||||
struct dhcp_context *dhcp, *dhcp6;
|
struct dhcp_context *dhcp, *dhcp6;
|
||||||
struct ra_interface *ra_interfaces;
|
struct ra_interface *ra_interfaces;
|
||||||
@@ -959,7 +965,7 @@ extern struct daemon {
|
|||||||
int doing_ra, doing_dhcp6;
|
int doing_ra, doing_dhcp6;
|
||||||
struct dhcp_netid_list *dhcp_ignore, *dhcp_ignore_names, *dhcp_gen_names;
|
struct dhcp_netid_list *dhcp_ignore, *dhcp_ignore_names, *dhcp_gen_names;
|
||||||
struct dhcp_netid_list *force_broadcast, *bootp_dynamic;
|
struct dhcp_netid_list *force_broadcast, *bootp_dynamic;
|
||||||
struct hostsfile *dhcp_hosts_file, *dhcp_opts_file;
|
struct hostsfile *dhcp_hosts_file, *dhcp_opts_file, *inotify_hosts;
|
||||||
int dhcp_max, tftp_max;
|
int dhcp_max, tftp_max;
|
||||||
int dhcp_server_port, dhcp_client_port;
|
int dhcp_server_port, dhcp_client_port;
|
||||||
int start_tftp_port, end_tftp_port;
|
int start_tftp_port, end_tftp_port;
|
||||||
@@ -1002,6 +1008,8 @@ extern struct daemon {
|
|||||||
struct randfd randomsocks[RANDOM_SOCKS];
|
struct randfd randomsocks[RANDOM_SOCKS];
|
||||||
int v6pktinfo;
|
int v6pktinfo;
|
||||||
struct addrlist *interface_addrs; /* list of all addresses/prefix lengths associated with all local interfaces */
|
struct addrlist *interface_addrs; /* list of all addresses/prefix lengths associated with all local interfaces */
|
||||||
|
int log_id, log_display_id; /* ids of transactions for logging */
|
||||||
|
union mysockaddr *log_source_addr;
|
||||||
|
|
||||||
/* DHCP state */
|
/* DHCP state */
|
||||||
int dhcpfd, helperfd, pxefd;
|
int dhcpfd, helperfd, pxefd;
|
||||||
@@ -1033,6 +1041,7 @@ extern struct daemon {
|
|||||||
|
|
||||||
/* utility string buffer, hold max sized IP address as string */
|
/* utility string buffer, hold max sized IP address as string */
|
||||||
char *addrbuff;
|
char *addrbuff;
|
||||||
|
char *addrbuff2; /* only allocated when OPT_EXTRALOG */
|
||||||
|
|
||||||
} *daemon;
|
} *daemon;
|
||||||
|
|
||||||
@@ -1192,7 +1201,7 @@ void reset_option_bool(unsigned int opt);
|
|||||||
struct hostsfile *expand_filelist(struct hostsfile *list);
|
struct hostsfile *expand_filelist(struct hostsfile *list);
|
||||||
char *parse_server(char *arg, union mysockaddr *addr,
|
char *parse_server(char *arg, union mysockaddr *addr,
|
||||||
union mysockaddr *source_addr, char *interface, int *flags);
|
union mysockaddr *source_addr, char *interface, int *flags);
|
||||||
|
int option_read_hostsfile(char *file);
|
||||||
/* forward.c */
|
/* forward.c */
|
||||||
void reply_query(int fd, int family, time_t now);
|
void reply_query(int fd, int family, time_t now);
|
||||||
void receive_query(struct listener *listen, time_t now);
|
void receive_query(struct listener *listen, time_t now);
|
||||||
@@ -1481,5 +1490,8 @@ int detect_loop(char *query, int type);
|
|||||||
/* inotify.c */
|
/* inotify.c */
|
||||||
#ifdef HAVE_LINUX_NETWORK
|
#ifdef HAVE_LINUX_NETWORK
|
||||||
void inotify_dnsmasq_init();
|
void inotify_dnsmasq_init();
|
||||||
int inotify_check(void);
|
int inotify_check(time_t now);
|
||||||
|
# ifdef HAVE_DHCP
|
||||||
|
void set_dhcp_inotify(void);
|
||||||
|
# endif
|
||||||
#endif
|
#endif
|
||||||
+15
-8
@@ -1038,7 +1038,7 @@ int dnssec_validate_by_ds(time_t now, struct dns_header *header, size_t plen, ch
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
a.addr.keytag = keytag;
|
a.addr.keytag = keytag;
|
||||||
log_query(F_KEYTAG | F_UPSTREAM, name, &a, "DNSKEY keytag %u");
|
log_query(F_NOEXTRA | F_KEYTAG | F_UPSTREAM, name, &a, "DNSKEY keytag %u");
|
||||||
|
|
||||||
recp1->addr.key.keylen = rdlen - 4;
|
recp1->addr.key.keylen = rdlen - 4;
|
||||||
recp1->addr.key.keydata = key;
|
recp1->addr.key.keydata = key;
|
||||||
@@ -1092,7 +1092,7 @@ int dnssec_validate_by_ds(time_t now, struct dns_header *header, size_t plen, ch
|
|||||||
return STAT_SECURE;
|
return STAT_SECURE;
|
||||||
}
|
}
|
||||||
|
|
||||||
log_query(F_UPSTREAM, name, NULL, "BOGUS DNSKEY");
|
log_query(F_NOEXTRA | F_UPSTREAM, name, NULL, "BOGUS DNSKEY");
|
||||||
return STAT_BOGUS;
|
return STAT_BOGUS;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1136,7 +1136,7 @@ int dnssec_validate_ds(time_t now, struct dns_header *header, size_t plen, char
|
|||||||
|
|
||||||
if (val == STAT_BOGUS)
|
if (val == STAT_BOGUS)
|
||||||
{
|
{
|
||||||
log_query(F_UPSTREAM, name, NULL, "BOGUS DS");
|
log_query(F_NOEXTRA | F_UPSTREAM, name, NULL, "BOGUS DS");
|
||||||
return STAT_BOGUS;
|
return STAT_BOGUS;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1201,7 +1201,7 @@ int dnssec_validate_ds(time_t now, struct dns_header *header, size_t plen, char
|
|||||||
|
|
||||||
cache_end_insert();
|
cache_end_insert();
|
||||||
|
|
||||||
log_query(F_UPSTREAM, name, NULL, nons ? "no delegation" : "no DS");
|
log_query(F_NOEXTRA | F_UPSTREAM, name, NULL, nons ? "no delegation" : "no DS");
|
||||||
}
|
}
|
||||||
|
|
||||||
return nons ? STAT_NO_NS : STAT_NO_DS;
|
return nons ? STAT_NO_NS : STAT_NO_DS;
|
||||||
@@ -1818,11 +1818,14 @@ int dnssec_validate_reply(time_t now, struct dns_header *header, size_t plen, ch
|
|||||||
struct blockdata *key;
|
struct blockdata *key;
|
||||||
struct crec *crecp;
|
struct crec *crecp;
|
||||||
char *wildname;
|
char *wildname;
|
||||||
|
int have_wildcard = 0;
|
||||||
|
|
||||||
rc = validate_rrset(now, header, plen, class1, type1, name, keyname, &wildname, NULL, 0, 0, 0);
|
rc = validate_rrset(now, header, plen, class1, type1, name, keyname, &wildname, NULL, 0, 0, 0);
|
||||||
|
|
||||||
if (rc == STAT_SECURE_WILDCARD)
|
if (rc == STAT_SECURE_WILDCARD)
|
||||||
{
|
{
|
||||||
|
have_wildcard = 1;
|
||||||
|
|
||||||
/* An attacker replay a wildcard answer with a different
|
/* An attacker replay a wildcard answer with a different
|
||||||
answer and overlay a genuine RR. To prove this
|
answer and overlay a genuine RR. To prove this
|
||||||
hasn't happened, the answer must prove that
|
hasn't happened, the answer must prove that
|
||||||
@@ -1885,7 +1888,7 @@ int dnssec_validate_reply(time_t now, struct dns_header *header, size_t plen, ch
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
a.addr.keytag = keytag;
|
a.addr.keytag = keytag;
|
||||||
log_query(F_KEYTAG | F_UPSTREAM, name, &a, "DS keytag %u");
|
log_query(F_NOEXTRA | F_KEYTAG | F_UPSTREAM, name, &a, "DS keytag %u");
|
||||||
crecp->addr.ds.digest = digest;
|
crecp->addr.ds.digest = digest;
|
||||||
crecp->addr.ds.keydata = key;
|
crecp->addr.ds.keydata = key;
|
||||||
crecp->addr.ds.algo = algo;
|
crecp->addr.ds.algo = algo;
|
||||||
@@ -1913,7 +1916,11 @@ int dnssec_validate_reply(time_t now, struct dns_header *header, size_t plen, ch
|
|||||||
p2 += 13; /* labels, orig_ttl, expiration, inception */
|
p2 += 13; /* labels, orig_ttl, expiration, inception */
|
||||||
GETSHORT(keytag, p2);
|
GETSHORT(keytag, p2);
|
||||||
|
|
||||||
if ((key = blockdata_alloc((char*)psave, rdlen2)))
|
/* We don't cache sigs for wildcard answers, because to reproduce the
|
||||||
|
answer from the cache will require one or more NSEC/NSEC3 records
|
||||||
|
which we don't cache. The lack of the RRSIG ensures that a query for
|
||||||
|
this RRset asking for a secure answer will always be forwarded. */
|
||||||
|
if (!have_wildcard && (key = blockdata_alloc((char*)psave, rdlen2)))
|
||||||
{
|
{
|
||||||
if (!(crecp = cache_insert(name, &a, now, ttl, F_FORWARD | F_DNSKEY | F_DS)))
|
if (!(crecp = cache_insert(name, &a, now, ttl, F_FORWARD | F_DNSKEY | F_DS)))
|
||||||
blockdata_free(key);
|
blockdata_free(key);
|
||||||
@@ -2058,10 +2065,10 @@ size_t dnssec_generate_query(struct dns_header *header, char *end, char *name, i
|
|||||||
char *types = querystr("dnssec-query", type);
|
char *types = querystr("dnssec-query", type);
|
||||||
|
|
||||||
if (addr->sa.sa_family == AF_INET)
|
if (addr->sa.sa_family == AF_INET)
|
||||||
log_query(F_DNSSEC | F_IPV4, name, (struct all_addr *)&addr->in.sin_addr, types);
|
log_query(F_NOEXTRA | F_DNSSEC | F_IPV4, name, (struct all_addr *)&addr->in.sin_addr, types);
|
||||||
#ifdef HAVE_IPV6
|
#ifdef HAVE_IPV6
|
||||||
else
|
else
|
||||||
log_query(F_DNSSEC | F_IPV6, name, (struct all_addr *)&addr->in6.sin6_addr, types);
|
log_query(F_NOEXTRA | F_DNSSEC | F_IPV6, name, (struct all_addr *)&addr->in6.sin6_addr, types);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
header->qdcount = htons(1);
|
header->qdcount = htons(1);
|
||||||
|
|||||||
+26
-4
@@ -279,10 +279,10 @@ static int forward_query(int udpfd, union mysockaddr *udpaddr,
|
|||||||
plen = forward->stash_len;
|
plen = forward->stash_len;
|
||||||
|
|
||||||
if (forward->sentto->addr.sa.sa_family == AF_INET)
|
if (forward->sentto->addr.sa.sa_family == AF_INET)
|
||||||
log_query(F_DNSSEC | F_IPV4, "retry", (struct all_addr *)&forward->sentto->addr.in.sin_addr, "dnssec");
|
log_query(F_NOEXTRA | F_DNSSEC | F_IPV4, "retry", (struct all_addr *)&forward->sentto->addr.in.sin_addr, "dnssec");
|
||||||
#ifdef HAVE_IPV6
|
#ifdef HAVE_IPV6
|
||||||
else
|
else
|
||||||
log_query(F_DNSSEC | F_IPV6, "retry", (struct all_addr *)&forward->sentto->addr.in6.sin6_addr, "dnssec");
|
log_query(F_NOEXTRA | F_DNSSEC | F_IPV6, "retry", (struct all_addr *)&forward->sentto->addr.in6.sin6_addr, "dnssec");
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
if (forward->sentto->sfd)
|
if (forward->sentto->sfd)
|
||||||
@@ -389,6 +389,9 @@ static int forward_query(int udpfd, union mysockaddr *udpaddr,
|
|||||||
struct server *firstsentto = start;
|
struct server *firstsentto = start;
|
||||||
int forwarded = 0;
|
int forwarded = 0;
|
||||||
|
|
||||||
|
/* If a query is retried, use the log_id for the retry when logging the answer. */
|
||||||
|
forward->log_id = daemon->log_id;
|
||||||
|
|
||||||
if (option_bool(OPT_ADD_MAC))
|
if (option_bool(OPT_ADD_MAC))
|
||||||
plen = add_mac(header, plen, ((char *) header) + daemon->packet_buff_sz, &forward->source);
|
plen = add_mac(header, plen, ((char *) header) + daemon->packet_buff_sz, &forward->source);
|
||||||
|
|
||||||
@@ -725,11 +728,16 @@ void reply_query(int fd, int family, time_t now)
|
|||||||
if (!(forward = lookup_frec(ntohs(header->id), hash)))
|
if (!(forward = lookup_frec(ntohs(header->id), hash)))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
|
/* log_query gets called indirectly all over the place, so
|
||||||
|
pass these in global variables - sorry. */
|
||||||
|
daemon->log_display_id = forward->log_id;
|
||||||
|
daemon->log_source_addr = &forward->source;
|
||||||
|
|
||||||
if (daemon->ignore_addr && RCODE(header) == NOERROR &&
|
if (daemon->ignore_addr && RCODE(header) == NOERROR &&
|
||||||
check_for_ignored_address(header, n, daemon->ignore_addr))
|
check_for_ignored_address(header, n, daemon->ignore_addr))
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if ((RCODE(header) == SERVFAIL || RCODE(header) == REFUSED) &&
|
if (RCODE(header) == REFUSED &&
|
||||||
!option_bool(OPT_ORDER) &&
|
!option_bool(OPT_ORDER) &&
|
||||||
forward->forwardall == 0)
|
forward->forwardall == 0)
|
||||||
/* for broken servers, attempt to send to another one. */
|
/* for broken servers, attempt to send to another one. */
|
||||||
@@ -1259,6 +1267,11 @@ void receive_query(struct listener *listen, time_t now)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* log_query gets called indirectly all over the place, so
|
||||||
|
pass these in global variables - sorry. */
|
||||||
|
daemon->log_display_id = ++daemon->log_id;
|
||||||
|
daemon->log_source_addr = &source_addr;
|
||||||
|
|
||||||
if (extract_request(header, (size_t)n, daemon->namebuff, &type))
|
if (extract_request(header, (size_t)n, daemon->namebuff, &type))
|
||||||
{
|
{
|
||||||
#ifdef HAVE_AUTH
|
#ifdef HAVE_AUTH
|
||||||
@@ -1675,6 +1688,7 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
struct in_addr dst_addr_4;
|
struct in_addr dst_addr_4;
|
||||||
union mysockaddr peer_addr;
|
union mysockaddr peer_addr;
|
||||||
socklen_t peer_len = sizeof(union mysockaddr);
|
socklen_t peer_len = sizeof(union mysockaddr);
|
||||||
|
int query_count = 0;
|
||||||
|
|
||||||
if (getpeername(confd, (struct sockaddr *)&peer_addr, &peer_len) == -1)
|
if (getpeername(confd, (struct sockaddr *)&peer_addr, &peer_len) == -1)
|
||||||
return packet;
|
return packet;
|
||||||
@@ -1712,7 +1726,8 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
|
|
||||||
while (1)
|
while (1)
|
||||||
{
|
{
|
||||||
if (!packet ||
|
if (query_count == TCP_MAX_QUERIES ||
|
||||||
|
!packet ||
|
||||||
!read_write(confd, &c1, 1, 1) || !read_write(confd, &c2, 1, 1) ||
|
!read_write(confd, &c1, 1, 1) || !read_write(confd, &c2, 1, 1) ||
|
||||||
!(size = c1 << 8 | c2) ||
|
!(size = c1 << 8 | c2) ||
|
||||||
!read_write(confd, payload, size, 1))
|
!read_write(confd, payload, size, 1))
|
||||||
@@ -1721,6 +1736,13 @@ unsigned char *tcp_request(int confd, time_t now,
|
|||||||
if (size < (int)sizeof(struct dns_header))
|
if (size < (int)sizeof(struct dns_header))
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
query_count++;
|
||||||
|
|
||||||
|
/* log_query gets called indirectly all over the place, so
|
||||||
|
pass these in global variables - sorry. */
|
||||||
|
daemon->log_display_id = ++daemon->log_id;
|
||||||
|
daemon->log_source_addr = &peer_addr;
|
||||||
|
|
||||||
check_subnet = 0;
|
check_subnet = 0;
|
||||||
|
|
||||||
/* save state of "cd" flag in query */
|
/* save state of "cd" flag in query */
|
||||||
|
|||||||
+112
-5
@@ -19,6 +19,11 @@
|
|||||||
|
|
||||||
#include <sys/inotify.h>
|
#include <sys/inotify.h>
|
||||||
|
|
||||||
|
#ifdef HAVE_DHCP
|
||||||
|
static void check_for_dhcp_inotify(struct inotify_event *in, time_t now);
|
||||||
|
#endif
|
||||||
|
|
||||||
|
|
||||||
/* the strategy is to set a inotify on the directories containing
|
/* the strategy is to set a inotify on the directories containing
|
||||||
resolv files, for any files in the directory which are close-write
|
resolv files, for any files in the directory which are close-write
|
||||||
or moved into the directory.
|
or moved into the directory.
|
||||||
@@ -40,8 +45,6 @@ void inotify_dnsmasq_init()
|
|||||||
struct resolvc *res;
|
struct resolvc *res;
|
||||||
|
|
||||||
inotify_buffer = safe_malloc(INOTIFY_SZ);
|
inotify_buffer = safe_malloc(INOTIFY_SZ);
|
||||||
|
|
||||||
|
|
||||||
daemon->inotifyfd = inotify_init1(IN_NONBLOCK | IN_CLOEXEC);
|
daemon->inotifyfd = inotify_init1(IN_NONBLOCK | IN_CLOEXEC);
|
||||||
|
|
||||||
if (daemon->inotifyfd == -1)
|
if (daemon->inotifyfd == -1)
|
||||||
@@ -66,6 +69,7 @@ void inotify_dnsmasq_init()
|
|||||||
{
|
{
|
||||||
*d = 0; /* make path just directory */
|
*d = 0; /* make path just directory */
|
||||||
res->wd = inotify_add_watch(daemon->inotifyfd, path, IN_CLOSE_WRITE | IN_MOVED_TO);
|
res->wd = inotify_add_watch(daemon->inotifyfd, path, IN_CLOSE_WRITE | IN_MOVED_TO);
|
||||||
|
|
||||||
res->file = d+1; /* pointer to filename */
|
res->file = d+1; /* pointer to filename */
|
||||||
*d = '/';
|
*d = '/';
|
||||||
|
|
||||||
@@ -78,7 +82,7 @@ void inotify_dnsmasq_init()
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
int inotify_check(void)
|
int inotify_check(time_t now)
|
||||||
{
|
{
|
||||||
int hit = 0;
|
int hit = 0;
|
||||||
|
|
||||||
@@ -101,13 +105,116 @@ int inotify_check(void)
|
|||||||
for (res = daemon->resolv_files; res; res = res->next)
|
for (res = daemon->resolv_files; res; res = res->next)
|
||||||
if (res->wd == in->wd && in->len != 0 && strcmp(res->file, in->name) == 0)
|
if (res->wd == in->wd && in->len != 0 && strcmp(res->file, in->name) == 0)
|
||||||
hit = 1;
|
hit = 1;
|
||||||
|
|
||||||
|
#ifdef HAVE_DHCP
|
||||||
|
if (daemon->dhcp || daemon->doing_dhcp6)
|
||||||
|
check_for_dhcp_inotify(in, now);
|
||||||
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return hit;
|
return hit;
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#ifdef HAVE_DHCP
|
||||||
|
/* initialisation for dhcp-hostdir. Set inotify watch for each directory, and read pre-existing files */
|
||||||
|
void set_dhcp_inotify(void)
|
||||||
|
{
|
||||||
|
struct hostsfile *ah;
|
||||||
|
|
||||||
|
for (ah = daemon->inotify_hosts; ah; ah = ah->next)
|
||||||
|
{
|
||||||
|
DIR *dir_stream = NULL;
|
||||||
|
struct dirent *ent;
|
||||||
|
struct stat buf;
|
||||||
|
|
||||||
|
if (stat(ah->fname, &buf) == -1 || !(S_ISDIR(buf.st_mode)))
|
||||||
|
{
|
||||||
|
my_syslog(LOG_ERR, _("bad directory in dhcp-hostsdir %s"), ah->fname);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!(ah->flags & AH_WD_DONE))
|
||||||
|
{
|
||||||
|
ah->wd = inotify_add_watch(daemon->inotifyfd, ah->fname, IN_CLOSE_WRITE | IN_MOVED_TO);
|
||||||
|
ah->flags |= AH_WD_DONE;
|
||||||
|
}
|
||||||
|
/* Read contents of dir _after_ calling add_watch, in the ho[e of avoiding
|
||||||
|
a race which misses files being added as we start */
|
||||||
|
if (ah->wd == -1 || !(dir_stream = opendir(ah->fname)))
|
||||||
|
{
|
||||||
|
my_syslog(LOG_ERR, _("failed to create inotify for %s"), ah->fname);
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
while ((ent = readdir(dir_stream)))
|
||||||
|
{
|
||||||
|
size_t lendir = strlen(ah->fname);
|
||||||
|
size_t lenfile = strlen(ent->d_name);
|
||||||
|
char *path;
|
||||||
|
|
||||||
|
/* ignore emacs backups and dotfiles */
|
||||||
|
if (lenfile == 0 ||
|
||||||
|
ent->d_name[lenfile - 1] == '~' ||
|
||||||
|
(ent->d_name[0] == '#' && ent->d_name[lenfile - 1] == '#') ||
|
||||||
|
ent->d_name[0] == '.')
|
||||||
|
continue;
|
||||||
|
|
||||||
|
if ((path = whine_malloc(lendir + lenfile + 2)))
|
||||||
|
{
|
||||||
|
strcpy(path, ah->fname);
|
||||||
|
strcat(path, "/");
|
||||||
|
strcat(path, ent->d_name);
|
||||||
|
|
||||||
|
/* ignore non-regular files */
|
||||||
|
if (stat(path, &buf) != -1 && S_ISREG(buf.st_mode))
|
||||||
|
option_read_hostsfile(path);
|
||||||
|
|
||||||
|
free(path);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void check_for_dhcp_inotify(struct inotify_event *in, time_t now)
|
||||||
|
{
|
||||||
|
struct hostsfile *ah;
|
||||||
|
|
||||||
|
/* ignore emacs backups and dotfiles */
|
||||||
|
if (in->len == 0 ||
|
||||||
|
in->name[in->len - 1] == '~' ||
|
||||||
|
(in->name[0] == '#' && in->name[in->len - 1] == '#') ||
|
||||||
|
in->name[0] == '.')
|
||||||
|
return;
|
||||||
|
|
||||||
|
for (ah = daemon->inotify_hosts; ah; ah = ah->next)
|
||||||
|
if (ah->wd == in->wd)
|
||||||
|
{
|
||||||
|
size_t lendir = strlen(ah->fname);
|
||||||
|
char *path;
|
||||||
|
|
||||||
|
if ((path = whine_malloc(lendir + in->len + 2)))
|
||||||
|
{
|
||||||
|
strcpy(path, ah->fname);
|
||||||
|
strcat(path, "/");
|
||||||
|
strcat(path, in->name);
|
||||||
|
|
||||||
|
if (option_read_hostsfile(path))
|
||||||
|
{
|
||||||
|
/* Propogate the consequences of loading a new dhcp-host */
|
||||||
|
dhcp_update_configs(daemon->dhcp_conf);
|
||||||
|
lease_update_from_configs();
|
||||||
|
lease_update_file(now);
|
||||||
|
lease_update_dns(1);
|
||||||
|
}
|
||||||
|
|
||||||
|
free(path);
|
||||||
|
}
|
||||||
|
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif /* DHCP */
|
||||||
|
|
||||||
|
#endif /* LINUX_NETWORK */
|
||||||
|
|
||||||
+37
-3
@@ -148,6 +148,8 @@ struct myoption {
|
|||||||
#define LOPT_DNSSEC_TIME 336
|
#define LOPT_DNSSEC_TIME 336
|
||||||
#define LOPT_LOOP_DETECT 337
|
#define LOPT_LOOP_DETECT 337
|
||||||
#define LOPT_IGNORE_ADDR 338
|
#define LOPT_IGNORE_ADDR 338
|
||||||
|
#define LOPT_MINCTTL 339
|
||||||
|
#define LOPT_DHCP_INOTIFY 340
|
||||||
|
|
||||||
#ifdef HAVE_GETOPT_LONG
|
#ifdef HAVE_GETOPT_LONG
|
||||||
static const struct option opts[] =
|
static const struct option opts[] =
|
||||||
@@ -160,7 +162,7 @@ static const struct myoption opts[] =
|
|||||||
{ "no-poll", 0, 0, 'n' },
|
{ "no-poll", 0, 0, 'n' },
|
||||||
{ "help", 0, 0, 'w' },
|
{ "help", 0, 0, 'w' },
|
||||||
{ "no-daemon", 0, 0, 'd' },
|
{ "no-daemon", 0, 0, 'd' },
|
||||||
{ "log-queries", 0, 0, 'q' },
|
{ "log-queries", 2, 0, 'q' },
|
||||||
{ "user", 2, 0, 'u' },
|
{ "user", 2, 0, 'u' },
|
||||||
{ "group", 2, 0, 'g' },
|
{ "group", 2, 0, 'g' },
|
||||||
{ "resolv-file", 2, 0, 'r' },
|
{ "resolv-file", 2, 0, 'r' },
|
||||||
@@ -246,6 +248,7 @@ static const struct myoption opts[] =
|
|||||||
{ "interface-name", 1, 0, LOPT_INTNAME },
|
{ "interface-name", 1, 0, LOPT_INTNAME },
|
||||||
{ "dhcp-hostsfile", 1, 0, LOPT_DHCP_HOST },
|
{ "dhcp-hostsfile", 1, 0, LOPT_DHCP_HOST },
|
||||||
{ "dhcp-optsfile", 1, 0, LOPT_DHCP_OPTS },
|
{ "dhcp-optsfile", 1, 0, LOPT_DHCP_OPTS },
|
||||||
|
{ "dhcp-hostsdir", 1, 0, LOPT_DHCP_INOTIFY },
|
||||||
{ "dhcp-no-override", 0, 0, LOPT_OVERRIDE },
|
{ "dhcp-no-override", 0, 0, LOPT_OVERRIDE },
|
||||||
{ "tftp-port-range", 1, 0, LOPT_TFTPPORTS },
|
{ "tftp-port-range", 1, 0, LOPT_TFTPPORTS },
|
||||||
{ "stop-dns-rebind", 0, 0, LOPT_REBIND },
|
{ "stop-dns-rebind", 0, 0, LOPT_REBIND },
|
||||||
@@ -255,6 +258,7 @@ static const struct myoption opts[] =
|
|||||||
{ "dhcp-broadcast", 2, 0, LOPT_BROADCAST },
|
{ "dhcp-broadcast", 2, 0, LOPT_BROADCAST },
|
||||||
{ "neg-ttl", 1, 0, LOPT_NEGTTL },
|
{ "neg-ttl", 1, 0, LOPT_NEGTTL },
|
||||||
{ "max-ttl", 1, 0, LOPT_MAXTTL },
|
{ "max-ttl", 1, 0, LOPT_MAXTTL },
|
||||||
|
{ "min-cache-ttl", 1, 0, LOPT_MINCTTL },
|
||||||
{ "max-cache-ttl", 1, 0, LOPT_MAXCTTL },
|
{ "max-cache-ttl", 1, 0, LOPT_MAXCTTL },
|
||||||
{ "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 },
|
||||||
@@ -333,6 +337,7 @@ static struct {
|
|||||||
{ 'G', ARG_DUP, "<hostspec>", gettext_noop("Set address or hostname for a specified machine."), NULL },
|
{ 'G', ARG_DUP, "<hostspec>", gettext_noop("Set address or hostname for a specified machine."), NULL },
|
||||||
{ LOPT_DHCP_HOST, ARG_DUP, "<path>", gettext_noop("Read DHCP host specs from file."), NULL },
|
{ LOPT_DHCP_HOST, ARG_DUP, "<path>", gettext_noop("Read DHCP host specs from file."), NULL },
|
||||||
{ LOPT_DHCP_OPTS, ARG_DUP, "<path>", gettext_noop("Read DHCP option specs from file."), NULL },
|
{ LOPT_DHCP_OPTS, ARG_DUP, "<path>", gettext_noop("Read DHCP option specs from file."), NULL },
|
||||||
|
{ LOPT_DHCP_INOTIFY, ARG_DUP, "<path>", gettext_noop("Read DHCP host specs from a directory."), NULL },
|
||||||
{ LOPT_TAG_IF, ARG_DUP, "tag-expression", gettext_noop("Evaluate conditional tag expression."), NULL },
|
{ LOPT_TAG_IF, ARG_DUP, "tag-expression", gettext_noop("Evaluate conditional tag expression."), NULL },
|
||||||
{ 'h', OPT_NO_HOSTS, NULL, gettext_noop("Do NOT load %s file."), HOSTSFILE },
|
{ 'h', OPT_NO_HOSTS, NULL, gettext_noop("Do NOT load %s file."), HOSTSFILE },
|
||||||
{ 'H', ARG_DUP, "<path>", gettext_noop("Specify a hosts file to be read in addition to %s."), HOSTSFILE },
|
{ 'H', ARG_DUP, "<path>", gettext_noop("Specify a hosts file to be read in addition to %s."), HOSTSFILE },
|
||||||
@@ -357,7 +362,7 @@ static struct {
|
|||||||
{ LOPT_FORCE, ARG_DUP, "<optspec>", gettext_noop("DHCP option sent even if the client does not request it."), NULL},
|
{ LOPT_FORCE, ARG_DUP, "<optspec>", gettext_noop("DHCP option sent even if the client does not request it."), NULL},
|
||||||
{ 'p', ARG_ONE, "<integer>", gettext_noop("Specify port to listen for DNS requests on (defaults to 53)."), NULL },
|
{ 'p', ARG_ONE, "<integer>", gettext_noop("Specify port to listen for DNS requests on (defaults to 53)."), NULL },
|
||||||
{ 'P', ARG_ONE, "<integer>", gettext_noop("Maximum supported UDP packet size for EDNS.0 (defaults to %s)."), "*" },
|
{ 'P', ARG_ONE, "<integer>", gettext_noop("Maximum supported UDP packet size for EDNS.0 (defaults to %s)."), "*" },
|
||||||
{ 'q', OPT_LOG, NULL, gettext_noop("Log DNS queries."), NULL },
|
{ 'q', ARG_DUP, NULL, gettext_noop("Log DNS queries."), NULL },
|
||||||
{ 'Q', ARG_ONE, "<integer>", gettext_noop("Force the originating port for upstream DNS queries."), NULL },
|
{ 'Q', ARG_ONE, "<integer>", gettext_noop("Force the originating port for upstream DNS queries."), NULL },
|
||||||
{ 'R', OPT_NO_RESOLV, NULL, gettext_noop("Do NOT read resolv.conf."), NULL },
|
{ 'R', OPT_NO_RESOLV, NULL, gettext_noop("Do NOT read resolv.conf."), NULL },
|
||||||
{ 'r', ARG_DUP, "<path>", gettext_noop("Specify path to resolv.conf (defaults to %s)."), RESOLVFILE },
|
{ 'r', ARG_DUP, "<path>", gettext_noop("Specify path to resolv.conf (defaults to %s)."), RESOLVFILE },
|
||||||
@@ -370,6 +375,8 @@ static struct {
|
|||||||
{ 'T', ARG_ONE, "<integer>", gettext_noop("Specify time-to-live in seconds for replies from /etc/hosts."), NULL },
|
{ 'T', ARG_ONE, "<integer>", gettext_noop("Specify time-to-live in seconds for replies from /etc/hosts."), NULL },
|
||||||
{ LOPT_NEGTTL, ARG_ONE, "<integer>", gettext_noop("Specify time-to-live in seconds for negative caching."), NULL },
|
{ LOPT_NEGTTL, ARG_ONE, "<integer>", gettext_noop("Specify time-to-live in seconds for negative caching."), NULL },
|
||||||
{ LOPT_MAXTTL, ARG_ONE, "<integer>", gettext_noop("Specify time-to-live in seconds for maximum TTL to send to clients."), NULL },
|
{ LOPT_MAXTTL, ARG_ONE, "<integer>", gettext_noop("Specify time-to-live in seconds for maximum TTL to send to clients."), NULL },
|
||||||
|
{ LOPT_MAXCTTL, ARG_ONE, "<integer>", gettext_noop("Specify time-to-live ceiling for cache."), NULL },
|
||||||
|
{ LOPT_MINCTTL, ARG_ONE, "<integer>", gettext_noop("Specify time-to-live floor for cache."), NULL },
|
||||||
{ 'u', ARG_ONE, "<username>", gettext_noop("Change to this user after startup. (defaults to %s)."), CHUSER },
|
{ 'u', ARG_ONE, "<username>", gettext_noop("Change to this user after startup. (defaults to %s)."), CHUSER },
|
||||||
{ 'U', ARG_DUP, "set:<tag>,<class>", gettext_noop("Map DHCP vendor class to tag."), NULL },
|
{ 'U', ARG_DUP, "set:<tag>,<class>", gettext_noop("Map DHCP vendor class to tag."), NULL },
|
||||||
{ 'v', 0, NULL, gettext_noop("Display dnsmasq version and copyright information."), NULL },
|
{ 'v', 0, NULL, gettext_noop("Display dnsmasq version and copyright information."), NULL },
|
||||||
@@ -1705,8 +1712,9 @@ static int one_opt(int option, char *arg, char *errstr, char *gen_err, int comma
|
|||||||
break;
|
break;
|
||||||
#endif /* HAVE_DHCP */
|
#endif /* HAVE_DHCP */
|
||||||
|
|
||||||
case LOPT_DHCP_HOST: /* --dhcp-hostfile */
|
case LOPT_DHCP_HOST: /* --dhcp-hostsfile */
|
||||||
case LOPT_DHCP_OPTS: /* --dhcp-optsfile */
|
case LOPT_DHCP_OPTS: /* --dhcp-optsfile */
|
||||||
|
case LOPT_DHCP_INOTIFY: /* dhcp-hostsdir */
|
||||||
case 'H': /* --addn-hosts */
|
case 'H': /* --addn-hosts */
|
||||||
{
|
{
|
||||||
struct hostsfile *new = opt_malloc(sizeof(struct hostsfile));
|
struct hostsfile *new = opt_malloc(sizeof(struct hostsfile));
|
||||||
@@ -1729,6 +1737,12 @@ static int one_opt(int option, char *arg, char *errstr, char *gen_err, int comma
|
|||||||
new->next = daemon->dhcp_opts_file;
|
new->next = daemon->dhcp_opts_file;
|
||||||
daemon->dhcp_opts_file = new;
|
daemon->dhcp_opts_file = new;
|
||||||
}
|
}
|
||||||
|
else if (option == LOPT_DHCP_INOTIFY)
|
||||||
|
{
|
||||||
|
new->next = daemon->inotify_hosts;
|
||||||
|
daemon->inotify_hosts = new;
|
||||||
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -2421,6 +2435,12 @@ 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 'q': /* --log-queries */
|
||||||
|
set_option_bool(OPT_LOG);
|
||||||
|
if (arg && strcmp(arg, "extra") == 0)
|
||||||
|
set_option_bool(OPT_EXTRALOG);
|
||||||
|
break;
|
||||||
|
|
||||||
case LOPT_MAX_LOGS: /* --log-async */
|
case LOPT_MAX_LOGS: /* --log-async */
|
||||||
daemon->max_logs = LOG_MAX; /* default */
|
daemon->max_logs = LOG_MAX; /* default */
|
||||||
if (arg && !atoi_check(arg, &daemon->max_logs))
|
if (arg && !atoi_check(arg, &daemon->max_logs))
|
||||||
@@ -2450,6 +2470,7 @@ static int one_opt(int option, char *arg, char *errstr, char *gen_err, int comma
|
|||||||
case 'T': /* --local-ttl */
|
case 'T': /* --local-ttl */
|
||||||
case LOPT_NEGTTL: /* --neg-ttl */
|
case LOPT_NEGTTL: /* --neg-ttl */
|
||||||
case LOPT_MAXTTL: /* --max-ttl */
|
case LOPT_MAXTTL: /* --max-ttl */
|
||||||
|
case LOPT_MINCTTL: /* --min-cache-ttl */
|
||||||
case LOPT_MAXCTTL: /* --max-cache-ttl */
|
case LOPT_MAXCTTL: /* --max-cache-ttl */
|
||||||
case LOPT_AUTHTTL: /* --auth-ttl */
|
case LOPT_AUTHTTL: /* --auth-ttl */
|
||||||
{
|
{
|
||||||
@@ -2460,6 +2481,12 @@ static int one_opt(int option, char *arg, char *errstr, char *gen_err, int comma
|
|||||||
daemon->neg_ttl = (unsigned long)ttl;
|
daemon->neg_ttl = (unsigned long)ttl;
|
||||||
else if (option == LOPT_MAXTTL)
|
else if (option == LOPT_MAXTTL)
|
||||||
daemon->max_ttl = (unsigned long)ttl;
|
daemon->max_ttl = (unsigned long)ttl;
|
||||||
|
else if (option == LOPT_MINCTTL)
|
||||||
|
{
|
||||||
|
if (ttl > TTL_FLOOR_LIMIT)
|
||||||
|
ttl = TTL_FLOOR_LIMIT;
|
||||||
|
daemon->min_cache_ttl = (unsigned long)ttl;
|
||||||
|
}
|
||||||
else if (option == LOPT_MAXCTTL)
|
else if (option == LOPT_MAXCTTL)
|
||||||
daemon->max_cache_ttl = (unsigned long)ttl;
|
daemon->max_cache_ttl = (unsigned long)ttl;
|
||||||
else if (option == LOPT_AUTHTTL)
|
else if (option == LOPT_AUTHTTL)
|
||||||
@@ -4024,6 +4051,13 @@ static void read_file(char *file, FILE *f, int hard_opt)
|
|||||||
fclose(f);
|
fclose(f);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
#ifdef HAVE_DHCP
|
||||||
|
int option_read_hostsfile(char *file)
|
||||||
|
{
|
||||||
|
return one_file(file, LOPT_BANK);
|
||||||
|
}
|
||||||
|
#endif
|
||||||
|
|
||||||
static int one_file(char *file, int hard_opt)
|
static int one_file(char *file, int hard_opt)
|
||||||
{
|
{
|
||||||
FILE *f;
|
FILE *f;
|
||||||
|
|||||||
+1
-1
@@ -1643,7 +1643,7 @@ size_t answer_request(struct dns_header *header, char *limit, size_t qlen,
|
|||||||
{
|
{
|
||||||
if (crecp->flags & F_NXDOMAIN)
|
if (crecp->flags & F_NXDOMAIN)
|
||||||
nxdomain = 1;
|
nxdomain = 1;
|
||||||
log_query(F_UPSTREAM, name, NULL, "secure no DS");
|
log_query(F_UPSTREAM, name, NULL, "no DS");
|
||||||
}
|
}
|
||||||
else if ((keydata = blockdata_retrieve(crecp->addr.ds.keydata, crecp->addr.ds.keylen, NULL)))
|
else if ((keydata = blockdata_retrieve(crecp->addr.ds.keydata, crecp->addr.ds.keylen, NULL)))
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -274,6 +274,7 @@ int sockaddr_isequal(union mysockaddr *s1, union mysockaddr *s2)
|
|||||||
#ifdef HAVE_IPV6
|
#ifdef HAVE_IPV6
|
||||||
if (s1->sa.sa_family == AF_INET6 &&
|
if (s1->sa.sa_family == AF_INET6 &&
|
||||||
s1->in6.sin6_port == s2->in6.sin6_port &&
|
s1->in6.sin6_port == s2->in6.sin6_port &&
|
||||||
|
s1->in6.sin6_scope_id == s2->in6.sin6_scope_id &&
|
||||||
IN6_ARE_ADDR_EQUAL(&s1->in6.sin6_addr, &s2->in6.sin6_addr))
|
IN6_ARE_ADDR_EQUAL(&s1->in6.sin6_addr, &s2->in6.sin6_addr))
|
||||||
return 1;
|
return 1;
|
||||||
#endif
|
#endif
|
||||||
|
|||||||
Reference in new issue
Block a user