├── .gitignore ├── AUTHORS ├── CONTRIBUTING ├── COPYING ├── DCO ├── INSTALL ├── Makefile ├── NEWS ├── README ├── README.solaris ├── configure ├── doc ├── getaddrinfo.html ├── index.html ├── libresolv.html ├── libs6dns │ ├── hosts.html │ ├── index.html │ ├── s6dns-domain.html │ ├── s6dns-engine.html │ ├── s6dns-fmt.html │ ├── s6dns-ip46.html │ ├── s6dns-message.html │ ├── s6dns-rci.html │ └── s6dns-resolve.html ├── s6-dns-hosts-compile.html ├── s6-dnsip.html ├── s6-dnsip4-filter.html ├── s6-dnsip4.html ├── s6-dnsip6-filter.html ├── s6-dnsip6.html ├── s6-dnsmx.html ├── s6-dnsname-filter.html ├── s6-dnsname.html ├── s6-dnsns.html ├── s6-dnsq.html ├── s6-dnsqr.html ├── s6-dnsqualify.html ├── s6-dnssoa.html ├── s6-dnssrv.html ├── s6-dnstxt.html ├── s6-randomip.html ├── skadns │ ├── index.html │ └── skadnsd.html └── upgrade.html ├── package ├── configure-snippets │ ├── configure_case_lines │ ├── configure_expand_dirs │ ├── configure_extra_checks │ ├── configure_generate_configh │ ├── configure_generate_make │ ├── configure_help_dependencies │ ├── configure_help_install │ ├── configure_help_options │ ├── configure_init_vars │ └── configure_slashpackage_other ├── deps-build ├── deps.mak ├── info ├── modes └── targets.mak ├── patch-for-solaris ├── src ├── clients │ ├── deps-exe │ │ ├── s6-dnsip │ │ ├── s6-dnsip4 │ │ ├── s6-dnsip4-filter │ │ ├── s6-dnsip6 │ │ ├── s6-dnsip6-filter │ │ ├── s6-dnsmx │ │ ├── s6-dnsname │ │ ├── s6-dnsname-filter │ │ ├── s6-dnsns │ │ ├── s6-dnsq │ │ ├── s6-dnsqr │ │ ├── s6-dnsqualify │ │ ├── s6-dnssoa │ │ ├── s6-dnssrv │ │ ├── s6-dnstxt │ │ └── s6-randomip │ ├── s6-dnsip.c │ ├── s6-dnsip4-filter.c │ ├── s6-dnsip4.c │ ├── s6-dnsip6-filter.c │ ├── s6-dnsip6.c │ ├── s6-dnsmx.c │ ├── s6-dnsname-filter.c │ ├── s6-dnsname.c │ ├── s6-dnsns.c │ ├── s6-dnsq.c │ ├── s6-dnsqr.c │ ├── s6-dnsqualify.c │ ├── s6-dnssoa.c │ ├── s6-dnssrv.c │ ├── s6-dnstxt.c │ ├── s6-randomip.c │ ├── s6dns-generic-filter.h │ ├── s6dns_generic_filter_main.c │ └── s6dns_namescanner.c ├── include │ └── s6-dns │ │ ├── dcache.h │ │ ├── hosts.h │ │ ├── s6dns-analyze.h │ │ ├── s6dns-constants.h │ │ ├── s6dns-debug.h │ │ ├── s6dns-domain.h │ │ ├── s6dns-engine.h │ │ ├── s6dns-fmt.h │ │ ├── s6dns-ip46.h │ │ ├── s6dns-message.h │ │ ├── s6dns-rci.h │ │ ├── s6dns-resolve.h │ │ ├── s6dns.h │ │ └── skadns.h ├── libs6dns │ ├── deps-lib │ │ └── s6dns │ ├── s6dns-message-internal.h │ ├── s6dns_analyze_packet.c │ ├── s6dns_analyze_qtype_parse.c │ ├── s6dns_analyze_record.c │ ├── s6dns_analyze_record_a.c │ ├── s6dns_analyze_record_aaaa.c │ ├── s6dns_analyze_record_caa.c │ ├── s6dns_analyze_record_domain.c │ ├── s6dns_analyze_record_hinfo.c │ ├── s6dns_analyze_record_mx.c │ ├── s6dns_analyze_record_soa.c │ ├── s6dns_analyze_record_srv.c │ ├── s6dns_analyze_record_strings.c │ ├── s6dns_analyze_record_unknown.c │ ├── s6dns_analyze_rtypetable.c │ ├── s6dns_constants_error.c │ ├── s6dns_constants_error_str.c │ ├── s6dns_debug_dumpdt_post_recv.c │ ├── s6dns_debug_dumpdt_post_send.c │ ├── s6dns_debug_dumpdt_pre_send.c │ ├── s6dns_debug_dumpdt_stderr.c │ ├── s6dns_debug_dumpdt_stdout.c │ ├── s6dns_debughook_zero.c │ ├── s6dns_domain_arpafromip4.c │ ├── s6dns_domain_arpafromip6.c │ ├── s6dns_domain_decode.c │ ├── s6dns_domain_encode.c │ ├── s6dns_domain_encodelist.c │ ├── s6dns_domain_fromstring.c │ ├── s6dns_domain_fromstring_noqualify_encode.c │ ├── s6dns_domain_fromstring_qualify_encode.c │ ├── s6dns_domain_noqualify.c │ ├── s6dns_domain_qualify.c │ ├── s6dns_domain_tostring.c │ ├── s6dns_engine.c │ ├── s6dns_engine_free.c │ ├── s6dns_engine_freen.c │ ├── s6dns_engine_here.c │ ├── s6dns_engine_nextdeadline.c │ ├── s6dns_engine_query.c │ ├── s6dns_engine_zero.c │ ├── s6dns_finish.c │ ├── s6dns_fmt_caa.c │ ├── s6dns_fmt_domainlist.c │ ├── s6dns_fmt_hinfo.c │ ├── s6dns_fmt_mx.c │ ├── s6dns_fmt_soa.c │ ├── s6dns_fmt_srv.c │ ├── s6dns_hosts_aaaaa_q.c │ ├── s6dns_hosts_aaaaa_string.c │ ├── s6dns_hosts_compile.c │ ├── s6dns_hosts_compile.txt │ ├── s6dns_hosts_here.c │ ├── s6dns_hosts_init.c │ ├── s6dns_hosts_ip_q.c │ ├── s6dns_hosts_ip_string.c │ ├── s6dns_hosts_name.c │ ├── s6dns_init.c │ ├── s6dns_message_counts_next.c │ ├── s6dns_message_counts_pack.c │ ├── s6dns_message_counts_unpack.c │ ├── s6dns_message_counts_zero.c │ ├── s6dns_message_get_caa.c │ ├── s6dns_message_get_domain.c │ ├── s6dns_message_get_domain_nodecode.c │ ├── s6dns_message_get_hinfo.c │ ├── s6dns_message_get_mx.c │ ├── s6dns_message_get_soa.c │ ├── s6dns_message_get_srv.c │ ├── s6dns_message_get_string.c │ ├── s6dns_message_get_string_internal.c │ ├── s6dns_message_get_strings.c │ ├── s6dns_message_header_pack.c │ ├── s6dns_message_header_unpack.c │ ├── s6dns_message_header_zero.c │ ├── s6dns_message_parse.c │ ├── s6dns_message_parse_answer_a.c │ ├── s6dns_message_parse_answer_aaaa.c │ ├── s6dns_message_parse_answer_caa.c │ ├── s6dns_message_parse_answer_domain.c │ ├── s6dns_message_parse_answer_hinfo.c │ ├── s6dns_message_parse_answer_mx.c │ ├── s6dns_message_parse_answer_soa.c │ ├── s6dns_message_parse_answer_srv.c │ ├── s6dns_message_parse_answer_strings.c │ ├── s6dns_message_parse_getrr.c │ ├── s6dns_message_parse_init.c │ ├── s6dns_message_parse_next.c │ ├── s6dns_message_parse_question.c │ ├── s6dns_message_parse_skipqd.c │ ├── s6dns_rci_free.c │ ├── s6dns_rci_here.c │ ├── s6dns_rci_init.c │ ├── s6dns_rci_zero.c │ ├── s6dns_resolve_core.c │ ├── s6dns_resolve_dpag.c │ ├── s6dns_resolve_mpag.c │ ├── s6dns_resolve_name4.c │ ├── s6dns_resolve_name6.c │ ├── s6dns_resolve_parse.c │ ├── s6dns_resolven_loop.c │ ├── s6dns_resolven_parse.c │ ├── s6dns_resolvenoq.c │ ├── s6dns_resolvenoq_aaaaa.c │ ├── s6dns_resolveq.c │ └── s6dns_resolveq_aaaaa.c ├── skadns │ ├── deps-exe │ │ └── skadnsd │ ├── deps-lib │ │ └── skadns │ ├── skadns_cancel.c │ ├── skadns_end.c │ ├── skadns_packet.c │ ├── skadns_packetlen.c │ ├── skadns_release.c │ ├── skadns_send.c │ ├── skadns_start.c │ ├── skadns_startf.c │ ├── skadns_update.c │ ├── skadns_zero.c │ └── skadnsd.c └── utilities │ ├── deps-exe │ └── s6-dns-hosts-compile │ └── s6-dns-hosts-compile.c └── tools ├── configure.template ├── gen-configure.el ├── gen-deps.sh ├── gen-dotpc.sh ├── install.sh └── run-test.sh /.gitignore: -------------------------------------------------------------------------------- 1 | /*.pc 2 | *.o 3 | *.lo 4 | /config.mak 5 | /src/include/s6-dns/config.h 6 | /libs6dns.a.xyzzy 7 | /libs6dns.so.xyzzy 8 | /libskadns.a.xyzzy 9 | /libskadns.so.xyzzy 10 | /libdcache.a.xyzzy 11 | /libdcache.so.xyzzy 12 | /s6-dnsip 13 | /s6-dnsip4 14 | /s6-dnsip4-filter 15 | /s6-dnsip6 16 | /s6-dnsip6-filter 17 | /s6-dnsmx 18 | /s6-dnsname 19 | /s6-dnsname-filter 20 | /s6-dnsns 21 | /s6-dnsq 22 | /s6-dnsqr 23 | /s6-dnsqualify 24 | /s6-dnssoa 25 | /s6-dnssrv 26 | /s6-dnstxt 27 | /s6-dns-hosts-compile 28 | /s6-randomip 29 | /skadnsd 30 | -------------------------------------------------------------------------------- /AUTHORS: -------------------------------------------------------------------------------- 1 | Main author: 2 | Laurent Bercot 3 | 4 | Thanks to: 5 | Dan J. Bernstein 6 | Vallo Kallaste 7 | A. Wilcox 8 | Andrew Ayer 9 | -------------------------------------------------------------------------------- /CONTRIBUTING: -------------------------------------------------------------------------------- 1 | Please add a Signed-Off-By: line at the end of your commit, 2 | which certifies that you have the right and authority to pass 3 | it on as an open-source patch, as explicited in the Developer's 4 | Certificate of Origin available in this project's DCO file, 5 | or at https://developercertificate.org/ 6 | -------------------------------------------------------------------------------- /COPYING: -------------------------------------------------------------------------------- 1 | Copyright (c) 2011-2025 Laurent Bercot 2 | 3 | Permission to use, copy, modify, and distribute this software for any 4 | purpose with or without fee is hereby granted, provided that the above 5 | copyright notice and this permission notice appear in all copies. 6 | 7 | THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES 8 | WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF 9 | MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR 10 | ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES 11 | WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN 12 | ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF 13 | OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. 14 | -------------------------------------------------------------------------------- /DCO: -------------------------------------------------------------------------------- 1 | Developer Certificate of Origin 2 | Version 1.1 3 | 4 | Copyright (C) 2004, 2006 The Linux Foundation and its contributors. 5 | 1 Letterman Drive 6 | Suite D4700 7 | San Francisco, CA, 94129 8 | 9 | Everyone is permitted to copy and distribute verbatim copies of this 10 | license document, but changing it is not allowed. 11 | 12 | 13 | Developer's Certificate of Origin 1.1 14 | 15 | By making a contribution to this project, I certify that: 16 | 17 | (a) The contribution was created in whole or in part by me and I 18 | have the right to submit it under the open source license 19 | indicated in the file; or 20 | 21 | (b) The contribution is based upon previous work that, to the best 22 | of my knowledge, is covered under an appropriate open source 23 | license and I have the right under that license to submit that 24 | work with modifications, whether created in whole or in part 25 | by me, under the same open source license (unless I am 26 | permitted to submit under a different license), as indicated 27 | in the file; or 28 | 29 | (c) The contribution was provided directly to me by some other 30 | person who certified (a), (b) or (c) and I have not modified 31 | it. 32 | 33 | (d) I understand and agree that this project and the contribution 34 | are public and that a record of the contribution (including all 35 | personal information I submit with it, including my sign-off) is 36 | maintained indefinitely and may be redistributed consistent with 37 | this project or the open source license(s) involved. 38 | -------------------------------------------------------------------------------- /NEWS: -------------------------------------------------------------------------------- 1 | Changelog for s6-dns. 2 | 3 | In 2.4.1.0 4 | ---------- 5 | 6 | - Bugfixes. (And a workaround for a bionic bug.) 7 | - pkg-config support. 8 | 9 | 10 | In 2.4.0.0 11 | ---------- 12 | 13 | - Depend on skalibs-2.14.3.0, remove s6dns_mininetstring_read. 14 | - Better debug packet dump in s6-dnsq[r]. 15 | - New s6dns_engine_query() to get the query encoded in a dt. 16 | - Install static libraries in /usr/lib by default. 17 | 18 | 19 | In 2.3.7.2 20 | ---------- 21 | 22 | - Bugfixes. 23 | 24 | 25 | In 2.3.7.1 26 | ---------- 27 | 28 | - Bugfixes. 29 | 30 | 31 | In 2.3.7.0 32 | ---------- 33 | 34 | - New s6dns_init_options() function, to choose whether 35 | to support /etc/hosts or not. 36 | - Properly ignore link-local addresses in hosts files 37 | instead of erroring out on them. 38 | - New s6dns_hosts_name46() macro. 39 | 40 | 41 | In 2.3.6.0 42 | ---------- 43 | 44 | - Bugfixes. 45 | - New s6dns_hosts functions. 46 | - New command: s6-dns-hosts-compile 47 | - s6-dnsip* and s6-dnsname now support a -h option, to make 48 | use of /etc/hosts data. 49 | 50 | 51 | In 2.3.5.5 52 | ---------- 53 | 54 | - Bugfixes. 55 | - Adaptation to skalibs-2.13.0.0. 56 | - Workarounds for broken DNS caches. 57 | 58 | 59 | In 2.3.5.4 60 | ---------- 61 | 62 | - Adaptation to skalibs-2.12.0.0. 63 | 64 | 65 | In 2.3.5.3 66 | ---------- 67 | 68 | - Bugfixes. 69 | 70 | 71 | In 2.3.5.2 72 | ---------- 73 | 74 | - Adaptation to skalibs-2.11.0.0. 75 | - Bugfixes. 76 | 77 | 78 | In 2.3.5.1 79 | ---------- 80 | 81 | - Bugfixes. 82 | 83 | 84 | In 2.3.5.0 85 | ---------- 86 | 87 | - s6dns_message_get_domain_internal() is now public under the 88 | name s6dns_message_get_domain_nodecode(). 89 | 90 | 91 | In 2.3.4.0 92 | ---------- 93 | 94 | - New function: s6dns_message_parse_question(). 95 | 96 | 97 | In 2.3.3.0 98 | ---------- 99 | 100 | - Bugfixes. 101 | - New binary: s6-dnsip, returning both v4 and v6 addresses. 102 | 103 | 104 | In 2.3.2.0 105 | ---------- 106 | 107 | - Bugfixes. 108 | - New caching library to build a DNS cache over. 109 | 110 | 111 | In 2.3.1.1 112 | ---------- 113 | 114 | - Bugfixes. 115 | 116 | 117 | In 2.3.1.0 118 | ---------- 119 | 120 | - Adaptation to skalibs-2.9.0.0. 121 | 122 | 123 | In 2.3.0.2 124 | ---------- 125 | 126 | - Adaptation to skalibs-2.8.0.0. 127 | - Everything now builds as PIC by default. 128 | 129 | 130 | In 2.3.0.1 131 | ---------- 132 | 133 | - Adaptation to skalibs-2.7.0.0. 134 | 135 | 136 | In 2.3.0.0 137 | ---------- 138 | 139 | - skadns now uses the textclient API/ABI instead of the skaclient one. 140 | The change is invisible, but it's leaner and faster. 141 | 142 | 143 | In 2.2.0.1 144 | ---------- 145 | 146 | - Optimization release for skalibs-2.6.0.0. 147 | 148 | 149 | In 2.2.0.0 150 | ---------- 151 | 152 | - Added this NEWS file. :) 153 | - Major types overhaul to make them more POSIXly correct: 154 | compatibility with skalibs-2.5.0.0. 155 | - Fixed a long-standing bug that sometimes prevented DNS reply headers 156 | from being correctly decoded on big-endian machines. 157 | 158 | -------------------------------------------------------------------------------- /README: -------------------------------------------------------------------------------- 1 | s6-dns - a DNS client suite 2 | --------------------------- 3 | 4 | s6-dns is a suite of DNS client programs and libraries for 5 | Unix systems, as an alternative to the BIND, djbdns, or 6 | other DNS clients. It also comes with a clean, easy-to-use 7 | library to perform asynchronous DNS requests. 8 | 9 | See https://skarnet.org/software/s6-dns/ for details. 10 | 11 | 12 | * Installation 13 | ------------ 14 | 15 | See the INSTALL file. 16 | 17 | 18 | * Contact information 19 | ------------------- 20 | 21 | Laurent Bercot 22 | 23 | Please use the mailing-list for 24 | questions about s6-dns. 25 | -------------------------------------------------------------------------------- /README.solaris: -------------------------------------------------------------------------------- 1 | This package assumes the existence of a POSIX shell in /bin/sh. 2 | On Solaris, /bin/sh is not POSIX. Most versions of Solaris provide 3 | a POSIX shell in /usr/xpg4/bin/sh. 4 | 5 | To compile this package on Solaris, you will need to run 6 | 7 | ./patch-for-solaris 8 | 9 | before you run ./configure. This script will change the #! invocation 10 | of the configure script and various tools so that a POSIX shell is used 11 | for the compilation process. 12 | -------------------------------------------------------------------------------- /doc/getaddrinfo.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the problem with getaddrinfo() 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The problem with getaddrinfo()

20 | 21 |

22 | The standard C library provides an API to perform name 23 | resolution: 24 | getaddrinfo(), 25 | formerly gethostbyname(). However, for DNS resolution as well as 26 | implementation in the libc, this interface is very impractical, to the point of 27 | being unusable. Here are a few reasons why. 28 |

29 | 30 |

getaddrinfo() performs NSS resolution, not DNS resolution.

31 | 32 |

33 | I explained this point in a message to the 34 | Busybox mailing-list. You can 35 | read 36 | the post here. 37 | (There is a mistake in that post about /etc/nsswitch.conf and 38 | /etc/host.conf syntax; the following two messages in the thread 39 | correct that mistake.) 40 |

41 | 42 |

43 | TLDR: depending on the machine configuration, it is possible that 44 | getaddrinfo() will not use DNS at all. 45 |

46 | 47 |

It is unboundedly synchronous.

48 | 49 |

50 | DNS resolution performs network I/O, which can take a non-negligible 51 | amount of time. getaddrinfo() is a blocking call and there is 52 | no way to specify a timeout to make it return early, so it may block 53 | indefinitely. This is bad design. 54 |

55 | 56 |

57 | Also, network operations being asynchronous by nature, even a 58 | synchronous API should provide a way to perform several queries at 59 | once and return when one of them, or all of them, get an answer. 60 | getaddrinfo() does not even offer that. 61 |

62 | 63 |

It focuses on the wrong details.

64 | 65 |

66 | Because it's generic, getaddrinfo() is cumbersome to use. 67 | The data structures are impractical, requiring the user to fill in 68 | information that is irrelevant to DNS resolution. The details of the 69 | network transport protocols are of no interest to the user who just 70 | wants answers to his DNS queries! 71 |

72 | 73 |

74 | But at the same time, getaddrinfo() does not allow the 75 | user to provide the details he wants or refine his search. It's a very 76 | basic and monolithic entry point, with no DNS-specific knobs. For 77 | instance, only A and AAAA queries are supported, which is clearly 78 | insufficient. 79 |

80 | 81 |

Conclusion

82 | 83 |

84 | getaddrinfo() is a toy interface. For any half-serious DNS work, 85 | another API must be used. 86 |

87 | 88 |

89 | Most people who need a real DNS client library use BIND's libresolv. 90 | This page explains what is wrong with it, 91 | and what s6-dns tries to do better. 92 |

93 | 94 | 95 | 96 | -------------------------------------------------------------------------------- /doc/libs6dns/s6dns-ip46.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6dns_ip46 library interface 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | libs6dns
15 | s6-dns
16 | Software
17 | skarnet.org 18 |

19 | 20 |

The s6dns_ip46 library interface

21 | 22 |

23 | The following functions are declared in the s6-dns/s6dns-ip46.h header, 24 | and implemented as macros. 25 |

26 | 27 |

General information

28 | 29 |

30 | s6dns_ip46 is the transport abstraction layer. It allows 31 | the functions declared in s6-dns/s6dns-engine.h 32 | and s6-dns/s6dns-rci.h to be transport-agnostic, 33 | i.e. to be able to work with both IPv4 and IPv6. 34 |

35 | 36 |

37 | If the underlying skalibs 38 | has been compiled with the 39 | --disable-ipv6 40 | configure option, 41 | or if it has detected at build time that the target host does not support 42 | IPv6, then the s6dns-ip46 abstraction will be totally transparent and use 43 | no resources at all. 44 |

45 | 46 |

Data structures

47 | 48 |

49 | A s6dns_ip46list_t structure holds a list of S6DNS_MAX_SERVERS (16) 50 | IPv4 or IPv6 addresses. Such a mixed list can be constructed, for 51 | instance, if the /etc/resolv.conf file contains both v4 and v6 52 | nameserver lines. 53 |

54 | 55 |

Functions

56 | 57 |

58 | If list is a s6dns_ip46list_t and i an integer 59 | between 0 and DNS_MAX_SERVERS-1, then 60 |

61 | 62 |
    63 |
  • s6dns_ip46list_is6(&list, i) is 1 if the ith 64 | address in list is IPv6 and 0 if it is IPv4.
  • 65 |
  • s6dns_ip46list_ip(&list, i) is a char * pointer to 66 | 16 (if IPv6) or 4 (IPv4) bytes representing the ith address in 67 | list, in network byte order.
  • 68 |
69 | 70 | 71 | 72 | -------------------------------------------------------------------------------- /doc/s6-dnsip.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsip program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsip program

20 | 21 |

22 | s6-dnsip finds both the IPv6 and IPv4 addresses associated to a domain name. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnsip [ -q ] [ -H | -h ] [ -r ] [ -t timeout ] domain
29 | 
30 | 31 |
    32 |
  • s6-dnsip makes both an A and an AAAA query for the name domain, 33 | in parallel. It waits for the results and prints the obtained addresses, 34 | one per line, then exits 0.
  • 35 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 36 |
  • If the DNS answered but no answer is available, it prints a relevant 37 | error message and exits 2.
  • 38 |
  • By default, s6-dnsip looks for DNS cache addresses in the 39 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 40 | and contains a list of IP (v4 or v6) addresses, separated by commas, 41 | semicolons, spaces, tabs, newlines or carriage returns, then this list 42 | is used instead.
  • 43 |
44 | 45 |

Options

46 | 47 |
    48 |
  • -q : qualify. Qualifies domain before resolution, 49 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 50 | environment variable is set and contains a list of suffixes separated by spaces, 51 | tabs, newlines or carriage returns, then this list is used instead. By 52 | default, no qualification is used: if domain is not a FQDN, a dot 53 | is just appended to it.
  • 54 |
  • -H : do not use data from /etc/hosts. This is 55 | the default.
  • 56 |
  • -h : use data from /etc/hosts, if available. 57 | If there's a compiled /etc/hosts.cdb file that is newer than /etc/hosts, 58 | it will be used instead. (See 59 | s6-dns-hosts-compile for details.) 60 | If the lookup in the hosts database returns at least one result, then 61 | no DNS lookup is performed.
  • 62 |
  • -r : random. By default, the program does not sort the 63 | result, but prints them in the order received from the DNS. With this 64 | option, it performs a random permutation on the results before printing 65 | them.
  • 66 |
  • -t timeout : if the resolution takes more 67 | than timeout milliseconds, then it exits 99 right away with an error 68 | message. By default, timeout is 0, which means no timeout.
  • 69 |
70 | 71 |

Notes

72 | 73 |

74 | Even if the underlying skalibs has been compiled without IPv6 support, 75 | or IPv6 DNS transport is unavailable for any reason, s6-dnsip will still 76 | return IPv6 addresses if the AAAA query has a positive result. 77 |

78 | 79 | 80 | 81 | -------------------------------------------------------------------------------- /doc/s6-dnsip4.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsip4 program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsip4 program

20 | 21 |

22 | s6-dnsip4 finds the IPv4 addresses associated to a domain name. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnsip4 [ -q ] [ -H | -h ] [ -r ] [ -t timeout ] domain
29 | 
30 | 31 |
    32 |
  • s6-dnsip4 makes an A query for the name domain. It 33 | waits for the result and prints the obtained IPv4 addresses, one per line, 34 | then exits 0.
  • 35 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 36 |
  • If the DNS answered but no answer is available, it prints a relevant 37 | error message and exits 2.
  • 38 |
  • By default, s6-dnsip4 looks for DNS cache addresses in the 39 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 40 | and contains a list of IP (v4 or v6) addresses, separated by commas, 41 | semicolons, spaces, tabs, newlines or carriage returns, then this list 42 | is used instead.
  • 43 |
44 | 45 |

Options

46 | 47 |
    48 |
  • -q : qualify. Qualifies domain before resolution, 49 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 50 | environment variable is set and contains a list of suffixes separated by spaces, 51 | tabs, newlines or carriage returns, then this list is used instead. By 52 | default, no qualification is used: if domain is not a FQDN, a dot 53 | is just appended to it.
  • 54 |
  • -H : do not use data from /etc/hosts. This is 55 | the default.
  • 56 |
  • -h : use data from /etc/hosts, if available. 57 | If there's a compiled /etc/hosts.cdb file that is newer than /etc/hosts, 58 | it will be used instead. (See 59 | s6-dns-hosts-compile for details.) 60 | If the lookup in the hosts database returns at least one result, then 61 | no DNS lookup is performed.
  • 62 |
  • -r : random. By default, the program does not sort the 63 | result, but prints them in the order received from the DNS. With this 64 | option, it performs a random permutation on the results before printing 65 | them.
  • 66 |
  • -t timeout : if the resolution takes more 67 | than timeout milliseconds, then it exits 99 right away with an error 68 | message. By default, timeout is 0, which means no timeout.
  • 69 |
70 | 71 | 72 | 73 | -------------------------------------------------------------------------------- /doc/s6-dnsip6.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsip6 program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsip6 program

20 | 21 |

22 | s6-dnsip6 finds the IPv6 addresses associated to a domain name. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnsip6 [ -q ] [ -H | -h ] [ -r ] [ -t timeout ] domain
29 | 
30 | 31 |
    32 |
  • s6-dnsip6 makes an AAAA query for the name domain. It 33 | waits for the result and prints the obtained IPv6 addresses, one per line, 34 | then exits 0.
  • 35 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 36 |
  • If the DNS answered but no answer is available, it prints a relevant 37 | error message and exits 2.
  • 38 |
  • By default, s6-dnsip6 looks for DNS cache addresses in the 39 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 40 | and contains a list of IP (v4 or v6) addresses, separated by commas, 41 | semicolons, spaces, tabs, newlines or carriage returns, then this list 42 | is used instead.
  • 43 |
44 | 45 |

Options

46 | 47 |
    48 |
  • -q : qualify. Qualifies domain before resolution, 49 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 50 | environment variable is set and contains a list of suffixes separated by spaces, 51 | tabs, newlines or carriage returns, then this list is used instead. By 52 | default, no qualification is used: if domain is not a FQDN, a dot 53 | is just appended to it.
  • 54 |
  • -H : do not use data from /etc/hosts. This is 55 | the default.
  • 56 |
  • -h : use data from /etc/hosts, if available. 57 | If there's a compiled /etc/hosts.cdb file that is newer than /etc/hosts, 58 | it will be used instead. (See 59 | s6-dns-hosts-compile for details.) 60 | If the lookup in the hosts database returns at least one result, then 61 | no DNS lookup is performed.
  • 62 |
  • -r : random. By default, the program does not sort the 63 | result, but prints them in the order received from the DNS. With this 64 | option, it performs a random permutation on the results before printing 65 | them.
  • 66 |
  • -t timeout : if the resolution takes more 67 | than timeout milliseconds, then it exits 99 right away with an error 68 | message. By default, timeout is 0, which means no timeout.
  • 69 |
70 | 71 |

Notes

72 | 73 |

74 | Bear in mind that making AAAA queries is very different, and 75 | totally independent, from using IPv6 transport for the DNS queries. 76 | Even if the underlying skalibs has been compiled without IPv6 support, 77 | or IPv6 DNS transport is unavailable for any reason, you can still perform 78 | AAAA queries and s6-dnsip6 will answer correctly. 79 |

80 | 81 | 82 | 83 | -------------------------------------------------------------------------------- /doc/s6-dnsmx.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsmx program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsmx program

20 | 21 |

22 | s6-dnsmx finds the MX information associated to a domain name. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnsmx [ -q ] [ -r ] [ -t timeout ] domain
29 | 
30 | 31 |
    32 |
  • s6-dnsmx makes an MX query for the name domain. It 33 | waits for the result and prints the obtained information, one exchanger 34 | per line, then exits 0. It prints the preference, then a space, then 35 | the exchanger name.
  • 36 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 37 |
  • If the DNS answered but no answer is available, it prints a relevant 38 | error message and exits 2.
  • 39 |
  • By default, s6-dnsmx looks for DNS cache addresses in the 40 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 41 | and contains a list of IP (v4 or v6) addresses, separated by commas, 42 | semicolons, spaces, tabs, newlines or carriage returns, then this list 43 | is used instead.
  • 44 |
45 | 46 |

Options

47 | 48 |
    49 |
  • -q : qualify. Qualifies domain before resolution, 50 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 51 | environment variable is set and contains a list of suffixes separated by spaces, 52 | tabs, newlines or carriage returns, then this list is used instead. By 53 | default, no qualification is used: if domain is not a FQDN, a dot 54 | is just appended to it.
  • 55 |
  • -r : random. By default, the program does not sort the 56 | result, but prints them in the order received from the DNS. With this 57 | option, it performs a random permutation on the results before printing 58 | them.
  • 59 |
  • -t timeout : if the resolution takes more 60 | than timeout milliseconds, then it exits 99 right away with an error 61 | message. By default, timeout is 0, which means no timeout.
  • 62 |
63 | 64 | 65 | 66 | -------------------------------------------------------------------------------- /doc/s6-dnsname.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsname program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsname program

20 | 21 |

22 | s6-dnsname finds the name associated to an IPv4 or IPv6 address. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnsname [ -4 | -6 ] [ -H | -h ] [ -r ] [ -t timeout ] ip
29 | 
30 | 31 |
    32 |
  • s6-dnsname converts the IP address ip to a name 33 | ending in in-addr.arpa. or ip6.arpa. then makes a 34 | PTR query for this name. 35 | It waits for the result and prints the obtained names, one per line, 36 | then exits 0.
  • 37 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 38 |
  • If the DNS answered but no answer is available, it prints a relevant 39 | error message and exits 2.
  • 40 |
  • By default, s6-dnsname looks for DNS cache addresses in the 41 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 42 | and contains a list of IP (v4 or v6) addresses, separated by commas, 43 | semicolons, spaces, tabs, newlines or carriage returns, then this list 44 | is used instead.
  • 45 |
46 | 47 |

Options

48 | 49 |
    50 |
  • -4 : interpret ip as an IPv4 address.
  • 51 |
  • -6 : interpret ip as an IPv6 address. 52 | If neither of the -4 and -6 is given, or if both are 53 | given, then ip will be interpreted as v4 or v6 depending on 54 | its syntax.
  • 55 |
  • -H : do not use data from /etc/hosts. This is 56 | the default.
  • 57 |
  • -h : use data from /etc/hosts, if available. 58 | If there's a compiled /etc/hosts.cdb file that is newer than /etc/hosts, 59 | it will be used instead. (See 60 | s6-dns-hosts-compile for details.) 61 | If the lookup in the hosts database returns at least one result, then 62 | no DNS lookup is performed.
  • 63 |
  • -r : random. By default, the program does not sort the 64 | result, but prints them in the order received from the DNS. With this 65 | option, it performs a random permutation on the results before printing 66 | them.
  • 67 |
  • -t timeout : if the resolution takes more 68 | than timeout milliseconds, then it exits 99 right away with an error 69 | message. By default, timeout is 0, which means no timeout.
  • 70 |
71 | 72 |

Notes

73 | 74 |
    75 |
  • If the underlying skalibs has been compiled with IPv6 support disabled, 76 | s6-dnsname will not be able to use IPv6 transport for its resolution, but it 77 | will still accept and resolve IPv6 addresses.
  • 78 |
79 | 80 | 81 | 82 | -------------------------------------------------------------------------------- /doc/s6-dnsns.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsns program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsns program

20 | 21 |

22 | s6-dnsns finds the relevant nameservers providing data for a domain. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnsns [ -q ] [ -r ] [ -t timeout ] domain
29 | 
30 | 31 |
    32 |
  • s6-dnsns makes an NS query for the name domain. It 33 | waits for the result and prints the obtained information, one name 34 | per line, then exits 0.
  • 35 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 36 |
  • If the DNS answered but no answer is available, it prints a relevant 37 | error message and exits 2.
  • 38 |
  • By default, s6-dnsns looks for DNS cache addresses in the 39 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 40 | and contains a list of IP (v4 or v6) addresses, separated by commas, 41 | semicolons, spaces, tabs, newlines or carriage returns, then this list 42 | is used instead.
  • 43 |
44 | 45 |

Options

46 | 47 |
    48 |
  • -q : qualify. Qualifies domain before resolution, 49 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 50 | environment variable is set and contains a list of suffixes separated by spaces, 51 | tabs, newlines or carriage returns, then this list is used instead. By 52 | default, no qualification is used: if domain is not a FQDN, a dot 53 | is just appended to it.
  • 54 |
  • -r : random. By default, the program does not sort the 55 | result, but prints them in the order received from the DNS. With this 56 | option, it performs a random permutation on the results before printing 57 | them.
  • 58 |
  • -t timeout : if the resolution takes more 59 | than timeout milliseconds, then it exits 99 right away with an error 60 | message. By default, timeout is 0, which means no timeout.
  • 61 |
62 | 63 | 64 | 65 | -------------------------------------------------------------------------------- /doc/s6-dnsq.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsq program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsq program

20 | 21 |

22 | s6-dnsq is an analysis and debug tool. It performs a non-recursive DNS query 23 | to a given list of servers, 24 | then prints the contents of the answer packet, and optionally debug 25 | information during the resolution. 26 |

27 | 28 |

Interface

29 | 30 |
31 |      s6-dnsq [ -1 | -2 ] [ -t timeout ] [ -D level ] qtype domain serverlist
32 | 
33 | 34 |
    35 |
  • s6-dnsq makes an iterative DNS query of type qtype for the name domain 36 | to serverlist. 37 | It prints the answer packet, in human-readable form, to its standard output, 38 | then exits 0.
  • 39 |
  • It does not qualify domain.
  • 40 |
  • If the resolution fails for some reason, s6-dnsq exits 2.
  • 41 |
  • serverlist is a list of IP addresses (v4 or v6), one or more addresses 42 | per argument on the command line (so you can use, for instance, 43 | `s6-dnsip4 ns.example.com` as argument, and get all the addresses for 44 | ns.example.com in your server list). 45 | Servers are tried in the order given, until a definitive 46 | answer is obtained or s6-dnsq runs out of server addresses.
  • 47 |
48 | 49 |

Options

50 | 51 |
    52 |
  • -1 : send debug information to stdout.
  • 53 |
  • -2 : send debug information to stderr. This is the default. Note that 54 | those options only apply to debug output, not to the regular packet dump, which 55 | is always printed to stdout.
  • 56 |
  • -t timeout : if the resolution takes more 57 | than timeout milliseconds, then it exits 99 right away with an error 58 | message. By default, timeout is 0, which means no timeout.
  • 59 |
  • -D level : produce debug output during 60 | resolution. If level is: 61 |
      62 |
    • 0: no debug output is produced
    • 63 |
    • 1: information is printed when s6-dnsq receives a DNS packet from a server
    • 64 |
    • 2: information is printed before and after s6-dnsq sends a DNS packet to a server
    • 65 |
    • 3: both 1. and 2. apply
    • 66 |
    67 |
68 | 69 |

Notes

70 | 71 |
    72 |
  • TXT records are printed in a quoted form similar to 73 | s6-quote's 74 | output.
  • 75 |
  • If s6-dnsq finds a record it cannot print, such as an unknown RR type, 76 | it dumps its contents in the same quoted form.
  • 77 |
  • The normal output format should be stable, so you can write programs that 78 | automatically parse it. However, the debug output format is undocumented and subject 79 | to change.
  • 80 |
81 | 82 | 83 | 84 | -------------------------------------------------------------------------------- /doc/s6-dnsqr.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsqr program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsqr program

20 | 21 |

22 | s6-dnsqr is an analysis and debug tool. It performs a DNS resolution, 23 | then prints the contents of the answer packet, and optionally debug 24 | information during the resolution. 25 |

26 | 27 |

Interface

28 | 29 |
30 |      s6-dnsqr [ -1 | -2 ] [ -t timeout ] [ -D level ] qtype domain
31 | 
32 | 33 |
    34 |
  • s6-dnsqr makes a recursive DNS query of type qtype for the name domain. 35 | It prints the answer packet, in human-readable form, to its standard output, 36 | then exits 0.
  • 37 |
  • It does not qualify domain.
  • 38 |
  • If the resolution fails for some reason, s6-dnsqr exits 2.
  • 39 |
  • By default, s6-dnsqr looks for DNS cache addresses in the 40 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 41 | and contains a list of IP (v4 or v6) addresses, separated by commas, 42 | semicolons, spaces, tabs, newlines or carriage returns, then this list 43 | is used instead.
  • 44 |
45 | 46 |

Options

47 | 48 |
    49 |
  • -1 : send debug information to stdout.
  • 50 |
  • -2 : send debug information to stderr. This is the default. Note that 51 | those options only apply to debug output, not to the regular packet dump, which 52 | is always printed to stdout.
  • 53 |
  • -t timeout : if the resolution takes more 54 | than timeout milliseconds, then it exits 99 right away with an error 55 | message. By default, timeout is 0, which means no timeout.
  • 56 |
  • -D level : produce debug output during 57 | resolution. If level is: 58 |
      59 |
    • 0: no debug output is produced
    • 60 |
    • 1: information is printed when s6-dnsqr receives a DNS packet from a cache
    • 61 |
    • 2: information is printed before and after s6-dnsqr sends a DNS packet to a cache
    • 62 |
    • 3: both 1. and 2. apply
    • 63 |
    64 | 65 |
66 | 67 |

Notes

68 | 69 |
    70 |
  • TXT records are printed in a quoted form similar to 71 | s6-quote's 72 | output.
  • 73 |
  • If s6-dnsqr finds a record it cannot print, such as an unknown RR type, 74 | it dumps its content in the same quoted form.
  • 75 |
  • The normal output format should be stable, so you can write programs that 76 | automatically parse it. However, the debug output format is undocumented and subject 77 | to change.
  • 78 |
79 | 80 | 81 | 82 | -------------------------------------------------------------------------------- /doc/s6-dnsqualify.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnsqualify program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnsqualify program

20 | 21 |

22 | s6-dnsqualify qualifies a domain name. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnsqualify domain
29 | 
30 | 31 |
    32 |
  • s6-dnsqualify qualifies domain according to the "domain" and 33 | "search" rules in /etc/resolv.conf. It prints the result on 34 | stdout, one FQDN per line.
  • 35 |
  • If the DNSQUALIFY 36 | environment variable is set and contains a list of suffixes separated by spaces, 37 | tabs, newlines or carriage returns, then this list is used instead of the 38 | /etc/resolv.conf rules.
  • 39 |
40 | 41 | 42 | 43 | -------------------------------------------------------------------------------- /doc/s6-dnssoa.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnssoa program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnssoa program

20 | 21 |

22 | s6-dnssoa finds the SOA information associated to a domain. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnssoa [ -q ] [ -r ] [ -t timeout ] domain
29 | 
30 | 31 |
    32 |
  • s6-dnsmx makes an SOA query for the name domain. It 33 | waits for the result and prints the obtained information line by line, 34 | then exits 0. It prints the mname, the rname, the serial number, and 35 | the refresh, retry, expiration and minimum times, in that order, 36 | separated by spaces.
  • 37 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 38 |
  • If the DNS answered but no answer is available, it prints a relevant 39 | error message and exits 2.
  • 40 |
  • By default, s6-dnssoa looks for DNS cache addresses in the 41 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 42 | and contains a list of IP (v4 or v6) addresses, separated by commas, 43 | semicolons, spaces, tabs, newlines or carriage returns, then this list 44 | is used instead.
  • 45 |
46 | 47 |

Options

48 | 49 |
    50 |
  • -q : qualify. Qualifies domain before resolution, 51 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 52 | environment variable is set and contains a list of suffixes separated by spaces, 53 | tabs, newlines or carriage returns, then this list is used instead. By 54 | default, no qualification is used: if domain is not a FQDN, a dot 55 | is just appended to it.
  • 56 |
  • -r : random. By default, the program does not sort the 57 | result, but prints them in the order received from the DNS. With this 58 | option, it performs a random permutation on the results before printing 59 | them.
  • 60 |
  • -t timeout : if the resolution takes more 61 | than timeout milliseconds, then it exits 99 right away with an error 62 | message. By default, timeout is 0, which means no timeout.
  • 63 |
64 | 65 | 66 | 67 | -------------------------------------------------------------------------------- /doc/s6-dnssrv.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnssrv program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnssrv program

20 | 21 |

22 | s6-dnssrv finds the SRV information associated to a 23 | service name, protocol name and domain name. 24 |

25 | 26 |

Interface

27 | 28 |
29 |      s6-dnssrv [ -q ] [ -r ] [ -t timeout ] service proto domain
30 | 
31 | 32 |
    33 |
  • s6-dnssrv makes an SRV query for _service._proto.domain. 34 | It waits for the result and prints the obtained information line by line, 35 | then exits 0. It prints the priority, the weight, the port number and the 36 | target, in that order, separated by spaces.
  • 37 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 38 |
  • If the DNS answered but no answer is available, it prints a relevant 39 | error message and exits 2.
  • 40 |
  • By default, s6-dnssrv looks for DNS cache addresses in the 41 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 42 | and contains a list of IP (v4 or v6) addresses, separated by commas, 43 | semicolons, spaces, tabs, newlines or carriage returns, then this list 44 | is used instead.
  • 45 |
46 | 47 |

Options

48 | 49 |
    50 |
  • -q : qualify. Qualifies domain before resolution, 51 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 52 | environment variable is set and contains a list of suffixes separated by spaces, 53 | tabs, newlines or carriage returns, then this list is used instead. By 54 | default, no qualification is used: if domain is not a FQDN, a dot 55 | is just appended to it.
  • 56 |
  • -r : random. By default, the program does not sort the 57 | result, but prints them in the order received from the DNS. With this 58 | option, it performs a random permutation on the results before printing 59 | them.
  • 60 |
  • -t timeout : if the resolution takes more 61 | than timeout milliseconds, then it exits 99 right away with an error 62 | message. By default, timeout is 0, which means no timeout.
  • 63 |
64 | 65 | 66 | 67 | -------------------------------------------------------------------------------- /doc/s6-dnstxt.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-dnstxt program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-dnstxt program

20 | 21 |

22 | s6-dnstxt finds the TXT information associated to a domain name. 23 |

24 | 25 |

Interface

26 | 27 |
28 |      s6-dnstxt [ -q ] [ -r ] [ -t timeout ] domain
29 | 
30 | 31 |
    32 |
  • s6-dnstxt makes a TXT query for the name domain. It 33 | waits for the result and prints the obtained strings, one by line, 34 | in a quoted form similar to 35 | s6-quote's 36 | output. You can pipe s6-dnstxt's output through 37 | s6-unquote-filter 38 | to get unquoted TXT fields.
  • 39 |
  • If the domain exists but no relevant field has been found, it exits 1.
  • 40 |
  • If the DNS answered but no answer is available, it prints a relevant 41 | error message and exits 2.
  • 42 |
  • By default, s6-dnstxt looks for DNS cache addresses in the 43 | /etc/resolv.conf file. If the DNSCACHEIP environment variable is set 44 | and contains a list of IP (v4 or v6) addresses, separated by commas, 45 | semicolons, spaces, tabs, newlines or carriage returns, then this list 46 | is used instead.
  • 47 |
48 | 49 |

Options

50 | 51 |
    52 |
  • -q : qualify. Qualifies domain before resolution, 53 | according to suffixes found in /etc/resolv.conf. If the DNSQUALIFY 54 | environment variable is set and contains a list of suffixes separated by spaces, 55 | tabs, newlines or carriage returns, then this list is used instead. By 56 | default, no qualification is used: if domain is not a FQDN, a dot 57 | is just appended to it.
  • 58 |
  • -r : random. By default, the program does not sort the 59 | result, but prints them in the order received from the DNS. With this 60 | option, it performs a random permutation on the results before printing 61 | them.
  • 62 |
  • -t timeout : if the resolution takes more 63 | than timeout milliseconds, then it exits 99 right away with an error 64 | message. By default, timeout is 0, which means no timeout.
  • 65 |
66 | 67 |

Notes

68 | 69 |

70 | There can be more than one character-string in a TXT RR, and there can be 71 | more than one TXT RR per domain. DNS clients usually concatenate all this 72 | and only give one string. s6-dnstxt concatenates all the character-strings 73 | in one TXT record, but separates different TXT records, printing each one 74 | on a separate line. 75 |

76 | 77 | 78 | 79 | -------------------------------------------------------------------------------- /doc/s6-randomip.html: -------------------------------------------------------------------------------- 1 | 2 | 3 | 4 | 5 | 6 | s6-dns: the s6-randomip program 7 | 8 | 9 | 10 | 11 | 12 | 13 |

14 | s6-dns
15 | Software
16 | skarnet.org 17 |

18 | 19 |

The s6-randomip program

20 | 21 |

22 | s6-randomip generates random IP addresses and prints them to 23 | its standard output, one per line. 24 |

25 | 26 |

Interface

27 | 28 |
29 |      s6-randomip [ -4 ] [ -6 ] [ -n max ]
30 | 
31 | 32 |
    33 |
  • s6-randomip makes up IP addresses and prints 34 | them to its stdout. It keeps running until it receives a signal.
  • 35 |
  • IP addresses are not guaranteed to represent anything. They are totally random.
  • 36 |
37 | 38 |

Options

39 | 40 |
    41 |
  • -4 : generate IPv4 addresses.
  • 42 |
  • -6 : generate IPv6 addresses. Both the -4 and 43 | -6 options may be given. If none is given, by default 44 | s6-randomip will only generate IPv4 addresses.
  • 45 |
  • -n max : s6-randomip will only generate 46 | max addresses, then exit 0, instead of running forever.
  • 47 |
48 | 49 |

Notes

50 | 51 |

52 | s6-randomip can be used in conjunction with 53 | s6-dnsname-filter to stress-test your 54 | DNS architecture. Please use this responsibly and ethically. 55 |

56 | 57 | 58 | 59 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_case_lines: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_expand_dirs: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_extra_checks: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_generate_configh: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_generate_make: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_help_dependencies: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_help_install: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_help_options: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_init_vars: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/configure-snippets/configure_slashpackage_other: -------------------------------------------------------------------------------- 1 | 2 | -------------------------------------------------------------------------------- /package/deps-build: -------------------------------------------------------------------------------- 1 | true true /package/prog/skalibs 2.14.4.0 libskarnet 2 | -------------------------------------------------------------------------------- /package/info: -------------------------------------------------------------------------------- 1 | package=s6-dns 2 | version=2.4.1.0 3 | category=web 4 | package_macro_name=S6_DNS 5 | -------------------------------------------------------------------------------- /package/modes: -------------------------------------------------------------------------------- 1 | skadnsd 0755 2 | s6-randomip 0755 3 | s6-dnsqualify 0755 4 | s6-dnsip4 0755 5 | s6-dnsip6 0755 6 | s6-dnsmx 0755 7 | s6-dnsname 0755 8 | s6-dnsns 0755 9 | s6-dnssoa 0755 10 | s6-dnssrv 0755 11 | s6-dnstxt 0755 12 | s6-dnsip4-filter 0755 13 | s6-dnsip6-filter 0755 14 | s6-dnsname-filter 0755 15 | s6-dnsq 0755 16 | s6-dnsqr 0755 17 | s6-dns-hosts-compile 0755 18 | -------------------------------------------------------------------------------- /package/targets.mak: -------------------------------------------------------------------------------- 1 | BIN_TARGETS := \ 2 | skadnsd \ 3 | s6-randomip \ 4 | s6-dnsqualify \ 5 | s6-dnsip \ 6 | s6-dnsip4 \ 7 | s6-dnsip6 \ 8 | s6-dnsmx \ 9 | s6-dnsname \ 10 | s6-dnsns \ 11 | s6-dnssoa \ 12 | s6-dnssrv \ 13 | s6-dnstxt \ 14 | s6-dnsip4-filter \ 15 | s6-dnsip6-filter \ 16 | s6-dnsname-filter \ 17 | s6-dnsq \ 18 | s6-dnsqr \ 19 | s6-dns-hosts-compile 20 | 21 | LIBEXEC_TARGETS := 22 | 23 | LIB_DEFS := S6DNS=s6dns SKADNS=skadns 24 | S6DNS_DESCRIPTION := A client library for DNS resolution 25 | SKADNS_DESCRIPTION := A client library for asynchronous DNS resolution 26 | -------------------------------------------------------------------------------- /patch-for-solaris: -------------------------------------------------------------------------------- 1 | #!/usr/xpg4/bin/sh -e 2 | 3 | patchit () { 4 | echo '#!/usr/xpg4/bin/sh' > $1.tmp 5 | tail -n +2 $1 >> $1.tmp 6 | mv -f $1.tmp $1 7 | chmod 0755 $1 8 | } 9 | 10 | # Solaris doesn't understand POSIX.1-2008 either. 11 | sed -e 's/XOPEN_SOURCE=700/XOPEN_SOURCE=600/' < configure > configure.tmp 12 | mv -f configure.tmp configure 13 | 14 | patchit ./configure 15 | patchit ./tools/install.sh 16 | patchit ./tools/gen-deps.sh 17 | 18 | echo 'SHELL := /usr/xpg4/bin/sh' > Makefile.tmp 19 | echo >> Makefile.tmp 20 | cat Makefile >> Makefile.tmp 21 | mv -f Makefile.tmp Makefile 22 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsip: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsip4: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsip4-filter: -------------------------------------------------------------------------------- 1 | s6dns_generic_filter_main.o 2 | s6dns_namescanner.o 3 | ${LIBSKADNS} 4 | ${LIBS6DNS} 5 | -lskarnet 6 | ${SOCKET_LIB} 7 | ${SYSCLOCK_LIB} 8 | ${SPAWN_LIB} 9 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsip6: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsip6-filter: -------------------------------------------------------------------------------- 1 | s6dns_generic_filter_main.o 2 | s6dns_namescanner.o 3 | ${LIBSKADNS} 4 | ${LIBS6DNS} 5 | -lskarnet 6 | ${SOCKET_LIB} 7 | ${SYSCLOCK_LIB} 8 | ${SPAWN_LIB} 9 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsmx: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsname: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsname-filter: -------------------------------------------------------------------------------- 1 | s6dns_generic_filter_main.o 2 | ${LIBSKADNS} 3 | ${LIBS6DNS} 4 | -lskarnet 5 | ${SOCKET_LIB} 6 | ${SYSCLOCK_LIB} 7 | ${SPAWN_LIB} 8 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsns: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsq: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsqr: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnsqualify: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnssoa: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnssrv: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-dnstxt: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/clients/deps-exe/s6-randomip: -------------------------------------------------------------------------------- 1 | -lskarnet 2 | ${SOCKET_LIB} 3 | ${SYSCLOCK_LIB} 4 | -------------------------------------------------------------------------------- /src/clients/s6-dnsip.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | 15 | #include 16 | 17 | #define USAGE "s6-dnsip [ -q ] [ -H | -h ] [ -r ] [ -t timeout ] domain" 18 | #define dieusage() strerr_dieusage(100, USAGE) 19 | 20 | int main (int argc, char const *const *argv) 21 | { 22 | genalloc ips = GENALLOC_ZERO ; /* ip46full */ 23 | tain deadline ; 24 | unsigned int t = 0 ; 25 | int flagqualify = 0 ; 26 | int flaghosts = 0 ; 27 | int flagunsort = 0 ; 28 | int r = 0 ; 29 | PROG = "s6-dnsip" ; 30 | 31 | { 32 | subgetopt l = SUBGETOPT_ZERO ; 33 | for (;;) 34 | { 35 | int opt = subgetopt_r(argc, argv, "qHhrt:", &l) ; 36 | if (opt == -1) break ; 37 | switch (opt) 38 | { 39 | case 'q' : flagqualify = 1 ; break ; 40 | case 'H' : flaghosts = 0 ; break ; 41 | case 'h' : flaghosts = 1 ; break ; 42 | case 'r' : flagunsort = 1 ; break ; 43 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 44 | default : dieusage() ; 45 | } 46 | } 47 | argc -= l.ind ; argv += l.ind ; 48 | } 49 | if (argc < 1) dieusage() ; 50 | 51 | tain_now_set_stopwatch_g() ; 52 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 53 | tain_add_g(&deadline, &deadline) ; 54 | 55 | if (!s6dns_init_options(flaghosts)) 56 | strerr_diefu1sys(111, "parse /etc/resolv.conf or /etc/hosts") ; 57 | 58 | if (flaghosts) 59 | { 60 | r = flagqualify ? s6dns_hosts_aaaaa_q(argv[0], &ips) : s6dns_hosts_aaaaa_noq(argv[0], &ips) ; 61 | if (r == -1) strerr_diefu3sys(111, "look up ", argv[0], " in hosts database") ; 62 | } 63 | 64 | if (!r) 65 | { 66 | r = s6dns_resolve_aaaaa_g(&ips, argv[0], strlen(argv[0]), flagqualify, &deadline) ; 67 | if (r < 0) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 68 | } 69 | 70 | if (!genalloc_len(ip46full, &ips)) return 1 ; 71 | if (flagunsort) random_unsort(ips.s, genalloc_len(ip46full, &ips), sizeof(ip46full)) ; 72 | for (size_t i = 0 ; i < genalloc_len(ip46full, &ips) ; i++) 73 | { 74 | char fmt[IP6_FMT] ; 75 | size_t n = ip46full_fmt(fmt, genalloc_s(ip46full, &ips) + i) ; 76 | fmt[n++] = '\n' ; 77 | if (buffer_put(buffer_1small, fmt, n) < 0) 78 | strerr_diefu1sys(111, "write to stdout") ; 79 | } 80 | if (!buffer_flush(buffer_1small)) 81 | strerr_diefu1sys(111, "write to stdout") ; 82 | return 0 ; 83 | } 84 | -------------------------------------------------------------------------------- /src/clients/s6-dnsip4-filter.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include "s6dns-generic-filter.h" 12 | 13 | #define USAGE "s6-dnsip4-filter [ -l lines ] [ -c concurrency ] [ -t timeout ] [ -f format ] [ -e errorformat ]" 14 | 15 | typedef struct s6dns_a1_s s6dns_a1_t, *s6dns_a1_t_ref ; 16 | struct s6dns_a1_s 17 | { 18 | char ip[4] ; 19 | unsigned int got : 1 ; 20 | } ; 21 | 22 | static int s6dns_message_parse_answer_a1 (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 23 | { 24 | if ((section == 2) && (rr->rtype == S6DNS_T_A) && (rr->rdlength == 4)) 25 | { 26 | s6dns_a1_t *data = stuff ; 27 | if (data->got) return 1 ; 28 | memcpy(data->ip, packet+pos, 4) ; 29 | data->got = 1 ; 30 | } 31 | (void)packetlen ; 32 | return 1 ; 33 | } 34 | 35 | static int ipformatter (stralloc *sa, char const *packet, unsigned int packetlen) 36 | { 37 | s6dns_a1_t data ; 38 | s6dns_message_header_t h ; 39 | int r ; 40 | data.got = 0 ; 41 | r = s6dns_message_parse(&h, packet, packetlen, &s6dns_message_parse_answer_a1, &data) ; 42 | if (r <= 0) return r ; 43 | if (!data.got) return 1 ; 44 | if (!stralloc_readyplus(sa, IP4_FMT)) return -1 ; 45 | sa->len += ip4_fmt(sa->s + sa->len, data.ip) ; 46 | stralloc_0(sa) ; 47 | return 1 ; 48 | } 49 | 50 | int main (int argc, char const *const *argv, char const *const *envp) 51 | { 52 | PROG = "s6-dnsip4-filter" ; 53 | return s6dns_generic_filter_main(argc, argv, envp, S6DNS_T_A, &s6dns_namescanner, &ipformatter, USAGE) ; 54 | } 55 | -------------------------------------------------------------------------------- /src/clients/s6-dnsip4.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | 14 | #include 15 | 16 | #define USAGE "s6-dnsip4 [ -q ] [ -H | -h ] [ -r ] [ -t timeout ] domain" 17 | #define dieusage() strerr_dieusage(100, USAGE) 18 | 19 | int main (int argc, char const *const *argv) 20 | { 21 | stralloc ips = STRALLOC_ZERO ; 22 | tain deadline ; 23 | unsigned int t = 0 ; 24 | int flagqualify = 0 ; 25 | int flaghosts = 0 ; 26 | int flagunsort = 0 ; 27 | int r = 0 ; 28 | PROG = "s6-dnsip4" ; 29 | 30 | { 31 | subgetopt l = SUBGETOPT_ZERO ; 32 | for (;;) 33 | { 34 | int opt = subgetopt_r(argc, argv, "qHhrt:", &l) ; 35 | if (opt == -1) break ; 36 | switch (opt) 37 | { 38 | case 'q' : flagqualify = 1 ; break ; 39 | case 'H' : flaghosts = 0 ; break ; 40 | case 'h' : flaghosts = 1 ; break ; 41 | case 'r' : flagunsort = 1 ; break ; 42 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 43 | default : dieusage() ; 44 | } 45 | } 46 | argc -= l.ind ; argv += l.ind ; 47 | } 48 | if (argc < 1) dieusage() ; 49 | 50 | tain_now_set_stopwatch_g() ; 51 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 52 | tain_add_g(&deadline, &deadline) ; 53 | 54 | if (!s6dns_init_options(flaghosts)) 55 | strerr_diefu1sys(111, "parse from /etc/resolv.conf or /etc/hosts") ; 56 | 57 | if (flaghosts) 58 | { 59 | r = flagqualify ? s6dns_hosts_a_q(argv[0], &ips) : s6dns_hosts_a_noq(argv[0], &ips) ; 60 | if (r == -1) strerr_diefu3sys(111, "look up ", argv[0], " in hosts database") ; 61 | } 62 | 63 | if (!r) 64 | { 65 | r = s6dns_resolve_a_g(&ips, argv[0], strlen(argv[0]), flagqualify, &deadline) ; 66 | if (r == -1) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 67 | if (!r) strerr_diefu4x(2, "resolve ", argv[0], ": ", s6dns_constants_error_str(errno)) ; 68 | } 69 | 70 | if (!ips.len) return 1 ; 71 | if (flagunsort) random_unsort(ips.s, ips.len / 4, 4) ; 72 | for (size_t i = 0 ; i < ips.len / 4 ; i++) 73 | { 74 | char fmt[IP4_FMT] ; 75 | size_t n = ip4_fmt(fmt, ips.s + 4 * i) ; 76 | fmt[n++] = '\n' ; 77 | if (buffer_put(buffer_1small, fmt, n) == -1) 78 | strerr_diefu1sys(111, "write to stdout") ; 79 | } 80 | if (!buffer_flush(buffer_1small)) 81 | strerr_diefu1sys(111, "write to stdout") ; 82 | return 0 ; 83 | } 84 | -------------------------------------------------------------------------------- /src/clients/s6-dnsip6-filter.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include "s6dns-generic-filter.h" 12 | 13 | #define USAGE "s6-dnsip6-filter [ -l lines ] [ -c concurrency ] [ -t timeout ] [ -f format ] [ -e errorformat ]" 14 | 15 | typedef struct s6dns_aaaa1_s s6dns_aaaa1_t, *s6dns_aaaa1_t_ref ; 16 | struct s6dns_aaaa1_s 17 | { 18 | char ip[16] ; 19 | unsigned int got : 1 ; 20 | } ; 21 | 22 | static int s6dns_message_parse_answer_aaaa1 (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 23 | { 24 | if ((section == 2) && (rr->rtype == S6DNS_T_AAAA) && (rr->rdlength == 16)) 25 | { 26 | s6dns_aaaa1_t *data = stuff ; 27 | if (data->got) return 1 ; 28 | memcpy(data->ip, packet+pos, 16) ; 29 | data->got = 1 ; 30 | } 31 | (void)packetlen ; 32 | return 1 ; 33 | } 34 | 35 | static int ipformatter (stralloc *sa, char const *packet, unsigned int packetlen) 36 | { 37 | s6dns_aaaa1_t data ; 38 | s6dns_message_header_t h ; 39 | int r ; 40 | data.got = 0 ; 41 | r = s6dns_message_parse(&h, packet, packetlen, &s6dns_message_parse_answer_aaaa1, &data) ; 42 | if (r <= 0) return r ; 43 | if (!data.got) return 1 ; 44 | if (!stralloc_readyplus(sa, IP6_FMT)) return -1 ; 45 | sa->len += ip6_fmt(sa->s + sa->len, data.ip) ; 46 | stralloc_0(sa) ; 47 | return 1 ; 48 | } 49 | 50 | int main (int argc, char const *const *argv, char const *const *envp) 51 | { 52 | PROG = "s6-dnsip6-filter" ; 53 | return s6dns_generic_filter_main(argc, argv, envp, S6DNS_T_AAAA, &s6dns_namescanner, &ipformatter, USAGE) ; 54 | } 55 | -------------------------------------------------------------------------------- /src/clients/s6-dnsip6.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | 14 | #include 15 | 16 | #define USAGE "s6-dnsip6 [ -q ] [ -H | -h ] [ -r ] [ -t timeout ] domain" 17 | #define dieusage() strerr_dieusage(100, USAGE) 18 | 19 | int main (int argc, char const *const *argv) 20 | { 21 | stralloc ips = STRALLOC_ZERO ; 22 | tain deadline ; 23 | unsigned int t = 0 ; 24 | int flagqualify = 0 ; 25 | int flaghosts = 0 ; 26 | int flagunsort = 0 ; 27 | int r = 0 ; 28 | PROG = "s6-dnsip6" ; 29 | 30 | { 31 | subgetopt l = SUBGETOPT_ZERO ; 32 | for (;;) 33 | { 34 | int opt = subgetopt_r(argc, argv, "qHhrt:", &l) ; 35 | if (opt == -1) break ; 36 | switch (opt) 37 | { 38 | case 'q' : flagqualify = 1 ; break ; 39 | case 'H' : flaghosts = 0 ; break ; 40 | case 'h' : flaghosts = 1 ; break ; 41 | case 'r' : flagunsort = 1 ; break ; 42 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 43 | default : dieusage() ; 44 | } 45 | } 46 | argc -= l.ind ; argv += l.ind ; 47 | } 48 | if (argc < 1) dieusage() ; 49 | 50 | tain_now_set_stopwatch_g() ; 51 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 52 | tain_add_g(&deadline, &deadline) ; 53 | 54 | if (!s6dns_init_options(flaghosts)) 55 | strerr_diefu1sys(111, "parse /etc/resolv.conf or /etc/hosts") ; 56 | 57 | if (flaghosts) 58 | { 59 | r = flagqualify ? s6dns_hosts_aaaa_q(argv[0], &ips) : s6dns_hosts_aaaa_noq(argv[0], &ips) ; 60 | if (r == -1) strerr_diefu3sys(111, "look up ", argv[0], " in hosts database") ; 61 | } 62 | 63 | if (!r) 64 | { 65 | r = s6dns_resolve_aaaa_g(&ips, argv[0], strlen(argv[0]), flagqualify, &deadline) ; 66 | if (r == -1) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 67 | if (!r) strerr_diefu4x(2, "resolve ", argv[0], ": ", s6dns_constants_error_str(errno)) ; 68 | } 69 | 70 | if (!ips.len) return 1 ; 71 | if (flagunsort) random_unsort(ips.s, ips.len / 16, 16) ; 72 | for (size_t i = 0 ; i < ips.len / 16 ; i++) 73 | { 74 | char fmt[IP6_FMT] ; 75 | size_t n = ip6_fmt(fmt, ips.s + 16 * i) ; 76 | fmt[n++] = '\n' ; 77 | if (buffer_put(buffer_1small, fmt, n) < (ssize_t)n) 78 | strerr_diefu1sys(111, "write to stdout") ; 79 | } 80 | if (!buffer_flush(buffer_1small)) 81 | strerr_diefu1sys(111, "write to stdout") ; 82 | return 0 ; 83 | } 84 | -------------------------------------------------------------------------------- /src/clients/s6-dnsmx.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | 14 | #include 15 | 16 | #define USAGE "s6-dnsmx [ -q ] [ -r ] [ -t timeout ] name" 17 | #define dieusage() strerr_dieusage(100, USAGE) 18 | 19 | int main (int argc, char const *const *argv) 20 | { 21 | genalloc mxs = GENALLOC_ZERO ; /* array of s6dns_message_rr_mx_t */ 22 | tain deadline ; 23 | unsigned int t = 0 ; 24 | int flagqualify = 0 ; 25 | int flagunsort = 0 ; 26 | int r ; 27 | PROG = "s6-dnsmx" ; 28 | 29 | { 30 | subgetopt l = SUBGETOPT_ZERO ; 31 | for (;;) 32 | { 33 | int opt = subgetopt_r(argc, argv, "qrt:", &l) ; 34 | if (opt == -1) break ; 35 | switch (opt) 36 | { 37 | case 'q' : flagqualify = 1 ; break ; 38 | case 'r' : flagunsort = 1 ; break ; 39 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 40 | default : dieusage() ; 41 | } 42 | } 43 | argc -= l.ind ; argv += l.ind ; 44 | } 45 | if (argc < 1) dieusage() ; 46 | 47 | tain_now_set_stopwatch_g() ; 48 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 49 | tain_add_g(&deadline, &deadline) ; 50 | 51 | if (!s6dns_rci_init(&s6dns_rci_here, "/etc/resolv.conf")) 52 | strerr_diefu1sys(111, "initialize structures from /etc/resolv.conf") ; 53 | 54 | r = s6dns_resolve_mx_g(&mxs, argv[0], strlen(argv[0]), flagqualify, &deadline) ; 55 | if (r < 0) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 56 | if (!r) strerr_diefu4x(2, "resolve ", argv[0], ": ", s6dns_constants_error_str(errno)) ; 57 | if (!genalloc_len(s6dns_message_rr_mx_t, &mxs)) return 1 ; 58 | if (flagunsort) random_unsort(mxs.s, genalloc_len(s6dns_message_rr_mx_t, &mxs), sizeof(s6dns_message_rr_mx_t)) ; 59 | for (size_t i = 0 ; i < genalloc_len(s6dns_message_rr_mx_t, &mxs) ; i++) 60 | { 61 | char buf[S6DNS_FMT_MX] ; 62 | size_t len = s6dns_fmt_mx(buf, S6DNS_FMT_MX, genalloc_s(s6dns_message_rr_mx_t, &mxs) + i) ; 63 | if (!len) strerr_diefu1sys(111, "format result") ; 64 | if (buffer_put(buffer_1, buf, len) < (ssize_t)len) goto err ; 65 | if (buffer_put(buffer_1, "\n", 1) < 1) goto err ; 66 | } 67 | if (!buffer_flush(buffer_1)) goto err ; 68 | return 0 ; 69 | err: 70 | strerr_diefu1sys(111, "write to stdout") ; 71 | } 72 | -------------------------------------------------------------------------------- /src/clients/s6-dnsname-filter.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | 11 | #include 12 | #include 13 | #include 14 | #include "s6dns-generic-filter.h" 15 | 16 | #define USAGE "s6-dnsname-filter [ -4 ] [ -6 ] [ -l lines ] [ -c concurrency ] [ -t timeout ] [ -f format ] [ -e errorformat ]" 17 | 18 | static size_t ipscanner (s6dns_domain_t *d, char const *s) 19 | { 20 | char ip[16] ; 21 | size_t pos ; 22 | if (flag6) 23 | { 24 | pos = ip6_scan(s, ip) ; 25 | if (pos) 26 | { 27 | s6dns_domain_arpafromip6(d, ip, 128) ; 28 | goto yes ; 29 | } 30 | } 31 | if (flag4) 32 | { 33 | pos = ip4_scan(s, ip) ; 34 | if (pos) 35 | { 36 | s6dns_domain_arpafromip4(d, ip) ; 37 | goto yes ; 38 | } 39 | } 40 | return (errno = 0, 0) ; 41 | yes: 42 | if (!s6dns_domain_encode(d)) return 0 ; 43 | return pos ; 44 | } 45 | 46 | typedef struct s6dns_domain1_s s6dns_domain1_t, *s6dns_domain1_t_ref ; 47 | struct s6dns_domain1_s 48 | { 49 | s6dns_domain_t d ; 50 | unsigned int got : 1 ; 51 | } ; 52 | 53 | static int s6dns_message_parse_answer_domain1 (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 54 | { 55 | if ((section == 2) && (rr->rtype == S6DNS_T_PTR)) 56 | { 57 | s6dns_domain1_t *data = stuff ; 58 | unsigned int start = pos ; 59 | if (data->got) return 1 ; 60 | if (!s6dns_message_get_domain(&data->d, packet, packetlen, &pos)) return 0 ; 61 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 62 | data->got = 1 ; 63 | } 64 | return 1 ; 65 | } 66 | 67 | static int domainformatter (stralloc *sa, char const *packet, unsigned int packetlen) 68 | { 69 | s6dns_domain1_t data ; 70 | s6dns_message_header_t h ; 71 | int r ; 72 | data.got = 0 ; 73 | r = s6dns_message_parse(&h, packet, packetlen, &s6dns_message_parse_answer_domain1, &data) ; 74 | if (r <= 0) return r ; 75 | if (!data.got) return 1 ; 76 | if (!stralloc_readyplus(sa, data.d.len + 1)) return -1 ; 77 | sa->len += s6dns_domain_tostring(sa->s + sa->len, data.d.len + 1, &data.d) ; 78 | stralloc_0(sa) ; 79 | return 1 ; 80 | } 81 | 82 | int main (int argc, char const *const *argv, char const *const *envp) 83 | { 84 | PROG = "s6-dnsname-filter" ; 85 | return s6dns_generic_filter_main(argc, argv, envp, S6DNS_T_PTR, &ipscanner, &domainformatter, USAGE) ; 86 | } 87 | -------------------------------------------------------------------------------- /src/clients/s6-dnsns.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | 15 | #include 16 | 17 | #define USAGE "s6-dnsns [ -q ] [ -r ] [ -t timeout ] name" 18 | #define dieusage() strerr_dieusage(100, USAGE) 19 | 20 | int main (int argc, char const *const *argv) 21 | { 22 | genalloc ds = GENALLOC_ZERO ; /* array of s6dns_domain_t */ 23 | tain deadline ; 24 | unsigned int t = 0 ; 25 | int flagqualify = 0 ; 26 | int flagunsort = 0 ; 27 | int r ; 28 | PROG = "s6-dnsns" ; 29 | 30 | { 31 | subgetopt l = SUBGETOPT_ZERO ; 32 | for (;;) 33 | { 34 | int opt = subgetopt_r(argc, argv, "qrt:", &l) ; 35 | if (opt == -1) break ; 36 | switch (opt) 37 | { 38 | case 'q' : flagqualify = 1 ; break ; 39 | case 'r' : flagunsort = 1 ; break ; 40 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 41 | default : dieusage() ; 42 | } 43 | } 44 | argc -= l.ind ; argv += l.ind ; 45 | } 46 | if (argc < 1) dieusage() ; 47 | 48 | tain_now_set_stopwatch_g() ; 49 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 50 | tain_add_g(&deadline, &deadline) ; 51 | 52 | if (!s6dns_rci_init(&s6dns_rci_here, "/etc/resolv.conf")) 53 | strerr_diefu1sys(111, "initialize structures from /etc/resolv.conf") ; 54 | 55 | r = s6dns_resolve_ns_g(&ds, argv[0], strlen(argv[0]), flagqualify, &deadline) ; 56 | if (r == -1) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 57 | if (!r) strerr_diefu4x(2, "resolve ", argv[0], ": ", s6dns_constants_error_str(errno)) ; 58 | if (!genalloc_len(s6dns_domain_t, &ds)) return 1 ; 59 | if (flagunsort) random_unsort(ds.s, genalloc_len(s6dns_domain_t, &ds), sizeof(s6dns_domain_t)) ; 60 | { 61 | char buf[S6DNS_FMT_DOMAINLIST(genalloc_len(s6dns_domain_t, &ds))] ; 62 | size_t len = s6dns_fmt_domainlist(buf, S6DNS_FMT_DOMAINLIST(genalloc_len(s6dns_domain_t, &ds)), genalloc_s(s6dns_domain_t, &ds), genalloc_len(s6dns_domain_t, &ds), "\n", 1) ; 63 | if (!len) strerr_diefu1sys(111, "format result") ; 64 | if (buffer_put(buffer_1, buf, len) < (ssize_t)len) goto err ; 65 | } 66 | if (buffer_putflush(buffer_1, "\n", 1) < 1) goto err ; 67 | return 0 ; 68 | err: 69 | strerr_diefu1sys(111, "write to stdout") ; 70 | } 71 | -------------------------------------------------------------------------------- /src/clients/s6-dnsqr.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | 14 | #include 15 | #include 16 | #include 17 | 18 | #define USAGE "s6-dnsqr [ -1 | -2 ] [ -t timeout ] [ -D debuglevel ] qtype query" 19 | #define dieusage() strerr_dieusage(100, USAGE) 20 | 21 | int main (int argc, char const *const *argv) 22 | { 23 | tain deadline ; 24 | unsigned int debuglevel = 0 ; 25 | genwrite *where = &genwrite_stderr ; 26 | PROG = "s6-dnsqr" ; 27 | { 28 | subgetopt l = SUBGETOPT_ZERO ; 29 | unsigned int t = 0 ; 30 | for (;;) 31 | { 32 | int opt = subgetopt_r(argc, argv, "12t:D:", &l) ; 33 | if (opt == -1) break ; 34 | switch (opt) 35 | { 36 | case '1' : where = &genwrite_stdout ; break ; 37 | case '2' : where = &genwrite_stderr ; break ; 38 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 39 | case 'D' : if (!uint0_scan(l.arg, &debuglevel)) dieusage() ; break ; 40 | default : dieusage() ; 41 | } 42 | } 43 | argc -= l.ind ; argv += l.ind ; 44 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 45 | } 46 | if (argc < 2) dieusage() ; 47 | { 48 | s6dns_debughook_t dbh = { .post_recv = 0, .pre_send = 0, .post_send = 0 } ; 49 | s6dns_domain_t d ; 50 | uint16_t qtype = s6dns_analyze_qtype_parse(argv[0]) ; 51 | if (!qtype) dieusage() ; 52 | if (!s6dns_domain_fromstring_noqualify_encode(&d, argv[1], strlen(argv[1]))) 53 | strerr_diefu2sys(100, "encode ", argv[1]) ; 54 | dbh.external = where ; 55 | if (debuglevel & 1) dbh.post_recv = &s6dns_debug_dumpdt_post_recv ; 56 | if (debuglevel & 2) { dbh.pre_send = &s6dns_debug_dumpdt_pre_send ; dbh.post_send = &s6dns_debug_dumpdt_post_send ; } 57 | tain_now_set_stopwatch_g() ; 58 | tain_add_g(&deadline, &deadline) ; 59 | if (!s6dns_rci_init(&s6dns_rci_here, "/etc/resolv.conf")) 60 | strerr_diefu1sys(111, "initialize structures from /etc/resolv.conf") ; 61 | 62 | if (!s6dns_resolve_core_r_g(&d, qtype, &s6dns_engine_here, &s6dns_rci_here.servers, &dbh, &deadline)) 63 | { 64 | char fmt[UINT16_FMT] ; 65 | fmt[uint16_fmt(fmt, qtype)] = 0 ; 66 | strerr_diefu6x((errno == ETIMEDOUT) ? 99 : 2, "resolve query ", argv[1], " of qtype ", fmt, ": ", s6dns_constants_error_str(errno)) ; 67 | } 68 | } 69 | if (!s6dns_analyze_packet(&genwrite_stdout, s6dns_engine_packet(&s6dns_engine_here), s6dns_engine_packetlen(&s6dns_engine_here), 1)) 70 | { 71 | int e = errno ; 72 | buffer_flush(buffer_1) ; 73 | errno = e ; 74 | strerr_diefu1sys(111, "analyze response") ; 75 | } 76 | if (!buffer_flush(buffer_1)) strerr_diefu1sys(111, "write to stdout") ; 77 | return 0 ; 78 | } 79 | -------------------------------------------------------------------------------- /src/clients/s6-dnsqualify.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | 9 | #include 10 | 11 | #define USAGE "s6-dnsqualify name" 12 | #define dieusage() strerr_dieusage(100, USAGE) 13 | 14 | int main (int argc, char const *const *argv) 15 | { 16 | s6dns_domain_t d ; 17 | PROG = "s6-dnsqualify" ; 18 | if (argc < 2) dieusage() ; 19 | if (!s6dns_domain_fromstring(&d, argv[1], strlen(argv[1]))) 20 | strerr_diefu2sys(100, "make a domain name from ", argv[1]) ; 21 | 22 | if (!s6dns_rci_init(&s6dns_rci_here, "/etc/resolv.conf")) 23 | strerr_diefu1sys(111, "initialize structures from /etc/resolv.conf") ; 24 | 25 | { 26 | s6dns_domain_t list[s6dns_rci_here.rulesnum] ; 27 | unsigned int n = s6dns_qualify(list, &d) ; 28 | if (!n) strerr_diefu2sys(111, "qualify ", argv[1]) ; 29 | { 30 | char buf[S6DNS_FMT_DOMAINLIST(n)] ; 31 | size_t len = s6dns_fmt_domainlist(buf, S6DNS_FMT_DOMAINLIST(n), list, n, "\n", 1) ; 32 | if (!len) strerr_diefu1sys(111, "format result") ; 33 | if (buffer_put(buffer_1, buf, len) < (ssize_t)len) goto err ; 34 | } 35 | } 36 | if (buffer_putflush(buffer_1, "\n", 1) < 1) goto err ; 37 | return 0 ; 38 | err: 39 | strerr_diefu1sys(111, "write to stdout") ; 40 | } 41 | -------------------------------------------------------------------------------- /src/clients/s6-dnssoa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | 15 | #include 16 | 17 | #define USAGE "s6-dnssoa [ -q ] [ -r ] [ -t timeout ] name" 18 | #define dieusage() strerr_dieusage(100, USAGE) 19 | 20 | int main (int argc, char const *const *argv) 21 | { 22 | genalloc soas = GENALLOC_ZERO ; /* array of s6dns_message_rr_soa_t */ 23 | tain deadline ; 24 | size_t i = 0 ; 25 | unsigned int t = 0 ; 26 | int flagqualify = 0 ; 27 | int flagunsort = 0 ; 28 | PROG = "s6-dnssoa" ; 29 | for (;;) 30 | { 31 | int opt = lgetopt(argc, argv, "qrt:") ; 32 | if (opt == -1) break ; 33 | switch (opt) 34 | { 35 | case 'q' : flagqualify = 1 ; break ; 36 | case 'r' : flagunsort = 1 ; break ; 37 | case 't' : if (!uint0_scan(subgetopt_here.arg, &t)) dieusage() ; break ; 38 | default : dieusage() ; 39 | } 40 | } 41 | argc -= subgetopt_here.ind ; argv += subgetopt_here.ind ; 42 | if (argc < 1) dieusage() ; 43 | 44 | tain_now_set_stopwatch_g() ; 45 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 46 | tain_add_g(&deadline, &deadline) ; 47 | if (!s6dns_init()) strerr_diefu1sys(111, "s6dns_init") ; 48 | { 49 | int r = s6dns_resolve_soa_g(&soas, argv[0], strlen(argv[0]), flagqualify, &deadline) ; 50 | if (r < 0) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 51 | if (!r) strerr_diefu4x(2, "resolve ", argv[0], ": ", s6dns_constants_error_str(errno)) ; 52 | } 53 | if (!genalloc_len(s6dns_message_rr_soa_t, &soas)) return 1 ; 54 | if (flagunsort) random_unsort(soas.s, genalloc_len(s6dns_message_rr_soa_t, &soas), sizeof(s6dns_message_rr_soa_t)) ; 55 | for (i = 0 ; i < genalloc_len(s6dns_message_rr_soa_t, &soas) ; i++) 56 | { 57 | char buf[S6DNS_FMT_SOA] ; 58 | size_t len = s6dns_fmt_soa(buf, S6DNS_FMT_SOA, genalloc_s(s6dns_message_rr_soa_t, &soas) + i) ; 59 | if (!len) strerr_diefu1sys(111, "format result") ; 60 | if (buffer_put(buffer_1, buf, len) < (ssize_t)len) goto err ; 61 | if (buffer_put(buffer_1, "\n", 1) < 1) goto err ; 62 | } 63 | if (!buffer_flush(buffer_1)) goto err ; 64 | return 0 ; 65 | err: 66 | strerr_diefu1sys(111, "write to stdout") ; 67 | } 68 | -------------------------------------------------------------------------------- /src/clients/s6-dnssrv.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | 15 | #include 16 | 17 | #define USAGE "s6-dnssrv [ -q ] [ -r ] [ -t timeout ] service protocol name" 18 | #define dieusage() strerr_dieusage(100, USAGE) 19 | 20 | int main (int argc, char const *const *argv) 21 | { 22 | genalloc srvs = GENALLOC_ZERO ; /* array of s6dns_message_rr_srv_t */ 23 | tain deadline ; 24 | unsigned int t = 0 ; 25 | int flagqualify = 0 ; 26 | int flagunsort = 0 ; 27 | PROG = "s6-dnssrv" ; 28 | 29 | { 30 | subgetopt l = SUBGETOPT_ZERO ; 31 | for (;;) 32 | { 33 | int opt = subgetopt_r(argc, argv, "qrt:", &l) ; 34 | if (opt == -1) break ; 35 | switch (opt) 36 | { 37 | case 'q' : flagqualify = 1 ; break ; 38 | case 'r' : flagunsort = 1 ; break ; 39 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 40 | default : dieusage() ; 41 | } 42 | } 43 | argc -= l.ind ; argv += l.ind ; 44 | } 45 | if (argc < 3) dieusage() ; 46 | 47 | tain_now_set_stopwatch_g() ; 48 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 49 | tain_add_g(&deadline, &deadline) ; 50 | 51 | if (!s6dns_rci_init(&s6dns_rci_here, "/etc/resolv.conf")) 52 | strerr_diefu1sys(111, "initialize structures from /etc/resolv.conf") ; 53 | 54 | { 55 | size_t n0 = strlen(argv[0]) ; 56 | size_t n1 = strlen(argv[1]) ; 57 | size_t n2 = strlen(argv[2]) ; 58 | int r ; 59 | char name[n0 + n1 + n2 + 5] ; 60 | name[0] = '_' ; 61 | memcpy(name + 1, argv[0], n0) ; 62 | name[n0 + 1] = '.' ; 63 | name[n0 + 2] = '_' ; 64 | memcpy(name + n0 + 3, argv[1], n1) ; 65 | name[n0 + n1 + 3] = '.' ; 66 | memcpy(name + n0 + n1 + 4, argv[2], n2) ; 67 | name[n0 + n1 + n2 + 4] = 0 ; 68 | r = s6dns_resolve_srv_g(&srvs, name, n0 + n1 + n2 + 4, flagqualify, &deadline) ; 69 | if (r < 0) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 70 | if (!r) strerr_diefu4x(2, "resolve ", name, ": ", s6dns_constants_error_str(errno)) ; 71 | } 72 | if (!genalloc_len(s6dns_message_rr_srv_t, &srvs)) return 1 ; 73 | if (flagunsort) random_unsort(srvs.s, genalloc_len(s6dns_message_rr_srv_t, &srvs), sizeof(s6dns_message_rr_srv_t)) ; 74 | for (size_t i = 0 ; i < genalloc_len(s6dns_message_rr_srv_t, &srvs) ; i++) 75 | { 76 | char buf[S6DNS_FMT_SRV] ; 77 | size_t len = s6dns_fmt_srv(buf, S6DNS_FMT_SRV, genalloc_s(s6dns_message_rr_srv_t, &srvs) + i) ; 78 | if (!len) strerr_diefu1sys(111, "format result") ; 79 | if (buffer_put(buffer_1, buf, len) < (ssize_t)len) goto err ; 80 | if (buffer_put(buffer_1, "\n", 1) < 1) goto err ; 81 | } 82 | if (!buffer_flush(buffer_1)) goto err ; 83 | return 0 ; 84 | err: 85 | strerr_diefu1sys(111, "write to stdout") ; 86 | } 87 | -------------------------------------------------------------------------------- /src/clients/s6-dnstxt.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | 16 | #include 17 | 18 | #define USAGE "s6-dnstxt [ -q ] [ -r ] [ -t timeout ] name" 19 | #define dieusage() strerr_dieusage(100, USAGE) 20 | 21 | int main (int argc, char const *const *argv) 22 | { 23 | stralloc quoted = STRALLOC_ZERO ; 24 | stralloc sa = STRALLOC_ZERO ; 25 | genalloc offsets = GENALLOC_ZERO ; /* array of size_t */ 26 | tain deadline ; 27 | size_t n ; 28 | unsigned int t = 0 ; 29 | int flagqualify = 0 ; 30 | int flagunsort = 0 ; 31 | PROG = "s6-dnstxt" ; 32 | 33 | { 34 | subgetopt l = SUBGETOPT_ZERO ; 35 | for (;;) 36 | { 37 | int opt = subgetopt_r(argc, argv, "qrt:", &l) ; 38 | if (opt == -1) break ; 39 | switch (opt) 40 | { 41 | case 'q' : flagqualify = 1 ; break ; 42 | case 'r' : flagunsort = 1 ; break ; 43 | case 't' : if (!uint0_scan(l.arg, &t)) dieusage() ; break ; 44 | default : dieusage() ; 45 | } 46 | } 47 | argc -= l.ind ; argv += l.ind ; 48 | } 49 | if (argc < 1) dieusage() ; 50 | if (t) tain_from_millisecs(&deadline, t) ; else deadline = tain_infinite_relative ; 51 | 52 | tain_now_set_stopwatch_g() ; 53 | tain_add_g(&deadline, &deadline) ; 54 | if (!s6dns_init()) strerr_diefu1sys(111, "s6dns_init") ; 55 | { 56 | int r = s6dns_resolve_txt_g(&sa, &offsets, argv[0], strlen(argv[0]), flagqualify, &deadline) ; 57 | if (r < 0) strerr_diefu2sys((errno == ETIMEDOUT) ? 99 : 111, "resolve ", argv[0]) ; 58 | if (!r) strerr_diefu4x(2, "resolve ", argv[0], ": ", s6dns_constants_error_str(errno)) ; 59 | } 60 | n = genalloc_len(size_t, &offsets) ; 61 | if (!n) return 1 ; 62 | { 63 | size_t printable_offsets[n] ; 64 | for (size_t i = 0 ; i < n ; i++) 65 | { 66 | size_t beg = genalloc_s(size_t, &offsets)[i] ; 67 | size_t end = (i < n-1 ? genalloc_s(size_t, &offsets)[i+1] : sa.len) - 1 ; 68 | printable_offsets[i] = quoted.len ; 69 | if (!string_quote("ed, sa.s + beg, end - beg) || !stralloc_0("ed)) 70 | strerr_diefu2sys(111, "quote ", sa.s + beg) ; 71 | } 72 | genalloc_free(size_t, &offsets) ; 73 | stralloc_free(&sa) ; 74 | if (flagunsort) random_unsort((char *)printable_offsets, n, sizeof(size_t)) ; 75 | for (size_t i = 0 ; i < n ; i++) 76 | if ((buffer_puts(buffer_1small, quoted.s + printable_offsets[i]) < 0) 77 | || (buffer_put(buffer_1small, "\n", 1) < 1)) 78 | strerr_diefu1sys(111, "write to stdout") ; 79 | } 80 | stralloc_free("ed) ; 81 | if (!buffer_flush(buffer_1small)) 82 | strerr_diefu1sys(111, "write to stdout") ; 83 | return 0 ; 84 | } 85 | -------------------------------------------------------------------------------- /src/clients/s6-randomip.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | #include 11 | #include 12 | 13 | #define USAGE "s6-randomip [ -4 ] [ -6 ] [ -n number ]" 14 | #define dieusage() strerr_dieusage(100, USAGE) 15 | 16 | int main (int argc, char const *const *argv) 17 | { 18 | char fmt[IP6_FMT] ; 19 | char ip[16] ; 20 | unsigned int n ; 21 | unsigned int i = 0 ; 22 | size_t what = 0 ; 23 | int finite = 0 ; 24 | PROG = "s6-randomip" ; 25 | { 26 | subgetopt l = SUBGETOPT_ZERO ; 27 | for (;;) 28 | { 29 | int opt = subgetopt_r(argc, argv, "46n:", &l) ; 30 | if (opt == -1) break ; 31 | switch (opt) 32 | { 33 | case '4' : what |= 1 ; break ; 34 | case '6' : what |= 2 ; break ; 35 | case 'n' : if (!uint0_scan(l.arg, &n)) dieusage() ; finite = 1 ; 36 | break ; 37 | default : dieusage() ; 38 | } 39 | } 40 | argc -= l.ind ; argv += l.ind ; 41 | } 42 | if (!what) what = 1 ; 43 | what = 1 << (1 << what) ; 44 | for (i = 0 ; !finite || (i < n) ; i++) 45 | { 46 | size_t len = what ; 47 | if (len > 16) 48 | { 49 | char c ; 50 | random_buf(&c, 1) ; 51 | len = (c & 1) ? 16 : 4 ; 52 | } 53 | random_buf(ip, len) ; 54 | len = (len == 16) ? ip6_fmt(fmt, ip) : ip4_fmt(fmt, ip) ; 55 | fmt[len++] = '\n' ; 56 | if (buffer_put(buffer_1, fmt, len) < len) 57 | strerr_diefu1sys(111, "write to stdout") ; 58 | } 59 | if (!buffer_flush(buffer_1)) 60 | strerr_diefu1sys(111, "write to stdout") ; 61 | return 0 ; 62 | } 63 | -------------------------------------------------------------------------------- /src/clients/s6dns-generic-filter.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef SKADNS_GENERIC_FILTER_H 4 | #define SKADNS_GENERIC_FILTER_H 5 | 6 | #include 7 | #include 8 | 9 | #include 10 | 11 | #include 12 | 13 | typedef size_t scan_func (s6dns_domain_t *, char const *) ; 14 | typedef scan_func *scan_func_ref ; 15 | typedef int fmt_func (stralloc *, char const *, unsigned int) ; 16 | typedef fmt_func *fmt_func_ref ; 17 | 18 | extern size_t s6dns_namescanner (s6dns_domain_t *, char const *) ; 19 | extern int s6dns_domainformatter (stralloc *, char const *, unsigned int) ; 20 | extern int s6dns_generic_filter_main (int, char const *const *, char const *const *, uint16_t, scan_func_ref, fmt_func_ref, char const *) ; 21 | 22 | extern int flag4 ; 23 | extern int flag6 ; 24 | 25 | #endif 26 | -------------------------------------------------------------------------------- /src/clients/s6dns_namescanner.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | #include "s6dns-generic-filter.h" 9 | 10 | size_t s6dns_namescanner (s6dns_domain_t *d, char const *s) 11 | { 12 | size_t pos = 0 ; 13 | while (s[pos] && (s[pos] != ' ') && (s[pos] != '\t') && (s[pos] != '\r') && (s[pos] != '\n')) pos++ ; 14 | if (pos > UINT_MAX) return (errno = ENAMETOOLONG, 0) ; 15 | if (!s6dns_domain_fromstring_noqualify_encode(d, s, pos)) return 0 ; 16 | return pos ; 17 | } 18 | -------------------------------------------------------------------------------- /src/include/s6-dns/dcache.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_DCACHE_H 4 | #define S6DNS_DCACHE_H 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | #include 12 | 13 | #define DCACHE_MAGIC "--DCACHE--\n" 14 | 15 | typedef struct dcache_key_s dcache_key_t, *dcache_key_t_ref ; 16 | struct dcache_key_s 17 | { 18 | char *s ; 19 | uint16_t len ; 20 | } ; 21 | 22 | typedef struct dcache_node_s dcache_node_t, *dcache_node_t_ref ; 23 | struct dcache_node_s 24 | { 25 | dcache_key_t key ; 26 | uint16_t datalen ; 27 | tain entry ; 28 | tain expire ; 29 | } ; 30 | 31 | typedef struct dcache_s dcache_t, *dcache_t_ref ; 32 | struct dcache_s 33 | { 34 | gensetdyn storage ; /* dcache_node_t */ 35 | avltree by_key ; 36 | avltree by_entry ; 37 | avltree by_expire ; 38 | uint64_t size ; 39 | uint64_t motion ; 40 | } ; 41 | #define DCACHE_ZERO { .storage = GENSETDYN_ZERO, .by_key = AVLTREE_ZERO, .by_entry = AVLTREE_ZERO, .by_expire = AVLTREE_ZERO, .size = 0, .motion = 0 } 42 | 43 | extern void dcache_init (dcache_t *, uint64_t) ; 44 | extern dcache_node_t *dcache_search (dcache_t *, char const *, uint16_t) ; 45 | extern int dcache_add (dcache_t *, uint64_t, char const *, uint16_t, char const *, uint16_t, tain const *, tain const *) ; 46 | #define dcache_add_g(d, max, key, keylen, data, datalen, expire) dcache_add(d, max, key, keylen, data, datalen, (expire), &STAMP) 47 | extern void dcache_clean_expired (dcache_t *, tain const *) ; 48 | #define dcache_clean_expired_g(d) dcache_clean_expired((d), &STAMP) 49 | extern void dcache_free (dcache_t *) ; 50 | 51 | extern int dcache_save (dcache_t const *, char const *) ; 52 | extern int dcache_load (dcache_t *, uint64_t, char const *) ; 53 | 54 | #endif 55 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns-analyze.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_ANALYZE_H 4 | #define S6DNS_ANALYZE_H 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | typedef int s6dns_analyze_record_func (genwrite *, s6dns_message_rr_t const *, char const *, unsigned int, unsigned int) ; 11 | typedef s6dns_analyze_record_func *s6dns_analyze_record_func_ref ; 12 | 13 | typedef struct s6dns_analyze_rtypetable_s s6dns_analyze_rtypetable_t, *s6dns_analyze_rtypetable_t_ref ; 14 | struct s6dns_analyze_rtypetable_s 15 | { 16 | uint16_t rtype ; 17 | char const *string ; 18 | s6dns_analyze_record_func_ref f ; 19 | } ; 20 | 21 | extern uint16_t s6dns_analyze_qtype_parse (char const *) ; 22 | 23 | extern s6dns_analyze_rtypetable_t const *s6dns_analyze_rtypetable ; 24 | 25 | extern s6dns_analyze_record_func s6dns_analyze_record_a ; 26 | extern s6dns_analyze_record_func s6dns_analyze_record_aaaa ; 27 | extern s6dns_analyze_record_func s6dns_analyze_record_hinfo ; 28 | extern s6dns_analyze_record_func s6dns_analyze_record_soa ; 29 | extern s6dns_analyze_record_func s6dns_analyze_record_mx ; 30 | extern s6dns_analyze_record_func s6dns_analyze_record_srv ; 31 | extern s6dns_analyze_record_func s6dns_analyze_record_caa ; 32 | extern s6dns_analyze_record_func s6dns_analyze_record_domain ; 33 | extern s6dns_analyze_record_func s6dns_analyze_record_strings ; 34 | extern s6dns_analyze_record_func s6dns_analyze_record_unknown ; 35 | 36 | extern s6dns_analyze_record_func s6dns_analyze_record ; 37 | 38 | extern int s6dns_analyze_packet (genwrite *, char const *, unsigned int, int) ; 39 | 40 | #endif 41 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns-constants.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_CONSTANTS_H 4 | #define S6DNS_CONSTANTS_H 5 | 6 | #include 7 | 8 | #define S6DNS_MAX_SERVERS 16U 9 | 10 | #define S6DNS_C_IN 0x0001U 11 | #define S6DNS_C_ANY 0x00ffU 12 | 13 | #define S6DNS_T_A 1U 14 | #define S6DNS_T_NS 2U 15 | #define S6DNS_T_CNAME 5U 16 | #define S6DNS_T_SOA 6U 17 | #define S6DNS_T_PTR 12U 18 | #define S6DNS_T_HINFO 13U 19 | #define S6DNS_T_MX 15U 20 | #define S6DNS_T_TXT 16U 21 | #define S6DNS_T_RP 17U 22 | #define S6DNS_T_SIG 24U 23 | #define S6DNS_T_KEY 25U 24 | #define S6DNS_T_AAAA 28U 25 | #define S6DNS_T_SRV 33U 26 | #define S6DNS_T_AXFR 252U 27 | #define S6DNS_T_ANY 255U 28 | #define S6DNS_T_CAA 257U 29 | 30 | #define S6DNS_O_RECURSIVE 0x0001U 31 | #define S6DNS_O_STRICT 0x0002U 32 | 33 | #define S6DNS_W_AND 0 34 | #define S6DNS_W_OR 1 35 | #define S6DNS_W_BEST 2 36 | 37 | typedef struct s6dns_constants_error_message_s s6dns_constants_error_message_t, *s6dns_constants_error_message_t_ref ; 38 | struct s6dns_constants_error_message_s 39 | { 40 | int num ; 41 | char const *string ; 42 | } ; 43 | 44 | extern s6dns_constants_error_message_t const *const s6dns_constants_error ; 45 | extern char const *s6dns_constants_error_str (int) ; 46 | 47 | #ifdef SKALIBS_IPV6_ENABLED 48 | # define S6DNS_LOCALHOST_IP IP6_LOCAL 49 | #else 50 | # define S6DNS_LOCALHOST_IP "\177\0\0\1" 51 | #endif 52 | 53 | #endif 54 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns-debug.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_DEBUG_H 4 | #define S6DNS_DEBUG_H 5 | 6 | #include 7 | 8 | extern s6dns_debughook_func s6dns_debug_dumpdt_post_recv ; 9 | extern s6dns_debughook_func s6dns_debug_dumpdt_pre_send ; 10 | extern s6dns_debughook_func s6dns_debug_dumpdt_post_send ; 11 | 12 | #define S6DNS_DEBUG_DUMPDT_INIT(gp) { &s6dns_debug_dumpdt_post_recv, &s6dns_debug_dumpdt_pre_send, &s6dns_debug_dumpdt_post_send, (gp) } 13 | extern s6dns_debughook_t const s6dns_debug_dumpdt_stdout ; 14 | extern s6dns_debughook_t const s6dns_debug_dumpdt_stderr ; 15 | 16 | #endif 17 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns-domain.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_DOMAIN_H 4 | #define S6DNS_DOMAIN_H 5 | 6 | #include 7 | #include 8 | 9 | typedef struct s6dns_domain_s s6dns_domain_t, *s6dns_domain_t_ref ; 10 | struct s6dns_domain_s 11 | { 12 | unsigned char len ; 13 | char s[255] ; 14 | } ; 15 | 16 | 17 | /* Conversions from/to user strings */ 18 | 19 | extern int s6dns_domain_fromstring (s6dns_domain_t *, char const *, size_t) ; 20 | extern unsigned int s6dns_domain_tostring (char *, size_t, s6dns_domain_t const *) ; 21 | 22 | 23 | /* Qualification */ 24 | 25 | extern int s6dns_domain_noqualify (s6dns_domain_t *) ; 26 | extern unsigned int s6dns_domain_qualify (s6dns_domain_t *, s6dns_domain_t const *, char const *, unsigned int) ; 27 | 28 | 29 | /* Internal coding/encoding to/from protocol form */ 30 | 31 | extern int s6dns_domain_encode (s6dns_domain_t *) ; 32 | extern unsigned int s6dns_domain_encodelist (s6dns_domain_t *, unsigned int) ; 33 | extern int s6dns_domain_decode (s6dns_domain_t *) ; 34 | 35 | 36 | /* Useful shortcuts */ 37 | 38 | extern int s6dns_domain_fromstring_noqualify_encode (s6dns_domain_t *, char const *, size_t) ; 39 | extern unsigned int s6dns_domain_fromstring_qualify_encode (s6dns_domain_t *, char const *, size_t, char const *, unsigned int) ; 40 | 41 | 42 | /* Helpers for PTR */ 43 | 44 | extern void s6dns_domain_arpafromip4 (s6dns_domain_t *, char const *) ; 45 | extern void s6dns_domain_arpafromip6 (s6dns_domain_t *, char const *, unsigned int) ; 46 | #define s6dns_domain_arpafromip46(d, i) (ip46_is6(i) ? s6dns_domain_arpafromip6(d, (i)->ip, 128) : s6dns_domain_arpafromip4(d, (i)->ip)) 47 | 48 | #endif 49 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns-fmt.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_FMT_H 4 | #define S6DNS_FMT_H 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | 11 | #define S6DNS_FMT_DOMAIN 256 12 | #define s6dns_fmt_domain(s, max, d) s6dns_domain_tostring(s, max, d) 13 | 14 | #define S6DNS_FMT_DOMAINLIST(n) ((n) * S6DNS_FMT_DOMAIN) 15 | extern size_t s6dns_fmt_domainlist (char *, size_t, s6dns_domain_t const *, unsigned int, char const *, size_t) ; 16 | 17 | #define S6DNS_FMT_HINFO 512 18 | extern size_t s6dns_fmt_hinfo (char *, size_t, s6dns_message_rr_hinfo_t const *) ; 19 | 20 | #define S6DNS_FMT_MX (S6DNS_FMT_DOMAIN + UINT16_FMT) 21 | extern size_t s6dns_fmt_mx (char *, size_t, s6dns_message_rr_mx_t const *) ; 22 | 23 | #define S6DNS_FMT_SOA (S6DNS_FMT_DOMAIN * 2 + 5 * UINT32_FMT) 24 | extern size_t s6dns_fmt_soa (char *, size_t, s6dns_message_rr_soa_t const *) ; 25 | 26 | #define S6DNS_FMT_SRV (S6DNS_FMT_DOMAIN + 3 * UINT16_FMT) 27 | extern size_t s6dns_fmt_srv (char *, size_t, s6dns_message_rr_srv_t const *) ; 28 | 29 | #define S6DNS_FMT_CAA 517 30 | extern size_t s6dns_fmt_caa (char *, size_t, s6dns_message_rr_caa_t const *) ; 31 | 32 | #endif 33 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns-ip46.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_IP46_H 4 | #define S6DNS_IP46_H 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | typedef struct s6dns_ip46list_s s6dns_ip46list_t, *s6dns_ip46list_t_ref ; 11 | struct s6dns_ip46list_s 12 | { 13 | char ip[S6DNS_MAX_SERVERS * SKALIBS_IP_SIZE] ; 14 | #ifdef SKALIBS_IPV6_ENABLED 15 | unsigned char is6[bitarray_div8(S6DNS_MAX_SERVERS)] ; 16 | #endif 17 | } ; 18 | 19 | #define s6dns_ip46list_ip(list, i) ((list)->ip + SKALIBS_IP_SIZE * (i)) 20 | 21 | #ifdef SKALIBS_IPV6_ENABLED 22 | # define S6DNS_IP46LIST_ZERO { .ip = S6DNS_LOCALHOST_IP, .is6 = "\0" } 23 | # define s6dns_ip46list_is6(list, i) bitarray_peek((list)->is6, i) 24 | #else 25 | # define S6DNS_IP46LIST_ZERO { .ip = S6DNS_LOCALHOST_IP } 26 | # define s6dns_ip46list_is6(list, i) 0 27 | #endif 28 | 29 | #endif 30 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns-rci.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_RCI_H 4 | #define S6DNS_RCI_H 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | 11 | /* rci: resolv.conf information */ 12 | 13 | typedef struct s6dns_rci_s s6dns_rci_t, *s6dns_rci_t_ref ; 14 | struct s6dns_rci_s 15 | { 16 | s6dns_ip46list_t servers ; 17 | stralloc rules ; 18 | unsigned int rulesnum ; 19 | } ; 20 | #define S6DNS_RCI_ZERO { .servers = S6DNS_IP46LIST_ZERO, .rules = STRALLOC_ZERO, .rulesnum = 0 } 21 | 22 | extern s6dns_rci_t const s6dns_rci_zero ; 23 | extern s6dns_rci_t s6dns_rci_here ; 24 | extern int s6dns_rci_init (s6dns_rci_t *, char const *) ; 25 | extern void s6dns_rci_free (s6dns_rci_t *) ; 26 | 27 | #define s6dns_qualify(list, d) s6dns_domain_qualify(list, (d), s6dns_rci_here.rules.s, s6dns_rci_here.rulesnum) 28 | 29 | #endif 30 | -------------------------------------------------------------------------------- /src/include/s6-dns/s6dns.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_H 4 | #define S6DNS_H 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | #include 16 | #include 17 | 18 | #define s6dns_init() s6dns_init_options(0) 19 | extern int s6dns_init_options (uint32_t) ; 20 | extern void s6dns_finish (void) ; 21 | 22 | #endif 23 | -------------------------------------------------------------------------------- /src/include/s6-dns/skadns.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef SKADNS_H 4 | #define SKADNS_H 5 | 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include 12 | #include 13 | 14 | #include 15 | #include 16 | 17 | #define SKADNSD_PROG S6_DNS_EXTBINPREFIX "skadnsd" 18 | #define SKADNS_BANNER1 "skadns v1.0 (b)\n" 19 | #define SKADNS_BANNER1_LEN (sizeof SKADNS_BANNER1 - 1) 20 | #define SKADNS_BANNER2 "skadns v1.0 (a)\n" 21 | #define SKADNS_BANNER2_LEN (sizeof SKADNS_BANNER2 - 1) 22 | 23 | typedef struct skadnsanswer_s skadnsanswer_t, *skadnsanswer_t_ref ; 24 | struct skadnsanswer_s 25 | { 26 | int status ; 27 | char *data ; 28 | unsigned int len ; 29 | } ; 30 | #define SKADNSANSWER_ZERO { .status = EINVAL, .data = 0, .len = 0 } 31 | 32 | typedef struct skadns_s skadns_t, *skadns_t_ref ; 33 | struct skadns_s 34 | { 35 | textclient connection ; 36 | genalloc list ; /* array of uint16_t */ 37 | gensetdyn q ; /* set of skadnsanswer_t */ 38 | } ; 39 | #define SKADNS_ZERO { .connection = TEXTCLIENT_ZERO, .list = GENALLOC_ZERO, .q = GENSETDYN_INIT(skadnsanswer_t, 3, 3, 8) } 40 | extern skadns_t const skadns_zero ; 41 | 42 | 43 | /* Starting and ending a session */ 44 | 45 | extern int skadns_start (skadns_t *, char const *, tain const *, tain *) ; 46 | #define skadns_start_g(a, path, deadline) skadns_start(a, path, (deadline), &STAMP) 47 | extern int skadns_startf (skadns_t *, tain const *, tain *) ; 48 | #define skadns_startf_g(a, deadline) skadns_startf(a, (deadline), &STAMP) 49 | extern void skadns_end (skadns_t *) ; 50 | 51 | 52 | /* Synchronous functions */ 53 | 54 | extern int skadns_send (skadns_t *, uint16_t *, s6dns_domain_t const *, uint16_t, tain const *, tain const *, tain *) ; 55 | #define skadns_send_g(a, id, d, qtype, limit, deadline) skadns_send(a, id, d, qtype, limit, (deadline), &STAMP) 56 | extern int skadns_cancel (skadns_t *, uint16_t, tain const *, tain *) ; 57 | #define skadns_cancel_g(a, id, deadline) skadns_cancel(a, id, (deadline), &STAMP) 58 | 59 | 60 | /* Asynchronous functions */ 61 | 62 | #define skadns_fd(a) textclient_fd(&(a)->connection) 63 | extern int skadns_update (skadns_t *) ; 64 | #define skadns_list(a) genalloc_s(uint16_t const, &(a)->list) 65 | #define skadns_clearlist(a) ((a)->list.len = 0) 66 | extern int skadns_packetlen (skadns_t const *, uint16_t) ; 67 | extern char const *skadns_packet (skadns_t const *, uint16_t) ; 68 | extern int skadns_release (skadns_t *, uint16_t) ; 69 | 70 | #endif 71 | -------------------------------------------------------------------------------- /src/libs6dns/deps-lib/s6dns: -------------------------------------------------------------------------------- 1 | s6dns_analyze_packet.o 2 | s6dns_analyze_qtype_parse.o 3 | s6dns_analyze_record.o 4 | s6dns_analyze_record_a.o 5 | s6dns_analyze_record_aaaa.o 6 | s6dns_analyze_record_caa.o 7 | s6dns_analyze_record_domain.o 8 | s6dns_analyze_record_hinfo.o 9 | s6dns_analyze_record_mx.o 10 | s6dns_analyze_record_soa.o 11 | s6dns_analyze_record_srv.o 12 | s6dns_analyze_record_strings.o 13 | s6dns_analyze_record_unknown.o 14 | s6dns_analyze_rtypetable.o 15 | s6dns_constants_error.o 16 | s6dns_constants_error_str.o 17 | s6dns_debug_dumpdt_post_recv.o 18 | s6dns_debug_dumpdt_post_send.o 19 | s6dns_debug_dumpdt_pre_send.o 20 | s6dns_debug_dumpdt_stderr.o 21 | s6dns_debug_dumpdt_stdout.o 22 | s6dns_debughook_zero.o 23 | s6dns_domain_arpafromip4.o 24 | s6dns_domain_arpafromip6.o 25 | s6dns_domain_decode.o 26 | s6dns_domain_encode.o 27 | s6dns_domain_encodelist.o 28 | s6dns_domain_fromstring.o 29 | s6dns_domain_fromstring_noqualify_encode.o 30 | s6dns_domain_fromstring_qualify_encode.o 31 | s6dns_domain_noqualify.o 32 | s6dns_domain_qualify.o 33 | s6dns_domain_tostring.o 34 | s6dns_engine.o 35 | s6dns_engine_free.o 36 | s6dns_engine_freen.o 37 | s6dns_engine_here.o 38 | s6dns_engine_nextdeadline.o 39 | s6dns_engine_query.o 40 | s6dns_engine_zero.o 41 | s6dns_finish.o 42 | s6dns_fmt_caa.o 43 | s6dns_fmt_domainlist.o 44 | s6dns_fmt_hinfo.o 45 | s6dns_fmt_mx.o 46 | s6dns_fmt_soa.o 47 | s6dns_fmt_srv.o 48 | s6dns_hosts_aaaaa_q.o 49 | s6dns_hosts_aaaaa_string.o 50 | s6dns_hosts_compile.o 51 | s6dns_hosts_here.o 52 | s6dns_hosts_init.o 53 | s6dns_hosts_ip_q.o 54 | s6dns_hosts_ip_string.o 55 | s6dns_hosts_name.o 56 | s6dns_init.o 57 | s6dns_message_counts_next.o 58 | s6dns_message_counts_pack.o 59 | s6dns_message_counts_unpack.o 60 | s6dns_message_counts_zero.o 61 | s6dns_message_get_caa.o 62 | s6dns_message_get_domain.o 63 | s6dns_message_get_domain_nodecode.o 64 | s6dns_message_get_hinfo.o 65 | s6dns_message_get_mx.o 66 | s6dns_message_get_soa.o 67 | s6dns_message_get_srv.o 68 | s6dns_message_get_string.o 69 | s6dns_message_get_string_internal.o 70 | s6dns_message_get_strings.o 71 | s6dns_message_header_pack.o 72 | s6dns_message_header_unpack.o 73 | s6dns_message_header_zero.o 74 | s6dns_message_parse.o 75 | s6dns_message_parse_answer_a.o 76 | s6dns_message_parse_answer_aaaa.o 77 | s6dns_message_parse_answer_caa.o 78 | s6dns_message_parse_answer_domain.o 79 | s6dns_message_parse_answer_hinfo.o 80 | s6dns_message_parse_answer_mx.o 81 | s6dns_message_parse_answer_soa.o 82 | s6dns_message_parse_answer_srv.o 83 | s6dns_message_parse_answer_strings.o 84 | s6dns_message_parse_getrr.o 85 | s6dns_message_parse_init.o 86 | s6dns_message_parse_next.o 87 | s6dns_message_parse_question.o 88 | s6dns_message_parse_skipqd.o 89 | s6dns_rci_free.o 90 | s6dns_rci_here.o 91 | s6dns_rci_init.o 92 | s6dns_rci_zero.o 93 | s6dns_resolve_core.o 94 | s6dns_resolve_dpag.o 95 | s6dns_resolve_mpag.o 96 | s6dns_resolve_name4.o 97 | s6dns_resolve_name6.o 98 | s6dns_resolve_parse.o 99 | s6dns_resolven_loop.o 100 | s6dns_resolven_parse.o 101 | s6dns_resolvenoq.o 102 | s6dns_resolvenoq_aaaaa.o 103 | s6dns_resolveq.o 104 | s6dns_resolveq_aaaaa.o 105 | -lskarnet 106 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns-message-internal.h: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #ifndef S6DNS_MESSAGE_INTERNAL_H 4 | #define S6DNS_MESSAGE_INTERNAL_H 5 | 6 | #include 7 | 8 | /* Low-level packet parsing */ 9 | 10 | extern int s6dns_message_get_string_internal (char *, size_t, char const *, unsigned int, unsigned int *) ; 11 | 12 | #endif 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_qtype_parse.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | typedef struct lookuptable_s lookuptable_t, *lookuptable_t_ref ; 9 | struct lookuptable_s 10 | { 11 | char const *text ; 12 | uint16_t qtype ; 13 | } ; 14 | 15 | static lookuptable_t const table[] = 16 | { 17 | { "ANY", S6DNS_T_ANY }, 18 | { "A", S6DNS_T_A }, 19 | { "NS", S6DNS_T_NS }, 20 | { "CNAME", S6DNS_T_CNAME }, 21 | { "SOA", S6DNS_T_SOA }, 22 | { "PTR", S6DNS_T_PTR }, 23 | { "HINFO", S6DNS_T_HINFO }, 24 | { "MX", S6DNS_T_MX }, 25 | { "TXT", S6DNS_T_TXT }, 26 | { "AAAA", S6DNS_T_AAAA }, 27 | { "SRV", S6DNS_T_SRV }, 28 | { "RP", S6DNS_T_RP }, 29 | { "SIG", S6DNS_T_SIG }, 30 | { "KEY", S6DNS_T_KEY }, 31 | { "AXFR", S6DNS_T_AXFR }, 32 | { "CAA", S6DNS_T_CAA }, 33 | { 0, 0 } 34 | } ; 35 | 36 | uint16_t s6dns_analyze_qtype_parse (char const *s) 37 | { 38 | { 39 | uint16_t u ; 40 | if (uint160_scan(s, &u)) return u ; 41 | } 42 | { 43 | lookuptable_t const *p = table ; 44 | for (; p->text ; p++) if (!strcasecmp(s, p->text)) return p->qtype ; 45 | } 46 | return 0 ; 47 | } 48 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | static s6dns_analyze_rtypetable_t const *rtypelookup (uint16_t rtype) 10 | { 11 | s6dns_analyze_rtypetable_t const *wut = s6dns_analyze_rtypetable ; 12 | while (wut->rtype && wut->rtype != rtype) wut++ ; 13 | return wut ; 14 | } 15 | 16 | int s6dns_analyze_record (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos) 17 | { 18 | s6dns_analyze_rtypetable_t const *wut = rtypelookup(rr->rtype) ; 19 | { 20 | char buf[256] ; 21 | unsigned int n = s6dns_domain_tostring(buf, 256, &rr->name) ; 22 | if (!n) return 0 ; 23 | if ((*gp->put)(gp->target, buf, n) < 0) return 0 ; 24 | } 25 | { 26 | char fmt[UINT32_FMT+1] = " " ; 27 | if ((*gp->put)(gp->target, fmt, 1 + uint32_fmt(fmt+1, rr->ttl)) < 0) return 0 ; 28 | } 29 | if ((*gp->put)(gp->target, " ", 1) < 0) return 0 ; 30 | if ((*gp->put)(gp->target, wut->string, strlen(wut->string)) < 0) return 0 ; 31 | if ((*gp->put)(gp->target, " ", 1) < 0) return 0 ; 32 | if (!(*wut->f)(gp, rr, packet, packetlen, pos)) return 0 ; 33 | if ((*gp->put)(gp->target, "\n", 1) < 0) return 0 ; 34 | return 1 ; 35 | } 36 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_a.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | 10 | int s6dns_analyze_record_a (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos) 11 | { 12 | char fmt[IP4_FMT] ; 13 | if (rr->rdlength != 4) return (errno = EPROTO, 0) ; 14 | if (pos + 4 > packetlen) return (errno = EPROTO, 0) ; 15 | if ((*gp->put)(gp->target, fmt, ip4_fmt(fmt, packet + pos)) < 0) return 0 ; 16 | return 1 ; 17 | } 18 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_aaaa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | 10 | int s6dns_analyze_record_aaaa (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos) 11 | { 12 | char fmt[IP6_FMT] ; 13 | if (rr->rdlength != 16) return (errno = EPROTO, 0) ; 14 | if (pos + 16 > packetlen) return (errno = EPROTO, 0) ; 15 | if ((*gp->put)(gp->target, fmt, ip6_fmt(fmt, packet + pos)) < 0) return 0 ; 16 | return 1 ; 17 | } 18 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_caa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | 12 | int s6dns_analyze_record_caa (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int start) 13 | { 14 | s6dns_message_rr_caa_t caa ; 15 | size_t len ; 16 | unsigned int pos = start ; 17 | char buf[S6DNS_FMT_CAA] ; 18 | if (!s6dns_message_get_caa(&caa, packet, packetlen, &pos, rr->rdlength)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | len = s6dns_fmt_caa(buf, S6DNS_FMT_CAA, &caa) ; 21 | if (!len) return 0 ; 22 | if ((*gp->put)(gp->target, buf, len) < 0) return 0 ; 23 | return 1 ; 24 | } 25 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_domain.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | #include 12 | 13 | int s6dns_analyze_record_domain (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int start) 14 | { 15 | s6dns_domain_t d ; 16 | size_t len ; 17 | unsigned int pos = start ; 18 | char buf[S6DNS_FMT_DOMAIN] ; 19 | if (!s6dns_message_get_domain(&d, packet, packetlen, &pos)) return 0 ; 20 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 21 | len = s6dns_fmt_domain(buf, 256, &d) ; 22 | if (!len) return 0 ; 23 | if ((*gp->put)(gp->target, buf, len) < 0) return 0 ; 24 | return 1 ; 25 | } 26 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_hinfo.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | 12 | int s6dns_analyze_record_hinfo (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int start) 13 | { 14 | s6dns_message_rr_hinfo_t hinfo ; 15 | size_t len ; 16 | unsigned int pos = start ; 17 | char buf[S6DNS_FMT_HINFO] ; 18 | if (!s6dns_message_get_hinfo(&hinfo, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | len = s6dns_fmt_hinfo(buf, S6DNS_FMT_HINFO, &hinfo) ; 21 | if (!len) return 0 ; 22 | if ((*gp->put)(gp->target, buf, len) < 0) return 0 ; 23 | return 1 ; 24 | } 25 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_mx.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | 12 | int s6dns_analyze_record_mx (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int start) 13 | { 14 | s6dns_message_rr_mx_t mx ; 15 | size_t len ; 16 | unsigned int pos = start ; 17 | char buf[S6DNS_FMT_MX] ; 18 | if (!s6dns_message_get_mx(&mx, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | len = s6dns_fmt_mx(buf, S6DNS_FMT_MX, &mx) ; 21 | if (!len) return 0 ; 22 | if ((*gp->put)(gp->target, buf, len) < 0) return 0 ; 23 | return 1 ; 24 | } 25 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_soa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | 12 | int s6dns_analyze_record_soa (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int start) 13 | { 14 | s6dns_message_rr_soa_t soa ; 15 | size_t len ; 16 | unsigned int pos = start ; 17 | char buf[S6DNS_FMT_SOA] ; 18 | if (!s6dns_message_get_soa(&soa, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | len = s6dns_fmt_soa(buf, S6DNS_FMT_SOA, &soa) ; 21 | if (!len) return 0 ; 22 | if ((*gp->put)(gp->target, buf, len) < 0) return 0 ; 23 | return 1 ; 24 | } 25 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_srv.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | 12 | int s6dns_analyze_record_srv (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int start) 13 | { 14 | s6dns_message_rr_srv_t srv ; 15 | size_t len ; 16 | unsigned int pos = start ; 17 | char buf[S6DNS_FMT_SRV] ; 18 | if (!s6dns_message_get_srv(&srv, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | len = s6dns_fmt_srv(buf, S6DNS_FMT_SRV, &srv) ; 21 | if (!len) return 0 ; 22 | if ((*gp->put)(gp->target, buf, len) < 0) return 0 ; 23 | return 1 ; 24 | } 25 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_strings.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | 12 | int s6dns_analyze_record_strings (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int start) 13 | { 14 | stralloc sa = STRALLOC_ZERO ; 15 | char buf[rr->rdlength] ; 16 | unsigned int pos = start ; 17 | int r = s6dns_message_get_strings(buf, rr->rdlength, packet, packetlen, &pos) ; 18 | if (r < 0) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | if (!string_quote(&sa, buf, r)) return 0 ; 21 | r = (*gp->put)(gp->target, sa.s, sa.len) >= 0 ; 22 | stralloc_free(&sa) ; 23 | return r ; 24 | } 25 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_record_unknown.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | int s6dns_analyze_record_unknown (genwrite *gp, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos) 9 | { 10 | char fmt[UINT16_FMT] ; 11 | if ((*gp->put)(gp->target, "rtype ", 6) < 0) return 0 ; 12 | if ((*gp->put)(gp->target, fmt, uint16_fmt(fmt, rr->rtype)) < 0) return 0 ; 13 | if ((*gp->put)(gp->target, " length ", 8) < 0) return 0 ; 14 | if ((*gp->put)(gp->target, fmt, uint16_fmt(fmt, rr->rdlength)) < 0) return 0 ; 15 | if ((*gp->put)(gp->target, ": ", 2) < 0) return 0 ; 16 | { 17 | uint16_t i = 0 ; 18 | for (; i < rr->rdlength ; i++) 19 | if ((*gp->put)(gp->target, fmt, ucharn_fmt(fmt, packet + pos + i, 1)) < 0) 20 | return 0 ; 21 | } 22 | (void)packetlen ; 23 | return 1 ; 24 | } 25 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_analyze_rtypetable.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | static s6dns_analyze_rtypetable_t const s6dns_analyze_rtypetable_array[] = 6 | { 7 | { 1, "A", &s6dns_analyze_record_a }, 8 | { 2, "NS", &s6dns_analyze_record_domain }, 9 | { 5, "CNAME", &s6dns_analyze_record_domain }, 10 | { 6, "SOA", &s6dns_analyze_record_soa }, 11 | { 12, "PTR", &s6dns_analyze_record_domain }, 12 | { 13, "HINFO", &s6dns_analyze_record_hinfo }, 13 | { 15, "MX", &s6dns_analyze_record_mx }, 14 | { 16, "TXT", &s6dns_analyze_record_strings }, 15 | { 28, "AAAA", &s6dns_analyze_record_aaaa }, 16 | { 33, "SRV", &s6dns_analyze_record_srv }, 17 | { 257, "CAA", &s6dns_analyze_record_caa }, 18 | { 0, "unknown", &s6dns_analyze_record_unknown } 19 | } ; 20 | 21 | s6dns_analyze_rtypetable_t const *s6dns_analyze_rtypetable = s6dns_analyze_rtypetable_array ; 22 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_constants_error.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | 9 | static s6dns_constants_error_message_t const array[] = 10 | { 11 | { ENETUNREACH, "no available DNS server" }, 12 | { EILSEQ, "server did not understand query" }, 13 | { EBUSY, "server failure" }, 14 | { ENOENT, "no such domain" }, 15 | { ENOTSUP, "not implemented in server" }, 16 | { ECONNREFUSED, "server refused" }, 17 | { EIO, "unknown network error" }, 18 | { EAGAIN, "query still processing" }, 19 | { ETIMEDOUT, "query timed out" }, 20 | { EPROTO, "malformed packet" }, 21 | { EDOM, "internal error (please submit a bug-report)" }, 22 | { -1, "unknown error" } 23 | } ; 24 | 25 | s6dns_constants_error_message_t const *const s6dns_constants_error = array ; 26 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_constants_error_str.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | char const *s6dns_constants_error_str (int e) 8 | { 9 | s6dns_constants_error_message_t const *p = s6dns_constants_error ; 10 | while ((p->num != e) && (p->num != -1)) p++ ; 11 | return p->num == -1 ? strerror(e) : p->string ; 12 | } 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_debug_dumpdt_post_recv.c: -------------------------------------------------------------------------------- 1 | /* ISC license */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | int s6dns_debug_dumpdt_post_recv (s6dns_engine_t const *dt, void *data) 9 | { 10 | genwrite *gp = data ; 11 | (void)dt ; 12 | if ((*gp->put)(gp->target, "Received a packet:\n", 19) < 19) return 0 ; 13 | if (!s6dns_analyze_packet(gp, dt->sa.s + dt->querylen, dt->sa.len - dt->querylen, 1)) return 0 ; 14 | if ((*gp->put)(gp->target, "\n", 1) < 1) return 0 ; 15 | return (*gp->flush)(gp->target) ; 16 | } 17 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_debug_dumpdt_post_send.c: -------------------------------------------------------------------------------- 1 | /* ISC license */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | int s6dns_debug_dumpdt_post_send (s6dns_engine_t const *dt, void *data) 11 | { 12 | genwrite *gp = data ; 13 | size_t len ; 14 | char buf[LOCALTMN_FMT] ; 15 | if ((*gp->put)(gp->target, "Sent query ", 11) < 11) return 0 ; 16 | { 17 | uint16_t id ; 18 | uint16_unpack_big(dt->sa.s + 2, &id) ; 19 | len = uint16_fmt(buf, id) ; 20 | } 21 | if ((*gp->put)(gp->target, buf, len) < (ssize_t)len) return 0 ; 22 | if ((*gp->put)(gp->target, " - next recv deadline is ", 25) < 25) return 0 ; 23 | { 24 | localtmn l ; 25 | if (!localtmn_from_tain(&l, &dt->localdeadline, 0)) return 0 ; 26 | len = localtmn_fmt(buf, &l) ; 27 | } 28 | if ((*gp->put)(gp->target, buf, len) < (ssize_t)len) return 0 ; 29 | if ((*gp->put)(gp->target, "\n\n", 2) < 2) return 0 ; 30 | return (*gp->flush)(gp->target) ; 31 | } 32 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_debug_dumpdt_pre_send.c: -------------------------------------------------------------------------------- 1 | /* ISC license */ 2 | 3 | /* For EOVERFLOW */ 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | #include 11 | #include 12 | #include 13 | #include 14 | 15 | #include 16 | #include 17 | #include 18 | 19 | #ifdef SKALIBS_IPV6_ENABLED 20 | # define s6dns_ipfmt(buf, ip, is6) ((is6) ? ip6_fmt(buf, ip) : ip4_fmt(buf, ip)) 21 | #else 22 | # define s6dns_ipfmt(buf, ip, is6) ip4_fmt(buf, ip) 23 | #endif 24 | 25 | int s6dns_debug_dumpdt_pre_send (s6dns_engine_t const *dt, void *data) 26 | { 27 | genwrite *gp = data ; 28 | size_t len ; 29 | char buf[LOCALTMN_FMT] ; 30 | if ((*gp->put)(gp->target, "Preparing to send via ", 22) < 22) return 0 ; 31 | if ((*gp->put)(gp->target, dt->flagtcp ? "TCP" : "UDP", 3) < 3) return 0 ; 32 | if ((*gp->put)(gp->target, " to ", 4) < 4) return 0 ; 33 | len = dt->sa.s[4] & 1 ; 34 | if ((*gp->put)(gp->target, len ? "cache" : "server", len ? 5 : 6) < (len ? 5 : 6)) return 0 ; 35 | if ((*gp->put)(gp->target, " ", 1) < 1) return 0 ; 36 | len = s6dns_ipfmt(buf, s6dns_ip46list_ip(&dt->servers, dt->curserver), s6dns_ip46list_is6(&dt->servers, dt->curserver)) ; 37 | if ((*gp->put)(gp->target, buf, len) < (ssize_t)len) return 0 ; 38 | if ((*gp->put)(gp->target, " with deadline ", 15) < 15) return 0 ; 39 | { 40 | localtmn l ; 41 | if (!localtmn_from_tain(&l, &dt->localdeadline, 0)) 42 | { 43 | if (errno != EOVERFLOW) return 0 ; 44 | memcpy(buf, "\"infinite\"", 10) ; len = 10 ; 45 | } 46 | else len = localtmn_fmt(buf, &l) ; 47 | } 48 | if ((*gp->put)(gp->target, buf, len) < (ssize_t)len) return 0 ; 49 | if ((*gp->put)(gp->target, ", ", 2) < 2) return 0 ; 50 | if (dt->flagstrict && (*gp->put)(gp->target, "strict, ", 8) < 8) return 0 ; 51 | if ((*gp->put)(gp->target, "query id ", 9) < 9) return 0 ; 52 | { 53 | uint16_t id ; 54 | uint16_unpack_big(dt->sa.s + 2, &id) ; 55 | len = uint16_fmt(buf, id) ; 56 | } 57 | if ((*gp->put)(gp->target, buf, len) < (ssize_t)len) return 0 ; 58 | if ((*gp->put)(gp->target, ":\n", 2) < 2) return 0 ; 59 | if (!s6dns_analyze_packet(gp, dt->sa.s + 2, dt->querylen - 2, 1)) return 0 ; 60 | if ((*gp->put)(gp->target, "\n", 1) < 1) return 0 ; 61 | return (*gp->flush)(gp->target) ; 62 | } 63 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_debug_dumpdt_stderr.c: -------------------------------------------------------------------------------- 1 | /* ISC license */ 2 | 3 | #include 4 | #include 5 | 6 | s6dns_debughook_t const s6dns_debug_dumpdt_stderr = S6DNS_DEBUG_DUMPDT_INIT((void *)&genwrite_stderr) ; 7 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_debug_dumpdt_stdout.c: -------------------------------------------------------------------------------- 1 | /* ISC license */ 2 | 3 | #include 4 | #include 5 | 6 | s6dns_debughook_t const s6dns_debug_dumpdt_stdout = S6DNS_DEBUG_DUMPDT_INIT((void *)&genwrite_stdout) ; 7 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_debughook_zero.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | s6dns_debughook_t const s6dns_debughook_zero = S6DNS_DEBUGHOOK_ZERO ; 6 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_arpafromip4.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | void s6dns_domain_arpafromip4 (s6dns_domain_t *d, char const *ip) 8 | { 9 | unsigned int i = 0 ; 10 | d->len = 0 ; 11 | d->s[d->len++] = '.' ; 12 | for (; i < 4 ; i++) 13 | { 14 | unsigned int u = ((unsigned char *)ip)[3-i] ; 15 | d->len += uint_fmt(d->s + d->len, u) ; 16 | d->s[d->len++] = '.' ; 17 | } 18 | memcpy(d->s + d->len, "in-addr.arpa.", 13) ; d->len += 13 ; 19 | } 20 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_arpafromip6.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | void s6dns_domain_arpafromip6 (s6dns_domain_t *d, char const *ip6, unsigned int mask) 8 | { 9 | unsigned int i ; 10 | if (mask > 128) mask = 128 ; 11 | mask = mask ? 1 + ((mask-1) >> 2) : 0 ; 12 | d->len = 0 ; 13 | d->s[d->len++] = '.' ; 14 | for (i = 32 - mask ; i < 32 ; i++) 15 | { 16 | unsigned char c = ip6[15-(i>>1)] ; 17 | d->s[d->len++] = fmtscan_asc((i & 1) ? (c >> 4) : (c & 15)) ; 18 | d->s[d->len++] = '.' ; 19 | } 20 | memcpy(d->s + d->len, "ip6.arpa.", 9) ; d->len += 9 ; 21 | } 22 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_decode.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | 9 | static inline unsigned int s6dns_domain_label_decode (char *s, unsigned int max) 10 | { 11 | unsigned int len = *(unsigned char *)s ; 12 | if ((len > 63) || (len >= max)) return (errno = EPROTO, 0) ; 13 | *s = '.' ; 14 | return len + 1 ; 15 | } 16 | 17 | int s6dns_domain_decode (s6dns_domain_t *d) 18 | { 19 | unsigned int max = 255 ; 20 | unsigned int pos = 0 ; 21 | for (;;) 22 | { 23 | unsigned int r = s6dns_domain_label_decode(d->s + pos, max - pos) ; 24 | if (!r) return 0 ; 25 | pos += r ; 26 | if (r == 1) break ; 27 | } 28 | d->len = pos ; 29 | return 1 ; 30 | } 31 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_encode.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_domain_encode (s6dns_domain_t *d) 8 | { 9 | char *s = d->s ; 10 | unsigned int len = d->len ; 11 | if (!d->len || (*s != '.')) return (errno = EINVAL, 0) ; 12 | while (len > 1) 13 | { 14 | unsigned int n = byte_chr(s + 1, len - 1, '.') ; 15 | if (n > 63) return (errno = EINVAL, 0) ; 16 | *s = n++ ; s += n ; len -= n ; 17 | } 18 | if (!len) return (errno = EINVAL, 0) ; 19 | *s = 0 ; 20 | return 1 ; 21 | } 22 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_encodelist.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | unsigned int s6dns_domain_encodelist (s6dns_domain_t *list, unsigned int n) 6 | { 7 | unsigned int i = 0 ; 8 | for (; i < n ; i++) 9 | if (!s6dns_domain_encode(list + i)) break ; 10 | return i ; 11 | } 12 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_fromstring.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | 9 | int s6dns_domain_fromstring (s6dns_domain_t *d, char const *s, size_t len) 10 | { 11 | size_t j = 1 ; 12 | size_t i = 0 ; 13 | unsigned int lastdot = 0 ; 14 | d->s[0] = '.' ; 15 | for (; i < len ; i++) 16 | { 17 | if (lastdot) 18 | { 19 | if ((j >= 255) || (lastdot++ >= 64)) return (errno = ENAMETOOLONG, 0) ; 20 | d->s[j++] = tolower(s[i]) ; 21 | } 22 | if (s[i] == '.') lastdot = 0 ; 23 | else if (!lastdot) 24 | { 25 | i-- ; 26 | lastdot = 1 ; 27 | } 28 | } 29 | d->len = j ; 30 | return 1 ; 31 | } 32 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_fromstring_noqualify_encode.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | int s6dns_domain_fromstring_noqualify_encode (s6dns_domain_t *d, char const *name, size_t len) 6 | { 7 | return s6dns_domain_fromstring(d, name, len) 8 | && s6dns_domain_noqualify(d) 9 | && s6dns_domain_encode(d) ; 10 | } 11 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_fromstring_qualify_encode.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | unsigned int s6dns_domain_fromstring_qualify_encode (s6dns_domain_t *list, char const *name, size_t len, char const *rules, unsigned int rulesnum) 6 | { 7 | s6dns_domain_t d ; 8 | if (!s6dns_domain_fromstring(&d, name, len)) return 0 ; 9 | return s6dns_domain_encodelist(list, s6dns_domain_qualify(list, &d, rules, rulesnum)) ; 10 | } 11 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_noqualify.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | int s6dns_domain_noqualify (s6dns_domain_t *d) 7 | { 8 | if (d->s[d->len-1] != '.') 9 | { 10 | if (d->len == 255) return (errno = ENAMETOOLONG, 0) ; 11 | d->s[d->len++] = '.' ; 12 | } 13 | return 1 ; 14 | } 15 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_qualify.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | unsigned int s6dns_domain_qualify (s6dns_domain_t *list, s6dns_domain_t const *d, char const *rules, unsigned int rulesnum) 8 | { 9 | if (!d->len) return (errno = EINVAL, 0) ; 10 | if (d->s[d->len - 1] == '.') 11 | { 12 | list[0] = *d ; 13 | return 1 ; 14 | } 15 | else 16 | { 17 | unsigned int i = 0 ; 18 | for (; i < rulesnum ; i++) 19 | { 20 | size_t n = strlen(rules) ; 21 | if (d->len + n >= 254) return (errno = ENAMETOOLONG, 0) ; 22 | list[i] = *d ; 23 | list[i].s[d->len] = '.' ; 24 | memcpy(list[i].s + d->len + 1, rules, n) ; 25 | list[i].len += n+1 ; 26 | rules += n+1 ; 27 | } 28 | return i ; 29 | } 30 | } 31 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_domain_tostring.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | 10 | unsigned int s6dns_domain_tostring (char *s, size_t max, s6dns_domain_t const *d) 11 | { 12 | if ((size_t)d->len + 1 > max) return (errno = ENAMETOOLONG, 0) ; 13 | if (!d->len || (d->s[0] != '.')) return (errno = EINVAL, 0) ; 14 | if (d->len == 1) 15 | { 16 | s[0] = '.' ; 17 | s[1] = 0 ; 18 | return 1 ; 19 | } 20 | else 21 | { 22 | memcpy(s, d->s + 1, d->len - 1) ; 23 | s[d->len - 1] = 0 ; 24 | case_lowerb(s, d->len - 1) ; 25 | return d->len - 1 ; 26 | } 27 | } 28 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_engine_free.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | void s6dns_engine_free (s6dns_engine_t *dt) 7 | { 8 | s6dns_engine_recycle(dt) ; 9 | stralloc_free(&dt->sa) ; 10 | *dt = s6dns_engine_zero ; 11 | } 12 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_engine_freen.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | void s6dns_engine_freen (s6dns_engine_t *dtl, unsigned int n) 6 | { 7 | while (n--) s6dns_engine_free(dtl + n) ; 8 | } 9 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_engine_here.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | /* MT-unsafe */ 4 | 5 | #include 6 | 7 | s6dns_engine_t s6dns_engine_here = S6DNS_ENGINE_ZERO ; 8 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_engine_nextdeadline.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | void s6dns_engine_nextdeadline (s6dns_engine_t const *dt, tain *deadline) 7 | { 8 | if (tain_less(&dt->deadline, deadline)) *deadline = dt->deadline ; 9 | if (tain_less(&dt->localdeadline, deadline)) *deadline = dt->localdeadline ; 10 | } 11 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_engine_query.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | void s6dns_engine_query (s6dns_engine_t const *dt, char **q, uint16_t *qlen, uint16_t *qtype) 8 | { 9 | uint16_t len ; 10 | uint16_unpack_big(dt->sa.s, &len) ; 11 | *q = dt->sa.s + 14 ; 12 | *qlen = len - 16 ; 13 | uint16_unpack_big(dt->sa.s + len - 2, qtype) ; 14 | } 15 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_engine_zero.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | s6dns_engine_t const s6dns_engine_zero = S6DNS_ENGINE_ZERO ; 6 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_finish.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | void s6dns_finish () 8 | { 9 | s6dns_engine_free(&s6dns_engine_here) ; 10 | s6dns_hosts_free(&s6dns_hosts_here) ; 11 | s6dns_rci_free(&s6dns_rci_here) ; 12 | } 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_fmt_caa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | size_t s6dns_fmt_caa (char *s, size_t max, s6dns_message_rr_caa_t const *caa) 10 | { 11 | size_t len = 0, taglen = strlen(caa->tag), valuelen = strlen(caa->value) ; 12 | char fmt[UINT16_FMT] ; 13 | size_t r = uint16_fmt(fmt, (uint16_t)caa->flags) ; 14 | if (r + taglen + valuelen + 2 > max) return (errno = ENAMETOOLONG, 0) ; 15 | memcpy(s + len, fmt, r) ; 16 | len += r ; s[len++] = ' ' ; 17 | memcpy(s + len, caa->tag, taglen) ; 18 | len += taglen ; s[len++] = ' ' ; 19 | memcpy(s + len, caa->value, valuelen) ; 20 | len += valuelen ; 21 | return len ; 22 | } 23 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_fmt_domainlist.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | 9 | size_t s6dns_fmt_domainlist (char *s, size_t max, s6dns_domain_t const *list, unsigned int n, char const *delim, size_t delimlen) 10 | { 11 | size_t len = 0 ; 12 | unsigned int i = 0 ; 13 | for (; i < n ; i++) 14 | { 15 | unsigned int r = s6dns_domain_tostring(s + len, max - len, list + i) ; 16 | if (!r) return 0 ; 17 | len += r ; 18 | if (i+1 < n) 19 | { 20 | if (len + delimlen > max) return (errno = ENAMETOOLONG, 0) ; 21 | memcpy(s + len, delim, delimlen) ; 22 | len += delimlen ; 23 | } 24 | } 25 | return len ; 26 | } 27 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_fmt_hinfo.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | size_t s6dns_fmt_hinfo (char *s, size_t max, s6dns_message_rr_hinfo_t const *hinfo) 8 | { 9 | if (hinfo->cpu.len + 1 + hinfo->os.len > max) return (errno = ENAMETOOLONG, 0) ; 10 | memcpy(s, hinfo->cpu.s, hinfo->cpu.len) ; 11 | s[hinfo->cpu.len] = ' ' ; 12 | memcpy(s + hinfo->cpu.len + 1, hinfo->os.s, hinfo->os.len) ; 13 | return hinfo->cpu.len + 1 + hinfo->os.len ; 14 | } 15 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_fmt_mx.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | size_t s6dns_fmt_mx (char *s, size_t max, s6dns_message_rr_mx_t const *mx) 9 | { 10 | char fmt[UINT16_FMT] ; 11 | size_t len = uint16_fmt(fmt, mx->preference) ; 12 | unsigned int r ; 13 | if (len >= max) return 0 ; 14 | fmt[len++] = ' ' ; 15 | r = s6dns_domain_tostring(s + len, max - len, &mx->exchange) ; 16 | if (!r) return 0 ; 17 | memcpy(s, fmt, len) ; 18 | return len + r ; 19 | } 20 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_fmt_soa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | size_t s6dns_fmt_soa (char *s, size_t max, s6dns_message_rr_soa_t const *soa) 10 | { 11 | size_t len = 0 ; 12 | char fmt[UINT32_FMT] ; 13 | size_t r = s6dns_domain_tostring(s + len, max - len, &soa->mname) ; 14 | if (!r) return 0 ; 15 | len += r ; 16 | if (len >= max) return (errno = ENAMETOOLONG, 0) ; 17 | s[len++] = ' ' ; 18 | r = s6dns_domain_tostring(s + len, max - len, &soa->rname) ; 19 | if (!r) return 0 ; 20 | len += r ; 21 | if (len >= max) return (errno = ENAMETOOLONG, 0) ; 22 | s[len++] = ' ' ; 23 | r = uint32_fmt(fmt, soa->serial) ; 24 | if (len + r >= max) return (errno = ENAMETOOLONG, 0) ; 25 | memcpy(s + len, fmt, r) ; 26 | len += r ; s[len++] = ' ' ; 27 | r = uint32_fmt(fmt, soa->refresh) ; 28 | if (len + r >= max) return (errno = ENAMETOOLONG, 0) ; 29 | memcpy(s + len, fmt, r) ; 30 | len += r ; s[len++] = ' ' ; 31 | r = uint32_fmt(fmt, soa->retry) ; 32 | if (len + r >= max) return (errno = ENAMETOOLONG, 0) ; 33 | memcpy(s + len, fmt, r) ; 34 | len += r ; s[len++] = ' ' ; 35 | r = uint32_fmt(fmt, soa->expire) ; 36 | if (len + r >= max) return (errno = ENAMETOOLONG, 0) ; 37 | memcpy(s + len, fmt, r) ; 38 | len += r ; s[len++] = ' ' ; 39 | r = uint32_fmt(fmt, soa->minimum) ; 40 | if (len + r > max) return (errno = ENAMETOOLONG, 0) ; 41 | memcpy(s + len, fmt, r) ; 42 | len += r ; 43 | return len ; 44 | } 45 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_fmt_srv.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | size_t s6dns_fmt_srv (char *s, size_t max, s6dns_message_rr_srv_t const *srv) 10 | { 11 | size_t len = 0 ; 12 | char fmt[UINT16_FMT] ; 13 | size_t r = uint16_fmt(fmt, srv->priority) ; 14 | if (len + r >= max) return (errno = ENAMETOOLONG, 0) ; 15 | memcpy(s + len, fmt, r) ; 16 | len += r ; s[len++] = ' ' ; 17 | r = uint16_fmt(fmt, srv->weight) ; 18 | if (len + r >= max) return (errno = ENAMETOOLONG, 0) ; 19 | memcpy(s + len, fmt, r) ; 20 | len += r ; s[len++] = ' ' ; 21 | r = uint16_fmt(fmt, srv->port) ; 22 | if (len + r >= max) return (errno = ENAMETOOLONG, 0) ; 23 | memcpy(s + len, fmt, r) ; 24 | len += r ; s[len++] = ' ' ; 25 | r = s6dns_domain_tostring(s + len, max - len, &srv->target) ; 26 | if (!r) return 0 ; 27 | len += r ; 28 | return len ; 29 | } 30 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_aaaaa_q.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | #include 10 | 11 | extern int s6dns_hosts_aaaaa_q_r (cdb const *c, char const *name, genalloc *ga, char const *rules, unsigned int rulesnum) 12 | { 13 | int r ; 14 | int gawn = !genalloc_s(ip46full, ga) ; 15 | size_t gabase = genalloc_len(ip46full, ga) ; 16 | s6dns_domain_t d[rulesnum + 1] ; 17 | if (!c->map) return 0 ; 18 | r = s6dns_hosts_aaaaa_unq_r(c, name, ga) ; 19 | if (r == -1) return -1 ; 20 | if (!s6dns_domain_fromstring(d + rulesnum, name, strlen(name))) goto err ; 21 | if (!s6dns_domain_qualify(d, d + rulesnum, rules, rulesnum)) goto err ; 22 | for (unsigned int i = 0 ; i < rulesnum ; i++) 23 | { 24 | char tmp[256] ; 25 | r = s6dns_domain_tostring(tmp, 256, d + i) ; 26 | if (!r) goto err ; 27 | tmp[r] = 0 ; 28 | r = s6dns_hosts_aaaaa_noq_r(c, tmp, ga) ; 29 | if (r == -1) goto err ; 30 | if (r) break ; 31 | } 32 | return genalloc_len(ip46full, ga) - gabase ; 33 | 34 | err: 35 | if (gawn) genalloc_free(ip46full, ga) ; else genalloc_setlen(ip46full, ga, gabase) ; 36 | return -1 ; 37 | } 38 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_aaaaa_string.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | #include 11 | 12 | extern int s6dns_hosts_aaaaa_string_r (cdb const *c, char const *name, genalloc *ga, int isunq) 13 | { 14 | stralloc sa = STRALLOC_ZERO ; 15 | int gawn = !genalloc_s(ip46full, ga) ; 16 | size_t gabase = genalloc_len(ip46full, ga) ; 17 | int r = s6dns_hosts_a_string_r(c, name, &sa, isunq) ; 18 | if (r <= 0) return r ; 19 | if (!genalloc_readyplus(ip46full, ga, r)) return -1 ; 20 | for (size_t i = 0 ; i < r ; i++) 21 | ip46full_from_ip4(genalloc_s(ip46full, ga) + gabase + i, sa.s + (i << 2)) ; 22 | genalloc_setlen(ip46full, ga, gabase + r) ; 23 | sa.len = 0 ; 24 | r = s6dns_hosts_aaaa_string_r(c, name, &sa, isunq) ; 25 | if (r == -1) goto err ; 26 | if (r) 27 | { 28 | if (!genalloc_readyplus(ip46full, ga, r)) goto err ; 29 | for (size_t i = 0 ; i < r ; i++) 30 | ip46full_from_ip6(genalloc_s(ip46full, ga) + genalloc_len(ip46full, ga) + i, sa.s + (i << 4)) ; 31 | genalloc_setlen(ip46full, ga, genalloc_len(ip46full, ga) + r) ; 32 | } 33 | stralloc_free(&sa) ; 34 | return genalloc_len(ip46full, ga) - gabase ; 35 | 36 | err: 37 | if (gawn) genalloc_free(ip46full, ga) ; else genalloc_setlen(ip46full, ga, gabase) ; 38 | stralloc_free(&sa) ; 39 | return -1 ; 40 | } 41 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_compile.txt: -------------------------------------------------------------------------------- 1 | 2 | 3 | class | 0 1 2 3 4 5 6 7 8 9 a 4 | st\ev | \0 space # \n - . : 0-9 alpha other % 5 | 6 | START | p p p 7 | 00 | END START COMMENT START X X IP IP IP X X 8 | 9 | COMMENT | 10 | 01 | END COMMENT COMMENT START COMMENT COMMENT COMMENT COMMENT COMMENT COMMENT COMMENT 11 | 12 | IP | s s s p p p p s 13 | 02 | END IPDONE X START X IP IP IP IP X COMMENT 14 | 15 | IPDONE | p 16 | 03 | END IPDONE COMMENT START X X X X NAME X X 17 | 18 | NAME | f fn f p p p p 19 | 04 | END NAMES X START NAME NAME X NAME NAME X X 20 | 21 | NAMES | p 22 | 05 | END NAMES COMMENT START X X X X NAME X X 23 | 24 | END = 0a 25 | X = 0b 26 | 27 | state: 4 bits 28 | actions: 4 bits 29 | 30 | 0x10 p store cur 31 | 0x20 s scan IP, reset fqdn 32 | 0x40 f scan name 33 | 0x80 n fqdn done, now aliases 34 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_here.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | cdb s6dns_hosts_here = CDB_ZERO ; 8 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_init.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | #include 9 | #include 10 | 11 | #include 12 | #include 13 | #include 14 | #include 15 | #include 16 | 17 | #include 18 | 19 | #include 20 | 21 | int s6dns_hosts_init (cdb *c, char const *txtfile, char const *cdbfile, char const *tmpprefix) 22 | { 23 | int fdr ; 24 | int fdc = openc_read(cdbfile) ; 25 | if (fdc >= 0) 26 | { 27 | struct stat stc, str ; 28 | if (fstat(fdc, &stc) == -1) goto errc ; 29 | if (stat(txtfile, &str) == -1) 30 | { 31 | if (errno == ENOENT) goto useit ; 32 | else goto errc ; 33 | } 34 | if (timespec_cmp(&stc.st_mtim, &str.st_mtim) > 0) goto useit ; 35 | fd_close(fdc) ; 36 | } 37 | 38 | fdr = openc_read(txtfile) ; 39 | if (fdr == -1) return errno == ENOENT ? (errno = 0, 0) : -1 ; 40 | { 41 | int fdw ; 42 | size_t len = strlen(tmpprefix) ; 43 | char tmp[len + 8] ; 44 | memcpy(tmp, tmpprefix, len) ; 45 | memcpy(tmp + len, ":XXXXXX", 8) ; 46 | fdw = mkstemp(tmp) ; 47 | if (fdw == -1) goto errr ; 48 | if (!s6dns_hosts_compile(fdr, fdw)) goto errw ; 49 | if (lseek(fdw, 0, SEEK_SET) == -1) goto errw ; 50 | if (!cdb_init_fromfd(c, fdw)) goto errw ; 51 | fd_close(fdw) ; 52 | unlink_void(tmp) ; 53 | fd_close(fdr) ; 54 | return 1 ; 55 | 56 | errw: 57 | fd_close(fdw) ; 58 | unlink_void(tmp) ; 59 | } 60 | errr: 61 | fd_close(fdr) ; 62 | return -1 ; 63 | 64 | errc: 65 | fd_close(fdc) ; 66 | return -1 ; 67 | 68 | useit: 69 | if (!cdb_init_fromfd(c, fdc)) 70 | { 71 | fd_close(fdc) ; 72 | return 0 ; 73 | } 74 | fd_close(fdc) ; 75 | return 1 ; 76 | } 77 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_ip_q.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | #include 9 | 10 | extern int s6dns_hosts_ip_q_r (cdb const *c, char const *name, stralloc *sa, char const *rules, unsigned int rulesnum, int is6) 11 | { 12 | int r ; 13 | int sawn = !sa->s ; 14 | size_t sabase = sa->len ; 15 | s6dns_domain_t d[rulesnum + 1] ; 16 | if (!c->map) return 0 ; 17 | r = s6dns_hosts_ip_unq_r(c, name, sa, is6) ; 18 | if (r == -1) return -1 ; 19 | if (!s6dns_domain_fromstring(d + rulesnum, name, strlen(name))) goto err ; 20 | if (!s6dns_domain_qualify(d, d + rulesnum, rules, rulesnum)) goto err ; 21 | for (unsigned int i = 0 ; i < rulesnum ; i++) 22 | { 23 | char tmp[256] ; 24 | r = s6dns_domain_tostring(tmp, 256, d + i) ; 25 | if (!r) goto err ; 26 | tmp[r] = 0 ; 27 | r = s6dns_hosts_ip_noq_r(c, tmp, sa, is6) ; 28 | if (r == -1) goto err ; 29 | if (r) break ; 30 | } 31 | return (sa->len - sabase) >> (is6 ? 4 : 2) ; 32 | 33 | err: 34 | if (sawn) stralloc_free(sa) ; else sa->len = sabase ; 35 | return -1 ; 36 | } 37 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_ip_string.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | #include 10 | 11 | #include 12 | 13 | extern int s6dns_hosts_ip_string_r (cdb const *c, char const *name, stralloc *sa, unsigned int flags) 14 | { 15 | s6dns_domain_t d ; 16 | cdb_data data ; 17 | if (!c->map) return 0 ; 18 | if (!s6dns_domain_fromstring(&d, name, strlen(name))) return -1 ; 19 | if (!(flags & 2) && !s6dns_domain_noqualify(&d)) return -1 ; 20 | { 21 | int r ; 22 | char tmp[4 + d.len] ; 23 | tmp[0] = flags & 2 ? 'u' : 'a' ; 24 | tmp[1] = flags & 1 ? '6' : '4' ; 25 | tmp[2] = ':' ; 26 | r = s6dns_domain_tostring(tmp + 3, d.len + 1, &d) ; 27 | tmp[3 + r] = 0 ; 28 | if (!r) return -1 ; 29 | r = cdb_find(c, &data, tmp, 3 + r) ; 30 | if (r <= 0) return r ; 31 | } 32 | if (!data.len) return 0 ; 33 | if (data.len & (flags & 1 ? 15 : 3)) return (errno = EPROTO, -1) ; 34 | if (!stralloc_catb(sa, data.s, data.len)) return -1 ; 35 | return data.len >> (flags & 1 ? 4 : 2) ; 36 | } 37 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_hosts_name.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | #include 10 | 11 | #include 12 | 13 | #include 14 | 15 | int s6dns_hosts_name_r (cdb const *c, char const *ip, stralloc *sa, genalloc *ga, int is6) 16 | { 17 | int r ; 18 | cdb_data data ; 19 | int sawn = !sa->s ; 20 | int gawn = !genalloc_s(size_t, ga) ; 21 | size_t sabase = sa->len ; 22 | size_t gabase = genalloc_len(size_t, ga) ; 23 | size_t i = sabase ; 24 | char tmp[19] = "p4:" ; 25 | if (!c->map) return 0 ; 26 | if (is6) tmp[1] = '6' ; 27 | memcpy(tmp + 3, ip, is6 ? 16 : 4) ; 28 | r = cdb_find(c, &data, tmp, is6 ? 19 : 7) ; 29 | if (r <= 0) return r ; 30 | if (!data.len) return 0 ; 31 | if (data.s[data.len - 1]) return (errno = EPROTO, -1) ; 32 | if (!stralloc_catb(sa, data.s, data.len)) return -1 ; 33 | while (i < sa->len) 34 | { 35 | if (!genalloc_catb(size_t, ga, &i, 1)) goto err ; 36 | i += strlen(sa->s + i) + 1 ; 37 | } 38 | return genalloc_len(size_t, ga) - gabase ; 39 | 40 | err: 41 | if (gawn) genalloc_free(size_t, ga) ; else genalloc_setlen(size_t, ga, 0) ; 42 | if (sawn) stralloc_free(sa) ; else sa->len = 0 ; 43 | return -1 ; 44 | } 45 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_init.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_init_options (uint32_t options) 8 | { 9 | if (!s6dns_rci_init(&s6dns_rci_here, "/etc/resolv.conf")) return 0 ; 10 | if (options & 1 && s6dns_hosts_init(&s6dns_hosts_here, "/etc/hosts", "/etc/hosts.cdb", "/tmp/hosts.cdb") == -1) goto err ; 11 | return 1 ; 12 | 13 | err: 14 | s6dns_rci_free(&s6dns_rci_here) ; 15 | return 0 ; 16 | } 17 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_counts_next.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | unsigned int s6dns_message_counts_next (s6dns_message_counts_t *counts) 6 | { 7 | if (counts->qd) { counts->qd-- ; return 1 ; } 8 | else if (counts->an) { counts->an-- ; return 2 ; } 9 | else if (counts->ns) { counts->ns-- ; return 3 ; } 10 | else if (counts->nr) { counts->nr-- ; return 4 ; } 11 | else return 0 ; 12 | } 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_counts_pack.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | void s6dns_message_counts_pack (char *s, s6dns_message_counts_t const *counts) 7 | { 8 | uint16_pack_big(s, counts->qd) ; 9 | uint16_pack_big(s+2, counts->an) ; 10 | uint16_pack_big(s+4, counts->ns) ; 11 | uint16_pack_big(s+6, counts->nr) ; 12 | } 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_counts_unpack.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | void s6dns_message_counts_unpack (char const *s, s6dns_message_counts_t *counts) 7 | { 8 | uint16_unpack_big(s, &counts->qd) ; 9 | uint16_unpack_big(s+2, &counts->an) ; 10 | uint16_unpack_big(s+4, &counts->ns) ; 11 | uint16_unpack_big(s+6, &counts->nr) ; 12 | } 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_counts_zero.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | s6dns_message_counts_t const s6dns_message_counts_zero = S6DNS_MESSAGE_COUNTS_ZERO ; 6 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_caa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | #include 8 | 9 | #include 10 | 11 | int s6dns_message_get_caa (s6dns_message_rr_caa_t *caa, char const *packet, unsigned int packetlen, unsigned int *pos, uint16_t rdlength) 12 | { 13 | unsigned char taglen ; 14 | if (rdlength < 4) return (errno = EPROTO, 0) ; 15 | if (*pos + rdlength > packetlen) return (errno = EPROTO, 0) ; 16 | caa->flags = packet[(*pos)++] ; 17 | taglen = packet[(*pos)++] ; 18 | if (rdlength < taglen + 3 || rdlength > taglen + 257) return (errno = EPROTO, 0) ; 19 | memcpy(caa->tag, packet + *pos, taglen) ; 20 | caa->tag[taglen] = 0 ; 21 | *pos += taglen ; 22 | memcpy(caa->value, packet + *pos, rdlength - taglen - 2) ; 23 | caa->value[rdlength - taglen - 1] = 0 ; 24 | *pos += rdlength - taglen - 2 ; 25 | return 1 ; 26 | } 27 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_domain.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | int s6dns_message_get_domain (s6dns_domain_t *d, char const *packet, unsigned int packetlen, unsigned int *pos) 7 | { 8 | return s6dns_message_get_domain_nodecode(d->s, 255, packet, packetlen, pos) 9 | && s6dns_domain_decode(d) ; 10 | } 11 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_domain_nodecode.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include 9 | 10 | size_t s6dns_message_get_domain_nodecode (char *out, size_t outmax, char const *s, unsigned int len, unsigned int *pos) 11 | { 12 | size_t w = 0 ; /* writing head */ 13 | unsigned int r = *pos ; /* reading head */ 14 | unsigned int jumps = 0 ; 15 | int hasjumped = 0 ; 16 | for (;;) 17 | { 18 | unsigned char c ; 19 | if (r >= len) return (errno = EPROTO, 0) ; 20 | c = s[r] ; 21 | if (c < 64) /* normal label */ 22 | { 23 | if (r + ++c > len) return (errno = EPROTO, 0) ; 24 | if (out) 25 | { 26 | if (w + c > outmax) return (errno = ENAMETOOLONG, 0) ; 27 | memcpy(out + w, s + r, c) ; 28 | } 29 | w += c ; r += c ; if (!hasjumped) *pos += c ; 30 | if (c == 1) break ; 31 | } 32 | else if (c >= 192) /* pointer */ 33 | { 34 | if (r + 1 >= len) return (errno = EPROTO, 0) ; 35 | if (hasjumped) 36 | { 37 | if (++jumps > 1000) return (errno = EPROTO, 0) ; 38 | } 39 | else 40 | { 41 | *pos += 2 ; 42 | hasjumped = 1 ; 43 | } 44 | r = (((unsigned int)c & 63) << 8) | (unsigned char)(s[r + 1]) ; 45 | } 46 | else return (errno = EPROTONOSUPPORT, 0) ; /* unsupported extension */ 47 | } 48 | return w ; 49 | } 50 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_hinfo.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | int s6dns_message_get_hinfo (s6dns_message_rr_hinfo_t_ref hinfo, char const *packet, unsigned int packetlen, unsigned int *pos) 6 | { 7 | return s6dns_message_get_string(&hinfo->cpu, packet, packetlen, pos) 8 | && s6dns_message_get_string(&hinfo->os, packet, packetlen, pos) ; 9 | } 10 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_mx.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | 10 | int s6dns_message_get_mx (s6dns_message_rr_mx_t *mx, char const *packet, unsigned int packetlen, unsigned int *pos) 11 | { 12 | if (*pos + 3 > packetlen) return (errno = EPROTO, 0) ; 13 | uint16_unpack_big(packet + *pos, &mx->preference) ; *pos += 2 ; 14 | return s6dns_message_get_domain(&mx->exchange, packet, packetlen, pos) ; 15 | } 16 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_soa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | 10 | int s6dns_message_get_soa (s6dns_message_rr_soa_t *soa, char const *packet, unsigned int packetlen, unsigned int *pos) 11 | { 12 | if (!s6dns_message_get_domain(&soa->mname, packet, packetlen, pos)) return 0 ; 13 | if (!s6dns_message_get_domain(&soa->rname, packet, packetlen, pos)) return 0 ; 14 | if (*pos + 20 > packetlen) return (errno = EPROTO, 0) ; 15 | uint32_unpack_big(packet + *pos, &soa->serial) ; *pos += 4 ; 16 | uint32_unpack_big(packet + *pos, &soa->refresh) ; *pos += 4 ; 17 | uint32_unpack_big(packet + *pos, &soa->retry) ; *pos += 4 ; 18 | uint32_unpack_big(packet + *pos, &soa->expire) ; *pos += 4 ; 19 | uint32_unpack_big(packet + *pos, &soa->minimum) ; *pos += 4 ; 20 | return 1 ; 21 | } 22 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_srv.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | 10 | int s6dns_message_get_srv (s6dns_message_rr_srv_t *srv, char const *packet, unsigned int packetlen, unsigned int *pos) 11 | { 12 | if (*pos + 7 > packetlen) return (errno = EPROTO, 0) ; 13 | uint16_unpack_big(packet + *pos, &srv->priority) ; *pos += 2 ; 14 | uint16_unpack_big(packet + *pos, &srv->weight) ; *pos += 2 ; 15 | uint16_unpack_big(packet + *pos, &srv->port) ; *pos += 2 ; 16 | return s6dns_message_get_domain(&srv->target, packet, packetlen, pos) ; 17 | } 18 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_string.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include "s6dns-message-internal.h" 5 | 6 | int s6dns_message_get_string (s6dns_domain_t *d, char const *packet, unsigned int packetlen, unsigned int *pos) 7 | { 8 | int r = s6dns_message_get_string_internal(d->s, 255, packet, packetlen, pos) ; 9 | if (r < 0) return 0 ; 10 | d->len = r ; 11 | return 1 ; 12 | } 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_string_internal.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | #include "s6dns-message-internal.h" 9 | 10 | int s6dns_message_get_string_internal (char *s, size_t max, char const *packet, unsigned int packetlen, unsigned int *pos) 11 | { 12 | unsigned char len = ((unsigned char const *)packet)[*pos] ; 13 | if (*pos + len + 1 > packetlen) return (errno = EPROTO, -1) ; 14 | if (len > max) return (errno = ENAMETOOLONG, -1) ; 15 | memcpy(s, packet + *pos + 1, len) ; 16 | *pos += len + 1 ; 17 | return len ; 18 | } 19 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_get_strings.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include "s6dns-message-internal.h" 5 | 6 | int s6dns_message_get_strings (char *s, unsigned int rdlength, char const *packet, unsigned int packetlen, unsigned int *pos) 7 | { 8 | unsigned int max = rdlength, len = 0 ; 9 | while (rdlength) 10 | { 11 | unsigned int start = *pos ; 12 | int r = s6dns_message_get_string_internal(s + len, max - len, packet, packetlen, pos) ; 13 | if (r < 0) return -1 ; 14 | len += r ; rdlength -= *pos - start ; 15 | } 16 | return len ; 17 | } 18 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_header_pack.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | void s6dns_message_header_pack (char *s, s6dns_message_header_t const *h) 7 | { 8 | uint16_pack_big(s, h->id) ; 9 | s[2] = (char)(unsigned char)((h->qr << 7) | (h->opcode << 3) | (h->aa << 2) | (h->tc << 1) | h->rd) ; 10 | s[3] = (h->z << 4) | h->rcode ; 11 | s6dns_message_counts_pack(s+4, &h->counts) ; 12 | } 13 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_header_unpack.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | void s6dns_message_header_unpack (char const *s, s6dns_message_header_t *h) 7 | { 8 | uint16_unpack_big(s, &h->id) ; 9 | h->qr = ((unsigned char *)s)[2] & 0x80U ? 1 : 0 ; 10 | h->opcode = (s[2] >> 3) & 15 ; 11 | h->aa = s[2] & 4 ? 1 : 0 ; 12 | h->tc = s[2] & 2 ? 1 : 0 ; 13 | h->rd = s[2] & 1 ; 14 | h->ra = s[3] & 0x80U ? 1 : 0 ; 15 | h->z = (s[3] >> 4) & 7 ; 16 | h->rcode = s[3] & 15 ; 17 | s6dns_message_counts_unpack(s+4, &h->counts) ; 18 | } 19 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_header_zero.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | s6dns_message_header_t const s6dns_message_header_zero = S6DNS_MESSAGE_HEADER_ZERO ; 6 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | #include 9 | 10 | int s6dns_message_parse (s6dns_message_header_t *h, char const *packet, unsigned int packetlen, s6dns_message_rr_func_ref f, void *data) 11 | { 12 | s6dns_message_counts_t counts ; 13 | unsigned int pos ; 14 | unsigned int section ; 15 | int gotans ; 16 | if (!s6dns_message_parse_init(h, &counts, packet, packetlen, &pos)) return 0 ; 17 | switch (h->rcode) 18 | { 19 | case 0 : break ; 20 | case 1 : return (errno = EILSEQ, 0) ; 21 | case 2 : return (errno = EBUSY, 0) ; 22 | case 3 : return (errno = ENOENT, 0) ; 23 | case 4 : return (errno = ENOTSUP, 0) ; 24 | case 5 : return (errno = ECONNREFUSED, 0) ; 25 | default: return (errno = EIO, 0) ; 26 | } 27 | gotans = !!counts.an ; 28 | section = s6dns_message_parse_skipqd(&counts, packet, packetlen, &pos) ; 29 | while (section) 30 | { 31 | s6dns_message_rr_t rr ; 32 | if (!s6dns_message_parse_getrr(&rr, packet, packetlen, &pos)) return 0 ; 33 | if (rr.rclass == S6DNS_C_IN) 34 | { 35 | int r = (*f)(&rr, packet, packetlen, pos, section, data) ; 36 | if (r < 1) return r ; 37 | } 38 | section = s6dns_message_parse_next(&counts, &rr, packet, packetlen, &pos) ; 39 | } 40 | return 1 + gotans ; 41 | } 42 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_a.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_message_parse_answer_a (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 8 | { 9 | if ((section == 2) && (rr->rtype == S6DNS_T_A) && (rr->rdlength == 4)) 10 | { 11 | stralloc *data = stuff ; 12 | if (!stralloc_catb(data, packet+pos, 4)) return -1 ; 13 | } 14 | (void)packetlen ; 15 | return 1 ; 16 | } 17 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_aaaa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_message_parse_answer_aaaa (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 8 | { 9 | if ((section == 2) && (rr->rtype == S6DNS_T_AAAA) && (rr->rdlength == 16)) 10 | { 11 | stralloc *data = stuff ; 12 | if (!stralloc_catb(data, packet + pos, 16)) return -1 ; 13 | } 14 | (void)packetlen ; 15 | return 1 ; 16 | } 17 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_caa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_message_parse_answer_caa (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 8 | { 9 | if ((section == 2) && (rr->rtype == S6DNS_T_CAA)) 10 | { 11 | genalloc *data = stuff ; 12 | s6dns_message_rr_caa_t caa ; 13 | if (!s6dns_message_get_caa(&caa, packet, packetlen, &pos, rr->rdlength)) return 0 ; 14 | if (!genalloc_append(s6dns_message_rr_caa_t, data, &caa)) return -1 ; 15 | } 16 | return 1 ; 17 | } 18 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_domain.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | 10 | int s6dns_message_parse_answer_domain (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 11 | { 12 | s6dns_dpag_t *data = stuff ; 13 | if ((section == 2) && (rr->rtype == data->rtype)) 14 | { 15 | s6dns_domain_t d ; 16 | unsigned int start = pos ; 17 | if (!s6dns_message_get_domain(&d, packet, packetlen, &pos)) return 0 ; 18 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 19 | if (!genalloc_append(s6dns_domain_t, &data->ds, &d)) return -1 ; 20 | } 21 | return 1 ; 22 | } 23 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_hinfo.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | #include 10 | 11 | int s6dns_message_parse_answer_hinfo (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 12 | { 13 | if ((section == 2) && (rr->rtype == S6DNS_T_HINFO)) 14 | { 15 | genalloc *data = stuff ; 16 | s6dns_message_rr_hinfo_t hinfo ; 17 | unsigned int start = pos ; 18 | if (!s6dns_message_get_hinfo(&hinfo, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | if (!genalloc_append(s6dns_message_rr_hinfo_t, data, &hinfo)) return -1 ; 21 | } 22 | return 1 ; 23 | } 24 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_mx.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | #include 10 | 11 | int s6dns_message_parse_answer_mx (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 12 | { 13 | if ((section == 2) && (rr->rtype == S6DNS_T_MX)) 14 | { 15 | genalloc *data = stuff ; 16 | s6dns_message_rr_mx_t mx ; 17 | unsigned int start = pos ; 18 | if (!s6dns_message_get_mx(&mx, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | if (!genalloc_append(s6dns_message_rr_mx_t, data, &mx)) return -1 ; 21 | } 22 | return 1 ; 23 | } 24 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_soa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | #include 10 | 11 | int s6dns_message_parse_answer_soa (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 12 | { 13 | if ((section == 2) && (rr->rtype == S6DNS_T_SOA)) 14 | { 15 | genalloc *data = stuff ; 16 | s6dns_message_rr_soa_t soa ; 17 | unsigned int start = pos ; 18 | if (!s6dns_message_get_soa(&soa, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | if (!genalloc_append(s6dns_message_rr_soa_t, data, &soa)) return -1 ; 21 | } 22 | return 1 ; 23 | } 24 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_srv.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | 8 | #include 9 | #include 10 | 11 | int s6dns_message_parse_answer_srv (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 12 | { 13 | if ((section == 2) && (rr->rtype == S6DNS_T_SRV)) 14 | { 15 | genalloc *data = stuff ; 16 | s6dns_message_rr_srv_t srv ; 17 | unsigned int start = pos ; 18 | if (!s6dns_message_get_srv(&srv, packet, packetlen, &pos)) return 0 ; 19 | if (rr->rdlength != pos - start) return (errno = EPROTO, 0) ; 20 | if (!genalloc_append(s6dns_message_rr_srv_t, data, &srv)) return -1 ; 21 | } 22 | return 1 ; 23 | } 24 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_answer_strings.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | #include 9 | 10 | #include 11 | 12 | int s6dns_message_parse_answer_strings (s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int pos, unsigned int section, void *stuff) 13 | { 14 | s6dns_mpag_t *data = stuff ; 15 | if ((section == 2) && (rr->rtype == data->rtype)) 16 | { 17 | size_t base = data->sa.len ; 18 | int wasnull = !data->sa.s ; 19 | unsigned int start = pos ; 20 | int r ; 21 | if (!stralloc_readyplus(&data->sa, rr->rdlength + 1)) return -1 ; 22 | r = s6dns_message_get_strings(data->sa.s + data->sa.len, rr->rdlength, packet, packetlen, &pos) ; 23 | if ((r < 0) || (rr->rdlength != pos - start)) 24 | { 25 | if (wasnull) stralloc_free(&data->sa) ; else data->sa.len = base ; 26 | return (errno = EPROTO, 0) ; 27 | } 28 | if (!genalloc_append(size_t, &data->offsets, &data->sa.len)) 29 | { 30 | if (wasnull) stralloc_free(&data->sa) ; else data->sa.len = base ; 31 | return (errno = EPROTO, -1) ; 32 | } 33 | data->sa.len += r ; 34 | stralloc_0(&data->sa) ; 35 | } 36 | return 1 ; 37 | } 38 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_getrr.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | 11 | int s6dns_message_parse_getrr (s6dns_message_rr_t_ref rr, char const *packet, unsigned int packetlen, unsigned int *pos) 12 | { 13 | if (!s6dns_message_get_domain(&rr->name, packet, packetlen, pos)) return 0 ; 14 | if (*pos + 10 > packetlen) return (errno = EPROTO, 0) ; 15 | uint16_unpack_big(packet + *pos, &rr->rtype) ; *pos += 2 ; 16 | uint16_unpack_big(packet + *pos, &rr->rclass) ; *pos += 2 ; 17 | uint32_unpack_big(packet + *pos, &rr->ttl) ; *pos += 4 ; 18 | uint16_unpack_big(packet + *pos, &rr->rdlength) ; *pos += 2 ; 19 | if (*pos + rr->rdlength > packetlen) return (errno = EPROTO, 0) ; 20 | return 1 ; 21 | } 22 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_init.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | 9 | int s6dns_message_parse_init (s6dns_message_header_t *h, s6dns_message_counts_t *counts, char const *packet, unsigned int packetlen, unsigned int *pos) 10 | { 11 | if (packetlen < 12) return (errno = EPROTO, 0) ; 12 | s6dns_message_header_unpack(packet, h) ; 13 | *counts = h->counts ; 14 | *pos = 12 ; 15 | return 1 ; 16 | } 17 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_next.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | unsigned int s6dns_message_parse_next (s6dns_message_counts_t *counts, s6dns_message_rr_t const *rr, char const *packet, unsigned int packetlen, unsigned int *pos) 6 | { 7 | *pos += rr->rdlength ; 8 | (void)packet ; (void)packetlen ; 9 | return s6dns_message_counts_next(counts) ; 10 | } 11 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_question.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include 12 | 13 | int s6dns_message_parse_question (s6dns_message_counts_t *counts, s6dns_domain_t *name, uint16_t *qtypep, char const *packet, unsigned int packetlen, unsigned int *pos) 14 | { 15 | s6dns_domain_t d ; 16 | uint16_t qtype ; 17 | uint16_t qclass ; 18 | if (!counts->qd) return (errno = EINVAL, 0) ; 19 | if (!s6dns_message_get_domain(&d, packet, packetlen, pos)) return 0 ; 20 | if (*pos + 4 > packetlen) return (errno = EPROTO, 0) ; 21 | uint16_unpack_big(packet + *pos, &qtype) ; *pos += 2 ; 22 | uint16_unpack_big(packet + *pos, &qclass) ; *pos += 2 ; 23 | if (qclass != S6DNS_C_IN) return (errno = ENOTSUP, 0) ; 24 | counts->qd-- ; 25 | *name = d ; 26 | *qtypep = qtype ; 27 | return 1 ; 28 | } 29 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_message_parse_skipqd.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | unsigned int s6dns_message_parse_skipqd (s6dns_message_counts_t *counts, char const *packet, unsigned int packetlen, unsigned int *pos) 6 | { 7 | for (;;) 8 | { 9 | unsigned int r = s6dns_message_counts_next(counts) ; 10 | if (r != 1) return r ; 11 | if (!s6dns_message_get_domain_nodecode(0, 255, packet, packetlen, pos)) return 0 ; 12 | *pos += 4 ; 13 | } 14 | } 15 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_rci_free.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | void s6dns_rci_free (s6dns_rci_t *rci) 7 | { 8 | stralloc_free(&rci->rules) ; 9 | *rci = s6dns_rci_zero ; 10 | } 11 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_rci_here.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | s6dns_rci_t s6dns_rci_here = S6DNS_RCI_ZERO ; 6 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_rci_zero.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | s6dns_rci_t const s6dns_rci_zero = S6DNS_RCI_ZERO ; 6 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolve_core.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | int s6dns_resolve_core_r (s6dns_domain_t const *d, uint16_t qtype, s6dns_engine_t *dt, s6dns_ip46list_t const *servers, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 9 | { 10 | if (!s6dns_engine_init_r(dt, servers, S6DNS_O_RECURSIVE, d->s, d->len, qtype, dbh, deadline, stamp)) return 0 ; 11 | if (!s6dns_resolve_loop_r(dt, deadline, stamp)) 12 | { 13 | s6dns_engine_recycle(dt) ; 14 | return 0 ; 15 | } 16 | return 1 ; 17 | } 18 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolve_dpag.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | int s6dns_resolve_dpag_r (genalloc *ds, char const *name, unsigned int len, uint16_t qtype, int qualif, s6dns_engine_t *dt, s6dns_rci_t const *rci, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 6 | { 7 | s6dns_dpag_t data ; 8 | int r ; 9 | data.ds = *ds ; 10 | data.rtype = qtype ; 11 | r = s6dns_resolve_r(name, len, qtype, &s6dns_message_parse_answer_domain, &data, qualif, dt, rci, dbh, deadline, stamp) ; 12 | *ds = data.ds ; 13 | return r ; 14 | } 15 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolve_mpag.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | int s6dns_resolve_mpag_r (stralloc *sa, genalloc *offsets, char const *name, unsigned int len, uint16_t qtype, s6dns_message_rr_func_ref parsefunc, int qualif, s6dns_engine_t *dt, s6dns_rci_t const *rci, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 6 | { 7 | s6dns_mpag_t data ; 8 | int r ; 9 | data.sa = *sa ; 10 | data.offsets = *offsets ; 11 | data.rtype = qtype ; 12 | r = s6dns_resolve_r(name, len, qtype, parsefunc, &data, qualif, dt, rci, dbh, deadline, stamp) ; 13 | *sa = data.sa ; 14 | *offsets = data.offsets ; 15 | return r ; 16 | } 17 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolve_name4.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_resolve_name4_r (genalloc *list, char const *ip, s6dns_engine_t *dt, s6dns_ip46list_t const *servers, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 8 | { 9 | s6dns_dpag_t data ; 10 | s6dns_domain_t d ; 11 | int r ; 12 | s6dns_domain_arpafromip4(&d, ip) ; 13 | s6dns_domain_encode(&d) ; 14 | data.ds = *list ; 15 | data.rtype = S6DNS_T_PTR ; 16 | r = s6dns_resolve_parse_r(&d, data.rtype, &s6dns_message_parse_answer_domain, &data, dt, servers, dbh, deadline, stamp) ; 17 | *list = data.ds ; 18 | return r ; 19 | } 20 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolve_name6.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_resolve_name6_r (genalloc *list, char const *ip, s6dns_engine_t *dt, s6dns_ip46list_t const *servers, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 8 | { 9 | s6dns_dpag_t data ; 10 | s6dns_domain_t d ; 11 | int r ; 12 | s6dns_domain_arpafromip6(&d, ip, 128) ; 13 | s6dns_domain_encode(&d) ; 14 | data.ds = *list ; 15 | data.rtype = S6DNS_T_PTR ; 16 | r = s6dns_resolve_parse_r(&d, data.rtype, &s6dns_message_parse_answer_domain, &data, dt, servers, dbh, deadline, stamp) ; 17 | *list = data.ds ; 18 | return r ; 19 | } 20 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolve_parse.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | int s6dns_resolve_parse_r (s6dns_domain_t const *d, uint16_t qtype, s6dns_message_rr_func_ref parsefunc, void *data, s6dns_engine_t *dt, s6dns_ip46list_t const *servers, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 8 | { 9 | int r ; 10 | if (!s6dns_resolve_core_r(d, qtype, dt, servers, dbh, deadline, stamp)) return -1 ; 11 | { 12 | s6dns_message_header_t h ; 13 | r = s6dns_message_parse(&h, s6dns_engine_packet(dt), s6dns_engine_packetlen(dt), parsefunc, data) ; 14 | } 15 | s6dns_engine_recycle(dt) ; 16 | return r ; 17 | } 18 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolven_loop.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | /* 10 | This is basically a synchronous interface to s6dns_engine. 11 | It resolves n dts at the same time. 12 | */ 13 | 14 | int s6dns_resolven_loop (s6dns_engine_t *dt, unsigned int n, unsigned int or, tain const *deadline, tain *stamp) 15 | { 16 | iopause_fd x[n] ; 17 | unsigned int count = 0 ; 18 | unsigned int got = 0 ; 19 | while (got < n) 20 | { 21 | tain localdeadline = *deadline ; 22 | int r ; 23 | unsigned int i = 0 ; 24 | unsigned int j = 0 ; 25 | for (; i < n ; i++) if (dt[i].status == EAGAIN) 26 | { 27 | s6dns_engine_nextdeadline(dt + i, &localdeadline) ; 28 | x[j].fd = dt[i].fd ; 29 | x[j].events = (s6dns_engine_isreadable(dt + i) ? IOPAUSE_READ : 0) | (s6dns_engine_iswritable(dt + i) ? IOPAUSE_WRITE : 0) ; 30 | j++ ; 31 | } 32 | if (!j) break ; 33 | r = iopause_stamp(x, j, &localdeadline, stamp) ; 34 | if (r < 0) return -1 ; 35 | else if (!r) 36 | { 37 | if (tain_less(deadline, stamp)) return (errno = ETIMEDOUT, -1) ; 38 | for (i = 0 ; i < n ; i++) if (dt[i].status == EAGAIN && s6dns_engine_timeout(dt + i, stamp)) 39 | { 40 | got++ ; 41 | if (or >= 2) return i ; 42 | } 43 | } 44 | else 45 | { 46 | for (i = 0 ; i < n ; i++) if (dt[i].status == EAGAIN) 47 | { 48 | r = s6dns_engine_event(dt + i, stamp) ; 49 | if (r) 50 | { 51 | got++ ; 52 | if (r > 0) count++ ; 53 | if (or && (r > 0 || or >= 2)) return i ; 54 | } 55 | } 56 | } 57 | } 58 | return or ? (errno = ENOENT, -1) : count ; 59 | } 60 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolven_parse.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | int s6dns_resolven_parse_r (s6dns_resolve_t *list, unsigned int n, s6dns_ip46list_t const *servers, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 9 | { 10 | s6dns_engine_t dtl[n] ; 11 | unsigned int i = 0 ; 12 | for (; i < n ; i++) list[i].status = ECONNABORTED ; 13 | for (i = 0 ; i < n ; i++) 14 | { 15 | dtl[i] = s6dns_engine_zero ; 16 | if (!s6dns_engine_init_r(dtl + i, servers, list[i].options, list[i].q.s, list[i].q.len, list[i].qtype, dbh, &list[i].deadline, stamp)) 17 | { 18 | list[i].status = errno ; 19 | s6dns_engine_freen(dtl, i) ; 20 | return 0 ; 21 | } 22 | list[i].status = EAGAIN ; 23 | } 24 | 25 | if (s6dns_resolven_loop(dtl, n, 0, deadline, stamp) < 0) goto err ; 26 | 27 | for (i = 0 ; i < n ; i++) 28 | { 29 | if (dtl[i].status) list[i].status = dtl[i].status ; 30 | else 31 | { 32 | s6dns_message_header_t h ; 33 | int r = s6dns_message_parse(&h, s6dns_engine_packet(dtl + i), s6dns_engine_packetlen(dtl + i), list[i].parsefunc, list[i].data) ; 34 | if (r < 0) goto err ; 35 | list[i].status = r ? 0 : errno ; 36 | } 37 | } 38 | s6dns_engine_freen(dtl, n) ; 39 | return 1 ; 40 | 41 | err: 42 | s6dns_engine_freen(dtl, n) ; 43 | return 0 ; 44 | } 45 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolvenoq.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | int s6dns_resolvenoq_r (char const *name, size_t len, uint16_t qtype, s6dns_message_rr_func_ref parsefunc, void *data, s6dns_engine_t *dt, s6dns_ip46list_t const *servers, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 7 | { 8 | s6dns_domain_t d ; 9 | if (!s6dns_domain_fromstring_noqualify_encode(&d, name, len)) return -1 ; 10 | return s6dns_resolve_parse_r(&d, qtype, parsefunc, data, dt, servers, dbh, deadline, stamp) ; 11 | } 12 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolvenoq_aaaaa.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include 12 | #include 13 | 14 | int s6dns_resolvenoq_aaaaa_r (genalloc *ips, char const *name, size_t len, s6dns_ip46list_t const *servers, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 15 | { 16 | stralloc sa[2] = { STRALLOC_ZERO, STRALLOC_ZERO } ; 17 | s6dns_resolve_t blob[2] ; 18 | if (!s6dns_domain_fromstring_noqualify_encode(&blob[0].q, name, len)) return -1 ; 19 | blob[0].qtype = S6DNS_T_AAAA ; 20 | blob[0].options = S6DNS_O_RECURSIVE ; 21 | blob[0].deadline = *deadline ; 22 | blob[0].parsefunc = &s6dns_message_parse_answer_aaaa ; 23 | blob[0].data = &sa[0] ; 24 | blob[1].q = blob[0].q ; 25 | blob[1].qtype = S6DNS_T_A ; 26 | blob[1].options = S6DNS_O_RECURSIVE ; 27 | blob[1].deadline = *deadline ; 28 | blob[1].parsefunc = &s6dns_message_parse_answer_a ; 29 | blob[1].data = &sa[1] ; 30 | if (!s6dns_resolven_parse_r(blob, 2, servers, dbh, deadline, stamp)) return -1 ; 31 | if (!sa[0].len && !sa[1].len) 32 | { 33 | errno = blob[1].status ? blob[1].status : blob[0].status ; 34 | return 0 ; 35 | } 36 | if (!genalloc_readyplus(ip46full, ips, (sa[0].len >> 4) + (sa[1].len >> 2))) 37 | { 38 | stralloc_free(&sa[0]) ; 39 | stralloc_free(&sa[1]) ; 40 | return -1 ; 41 | } 42 | { 43 | int e = (!!sa[0].len << 1) | !!sa[1].len ; 44 | size_t n = genalloc_len(ip46full, ips) ; 45 | size_t i = 0 ; 46 | for (; i < (sa[0].len >> 4) ; i++) 47 | ip46full_from_ip6(genalloc_s(ip46full, ips) + n + i, sa[0].s + (i << 4)) ; 48 | n += i ; 49 | for (i = 0 ; i < (sa[1].len >> 2) ; i++) 50 | ip46full_from_ip4(genalloc_s(ip46full, ips) + n + i, sa[1].s + (i << 2)) ; 51 | n += i ; 52 | genalloc_setlen(ip46full, ips, n) ; 53 | stralloc_free(&sa[0]) ; 54 | stralloc_free(&sa[1]) ; 55 | return e ; 56 | } 57 | } 58 | -------------------------------------------------------------------------------- /src/libs6dns/s6dns_resolveq.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | #include 9 | #include 10 | #include 11 | 12 | int s6dns_resolveq_r (char const *name, size_t len, uint16_t qtype, s6dns_message_rr_func_ref parsefunc, void *data, s6dns_rci_t const *rci, s6dns_debughook_t const *dbh, tain const *deadline, tain *stamp) 13 | { 14 | s6dns_engine_t dtl[rci->rulesnum] ; 15 | unsigned int best = 0 ; 16 | unsigned int n ; 17 | int e = 0 ; 18 | unsigned int i = 0 ; 19 | { 20 | s6dns_domain_t domains[rci->rulesnum] ; 21 | n = s6dns_domain_fromstring_qualify_encode(domains, name, len, rci->rules.s, rci->rulesnum) ; 22 | if (!n) return -1 ; 23 | for (; i < n ; i++) 24 | { 25 | dtl[i] = s6dns_engine_zero ; 26 | if (!s6dns_engine_init_r(dtl + i, &rci->servers, S6DNS_O_RECURSIVE, domains[i].s, domains[i].len, qtype, dbh, deadline, stamp)) 27 | { 28 | s6dns_engine_freen(dtl, i) ; 29 | return -1 ; 30 | } 31 | } 32 | } 33 | 34 | /* 35 | Wait until the "best" answer arrives, then scan until a positive answer 36 | is found. 37 | 38 | dtl[i].status == EAGAIN : query still pending 39 | other nonzero dtl[i].status : error, give up 40 | dtl[i].status == 0 : answer #i has arrived, in which case parse it; 41 | r < 0 : error, give up 42 | r > 0 : positive answer, return it 43 | r == 0 : negative answer. If it's non-fatal (i.e. NXDOMAIN), 44 | then move on to the next best FQDN. 45 | */ 46 | 47 | for (;;) 48 | { 49 | int k = s6dns_resolven_loop(dtl, n, 1, deadline, stamp) ; 50 | if (k < 0) goto err ; 51 | if ((unsigned int)k == best) 52 | { 53 | for (;; best++) 54 | { 55 | s6dns_message_header_t h ; 56 | int r ; 57 | if (best >= n) goto notfound ; 58 | if (error_isagain(dtl[best].status)) break ; 59 | if (dtl[best].status) { errno = dtl[best].status ; goto err ; } 60 | r = s6dns_message_parse(&h, s6dns_engine_packet(dtl + best), s6dns_engine_packetlen(dtl + best), parsefunc, data) ; 61 | if (r < 0) goto err ; 62 | else if (r) goto found ; 63 | else switch (errno) 64 | { 65 | case EBUSY : 66 | case ENOENT : 67 | case ECONNREFUSED : 68 | case EIO : 69 | break ; 70 | default : goto err ; 71 | } 72 | if (!best) e = errno ; 73 | } 74 | } 75 | } 76 | 77 | found: 78 | s6dns_engine_freen(dtl, n) ; 79 | return 1 ; 80 | 81 | notfound: 82 | s6dns_engine_freen(dtl, n) ; 83 | return (errno = e, 0) ; 84 | 85 | err: 86 | s6dns_engine_freen(dtl, n) ; 87 | return -1 ; 88 | } 89 | -------------------------------------------------------------------------------- /src/skadns/deps-exe/skadnsd: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | ${SOCKET_LIB} 4 | ${SYSCLOCK_LIB} 5 | -------------------------------------------------------------------------------- /src/skadns/deps-lib/skadns: -------------------------------------------------------------------------------- 1 | skadns_cancel.o 2 | skadns_end.o 3 | skadns_packet.o 4 | skadns_packetlen.o 5 | skadns_release.o 6 | skadns_send.o 7 | skadns_start.o 8 | skadns_startf.o 9 | skadns_update.o 10 | skadns_zero.o 11 | -lskarnet 12 | -------------------------------------------------------------------------------- /src/skadns/skadns_cancel.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | #include 9 | #include 10 | #include 11 | 12 | #include 13 | 14 | int skadns_cancel (skadns_t *a, uint16_t id, tain const *deadline, tain *stamp) 15 | { 16 | int e = errno ; 17 | char pack[3] = "--q" ; 18 | skadnsanswer_t *p = GENSETDYN_P(skadnsanswer_t, &a->q, id) ; 19 | if (!error_isagain(p->status)) return skadns_release(a, id) ; 20 | uint16_pack_big(pack, id) ; 21 | if (textclient_command(&a->connection, pack, 3, deadline, stamp)) 22 | return gensetdyn_delete(&a->q, id) ; 23 | if (errno != ENOENT) return 0 ; 24 | p->status = ECANCELED ; 25 | errno = e ; 26 | return 1 ; 27 | } 28 | -------------------------------------------------------------------------------- /src/skadns/skadns_end.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #include 11 | 12 | static int skadnsanswer_free (void *p, void *stuff) 13 | { 14 | skadnsanswer_t *q = p ; 15 | alloc_free(q->data) ; 16 | (void)stuff ; 17 | return 1 ; 18 | } 19 | 20 | void skadns_end (skadns_t *a) 21 | { 22 | textclient_end(&a->connection) ; 23 | genalloc_free(uint16_t, &a->list) ; 24 | gensetdyn_iter(&a->q, &skadnsanswer_free, 0) ; 25 | gensetdyn_free(&a->q) ; 26 | *a = skadns_zero ; 27 | } 28 | -------------------------------------------------------------------------------- /src/skadns/skadns_packet.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | 7 | char const *skadns_packet (skadns_t const *a, uint16_t id) 8 | { 9 | skadnsanswer_t *p = GENSETDYN_P(skadnsanswer_t, &a->q, id) ; 10 | switch (p->status) 11 | { 12 | case 0 : return (char const *)p->data ; 13 | default : return (errno = p->status, (char const *)0) ; 14 | } 15 | } 16 | -------------------------------------------------------------------------------- /src/skadns/skadns_packetlen.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | 9 | int skadns_packetlen (skadns_t const *a, uint16_t id) 10 | { 11 | skadnsanswer_t *p = GENSETDYN_P(skadnsanswer_t, &a->q, id) ; 12 | switch (p->status) 13 | { 14 | case 0 : return p->len ; 15 | default : return (errno = p->status, -1) ; 16 | } 17 | } 18 | -------------------------------------------------------------------------------- /src/skadns/skadns_release.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | #include 8 | #include 9 | 10 | #include 11 | 12 | int skadns_release (skadns_t *a, uint16_t id) 13 | { 14 | skadnsanswer_t *p = GENSETDYN_P(skadnsanswer_t, &a->q, id) ; 15 | switch (p->status) 16 | { 17 | case 0 : 18 | alloc_free(p->data) ; p->data = 0 ; p->len = 0 ; 19 | break ; 20 | case EAGAIN : 21 | case ECANCELED : 22 | return (errno = EBUSY, 0) ; 23 | case EINVAL : 24 | return (errno = EINVAL, 0) ; 25 | default : break ; 26 | } 27 | p->status = EINVAL ; 28 | return gensetdyn_delete(&a->q, id) ; 29 | } 30 | -------------------------------------------------------------------------------- /src/skadns/skadns_send.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | 8 | #include 9 | #include 10 | #include 11 | 12 | #include 13 | 14 | 15 | int skadns_send (skadns_t *a, uint16_t *u, s6dns_domain_t const *d, uint16_t qtype, tain const *limit, tain const *deadline, tain *stamp) 16 | { 17 | static skadnsanswer_t const skadnsanswer_initial = { .status = EAGAIN, .data = 0, .len = 0 } ; 18 | uint32_t i ; 19 | char tmp[17] = "--Q" ; 20 | struct iovec v[2] = { { .iov_base = tmp, .iov_len = 17 }, { .iov_base = (void *)d->s, .iov_len = d->len } } ; 21 | if (!gensetdyn_new(&a->q, &i)) return 0 ; 22 | if (i > UINT16_MAX) 23 | { 24 | gensetdyn_delete(&a->q, i) ; 25 | return (errno = EMFILE, 0) ; 26 | } 27 | uint16_pack_big(tmp, (uint16_t)i) ; 28 | uint16_pack_big(tmp + 3, qtype) ; 29 | if (limit) tain_pack(tmp + 5, limit) ; else memset(tmp + 5, 0, 12) ; 30 | if (!textclient_commandv(&a->connection, v, 2, deadline, stamp)) 31 | { 32 | int e = errno ; 33 | gensetdyn_delete(&a->q, i) ; 34 | errno = e ; 35 | return 0 ; 36 | } 37 | *GENSETDYN_P(skadnsanswer_t, &a->q, i) = skadnsanswer_initial ; 38 | *u = i ; 39 | return 1 ; 40 | } 41 | -------------------------------------------------------------------------------- /src/skadns/skadns_start.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | 7 | int skadns_start (skadns_t *a, char const *path, tain const *deadline, tain *stamp) 8 | { 9 | return textclient_start(&a->connection, path, 0, SKADNS_BANNER1, SKADNS_BANNER1_LEN, SKADNS_BANNER2, SKADNS_BANNER2_LEN, deadline, stamp) ; 10 | } 11 | -------------------------------------------------------------------------------- /src/skadns/skadns_startf.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | 6 | #include 7 | 8 | int skadns_startf (skadns_t *a, tain const *deadline, tain *stamp) 9 | { 10 | static char const *const cargv[2] = { SKADNSD_PROG, 0 } ; 11 | return textclient_startf(&a->connection, cargv, (char const *const *)environ, TEXTCLIENT_OPTION_WAITPID, SKADNS_BANNER1, SKADNS_BANNER1_LEN, SKADNS_BANNER2, SKADNS_BANNER2_LEN, deadline, stamp) ; 12 | } 13 | -------------------------------------------------------------------------------- /src/skadns/skadns_update.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | #include 6 | #include 7 | #include 8 | #include 9 | 10 | #include 11 | #include 12 | #include 13 | #include 14 | #include 15 | #include 16 | #include 17 | 18 | #include 19 | 20 | static int msghandler (struct iovec const *v, void *context) 21 | { 22 | skadns_t *a = (skadns_t *)context ; 23 | char const *s = v->iov_base ; 24 | skadnsanswer_t *p ; 25 | uint16_t id ; 26 | if (v->iov_len < 3) return (errno = EPROTO, 0) ; 27 | uint16_unpack_big(s, &id) ; 28 | p = GENSETDYN_P(skadnsanswer_t, &a->q, id) ; 29 | if (p->status == ECANCELED) 30 | { 31 | p->status = EINVAL ; 32 | return gensetdyn_delete(&a->q, id) ; 33 | } 34 | if (!error_isagain(p->status)) return (errno = EINVAL, 0) ; 35 | if (!genalloc_readyplus(uint16_t, &a->list, 1)) return 0 ; 36 | if (!s[2]) 37 | { 38 | p->data = alloc(v->iov_len-3) ; 39 | if (!p->data) return 0 ; 40 | memcpy(p->data, s+3, v->iov_len-3) ; 41 | p->len = v->iov_len-3 ; 42 | } 43 | p->status = (unsigned char)s[2] ; 44 | genalloc_append(uint16_t, &a->list, &id) ; 45 | return 1 ; 46 | } 47 | 48 | int skadns_update (skadns_t *a) 49 | { 50 | genalloc_setlen(uint16_t, &a->list, 0) ; 51 | return textclient_update(&a->connection, &msghandler, a) ; 52 | } 53 | -------------------------------------------------------------------------------- /src/skadns/skadns_zero.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | 5 | skadns_t const skadns_zero = SKADNS_ZERO ; 6 | -------------------------------------------------------------------------------- /src/utilities/deps-exe/s6-dns-hosts-compile: -------------------------------------------------------------------------------- 1 | ${LIBS6DNS} 2 | -lskarnet 3 | -------------------------------------------------------------------------------- /src/utilities/s6-dns-hosts-compile.c: -------------------------------------------------------------------------------- 1 | /* ISC license. */ 2 | 3 | #include 4 | #include 5 | #include 6 | #include 7 | #include 8 | 9 | #include 10 | #include 11 | #include 12 | 13 | #include 14 | 15 | #define USAGE "s6-dns-hosts-compile [ -i ifile ] [ -o ofile ]" 16 | #define dieusage() strerr_dieusage(100, USAGE) 17 | 18 | int main (int argc, char const *const *argv) 19 | { 20 | char const *ifile = "/etc/hosts" ; 21 | char const *ofile = "/etc/hosts.cdb" ; 22 | PROG = "s6-dns-hosts-compile" ; 23 | { 24 | subgetopt l = SUBGETOPT_ZERO ; 25 | for (;;) 26 | { 27 | int opt = subgetopt_r(argc, argv, "i:o:", &l) ; 28 | if (opt == -1) break ; 29 | switch (opt) 30 | { 31 | case 'i' : ifile = l.arg ; break ; 32 | case 'o' : ofile = l.arg ; break ; 33 | default : dieusage() ; 34 | } 35 | } 36 | argc -= l.ind ; argv += l.ind ; 37 | } 38 | 39 | { 40 | int fdr, fdw ; 41 | size_t len = strlen(ofile) ; 42 | char tmp[len + 29] ; 43 | memcpy(tmp, ofile, len) ; 44 | memcpy(tmp + len, ":s6-dns-hosts-compile:XXXXXX", 29) ; 45 | fdr = openc_read(ifile) ; 46 | if (fdr == -1) strerr_diefu2sys(111, "open ", ifile) ; 47 | fdw = mkstemp(tmp) ; 48 | if (fdw == -1) strerr_diefu2sys(111, "create ", tmp) ; 49 | if (!s6dns_hosts_compile(fdr, fdw)) 50 | { 51 | unlink_void(tmp) ; 52 | strerr_diefu2sys(111, "compile ", ifile) ; 53 | } 54 | if (fsync(fdw) == -1) 55 | { 56 | unlink_void(tmp) ; 57 | strerr_diefu2sys(111, "fsync ", tmp) ; 58 | } 59 | if (fchmod(fdw, 0644) == -1) 60 | { 61 | unlink_void(tmp) ; 62 | strerr_diefu2sys(111, "fchmod ", tmp) ; 63 | } 64 | if (rename(tmp, ofile) == -1) 65 | { 66 | unlink_void(tmp) ; 67 | strerr_diefu4sys(111, "rename ", tmp, " to ", ofile) ; 68 | } 69 | } 70 | return 0 ; 71 | } 72 | -------------------------------------------------------------------------------- /tools/gen-configure.el: -------------------------------------------------------------------------------- 1 | #!/command/execlineb -S0 2 | 3 | # For dev use only. Don't run this, it overwrites your configure. 4 | 5 | # The quoting interactions in sed and sh make it impossible to get 6 | # such a simple thing done. It's amazing how bad traditional Unix is. 7 | 8 | backtick -E TEMPLATE { redirfd -r 0 tools/configure.template s6-cat } 9 | s6-envdir -Lf package/configure-snippets 10 | multisubstitute 11 | { 12 | importas -uS configure_help_install 13 | importas -uS configure_help_dependencies 14 | importas -uS configure_help_options 15 | importas -uS configure_init_vars 16 | importas -uS configure_case_lines 17 | importas -uS configure_expand_dirs 18 | importas -uS configure_slashpackage_other 19 | importas -uS configure_extra_checks 20 | importas -uS configure_generate_make 21 | importas -uS configure_generate_configh 22 | } 23 | 24 | if 25 | { 26 | redirfd -w 1 configure.new 27 | if { heredoc 0 ${TEMPLATE} s6-cat } 28 | s6-echo 29 | } 30 | 31 | if { s6-chmod 0755 configure.new } 32 | s6-rename configure.new configure 33 | -------------------------------------------------------------------------------- /tools/gen-deps.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh -e 2 | 3 | . package/info 4 | 5 | echo '#' 6 | echo '# This file has been generated by tools/gen-deps.sh' 7 | echo '#' 8 | echo 9 | 10 | internal_libs= 11 | 12 | for dir in src/include/${package} src/* ; do 13 | for file in $(ls -1 $dir | grep -- \\.h$) ; do 14 | { 15 | grep -F -- "#include <${package}/" < ${dir}/$file | cut -d'<' -f2 | cut -d'>' -f1 ; 16 | grep -- '#include ".*\.h"' < ${dir}/$file | cut -d'"' -f2 17 | } | sort -u | { 18 | deps= 19 | while read dep ; do 20 | if echo $dep | grep -q "^${package}/" ; then 21 | deps="$deps src/include/$dep" 22 | elif test -f "${dir}/$dep" ; then 23 | deps="$deps ${dir}/$dep" 24 | else 25 | deps="$deps src/include-local/$dep" 26 | fi 27 | done 28 | if test -n "$deps" ; then 29 | echo "${dir}/${file}:${deps}" 30 | fi 31 | } 32 | done 33 | done 34 | 35 | for dir in src/* ; do 36 | for file in $(ls -1 $dir | grep -- \\.c$) ; do 37 | { 38 | grep -F -- "#include <${package}/" < ${dir}/$file | cut -d'<' -f2 | cut -d'>' -f1 ; 39 | grep -- '#include ".*\.h"' < ${dir}/$file | cut -d'"' -f2 40 | } | sort -u | { 41 | deps=" ${dir}/$file" 42 | while read dep ; do 43 | if echo $dep | grep -q "^${package}/" ; then 44 | deps="$deps src/include/$dep" 45 | elif test -f "${dir}/$dep" ; then 46 | deps="$deps ${dir}/$dep" 47 | else 48 | deps="$deps src/include-local/$dep" 49 | fi 50 | done 51 | o=$(echo $file | sed s/\\.c$/.o/) 52 | lo=$(echo $file | sed s/\\.c$/.lo/) 53 | echo "${dir}/${o} ${dir}/${lo}:${deps}" 54 | } 55 | done 56 | done 57 | echo 58 | 59 | for dir in $(ls -1 src | grep -v ^include) ; do 60 | for file in $(ls -1 src/$dir/deps-lib) ; do 61 | deps= 62 | libs= 63 | while read dep ; do 64 | if echo $dep | grep -q -e '^-l' -e '^\${.*_LIB}' ; then 65 | libs="$libs $dep" 66 | elif echo $dep | grep -q '^\${LIB' ; then 67 | deps="$deps $dep" 68 | else 69 | deps="$deps src/$dir/$dep" 70 | fi 71 | done < src/$dir/deps-lib/$file 72 | echo 'ifeq ($(strip $(STATIC_LIBS_ARE_PIC)),)' 73 | echo "lib${file}.a.xyzzy:${deps}" 74 | echo else 75 | echo "lib${file}.a.xyzzy:$(echo ${deps} | sed 's/\.o/.lo/g')" 76 | echo endif 77 | if grep -qE "^LIB_DEFS [+:]= .*=$file" package/targets.mak ; then 78 | echo "lib${file}.pc: EXTRA_LIBS :=${libs}" 79 | echo "lib${file}.so.xyzzy: EXTRA_LIBS :=$libs" 80 | echo "lib${file}.so.xyzzy:$(echo ${deps} | sed 's/\.o/.lo/g')" 81 | echo "lib${file}.dylib.xyzzy: EXTRA_LIBS :=$libs" 82 | echo "lib${file}.dylib.xyzzy:$(echo ${deps} | sed 's/\.o/.lo/g')" 83 | else 84 | internal_libs="$internal_libs lib${file}.a.xyzzy" 85 | fi 86 | done 87 | 88 | for file in $(ls -1 src/$dir/deps-exe) ; do 89 | deps= 90 | libs= 91 | while read dep ; do 92 | if echo $dep | grep -q \\.o$ ; then 93 | dep="src/$dir/$dep" 94 | fi 95 | if echo $dep | grep -qx '\${.*_LIB}' ; then 96 | libs="$libs $dep" 97 | else 98 | deps="$deps $dep" 99 | fi 100 | done < src/$dir/deps-exe/$file 101 | echo "$file: EXTRA_LIBS :=$libs" 102 | echo "$file: src/$dir/$file.o$deps" 103 | done 104 | done 105 | echo "INTERNAL_LIBS :=$internal_libs" 106 | -------------------------------------------------------------------------------- /tools/gen-dotpc.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh -e 2 | 3 | isunique () { 4 | x=$1 5 | set -- $2 6 | while test "$#" -gt 0 ; do 7 | if test "$x" = "$1" ; then 8 | return 1 9 | fi 10 | shift 11 | done 12 | return 0 13 | } 14 | 15 | uniqit () { 16 | res= 17 | while test "$#" -gt 0 ; do 18 | if isunique "$1" "$res" ; then 19 | res="${res}${res:+ }${1}" 20 | fi 21 | shift 22 | done 23 | printf %s\\n "$res" 24 | } 25 | 26 | filterout () { 27 | res= 28 | filter="$1" 29 | shift 30 | while test "$#" -gt 0 ; do 31 | if isunique "$1" "$filter" ; then 32 | res="${res}${res:+ }${1}" 33 | fi 34 | shift 35 | done 36 | printf %s\\n "$res" 37 | } 38 | 39 | print_requires () { 40 | line= 41 | oldifs="$IFS" 42 | while IFS=" " read condvar usedinlibs pkg ver libs ; do 43 | IFS="$oldifs" 44 | for h ; do 45 | i=lib${h##-l} 46 | for j in $libs ; do 47 | if test "$i" = "$j" ; then 48 | line="${line}${line:+, }${i} >= ${ver}" 49 | fi 50 | done 51 | done 52 | done < package/deps-build 53 | IFS="$oldifs" 54 | echo "Requires: $line" 55 | } 56 | 57 | . package/info 58 | 59 | ilist= 60 | dlist= 61 | slist= 62 | 63 | if test "${includedir}" != /usr/include ; then 64 | ilist="-I${includedir}" 65 | fi 66 | if test -n "${extra_includedirs}" ; then 67 | ilist="${ilist}${ilist:+ }${extra_includedirs}" 68 | fi 69 | ilist=`uniqit ${ilist}` 70 | 71 | if test "${dynlibdir}" != /usr/lib && test "${dynlibdir}" != /lib ; then 72 | dlist="-L${dynlibdir}" 73 | fi 74 | 75 | if test "${libdir}" != /usr/lib && test "${libdir}" != /lib ; then 76 | slist="-L${libdir}" 77 | fi 78 | if test -n "${extra_libdirs}" ; then 79 | slist="${slist}${slist:+ }${extra_libdirs}" 80 | fi 81 | slist="$(filterout "${dlist}" $(uniqit ${slist}))" 82 | 83 | echo "prefix=${prefix}" 84 | echo "includedir=${includedir}" 85 | echo "libdir=${libdir}" 86 | echo "dynlibdir=${dynlibdir}" 87 | echo 88 | echo "Name: lib${library}" 89 | echo "Version: ${version}" 90 | echo "Description: ${description:-The ${library} library.}" 91 | echo "URL: ${url:-https://skarnet.org/software/${package}/}" 92 | if test -n "${extra_libs}" ; then 93 | print_requires ${extra_libs} 94 | fi 95 | if test -n "$ilist" ; then 96 | echo "Cflags: ${ilist}" 97 | fi 98 | echo "Libs: ${dlist}${dlist:+ }-l${library}${ldlibs:+ }${ldlibs}" 99 | if test -n "${extra_libs}" ; then 100 | echo "Libs.private: ${slist}${slist:+ }${extra_libs}" 101 | fi 102 | -------------------------------------------------------------------------------- /tools/install.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh 2 | 3 | usage() { 4 | echo "usage: $0 [ -D ] [ -l ] [ -m mode ] [ -O owner:group ] src dst" 1>&2 5 | exit 1 6 | } 7 | 8 | mkdirp=false 9 | symlink=false 10 | mode=0755 11 | og= 12 | 13 | while getopts Dlm:O: name ; do 14 | case "$name" in 15 | D) mkdirp=true ;; 16 | l) symlink=true ;; 17 | m) mode=$OPTARG ;; 18 | O) og=$OPTARG ;; 19 | ?) usage ;; 20 | esac 21 | done 22 | shift $(($OPTIND - 1)) 23 | 24 | test "$#" -eq 2 || usage 25 | src=$1 26 | dst=$2 27 | tmp="$dst.tmp.$$" 28 | 29 | case "$dst" in 30 | */) echo "$0: $dst ends in /" 1>&2 ; exit 1 ;; 31 | esac 32 | 33 | set -C 34 | set -e 35 | 36 | if $mkdirp ; then 37 | umask 022 38 | case "$2" in 39 | */*) mkdir -p "${dst%/*}" ;; 40 | esac 41 | fi 42 | 43 | trap 'rm -f "$tmp"' EXIT INT QUIT TERM HUP 44 | 45 | umask 077 46 | 47 | if $symlink ; then 48 | ln -s "$src" "$tmp" 49 | else 50 | cat < "$1" > "$tmp" 51 | if test -n "$og" ; then 52 | chown -- "$og" "$tmp" 53 | fi 54 | chmod -- "$mode" "$tmp" 55 | fi 56 | 57 | mv -f "$tmp" "$dst" 58 | if test -d "$dst" ; then 59 | rm -f "$dst/$(basename $tmp)" 60 | if $symlink ; then 61 | mkdir "$tmp" 62 | ln -s "$src" "$tmp/$(basename $dst)" 63 | mv -f "$tmp/$(basename $dst)" "${dst%/*}" 64 | rmdir "$tmp" 65 | else 66 | echo "$0: $dst is a directory" 1>&2 67 | exit 1 68 | fi 69 | fi 70 | -------------------------------------------------------------------------------- /tools/run-test.sh: -------------------------------------------------------------------------------- 1 | #!/bin/sh -e 2 | 3 | prog="$1" 4 | 5 | if test -x "./src/tests/${prog}.wrapper" ; then 6 | cmd="./src/tests/${prog}.wrapper $prog" 7 | else 8 | cmd="./$prog" 9 | fi 10 | 11 | if test -r "./src/tests/${prog}.expected" ; then 12 | cp -f "./src/tests/${prog}.expected" "./${prog}.expected" 13 | elif test -x "./src/tests/${prog}.baseline" ; then 14 | "./src/tests/${prog}.baseline" > "./${prog}.expected" 15 | else 16 | echo "run-test.sh: fatal: missing baseline for $prog" 1>&2 ; exit 100 17 | fi 18 | 19 | $cmd | diff "./${prog}.expected" - 20 | 21 | rm -f "./${prog}.expected" 22 | echo "run-test.sh: info: $prog: pass" 1>&2 23 | --------------------------------------------------------------------------------