diff --git a/CHANGELOG b/CHANGELOG index 6912b4a..35adf66 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -14,6 +14,13 @@ version 2.63 A couple of fixes to the build system for Android. Thanks to Metin Kaya for the patches. + Remove the interface: argument in --dhcp-range, and + the interface argument to --enable-tftp. These were a + still-born attempt to allow automatic isolated + configuration by libvirt, but have never (to my knowledge) + been used, had very strange semantics, and have been + superceded by other mechanisms. + version 2.62 Update German translation. Thanks to Conrad Kostecki. diff --git a/man/dnsmasq.8 b/man/dnsmasq.8 index 79f8ccc..9357cf5 100644 --- a/man/dnsmasq.8 +++ b/man/dnsmasq.8 @@ -529,9 +529,9 @@ compiled in and the kernel must have conntrack support included and configured. This option cannot be combined with --query-port. .TP -.B \-F, --dhcp-range=[interface:,][tag:[,tag:],][set:[,][,][,[,]][,] +.B \-F, --dhcp-range=[tag:[,tag:],][set:[,][,][,[,]][,] .TP -.B \-F, --dhcp-range=[interface:,][tag:[,tag:],][set:[,][,][,][,] +.B \-F, --dhcp-range=[tag:[,tag:],][set:[,][,][,][,] Enable the DHCP server. Addresses will be given out from the range to and from statically defined addresses given @@ -624,8 +624,6 @@ can be combined with and .B slaac. -The interface: section is not normally used. See the -NOTES section for details of this. .TP .B \-G, --dhcp-host=[][,id:|*][,set:][,][,][,][,ignore] Specify per host parameters for the DHCP server. This allows a machine @@ -1369,12 +1367,11 @@ the relevant link-local address of the machine running dnsmasq is sent as recursive DNS server. If provided, the DHCPv6 options dns-server and domain-search are used for RDNSS and DNSSL. .TP -.B --enable-tftp[=] +.B --enable-tftp Enable the TFTP server function. This is deliberately limited to that needed to net-boot a client. Only reading is allowed; the tsize and blksize extensions are supported (tsize is only supported in octet -mode). See NOTES section for use of the interface argument. - +mode). .TP .B --tftp-root=[,] Look for files to transfer using TFTP relative to the given @@ -1638,52 +1635,6 @@ parameter in a BOOTP request is used as a tag, as is the tag "bootp", allowing some control over the options returned to different classes of hosts. -.B dhcp-range -may have an interface name supplied as -"interface:". The semantics if this are as follows: -For DHCP, if any other dhcp-range exists _without_ an interface name, -then the interface name is ignored and and dnsmasq behaves as if the -interface parts did not exist, otherwise DHCP is only provided to -interfaces mentioned in dhcp-range -declarations. For DNS, if there are no -.B --interface -or -.B --listen-address -flags, behaviour is unchanged by the interface part. If either of -these flags are present, the interfaces mentioned in -dhcp-ranges are added to the set which get DNS service. - -Similarly, -.B enable-tftp -may take an interface name, which enables TFTP only for a particular -interface, ignoring -.B --interface -or -.B --listen-address -flags. In addition -.B --tftp-secure -and -.B --tftp-unique-root -and -.B --tftp-no-blocksize -are ignored for requests from such interfaces. (A -.B --tftp-root -directive giving a root path and an interface should be -provided too.) - -These rules may seem odd at first sight, but they -allow a single line of the form "dhcp-range=interface:virt0,192.168.0.4,192.168.0.200" -to be added to dnsmasq configuration which then supplies -DHCP and DNS services to that interface, without affecting -what services are supplied to other interfaces and irrespective of -the existance or lack of "interface=" -lines elsewhere in the dnsmasq configuration. -"enable-tftp=virt0" and "tftp-root=,virt0" do the same job for TFTP. - The idea is -that such a line can be added automatically by libvirt -or equivalent systems, without disturbing any manual -configuration. - .SH EXIT CODES .PP 0 - Dnsmasq successfully forked into the background, or terminated diff --git a/src/dhcp-common.c b/src/dhcp-common.c index 041b46c..2bf11a6 100644 --- a/src/dhcp-common.c +++ b/src/dhcp-common.c @@ -372,7 +372,6 @@ static int join_multicast_worker(struct in6_addr *local, int prefix, char ifrn_name[IFNAMSIZ]; struct ipv6_mreq mreq; int fd, i, max = *((int *)vparam); - struct dhcp_context *context; struct iname *tmp; (void)prefix; @@ -406,15 +405,6 @@ static int join_multicast_worker(struct in6_addr *local, int prefix, if (tmp->name && (strcmp(tmp->name, ifrn_name) == 0)) return 1; - /* weird libvirt-inspired access control */ - for (context = daemon->ra_contexts ? daemon->ra_contexts : daemon->dhcp6; - context; context = context->next) - if (!context->interface || strcmp(context->interface, ifrn_name) == 0) - break; - - if (!context) - return 1; - mreq.ipv6mr_interface = if_index; inet_pton(AF_INET6, ALL_RELAY_AGENTS_AND_SERVERS, &mreq.ipv6mr_multiaddr); diff --git a/src/dhcp.c b/src/dhcp.c index 9496ba2..83ba87e 100644 --- a/src/dhcp.c +++ b/src/dhcp.c @@ -257,14 +257,6 @@ void dhcp_packet(time_t now, int pxe_fd) if (tmp->name && (strcmp(tmp->name, ifr.ifr_name) == 0)) return; - /* weird libvirt-inspired access control */ - for (context = daemon->dhcp; context; context = context->next) - if (!context->interface || strcmp(context->interface, ifr.ifr_name) == 0) - break; - - if (!context) - return; - /* unlinked contexts are marked by context->current == context */ for (context = daemon->dhcp; context; context = context->next) context->current = context; @@ -277,7 +269,7 @@ void dhcp_packet(time_t now, int pxe_fd) /* If we failed to match the primary address of the interface, see if we've got a --listen-address for a secondary */ struct match_param match; - + match.matched = 0; match.ind = iface_index; diff --git a/src/dhcp6.c b/src/dhcp6.c index cf613ad..e31456c 100644 --- a/src/dhcp6.c +++ b/src/dhcp6.c @@ -111,14 +111,6 @@ void dhcp6_packet(time_t now) if (tmp->name && (strcmp(tmp->name, ifr.ifr_name) == 0)) return; - /* weird libvirt-inspired access control */ - for (context = daemon->dhcp6; context; context = context->next) - if (!context->interface || strcmp(context->interface, ifr.ifr_name) == 0) - break; - - if (!context) - return; - /* unlinked contexts are marked by context->current == context */ for (context = daemon->dhcp6; context; context = context->next) { diff --git a/src/dnsmasq.c b/src/dnsmasq.c index 3a550a9..25943d7 100644 --- a/src/dnsmasq.c +++ b/src/dnsmasq.c @@ -125,7 +125,7 @@ int main (int argc, char **argv) #endif #ifndef HAVE_TFTP - if (daemon->tftp_unlimited || daemon->tftp_interfaces) + if (option_bool(OPT_TFTP) die(_("TFTP server not available: set HAVE_TFTP in src/config.h"), NULL, EC_BADCONF); #endif @@ -512,7 +512,7 @@ int main (int argc, char **argv) #endif #ifdef HAVE_TFTP - if (daemon->tftp_unlimited || daemon->tftp_interfaces) + if (option_bool(OPT_TFTP)) { DIR *dir; struct tftp_prefix *p; @@ -668,7 +668,7 @@ int main (int argc, char **argv) #ifdef HAVE_TFTP - if (daemon->tftp_unlimited || daemon->tftp_interfaces) + if (option_bool(OPT_TFTP)) { #ifdef FD_SETSIZE if (FD_SETSIZE < (unsigned)max_fd) diff --git a/src/dnsmasq.h b/src/dnsmasq.h index 2d8d9b2..8a594f0 100644 --- a/src/dnsmasq.h +++ b/src/dnsmasq.h @@ -220,7 +220,8 @@ struct event_desc { #define OPT_RA 37 #define OPT_TFTP_LC 38 #define OPT_CLEVERBIND 39 -#define OPT_LAST 40 +#define OPT_TFTP 40 +#define OPT_LAST 41 /* 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. */ @@ -664,7 +665,6 @@ struct dhcp_context { time_t ra_time; #endif int flags; - char *interface; struct dhcp_netid netid, *filter; struct dhcp_context *next, *current; }; @@ -712,11 +712,6 @@ struct addr_list { struct addr_list *next; }; -struct interface_list { - char *interface; - struct interface_list *next; -}; - struct tftp_prefix { char *interface; char *prefix; @@ -780,8 +775,6 @@ extern struct daemon { unsigned short edns_pktsz; char *tftp_prefix; struct tftp_prefix *if_prefix; /* per-interface TFTP prefixes */ - struct interface_list *tftp_interfaces; /* interfaces for limited TFTP service */ - int tftp_unlimited; unsigned int duid_enterprise, duid_config_len; unsigned char *duid_config; diff --git a/src/network.c b/src/network.c index 6be41a8..90fdde9 100644 --- a/src/network.c +++ b/src/network.c @@ -117,18 +117,8 @@ int iface_check(int family, struct all_addr *addr, char *name) if (daemon->if_names || daemon->if_addrs) { -#ifdef HAVE_DHCP - struct dhcp_context *range; -#endif - ret = 0; -#ifdef HAVE_DHCP - for (range = daemon->dhcp; range; range = range->next) - if (range->interface && strcmp(range->interface, name) == 0) - ret = 1; -#endif - for (tmp = daemon->if_names; tmp; tmp = tmp->next) if (tmp->name && (strcmp(tmp->name, name) == 0)) ret = tmp->used = 1; @@ -161,12 +151,11 @@ static int iface_allowed(struct irec **irecp, int if_index, struct irec *iface; int fd, mtu = 0, loopback; struct ifreq ifr; - int tftp_ok = daemon->tftp_unlimited; + int tftp_ok = !!option_bool(OPT_TFTP); int dhcp_ok = 1; #ifdef HAVE_DHCP struct iname *tmp; #endif - struct interface_list *ir = NULL; /* check whether the interface IP has been added already we call this routine multiple times. */ @@ -220,37 +209,25 @@ static int iface_allowed(struct irec **irecp, int if_index, } } -#ifdef HAVE_TFTP - /* implement wierd TFTP service rules */ - for (ir = daemon->tftp_interfaces; ir; ir = ir->next) - if (strcmp(ir->interface, ifr.ifr_name) == 0) + if (addr->sa.sa_family == AF_INET && + !iface_check(AF_INET, (struct all_addr *)&addr->in.sin_addr, ifr.ifr_name)) + return 1; + +#ifdef HAVE_DHCP + for (tmp = daemon->dhcp_except; tmp; tmp = tmp->next) + if (tmp->name && (strcmp(tmp->name, ifr.ifr_name) == 0)) { - tftp_ok = 1; - break; + tftp_ok = 0; + dhcp_ok = 0; } #endif - if (!ir) - { - if (addr->sa.sa_family == AF_INET && - !iface_check(AF_INET, (struct all_addr *)&addr->in.sin_addr, ifr.ifr_name)) - return 1; - -#ifdef HAVE_DHCP - for (tmp = daemon->dhcp_except; tmp; tmp = tmp->next) - if (tmp->name && (strcmp(tmp->name, ifr.ifr_name) == 0)) - { - tftp_ok = 0; - dhcp_ok = 0; - } -#endif - #ifdef HAVE_IPV6 - if (addr->sa.sa_family == AF_INET6 && - !iface_check(AF_INET6, (struct all_addr *)&addr->in6.sin6_addr, ifr.ifr_name)) - return 1; + if (addr->sa.sa_family == AF_INET6 && + !iface_check(AF_INET6, (struct all_addr *)&addr->in6.sin6_addr, ifr.ifr_name)) + return 1; #endif - } + /* add to list */ if ((iface = whine_malloc(sizeof(struct irec)))) @@ -485,8 +462,7 @@ static struct listener *create_listeners(union mysockaddr *addr, int do_tftp, in void create_wildcard_listeners(void) { union mysockaddr addr; - struct listener *l; - int tftp_enabled = daemon->tftp_unlimited || daemon->tftp_interfaces; + struct listener *l, *l6; memset(&addr, 0, sizeof(addr)); #ifdef HAVE_SOCKADDR_SA_LEN @@ -496,7 +472,7 @@ void create_wildcard_listeners(void) addr.in.sin_addr.s_addr = INADDR_ANY; addr.in.sin_port = htons(daemon->port); - l = create_listeners(&addr, tftp_enabled, 1); + l = create_listeners(&addr, !!option_bool(OPT_TFTP), 1); #ifdef HAVE_IPV6 memset(&addr, 0, sizeof(addr)); @@ -506,11 +482,12 @@ void create_wildcard_listeners(void) addr.in6.sin6_family = AF_INET6; addr.in6.sin6_addr = in6addr_any; addr.in6.sin6_port = htons(daemon->port); - + + l6 = create_listeners(&addr, !!option_bool(OPT_TFTP), 1); if (l) - l->next = create_listeners(&addr, tftp_enabled, 1); + l->next = l6; else - l = create_listeners(&addr, tftp_enabled, 1); + l = l6; #endif daemon->listeners = l; @@ -544,7 +521,7 @@ void create_bound_listeners(int dienow) for (if_tmp = daemon->if_addrs; if_tmp; if_tmp = if_tmp->next) if (!if_tmp->used && - (new = create_listeners(&if_tmp->addr, daemon->tftp_unlimited, dienow))) + (new = create_listeners(&if_tmp->addr, !!option_bool(OPT_TFTP), dienow))) { new->iface = NULL; new->next = daemon->listeners; diff --git a/src/option.c b/src/option.c index 7eea357..db67a37 100644 --- a/src/option.c +++ b/src/option.c @@ -195,7 +195,7 @@ static const struct myoption opts[] = { "dns-forward-max", 1, 0, '0' }, { "clear-on-reload", 0, 0, LOPT_RELOAD }, { "dhcp-ignore-names", 2, 0, LOPT_NO_NAMES }, - { "enable-tftp", 2, 0, LOPT_TFTP }, + { "enable-tftp", 0, 0, LOPT_TFTP }, { "tftp-secure", 0, 0, LOPT_SECURE }, { "tftp-unique-root", 0, 0, LOPT_APREF }, { "tftp-root", 1, 0, LOPT_PREFIX }, @@ -342,7 +342,7 @@ static struct { { LOPT_RELOAD, OPT_RELOAD, NULL, gettext_noop("Clear DNS cache when reloading %s."), RESOLVFILE }, { LOPT_NO_NAMES, ARG_DUP, "[=tag:]...", gettext_noop("Ignore hostnames provided by DHCP clients."), NULL }, { LOPT_OVERRIDE, OPT_NO_OVERRIDE, NULL, gettext_noop("Do NOT reuse filename and server fields for extra DHCP options."), NULL }, - { LOPT_TFTP, ARG_DUP, "[=]", gettext_noop("Enable integrated read-only TFTP server."), NULL }, + { LOPT_TFTP, OPT_TFTP, NULL, gettext_noop("Enable integrated read-only TFTP server."), NULL }, { LOPT_PREFIX, ARG_DUP, "[,]", gettext_noop("Export files by TFTP only from the specified subtree."), NULL }, { LOPT_APREF, OPT_TFTP_APREF, NULL, gettext_noop("Add client IP address to tftp-root."), NULL }, { LOPT_SECURE, OPT_TFTP_SECURE, NULL, gettext_noop("Allow access only to files owned by the user running dnsmasq."), NULL }, @@ -1909,18 +1909,6 @@ static char *one_opt(int option, char *arg, char *gen_prob, int command_line) #endif #ifdef HAVE_TFTP - case LOPT_TFTP: /* --enable-tftp */ - if (arg) - { - struct interface_list *new = opt_malloc(sizeof(struct interface_list)); - new->interface = opt_string_alloc(arg); - new->next = daemon->tftp_interfaces; - daemon->tftp_interfaces = new; - } - else - daemon->tftp_unlimited = 1; - break; - case LOPT_TFTP_MAX: /* --tftp-max */ if (!atoi_check(arg, &daemon->tftp_max)) option = '?'; @@ -2013,9 +2001,7 @@ static char *one_opt(int option, char *arg, char *gen_prob, int command_line) if (*cp != ',' && (comma = split(arg))) { - if (strstr(arg, "interface:") == arg) - new->interface = opt_string_alloc(arg+10); - else if (is_tag_prefix(arg)) + if (is_tag_prefix(arg)) { struct dhcp_netid *tt = opt_malloc(sizeof (struct dhcp_netid)); tt->net = opt_string_alloc(arg+4); diff --git a/src/radv.c b/src/radv.c index 632e008..a3e691a 100644 --- a/src/radv.c +++ b/src/radv.c @@ -119,7 +119,6 @@ void icmp6_packet(void) struct sockaddr_in6 from; unsigned char *packet; struct iname *tmp; - struct dhcp_context *context; /* Note: use outpacket for input buffer */ msg.msg_control = control_u.control6; @@ -157,15 +156,9 @@ void icmp6_packet(void) if (tmp->name && (strcmp(tmp->name, interface) == 0)) return; - /* weird libvirt-inspired access control */ - for (context = daemon->ra_contexts ? daemon->ra_contexts : daemon->dhcp6; - context; context = context->next) - if (!context->interface || strcmp(context->interface, interface) == 0) - break; - - if (!context || packet[1] != 0) + if (packet[1] != 0) return; - + if (packet[0] == ICMP6_ECHO_REPLY) lease_ping_reply(&from.sin6_addr, packet, interface); else if (packet[0] == ND_ROUTER_SOLICIT) diff --git a/src/tftp.c b/src/tftp.c index 0ab966d..a7f5680 100644 --- a/src/tftp.c +++ b/src/tftp.c @@ -18,7 +18,7 @@ #ifdef HAVE_TFTP -static struct tftp_file *check_tftp_fileperm(ssize_t *len, char *prefix, int special); +static struct tftp_file *check_tftp_fileperm(ssize_t *len, char *prefix); static void free_transfer(struct tftp_transfer *transfer); static ssize_t tftp_err(int err, char *packet, char *mess, char *file); static ssize_t tftp_err_oops(char *packet, char *file); @@ -48,7 +48,7 @@ void tftp_request(struct listener *listen, time_t now) struct msghdr msg; struct iovec iov; struct ifreq ifr; - int is_err = 1, if_index = 0, mtu = 0, special = 0; + int is_err = 1, if_index = 0, mtu = 0; #ifdef HAVE_DHCP struct iname *tmp; #endif @@ -61,7 +61,6 @@ void tftp_request(struct listener *listen, time_t now) char *name = NULL; char *prefix = daemon->tftp_prefix; struct tftp_prefix *pref; - struct interface_list *ir; union { struct cmsghdr align; /* this ensures alignment */ @@ -115,7 +114,6 @@ void tftp_request(struct listener *listen, time_t now) { struct cmsghdr *cmptr; int check; - struct interface_list *ir; if (msg.msg_controllen < sizeof(struct cmsghdr)) return; @@ -200,24 +198,13 @@ void tftp_request(struct listener *listen, time_t now) #endif check = iface_check(AF_INET, (struct all_addr *)&addr.in.sin_addr, name); - /* wierd TFTP service override */ - for (ir = daemon->tftp_interfaces; ir; ir = ir->next) - if (strcmp(ir->interface, name) == 0) - break; - - if (!ir) - { - if (!daemon->tftp_unlimited || !check) - return; - #ifdef HAVE_DHCP - /* allowed interfaces are the same as for DHCP */ - for (tmp = daemon->dhcp_except; tmp; tmp = tmp->next) - if (tmp->name && (strcmp(tmp->name, name) == 0)) - return; + /* allowed interfaces are the same as for DHCP */ + for (tmp = daemon->dhcp_except; tmp; tmp = tmp->next) + if (tmp->name && (strcmp(tmp->name, name) == 0)) + return; #endif - } - + strncpy(ifr.ifr_name, name, IF_NAMESIZE); if (ioctl(listen->tftpfd, SIOCGIFMTU, &ifr) != -1) mtu = ifr.ifr_mtu; @@ -228,12 +215,7 @@ void tftp_request(struct listener *listen, time_t now) /* check for per-interface prefix */ for (pref = daemon->if_prefix; pref; pref = pref->next) if (strcmp(pref->interface, name) == 0) - prefix = pref->prefix; - - /* wierd TFTP interfaces disable special options. */ - for (ir = daemon->tftp_interfaces; ir; ir = ir->next) - if (strcmp(ir->interface, name) == 0) - special = 1; + prefix = pref->prefix; } if (listen->family == AF_INET) @@ -325,8 +307,7 @@ void tftp_request(struct listener *listen, time_t now) { if (strcasecmp(opt, "blksize") == 0) { - if ((opt = next(&p, end)) && - (special || !option_bool(OPT_TFTP_NOBLOCK))) + if ((opt = next(&p, end)) && !option_bool(OPT_TFTP_NOBLOCK)) { transfer->blocksize = atoi(opt); if (transfer->blocksize < 1) @@ -363,7 +344,7 @@ void tftp_request(struct listener *listen, time_t now) if (prefix[strlen(prefix)-1] != '/') strncat(daemon->namebuff, "/", (MAXDNAME-1) - strlen(daemon->namebuff)); - if (!special && option_bool(OPT_TFTP_APREF)) + if (option_bool(OPT_TFTP_APREF)) { size_t oldlen = strlen(daemon->namebuff); struct stat statbuf; @@ -390,7 +371,7 @@ void tftp_request(struct listener *listen, time_t now) strncat(daemon->namebuff, filename, (MAXDNAME-1) - strlen(daemon->namebuff)); /* check permissions and open file */ - if ((transfer->file = check_tftp_fileperm(&len, prefix, special))) + if ((transfer->file = check_tftp_fileperm(&len, prefix))) { if ((len = get_block(packet, transfer)) == -1) len = tftp_err_oops(packet, daemon->namebuff); @@ -411,7 +392,7 @@ void tftp_request(struct listener *listen, time_t now) } } -static struct tftp_file *check_tftp_fileperm(ssize_t *len, char *prefix, int special) +static struct tftp_file *check_tftp_fileperm(ssize_t *len, char *prefix) { char *packet = daemon->packet, *namebuff = daemon->namebuff; struct tftp_file *file; @@ -448,7 +429,7 @@ static struct tftp_file *check_tftp_fileperm(ssize_t *len, char *prefix, int spe goto perm; } /* in secure mode, must be owned by user running dnsmasq */ - else if (!special && option_bool(OPT_TFTP_SECURE) && uid != statbuf.st_uid) + else if (option_bool(OPT_TFTP_SECURE) && uid != statbuf.st_uid) goto perm; /* If we're doing many tranfers from the same file, only