diff options
author | Laurent Bercot <ska-skaware@skarnet.org> | 2020-12-28 22:09:00 +0000 |
---|---|---|
committer | Laurent Bercot <ska-skaware@skarnet.org> | 2020-12-28 22:09:00 +0000 |
commit | fab29b78d87d0114ecbdfbcac3b0e7c0edb463ba (patch) | |
tree | 786d09f619fa7302851e02fa7d51f53151db518c /doc | |
download | dnsfunnel-fab29b78d87d0114ecbdfbcac3b0e7c0edb463ba.tar.gz dnsfunnel-fab29b78d87d0114ecbdfbcac3b0e7c0edb463ba.tar.xz dnsfunnel-fab29b78d87d0114ecbdfbcac3b0e7c0edb463ba.zip |
Initial commit
Diffstat (limited to 'doc')
-rw-r--r-- | doc/dnsfunnel-daemon.html | 112 | ||||
-rw-r--r-- | doc/dnsfunnel-translate.html | 70 | ||||
-rw-r--r-- | doc/dnsfunneld.html | 160 | ||||
-rw-r--r-- | doc/index.html | 116 | ||||
-rw-r--r-- | doc/upgrade.html | 28 |
5 files changed, 486 insertions, 0 deletions
diff --git a/doc/dnsfunnel-daemon.html b/doc/dnsfunnel-daemon.html new file mode 100644 index 0000000..d93d463 --- /dev/null +++ b/doc/dnsfunnel-daemon.html @@ -0,0 +1,112 @@ +<html> + <head> + <meta name="viewport" content="width=device-width, initial-scale=1.0" /> + <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> + <meta http-equiv="Content-Language" content="en" /> + <title>dnsfunnel: the dnsfunnel-daemon program</title> + <meta name="Description" content="dnsfunnel: the dnsfunnel-daemon program" /> + <meta name="Keywords" content="dnsfunnel daemon /etc/resolv.conf local cache resolver 127.0.0.1" /> + <!-- <link rel="stylesheet" type="text/css" href="//skarnet.org/default.css" /> --> + </head> +<body> + +<p> +<a href="index.html">dnsfunnel</a><br /> +<a href="//skarnet.org/software/">Software</a><br /> +<a href="//skarnet.org/">skarnet.org</a> +</p> + +<h1> The <tt>dnsfunnel-daemon</tt> program </h1> + +<p> +<tt>dnsfunnel-daemon</tt> binds to a local UDP socket, drops its +privileges, then executes into <a href="dnsfunneld.html">dnsfunneld</a>. +</p> + +<h2> Interface </h2> + +<pre> + dnsfunnel-daemon [ -v verbosity ] [ -d notif ] [ -U | -u uid -g gid ] [ -i ip:port ] [ -R root ] [ -b bufsize ] [ -f cachelist ] [ -T | -t ] [ -N | -n ] +</pre> + +<ul> + <li> dnsfunnel-daemon creates a UDP inet domain socket and binds it +to IPv4 address <em>ip</em> (normally 127.0.0.1) and port <em>port</em> +(normally 53). </li> + <li> Depending on the options it has been given, it may chroot and lose +privileges on its gid and uid. </li> + <li> It execs into <a href="dnsfunneld.html">dnsfunneld</a> with the +UDP socket as its standard input. </li> +</ul> + +<p> + The point of <tt>dnsfunnel-daemon</tt> is to separate the administrative +operations of starting a daemon from the actual serving part, which is +handled by <a href="dnsfunneld.html">dnsfunneld</a>. +</p> + +<h2> Exit codes </h2> + +<ul> + <li> 100: wrong usage </li> + <li> 111: system call failed </li> + <li> 126: failed to exec <a href="dnsfunneld.html">dnsfunneld</a> </li> + <li> 127: could not find the <a href="dnsfunneld.html">dnsfunneld</a> executable </li> +</ul> + +<h2> Options </h2> + +<ul> + <li> <tt>-v <em>verbosity</em></tt> : verbosity of the +<a href="dnsfunneld.html">dnsfunneld</a> program. This option is passed as is +to <a href="dnsfunneld.html">dnsfunneld</a>. Default is 1. 0 suppresses warning +messages. Higher values may give more informational messages. </li> + <li> <tt>-d <em>notif</em></tt> : readiness notification. This option +is passed as is to <a href="dnsfunneld.html">dnsfunneld</a>, which will print a +newline to descriptor <em>notif</em> when it is ready. Default is no readiness +notification. </li> + <li> <tt>-U</tt> : read an uid in the UID environment variable and a gid +in the GID environment variable, and drop privileges to that uid/gid. </li> + <li> <tt>-u <em>uid</em></tt> : drop privileges to numerical uid +<em>uid</em>. </li> + <li> <tt>-g <em>gid</em></tt> : drop privileges to numerical gid +<em>gid</em>. </li> + <li> <tt>-i <em>ip</em>:<em>port</em></tt> : bind the socket to +IPv4 <em>ip</em> and port <em>port</em>. Default for <em>ip</em> is +<tt>127.0.0.1</tt>; default for <em>port</em> is 53. </li> + <li> <tt>-R <em>root</em></tt> : chroot to <em>root</em>. Note that +this option only increases security if you also drop privileges. </li> + <li> <tt>-b <em>bufsize</em></tt> : try and reserve a kernel buffer +size of <em>bufsize</em> bytes for the socket. Default is 131072. If the given +<em>bufsize</em> is 0, then <tt>dnsfunnel-daemon</tt> will use whatever the +default is for your kernel. </li> + <li> <tt>-f <em>cachelist</em></tt> : Use <em>cachelist</em> as the +file that <a href="dnsfunneld.html">dnsfunneld</a> reads its cache addresses +from. Default is <tt>/run/dnsfunnel-caches</tt>, or <em>file</em> +if the <tt>--with-cachelist=<em>file</em></tt> option has been given to the +configure script at build time. </li> +</ul> + +<p> + The other options control the activation or deactivation of various +<a href="dnsfunneld.html">dnsfunneld</a> features: +</p> + <li> <tt>-T</tt> : Do not activate truncation of responses. This is +the default. </li> + <li> <tt>-t</tt> : If a DNS response is bigger than 510 bytes, +truncate its last resource records until it fits into 510 bytes and can +be sent in a UDP packet. </li> + <li> <tt>-N</tt> : Do not activate nxdomain workaround. This is the +default. </li> + <li> <tt>-n</tt> : Activate nxdomain workaround. When receiving an A +(resp. AAAA) query to forward, also make an AAAA (resp. A) query, and adjust +the response accordingly. Some DNS servers incorrectly answer NXDOMAIN when +they should just answer NODATA, and querying for another, existing, record +type for the same domain allows dnsfunneld to tell the difference between a +real NXDOMAIN (in which case that response is forwarded to the client) and +an incorrect one (in which case NODATA is answered to the client instead). </li> + <li> Other options may be added in the future. </li> +</ul> + +</body> +</html> diff --git a/doc/dnsfunnel-translate.html b/doc/dnsfunnel-translate.html new file mode 100644 index 0000000..9dde27d --- /dev/null +++ b/doc/dnsfunnel-translate.html @@ -0,0 +1,70 @@ +<html> + <head> + <meta name="viewport" content="width=device-width, initial-scale=1.0" /> + <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> + <meta http-equiv="Content-Language" content="en" /> + <title>dnsfunnel: the dnsfunnel-translate program</title> + <meta name="Description" content="dnsfunnel: the dnsfunnel-translate program" /> + <meta name="Keywords" content="dnsfunnel translate /etc/resolv.conf nameserver cache address" /> + <!-- <link rel="stylesheet" type="text/css" href="//skarnet.org/default.css" /> --> + </head> +<body> + +<p> +<a href="index.html">dnsfunnel</a><br /> +<a href="//skarnet.org/software/">Software</a><br /> +<a href="//skarnet.org/">skarnet.org</a> +</p> + +<h1> The <tt>dnsfunnel-translate</tt> program </h1> + +<p> +<tt>dnsfunnel-translate</tt> translates a file in <tt>resolv.conf</tt> +format to a file in <a href="dnsfunneld.html">dnsfunneld</a> format. +</p> + +<h2> Interface </h2> + +<pre> + dnsfunnel-translate [ -i inputfile ] [ -o outputfile ] [ -x ignoredip ] +</pre> + +<ul> + <li> dnsfunnel-translate opens <em>inputfile</em> and parses it. It reads +and processes lines beginning with <tt>nameserver</tt> followed by an IP +address (v4 or v6). It ignores other lines. </li> + <li> It writes the IP addresses, without the <tt>nameserver</tt> keyword, +to <tt>outputfile</tt>, one per line. </li> + <li> If a <tt>nameserver</tt> address is <em>ignoredip</em>, it does not +get printed to <tt>outputfile</tt> + <li> dnsfunnel-translate exits 0 when it has finished processing +<em>inputfile</em>. </li> +</ul> + +<h2> Exit codes </h2> + +<ul> + <li> 0: success </li> + <li> 1: no suitable IP found in the input file </li> + <li> 100: wrong usage </li> + <li> 111: system call failed </li> +</ul> + +<h2> Options </h2> + +<ul> + <li> <tt>-i <em>inputfile</em></tt> : process <em>inputfile</em>. +Default is <tt>/etc/resolv.conf</tt>. </li> + <li> <tt>-o <em>outputfile</em></tt> : write the result to +<em>outputfile</em>. Default is <tt>/run/dnsfunnel-caches</tt>, or <em>file</em> +if the <tt>--with-cachelist=<em>file</em></tt> option has been given to the +configure script at build time. </li> + <li> <tt>-x <em>ignoredip</em></tt> : ignore the <em>ignoredip</em> +IPv4 address if it shows up as a <tt>nameserver</tt> in <em>inputfile</em>. +Default is <tt>127.0.0.1</tt>. The point of this option is to avoid copying +to <tt>outputfile</tt> the IPv4 address that the +<a href="dnsfunnel-daemon.html">dnsfunnel-daemon</a> daemon will be bound to. </li> +</ul> + +</body> +</html> diff --git a/doc/dnsfunneld.html b/doc/dnsfunneld.html new file mode 100644 index 0000000..006a6d6 --- /dev/null +++ b/doc/dnsfunneld.html @@ -0,0 +1,160 @@ +<html> + <head> + <meta name="viewport" content="width=device-width, initial-scale=1.0" /> + <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> + <meta http-equiv="Content-Language" content="en" /> + <title>dnsfunnel: the dnsfunnel-daemon program</title> + <meta name="Description" content="dnsfunnel: the dnsfunnel-daemon program" /> + <meta name="Keywords" content="dnsfunnel daemon /etc/resolv.conf local cache resolver 127.0.0.1" /> + <!-- <link rel="stylesheet" type="text/css" href="//skarnet.org/default.css" /> --> + </head> +<body> + +<p> +<a href="index.html">dnsfunnel</a><br /> +<a href="//skarnet.org/software/">Software</a><br /> +<a href="//skarnet.org/">skarnet.org</a> +</p> + +<h1> The <tt>dnsfunneld</tt> program </h1> + +<p> +<tt>dnsfunneld</tt> is a small DNS forwarder daemon. It receives +DNS queries from clients, then forwards them to one or more DNS caches. +It collects the responses and forwards them back to the clients. Depending +on the options it is given, it may perform light processing on the +queries, the responses, or both. +</p> + +<h2> Interface </h2> + +<pre> + dnsfunneld [ -v verbosity ] [ -d notif ] [ -o ops ] cachelist +</pre> + +<ul> + <li> dnsfunneld reads the <em>cachelist</em> file, expecting to find +a list of IP (v4 or v6) addresses, one per line. These addresses are the +DNS caches it will forward the queries to. </li> + <li> dnsfunneld expects to have a bound UDP inet domain socket as +its standard input. It expects to receive packets no more than 512 +bytes long, only containing DNS normal queries (QUERY) for the IN +class. </li> + <li> Depending on <em>ops</em>, dnsfunneld may send additional queries +to the caches listed in <em>cachelist</em>. It handles the answers +internally: the additional queries are invisible to clients. </li> + <li> dnsfunneld is a long-lived process. </li> +</ul> + +<h2> Signals </h2> + +<ul> + <li> SIGHUP: read the <em>cachelist</em> file again, updating its +in-memory cache list. In-flight queries are still handled by the old +list; the new list will only apply for queries arriving after the SIGHUP. </li> + <li> SIGTERM: enter lame-duck mode, do not accept any more queries. When +all in-flight queries have been answered, exit 0. +</ul> + +<h2> Exit codes </h2> + +<ul> + <li> 0: SIGTERM received and all in-flight queries have been answered </li> + <li> 100: wrong usage </li> + <li> 111: system call failed </li> +</ul> + +<h2> Options </h2> + +<ul> + <li> <tt>-v <em>verbosity</em></tt> : verbosity. +Default is 1. 0 suppresses warning messages. Higher values may give more +informational messages in the future. </li> + <li> <tt>-d <em>notif</em></tt> : readiness notification. When +dnsfunneld is ready to process queries, write a newline to file descriptor +<em>notif</em>. <em>notif</em> must be 3 or greater. Default is no notification +at all. </li> + <li> <tt>-o <em>ops</em></tt> : perform various operations on +queries. <em>ops</em> is a decimal integer that is treated as a bitfield. +Default is 0. Operations are listed below. </li> +</ul> + +<h2> DNS forwarding behaviour </h2> + +<ul> + <li> When it receives a query, dnsfunneld forwards it to the first DNS cache +in the list it has read from the <em>cachelist</em> file. </li> + <li> If it receives a response with the TC bit, it resends the query over TCP. </li> + <li> If it receives a suitable response within a given time frame, it forwards +it to the client. </li> + <li> On SERVFAIL, or after a timeout of 1 second, it gives up and sends the +query to the next DNS cache in its list. (If the first cache answers after the time +frame, the answer is dropped.) + <li> If dnsfunneld reaches the end of its cache list, it retries the whole +procedure starting at the beginning of the list, but with a timeout of 3 seconds. +Caches that returned a SERVFAIL are crossed off the list for that query. </li> + <li> If the second pass fails again, dnsfunneld tries again with a timeout of +11 seconds, then with a timeout of 45 seconds. If all of this fails, it returns +a SERVFAIL to the client. </li> + <li> A machine should not use a DNS cache that is too far away. In normal operation, +a timeout of 1 second should be more than enough for a cache to answer, if it already +has the answer. If the answer is absent from all caches and it takes them more than +1 second to resolve the query, the answer will be obtained by dnsfunneld in the second +pass. Realistically, the only cases when caches that are not at the top of the list +are used are: + <ul> + <li> obscure DNS queries, not likely to be in the caches, and that will take +time to resolve; </li> + <li> or the first cache has really gone to lunch. </li> + </ul> +</ul> + +<h2> dnsfunneld operations </h2> + +<p> + <em>ops</em> is an integer used as a bitfield. Depending on which bits are set, +various operations are performed on queries or answers, slightly modifying the +behaviour described above. +</p> + +<ul> + <li> bit 0: activate truncation. If a DNS response is more than 510 bytes +long, dnsfunneld will truncate the <em>last</em> resource records in the response, +until it fits into 510 bytes and can be given to the client in a UDP packet. +The structure of a DNS packet makes it so the RRs are listed in order of +decreasing importance, so keeping as many RRs as will fit in 510 bytes +without reordering them is the natural way of truncating a response. </li> + <li> bit 1: activate workaround for some servers that incorrectly report +NXDOMAIN when they're asked for an AAAA record, and no such record exists +for the domain but an A record exists. When that bit is set in <em>ops</em>, +for every A or AAAA query dnsfunneld receives and forwards, it also sends +an additional AAAA or A query for the same domain. If the main query returns +NXDOMAIN, dnsfunneld waits for the response to the auxiliary query: if this +response is not NXDOMAIN, then dnsfunneld answers NODATA to the client instead +of NXDOMAIN. Be aware that activating this workaround can practically double +the number of queries sent to the DNS caches, and may cause additional delays +before the clients get their answers. </li> +</ul> + +<h2> Notes </h2> + +<ul> + <li> The point of dnsfunneld is to work around ill-designed or unreliable +client setups with several motley <tt>nameserver</tt> entries in +<tt>/etc/resolv.conf</tt>. By converting those entries to a cache list +instead (via the <a href="dnsfunnel-translate.html">dnsfunnel-translate</a> +program), running dnsfunneld on 127.0.0.1, and enforcing a policy of one +single <tt>nameserver 127.0.0.1</tt> entry in <tt>/etc/resolv.conf</tt>, +the setup can be made more reliable and more consistent. </li> + <li> Such a policy can be automated, for instance, by listening to +changes on the <tt>/etc/resolv.conf</tt> file (via inotify or kqueue, +depending on your system) and immediately calling +<a href="dnsfunnel-translate.html">dnsfunnel-translate</a>, sending +a SIGHUP to dnsfunneld, and forcefully overwriting <tt>/etc/resolv.conf</tt>. </li> + <li> It is easy to send a SIGHUP to dnsfunneld even without knowing its +pid, if it is run under a process supervision system such as +<a href="//skarnet.org/software/s6/">s6</a>. </li> +</ul> + +</body> +</html> diff --git a/doc/index.html b/doc/index.html new file mode 100644 index 0000000..fe8e8d4 --- /dev/null +++ b/doc/index.html @@ -0,0 +1,116 @@ +<html> + <head> + <meta name="viewport" content="width=device-width, initial-scale=1.0" /> + <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> + <meta http-equiv="Content-Language" content="en" /> + <title>dnsfunnel - A small local DNS cache daemon</title> + <meta name="Description" content="dnsfunnel - a small local DNS cache daemon" /> + <meta name="Keywords" content="dnsfunnel DNS domain cache local /etc/resolv.conf resolver forwarder laurent bercot ska skarnet" /> + <!-- <link rel="stylesheet" type="text/css" href="//skarnet.org/default.css" /> --> + </head> +<body> + +<p> +<a href="//skarnet.org/software/">Software</a><br /> +<a href="//skarnet.org/">skarnet.org</a> +</p> + +<h1> dnsfunnel </h1> + +<h2> What is it ? </h2> + +<p> + dnsfunnel is a small daemon listening to DNS client requests over UDP +(typically from the libc's +<a href="https://pubs.opengroup.org/onlinepubs/9699919799/functions/getaddrinfo.html">getaddrinfo()</a> +function) and forwards them to a list of DNS caches. It provides the +client with the first answer it gets, trimming the answer so it fits +in an UDP packet. +</p> + +<p> + dnsfunnel is especially useful for distributions using the +<a href="https://musl-libc.org">musl</a> libc, which does not support +TCP DNS transport. It was originally written to be used in the +<a href="https://alpinelinux.org/">Alpine Linux</a> distribution. +</p> + +<hr /> + +<h2> Installation </h2> + +<h3> Requirements </h3> + +<ul> + <li> A POSIX-compliant system with a standard C development environment. +The system must also support <tt>chroot()</tt> </li> + <li> GNU make, version 3.81 or later </li> + <li> <a href="//skarnet.org/software/skalibs/">skalibs</a> version +2.10.0.0 or later. It's a build-time requirement. It's also a run-time +requirement if you link against the shared version of the skalibs +library. </li> + <li> <a href="//skarnet.org/software/s6-dns/">s6-dns</a> version +2.3.3.0 or later. It's a build-time requirement. It's also a run-time +requirement if you link against the shared version of the s6dns +library. </li> + +</ul> + +<h3> Licensing </h3> + +<p> + dnsfunnel is free software. It is available under the +<a href="https://opensource.org/licenses/ISC">ISC license</a>. +</p> + +<h3> Download </h3> + +<ul> + <li> The current released version of dnsfunnel is +<a href="dnsfunnel-0.0.1.0.tar.gz">0.0.1.0</a>. + (This is a lie. +dnsfunnel is in alpha development at the moment, and only +available through git.) </li> + <li> Alternatively, you can checkout a copy of the +<a href="//git.skarnet.org/cgi-bin/cgit.cgi/dnsfunnel/">dnsfunnel +git repository</a>: +<pre> git clone git://git.skarnet.org/dnsfunnel </pre> </li> + <li> There's also a +<a href="https://github.com/skarnet/dnsfunnel">GitHub mirror</a> +of the dnsfunnel git repository. </li> +</ul> + +<h3> Compilation </h3> + +<ul> + <li> See the enclosed INSTALL file for installation details. </li> +</ul> + +<h3> Upgrade notes </h3> + +<ul> + <li> <a href="upgrade.html">This page</a> lists the differences to be aware of between +the previous versions of dnsfunnel and the current one. </li> +</ul> + +<hr /> + +<h2> Reference </h2> + +<h3> Commands </h3> + +<ul> +<li><a href="dnsfunnel-daemon.html">The <tt>dnsfunnel-daemon</tt> program</a></li> +<li><a href="dnsfunneld.html">The <tt>dnsfunneld</tt> program</a></li> +<li><a href="dnsfunnel-translate.html">The <tt>dnsfunnel-translate</tt> program</a></li> +</ul> + +<h2> Related resources </h2> + +<ul> + <li> <tt>dnsfunnel</tt> is discussed on the +<a href="//skarnet.org/lists.html#skaware">skaware</a> mailing-list. </li> +</ul> + +</body> +</html> diff --git a/doc/upgrade.html b/doc/upgrade.html new file mode 100644 index 0000000..6b46bde --- /dev/null +++ b/doc/upgrade.html @@ -0,0 +1,28 @@ +<html> + <head> + <meta name="viewport" content="width=device-width, initial-scale=1.0" /> + <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" /> + <meta http-equiv="Content-Language" content="en" /> + <title>dnsfunnel: how to upgrade</title> + <meta name="Description" content="dnsfunnel: how to upgrade" /> + <meta name="Keywords" content="dnsfunnel installation upgrade" /> + <!-- <link rel="stylesheet" type="text/css" href="//skarnet.org/default.css" /> --> + </head> +<body> + +<p> +<a href="index.html">dnsfunnel</a><br /> +<a href="//skarnet.org/software/">Software</a><br /> +<a href="//skarnet.org/">skarnet.org</a> +</p> + +<h1> What has changed in dnsfunnel </h1> + +<h2> in 0.0.1.0 </h2> + +<ul> + <li> Initial release. </li> +</ul> + +</body> +</html> |