Commit 4a4d7bbd authored by Jeremy C. Reed's avatar Jeremy C. Reed
Browse files

Merge branch 'master' into trac1091

parents 70f72008 4e99a42d
296. [bug] jinmei
__init__.py for isc.dns was installed in the wrong directory,
which would now make xfrin fail to start. It was also bad
in that it replaced any existing __init__.py in th public
site-packages directory. After applying this fix You may want to
check if the wrong init file is in the wrong place, in which
case it should be removed.
(Trac #1285, git af3b17472694f58b3d6a56d0baf64601b0f6a6a1)
295. [func]* jinmei
b10-xfrin: the AXFR implementation is unified with IXFR, and
handles corner cases more carefully. Note: As a result of this
change, xfrin does not create a new (SQLite3) zone in a fresh DB
file upon receiving AXFR any more. Initial zone content must be
prepared by hand (e.g. with b10-loadzone) until a more generic
tool for zone management is provided.
(Trac #1209, git 5ca7b409bccc815cee58c804236504fda1c1c147)
294. [func] jelte, jinmei, vorner
b10-xfrin now supports incoming IXFR. See BIND 10 Guide for
how to configure it and operational notes.
(Trac #1212, multiple git merges)
293. [func]* tomek
b10-dhcp6: Implemented DHCPv6 echo server. It joins DHCPv6
multicast groups and listens to incoming DHCPv6 client messages.
Received messages are then echoed back to clients. This
functionality is limited, but it can be used to test out client
resiliency to unexpected messages. Note that network interface
detection routines are not implemented yet, so interface name
and its address must be specified in interfaces.txt.
(Trac #878, git 3b1a604abf5709bfda7271fa94213f7d823de69d)
292. [func] dvv
Implement the DLV rrtype according to RFC4431.
(Trac #1144, git d267c0511a07c41cd92e3b0b9ee9bf693743a7cf)
......@@ -35,7 +68,7 @@
configuration.
(Trac #1165, git 698176eccd5d55759fe9448b2c249717c932ac31)
288. [bug] stephen
288. [bug] stephen
Fixed problem whereby the order in which component files appeared in
rdataclass.cc was system dependent, leading to problems on some
systems where data types were used before the header file in which
......
......@@ -2,12 +2,16 @@ SUBDIRS = doc src tests
USE_LCOV=@USE_LCOV@
LCOV=@LCOV@
GENHTML=@GENHTML@
DISTCHECK_GTEST_CONFIGURE_FLAG=@DISTCHECK_GTEST_CONFIGURE_FLAG@
DISTCLEANFILES = config.report
# When running distcheck target, do not install the configurations
DISTCHECK_CONFIGURE_FLAGS = --disable-install-configurations
# Use same --with-gtest flag if set
DISTCHECK_CONFIGURE_FLAGS += $(DISTCHECK_GTEST_CONFIGURE_FLAG)
clean-cpp-coverage:
@if [ $(USE_LCOV) = yes ] ; then \
$(LCOV) --directory . --zerocounters; \
......
......@@ -650,6 +650,7 @@ fi
#
if test "$gtest_path" != "no"
then
DISTCHECK_GTEST_CONFIGURE_FLAG="--with-gtest=\"$gtest_path\""
if test "$gtest_path" != "yes"; then
GTEST_PATHS=$gtest_path
if test -x "${gtest_path}/bin/gtest-config" ; then
......@@ -690,8 +691,10 @@ else
GTEST_INCLUDES=
GTEST_LDFLAGS=
GTEST_LDADD=
DISTCHECK_GTEST_CONFIGURE_FLAG=
fi
AM_CONDITIONAL(HAVE_GTEST, test $gtest_path != "no")
AC_SUBST(DISTCHECK_GTEST_CONFIGURE_FLAG)
AC_SUBST(GTEST_INCLUDES)
AC_SUBST(GTEST_LDFLAGS)
AC_SUBST(GTEST_LDADD)
......@@ -811,6 +814,7 @@ AC_CONFIG_FILES([Makefile
src/bin/sockcreator/tests/Makefile
src/bin/xfrin/Makefile
src/bin/xfrin/tests/Makefile
src/bin/xfrin/tests/testdata/Makefile
src/bin/xfrout/Makefile
src/bin/xfrout/tests/Makefile
src/bin/zonemgr/Makefile
......
......@@ -574,7 +574,7 @@ INPUT = ../src/lib/exceptions ../src/lib/cc \
../src/lib/log/compiler ../src/lib/asiolink/ ../src/lib/nsas \
../src/lib/testutils ../src/lib/cache ../src/lib/server_common/ \
../src/bin/sockcreator/ ../src/lib/util/ \
../src/lib/resolve ../src/lib/acl
../src/lib/resolve ../src/lib/acl ../src/bin/dhcp6
# This tag can be used to specify the character encoding of the source files
# that doxygen parses. Internally doxygen uses the UTF-8 encoding, which is
......
......@@ -1257,21 +1257,72 @@ TODO
<para>
Incoming zones are transferred using the <command>b10-xfrin</command>
process which is started by <command>bind10</command>.
When received, the zone is stored in the BIND 10
data store, and its records can be served by
When received, the zone is stored in the corresponding BIND 10
data source, and its records can be served by
<command>b10-auth</command>.
In combination with <command>b10-zonemgr</command> (for
automated SOA checks), this allows the BIND 10 server to
provide <quote>secondary</quote> service.
</para>
<para>
The <command>b10-xfrin</command> process supports both AXFR and
IXFR. Due to some implementation limitations of the current
development release, however, it only tries AXFR by default,
and care should be taken to enable IXFR.
</para>
<note><simpara>
The current development release of BIND 10 only supports
AXFR. (IXFR is not supported.)
In the current development release of BIND 10, incoming zone
transfers are only available for SQLite3-based data sources,
that is, they don't work for an in-memory data source.
Furthermore, the corresponding SQLite3 database must be
configured with a list of zone names by hand. One possible way
to do this is to use the <command>b10-loadzone</command> command
to load dummy zone content of the zone for which the secondary
service is provided (and then force transfer using AXFR from the primary
server). In future versions we will provide more convenient way
to set up the secondary.
</simpara></note>
<!-- TODO: sqlite3 data source only? -->
<para>
To enable IXFR, you need to
configure <command>b10-xfrin</command> with an explicit zone
configuration for the zone.
For example, to enable IXFR for a zone named "example.com"
(whose master address is assumed to be 2001:db8::53 here),
run the following at the <command>bindctl</command> prompt:
<screen>&gt; <userinput>config add Xfrin/zones</userinput>
&gt; <userinput>config set Xfrin/zones[0]/name "<option>example.com</option>"</userinput>
&gt; <userinput>config set Xfrin/zones[0]/master_addr "<option>2001:db8::53</option>"</userinput>
&gt; <userinput>config commit</userinput></screen>
(We assume there has been no zone configuration before).
Note that you do NOT have to explicitly enable IXFR in the zone
configuration; once it's defined, IXFR is enabled by default.
This also means if you specify a zone configuration for some
other reason but don't want to use IXFR for that zone, you need
to disable it explicitly:
<screen>&gt; <userinput>config set Xfrin/zones[0]/ixfr_disabled true</userinput></screen>
</para>
</simpara></note>
<para>
One reason why IXFR is disabled by default in the current
release is because it does not support automatic fallback from IXFR to
AXFR when it encounters a primary server that doesn't support
outbound IXFR (and, not many existing implementations support
it). Another, related reason is that it does not use AXFR even
if it has no knowledge about the zone (like at the very first
time the secondary server is set up). IXFR requires the
"current version" of the zone, so obviously it doesn't work
in this situation and AXFR is the only workable choice.
The current release of <command>b10-xfrin</command> does not
make this selection automatically.
These features will be implemented in a near future
version, at which point we will enable IXFR by default.
</para>
<!-- TODO:
......
......@@ -19,7 +19,7 @@ pkglibexecdir = $(libexecdir)/@PACKAGE@
CLEANFILES = *.gcno *.gcda spec_config.h
man_MANS = b10-dhcp6.8
EXTRA_DIST = $(man_MANS) dhcp6.spec
EXTRA_DIST = $(man_MANS) dhcp6.spec interfaces.txt
#if ENABLE_MAN
#b10-dhcp6.8: b10-dhcp6.xml
......@@ -31,8 +31,8 @@ spec_config.h: spec_config.h.pre
BUILT_SOURCES = spec_config.h
pkglibexec_PROGRAMS = b10-dhcp6
b10_dhcp6_SOURCES = main.cc
b10_dhcp6_SOURCES += dhcp6.h
b10_dhcp6_SOURCES = main.cc iface_mgr.cc pkt6.cc dhcp6_srv.cc
b10_dhcp6_SOURCES += iface_mgr.h pkt6.h dhcp6_srv.h dhcp6.h
b10_dhcp6_LDADD = $(top_builddir)/src/lib/datasrc/libdatasrc.la
b10_dhcp6_LDADD += $(top_builddir)/src/lib/dns/libdns++.la
b10_dhcp6_LDADD += $(top_builddir)/src/lib/util/libutil.la
......@@ -49,5 +49,4 @@ b10_dhcp6_LDADD += $(SQLITE_LIBS)
# TODO: config.h.in is wrong because doesn't honor pkgdatadir
# and can't use @datadir@ because doesn't expand default ${prefix}
b10_dhcp6dir = $(pkgdatadir)
b10_dhcp6_DATA = dhcp6.spec
b10_dhcp6_DATA = dhcp6.spec interfaces.txt
......@@ -21,8 +21,8 @@
.SH "NAME"
b10-dhcp6 \- DHCPv6 daemon in BIND10 architecture
.SH "SYNOPSIS"
.HP \w'\fBb10\-dhcp6\fR\ 'u
\fBb10\-dhcp6\fR [\fB\-u\ \fR\fB\fIusername\fR\fR] [\fB\-v\fR]
.HP \w'\fBb10\-dhcp6
\fBb10\-dhcp6\fR [\fB\-v\fR]
.SH "DESCRIPTION"
.PP
The
......
/* dhcp6.h
DHCPv6 Protocol structures... */
/*
* Copyright (c) 2006-2011 by Internet Systems Consortium, Inc. ("ISC")
*
* Permission to use, copy, modify, and distribute this software for any
* purpose with or without fee is hereby granted, provided that the above
* copyright notice and this permission notice appear in all copies.
*
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
*
* Internet Systems Consortium, Inc.
* 950 Charter Street
* Redwood City, CA 94063
* <info@isc.org>
* https://www.isc.org/
*/
// Copyright (C) 2006-2011 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
// copyright notice and this permission notice appear in all copies.
//
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
// PERFORMANCE OF THIS SOFTWARE.
#ifndef DHCP6_H
#define DHCP6_H
/* DHCPv6 Option codes: */
......@@ -136,8 +126,11 @@ extern const int dhcpv6_type_name_max;
/*
* DHCPv6 well-known multicast addressess, from section 5.1 of RFC 3315
*/
#define All_DHCP_Relay_Agents_and_Servers "FF02::1:2"
#define All_DHCP_Servers "FF05::1:3"
#define ALL_DHCP_RELAY_AGENTS_AND_SERVERS "ff02::1:2"
#define ALL_DHCP_SERVERS "ff05::1:3"
#define DHCP6_CLIENT_PORT 546
#define DHCP6_SERVER_PORT 547
/*
* DHCPv6 Retransmission Constants (RFC3315 section 5.5, RFC 5007)
......@@ -171,29 +164,6 @@ extern const int dhcpv6_type_name_max;
#define LQ6_MAX_RT 10
#define LQ6_MAX_RC 5
/*
* Normal packet format, defined in section 6 of RFC 3315
*/
struct dhcpv6_packet {
unsigned char msg_type;
unsigned char transaction_id[3];
unsigned char options[FLEXIBLE_ARRAY_MEMBER];
};
/* Offset into DHCPV6 Reply packets where Options spaces commence. */
#define REPLY_OPTIONS_INDEX 4
/*
* Relay packet format, defined in section 7 of RFC 3315
*/
struct dhcpv6_relay_packet {
unsigned char msg_type;
unsigned char hop_count;
unsigned char link_address[16];
unsigned char peer_address[16];
unsigned char options[FLEXIBLE_ARRAY_MEMBER];
};
/* Leasequery query-types (RFC 5007) */
#define LQ6QT_BY_ADDRESS 1
......@@ -211,3 +181,4 @@ struct dhcpv6_relay_packet {
#define IRT_DEFAULT 86400
#define IRT_MINIMUM 600
#endif
// Copyright (C) 2011 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
// copyright notice and this permission notice appear in all copies.
//
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
// PERFORMANCE OF THIS SOFTWARE.
#include "dhcp6/pkt6.h"
#include "dhcp6/iface_mgr.h"
#include "dhcp6/dhcp6_srv.h"
using namespace std;
using namespace isc;
Dhcpv6Srv::Dhcpv6Srv() {
cout << "Initialization" << endl;
// first call to instance() will create IfaceMgr (it's a singleton)
// it may throw something if things go wrong
IfaceMgr::instance();
}
Dhcpv6Srv::~Dhcpv6Srv() {
cout << "DHCPv6 Srv shutdown." << endl;
}
bool
Dhcpv6Srv::run() {
while (true) {
Pkt6* pkt;
pkt = IfaceMgr::instance().receive();
if (pkt) {
cout << "Received " << pkt->data_len_ << " bytes, echoing back."
<< endl;
IfaceMgr::instance().send(*pkt);
delete pkt;
}
// TODO add support for config session (see src/bin/auth/main.cc)
// so this daemon can be controlled from bob
sleep(1);
}
return (true);
}
// Copyright (C) 2011 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
// copyright notice and this permission notice appear in all copies.
//
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
// PERFORMANCE OF THIS SOFTWARE.
#ifndef DHCPV6_SRV_H
#define DHCPV6_SRV_H
#include <iostream>
namespace isc {
class Dhcpv6Srv {
private:
// defined private on purpose. We don't want to have more than
// one copy
Dhcpv6Srv(const Dhcpv6Srv& src);
Dhcpv6Srv& operator=(const Dhcpv6Srv& src);
public:
// default constructor
Dhcpv6Srv();
~Dhcpv6Srv();
bool run();
protected:
bool shutdown;
};
};
#endif // DHCP6_SRV_H
// Copyright (C) 2011 Internet Systems Consortium, Inc. ("ISC")
//
// Permission to use, copy, modify, and/or distribute this software for any
// purpose with or without fee is hereby granted, provided that the above
// copyright notice and this permission notice appear in all copies.
//
// THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES WITH
// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY
// AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR ANY SPECIAL, DIRECT,
// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM
// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE
// OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
// PERFORMANCE OF THIS SOFTWARE.
#include <sstream>
#include <fstream>
#include <string.h>
#include <netinet/in.h>
#include <arpa/inet.h>
#include "dhcp6/iface_mgr.h"
#include "dhcp6/dhcp6.h"
#include "exceptions/exceptions.h"
using namespace std;
using namespace isc;
using namespace isc::asiolink;
namespace isc {
// IfaceMgr is a singleton implementation
IfaceMgr* IfaceMgr::instance_ = 0;
void
IfaceMgr::instanceCreate() {
if (instance_) {
// no need to do anything. Instance is already created.
// Who called it again anyway? Uh oh. Had to be us, as
// this is private method.
return;
}
instance_ = new IfaceMgr();
}
IfaceMgr&
IfaceMgr::instance() {
if (instance_ == 0)
instanceCreate();
return (*instance_);
}
IfaceMgr::Iface::Iface(const std::string& name, int ifindex)
:name_(name), ifindex_(ifindex), mac_len_(0) {
memset(mac_, 0, 20);
}
std::string
IfaceMgr::Iface::getFullName() const {
ostringstream tmp;
tmp << name_ << "/" << ifindex_;
return (tmp.str());
}
std::string
IfaceMgr::Iface::getPlainMac() const {
ostringstream tmp;
for (int i=0; i<mac_len_; i++) {
tmp.fill('0');
tmp.width(2);
tmp << (hex) << (int) mac_[i];
if (i<mac_len_-1) {
tmp << ":";
}
}
return (tmp.str());
}
IfaceMgr::IfaceMgr() {
cout << "IfaceMgr initialization." << endl;
try {
// required for sending/receiving packets
// let's keep it in front, just in case someone
// wants to send anything during initialization
control_buf_len_ = CMSG_SPACE(sizeof(struct in6_pktinfo));
control_buf_ = new char[control_buf_len_];
detectIfaces();
if (!openSockets()) {
isc_throw(Unexpected, "Failed to open/bind sockets.");
}
} catch (const std::exception& ex) {
cout << "IfaceMgr creation failed:" << ex.what() << endl;
// TODO Uncomment this (or call LOG_FATAL) once
// interface detection is implemented. Otherwise
// it is not possible to run tests in a portable
// way (see detectIfaces() method).
// throw ex;
}
}
IfaceMgr::~IfaceMgr() {
if (control_buf_) {
delete [] control_buf_;
control_buf_ = 0;
control_buf_len_ = 0;
}
}
void
IfaceMgr::detectIfaces() {
string ifaceName, linkLocal;
// TODO do the actual detection. Currently interface detection is faked
// by reading a text file.
cout << "Interface detection is not implemented yet. "
<< "Reading interfaces.txt file instead." << endl;
cout << "Please use format: interface-name link-local-address" << endl;
try {
ifstream interfaces("interfaces.txt");
if (!interfaces.good()) {
cout << "Failed to read interfaces.txt file." << endl;
isc_throw(Unexpected, "Failed to read interfaces.txt");
}
interfaces >> ifaceName;
interfaces >> linkLocal;
cout << "Detected interface " << ifaceName << "/" << linkLocal << endl;
Iface iface(ifaceName, if_nametoindex( ifaceName.c_str() ) );
IOAddress addr(linkLocal);
iface.addrs_.push_back(addr);
ifaces_.push_back(iface);
interfaces.close();
} catch (const std::exception& ex) {
// TODO: deallocate whatever memory we used
// not that important, since this function is going to be
// thrown away as soon as we get proper interface detection
// implemented
// TODO Do LOG_FATAL here
std::cerr << "Interface detection failed." << std::endl;
throw ex;
}
}
bool
IfaceMgr::openSockets() {
int sock;
for (IfaceLst::iterator iface=ifaces_.begin();
iface!=ifaces_.end();
++iface) {
for (Addr6Lst::iterator addr=iface->addrs_.begin();
addr!=iface->addrs_.end();
++addr) {
sock = openSocket(iface->name_, *addr,
DHCP6_SERVER_PORT);
if (sock<0) {
cout << "Failed to open unicast socket." << endl;
return (false);
}
sendsock_ = sock;
sock = openSocket(iface->name_,
IOAddress(ALL_DHCP_RELAY_AGENTS_AND_SERVERS),
DHCP6_SERVER_PORT);
if (sock<0) {
cout << "Failed to open multicast socket." << endl;
close(sendsock_);
return (false);
}
recvsock_ = sock;
}
}
return (true);
}
void
IfaceMgr::printIfaces(std::ostream& out /*= std::cout*/) {
for (IfaceLst::const_iterator iface=ifaces_.begin();
iface!=ifaces_.end();
++iface) {
out << "Detected interface " << iface->getFullName() << endl;
out << " " << iface->addrs_.size() << " addr(s):" << endl;
for (Addr6Lst::const_iterator addr=iface->addrs_.begin();
addr != iface->addrs_.end();
++addr) {
out << " " << addr->toText() << endl;
}
out << " mac: " << iface->getPlainMac() << endl;
}
}
IfaceMgr::Iface*
IfaceMgr::getIface(int ifindex) {
for (IfaceLst::iterator iface=ifaces_.begin();
iface!=ifaces_.end();
++iface) {
if (iface->ifindex_ == ifindex)
return (&(*iface));
}
return (NULL); // not found
}
IfaceMgr::Iface*
IfaceMgr::getIface(const std::string& ifname) {
for (IfaceLst::iterator iface=ifaces_.begin();
iface!=ifaces_.end();
++iface) {
if (iface->name_ == ifname)
return (&(*iface));
}
return (NULL); // not found