Home | History | Annotate | Line # | Download | only in dig
      1 /*	$NetBSD: dighost.h,v 1.5 2025/07/17 19:01:43 christos Exp $	*/
      2 
      3 /*
      4  * Copyright (C) Internet Systems Consortium, Inc. ("ISC")
      5  *
      6  * SPDX-License-Identifier: MPL-2.0
      7  *
      8  * This Source Code Form is subject to the terms of the Mozilla Public
      9  * License, v. 2.0. If a copy of the MPL was not distributed with this
     10  * file, you can obtain one at https://mozilla.org/MPL/2.0/.
     11  *
     12  * See the COPYRIGHT file distributed with this work for additional
     13  * information regarding copyright ownership.
     14  */
     15 
     16 #pragma once
     17 
     18 /*! \file */
     19 
     20 #include <inttypes.h>
     21 #include <stdbool.h>
     22 
     23 #include <isc/attributes.h>
     24 #include <isc/buffer.h>
     25 #include <isc/formatcheck.h>
     26 #include <isc/lang.h>
     27 #include <isc/list.h>
     28 #include <isc/loop.h>
     29 #include <isc/magic.h>
     30 #include <isc/mem.h>
     31 #include <isc/netmgr.h>
     32 #include <isc/refcount.h>
     33 #include <isc/sockaddr.h>
     34 #include <isc/time.h>
     35 
     36 #include <dns/rdatalist.h>
     37 
     38 #include <dst/dst.h>
     39 
     40 #ifdef __APPLE__
     41 #include <TargetConditionals.h>
     42 #endif /* ifdef __APPLE__ */
     43 
     44 #define MXSERV 20
     45 #define MXNAME (DNS_NAME_MAXTEXT + 1)
     46 #define MXRD   32
     47 /*% Buffer Size */
     48 #define BUFSIZE	 512
     49 #define COMMSIZE 0xffff
     50 #ifndef RESOLV_CONF
     51 /*% location of resolve.conf */
     52 #define RESOLV_CONF "/etc/resolv.conf"
     53 #endif /* ifndef RESOLV_CONF */
     54 /*% output buffer */
     55 #define OUTPUTBUF 32767
     56 /*% Max RR Limit */
     57 #define MAXRRLIMIT 0xffffffff
     58 #define MAXTIMEOUT 0xffff
     59 /*% Max number of tries */
     60 #define MAXTRIES 0xffffffff
     61 /*% Max number of dots */
     62 #define MAXNDOTS 0xffff
     63 /*% Max number of ports */
     64 #define MAXPORT 0xffff
     65 /*% Max serial number */
     66 #define MAXSERIAL 0xffffffff
     67 /*% Max query ID */
     68 #define MAXQID 0xffff
     69 
     70 /*% Default TCP Timeout */
     71 #define TCP_TIMEOUT 10
     72 /*% Default UDP Timeout */
     73 #define UDP_TIMEOUT 5
     74 
     75 #define SERVER_TIMEOUT 1
     76 
     77 #define LOOKUP_LIMIT 64
     78 
     79 #define DEFAULT_EDNS_VERSION 0
     80 #define DEFAULT_EDNS_BUFSIZE 1232
     81 
     82 #define DEFAULT_HTTPS_QUERY "?dns="
     83 
     84 /*%
     85  * Lookup_limit is just a limiter, keeping too many lookups from being
     86  * created.  It's job is mainly to prevent the program from running away
     87  * in a tight loop of constant lookups.  It's value is arbitrary.
     88  */
     89 
     90 ISC_LANG_BEGINDECLS
     91 
     92 typedef struct dig_lookup dig_lookup_t;
     93 typedef struct dig_query dig_query_t;
     94 typedef struct dig_server dig_server_t;
     95 typedef ISC_LIST(dig_server_t) dig_serverlist_t;
     96 typedef struct dig_searchlist dig_searchlist_t;
     97 
     98 #define DIG_LOOKUP_MAGIC ISC_MAGIC('D', 'i', 'g', 'l')
     99 
    100 #define DIG_VALID_LOOKUP(x) ISC_MAGIC_VALID((x), DIG_LOOKUP_MAGIC)
    101 
    102 #define DIG_QUERY_MAGIC ISC_MAGIC('D', 'i', 'g', 'q')
    103 
    104 #define DIG_VALID_QUERY(x) ISC_MAGIC_VALID((x), DIG_QUERY_MAGIC)
    105 
    106 /*% The dig_lookup structure */
    107 struct dig_lookup {
    108 	unsigned int magic;
    109 	isc_refcount_t references;
    110 	bool aaonly, adflag, badcookie, besteffort, cdflag, cleared, coflag,
    111 		comments, dns64prefix, dnssec, doing_xfr, done_as_is, ednsneg,
    112 		expandaaaa, expire, fuzzing, header_only,
    113 		identify, /*%< Append an "on server <foo>" message */
    114 		identify_previous_line, /*% Prepend a "Nameserver <foo>:"
    115 					   message, with newline and tab */
    116 		idnin, idnout, ignore, multiline, need_search, new_search,
    117 		noclass, nocrypto, nottl, ns_search_only, /*%< dig +nssearch,
    118 							     host -C */
    119 		ns_search_success, nsid, /*% Name Server ID (RFC 5001) */
    120 		onesoa, pending,	 /*%< Pending a successful answer */
    121 		print_unknown_format, qr, raflag, recurse, section_additional,
    122 		section_answer, section_authority, section_question,
    123 		seenbadcookie, sendcookie, servfail_stops,
    124 		setqid, /*% use a speciied query ID */
    125 		showbadcookie, showbadvers, stats, tcflag, tcp_keepalive,
    126 		tcp_mode, tcp_mode_set, tls_mode, /*% connect using TLS */
    127 		trace,				  /*% dig +trace */
    128 		trace_root, /*% initial query for either +trace or +nssearch */
    129 		ttlunits, use_usec, waiting_connect, zflag;
    130 	char textname[MXNAME]; /*% Name we're going to be looking up */
    131 	char cmdline[MXNAME];
    132 	dns_rdatatype_t rdtype;
    133 	dns_rdatatype_t qrdtype;
    134 	dns_rdataclass_t rdclass;
    135 	bool rdtypeset;
    136 	bool rdclassset;
    137 	char name_space[BUFSIZE];
    138 	char oname_space[BUFSIZE];
    139 	isc_buffer_t namebuf;
    140 	isc_buffer_t onamebuf;
    141 	isc_buffer_t renderbuf;
    142 	char *sendspace;
    143 	dns_name_t *name;
    144 	isc_interval_t interval;
    145 	dns_message_t *sendmsg;
    146 	dns_name_t *oname;
    147 	ISC_LINK(dig_lookup_t) link;
    148 	ISC_LIST(dig_query_t) q;
    149 	ISC_LIST(dig_query_t) connecting;
    150 	dig_query_t *current_query;
    151 	dig_serverlist_t my_server_list;
    152 	dig_searchlist_t *origin;
    153 	dig_query_t *xfr_q;
    154 	uint32_t retries;
    155 	int nsfound;
    156 	int16_t udpsize;
    157 	int16_t edns;
    158 	int16_t original_edns;
    159 	int16_t padding;
    160 	uint32_t ixfr_serial;
    161 	isc_buffer_t rdatabuf;
    162 	char rdatastore[MXNAME];
    163 	dst_context_t *tsigctx;
    164 	isc_buffer_t *querysig;
    165 	uint32_t msgcounter;
    166 	dns_fixedname_t fdomain;
    167 	isc_sockaddr_t *ecs_addr;
    168 	char *cookie;
    169 	dns_ednsopt_t *ednsopts;
    170 	unsigned int ednsoptscnt;
    171 	unsigned int ednsflags;
    172 	dns_opcode_t opcode;
    173 	int rrcomments;
    174 	uint16_t qid;
    175 	struct {
    176 		bool http_plain;
    177 		bool https_mode;
    178 		bool https_get;
    179 		char *https_path;
    180 	};
    181 	struct {
    182 		bool tls_ca_set;
    183 		char *tls_ca_file;
    184 		bool tls_hostname_set;
    185 		char *tls_hostname;
    186 		bool tls_cert_file_set;
    187 		char *tls_cert_file;
    188 		bool tls_key_file_set;
    189 		char *tls_key_file;
    190 		isc_tlsctx_cache_t *tls_ctx_cache;
    191 	};
    192 	struct {
    193 		bool proxy_mode;
    194 		bool proxy_plain;
    195 		bool proxy_local;
    196 		isc_sockaddr_t proxy_src_addr;
    197 		isc_sockaddr_t proxy_dst_addr;
    198 	};
    199 	isc_stdtime_t fuzztime;
    200 };
    201 
    202 /*% The dig_query structure */
    203 struct dig_query {
    204 	unsigned int magic;
    205 	dig_lookup_t *lookup;
    206 	bool started;
    207 	bool first_soa_rcvd;
    208 	bool second_rr_rcvd;
    209 	bool first_repeat_rcvd;
    210 	bool warn_id;
    211 	bool canceled;
    212 	uint32_t first_rr_serial;
    213 	uint32_t second_rr_serial;
    214 	uint32_t msg_count;
    215 	uint32_t rr_count;
    216 	bool ixfr_axfr;
    217 	char *servname;
    218 	char *userarg;
    219 	isc_buffer_t sendbuf;
    220 	char *recvspace, *tmpsendspace, lengthspace[4];
    221 	isc_refcount_t references;
    222 	isc_nmhandle_t *handle;
    223 	isc_nmhandle_t *readhandle;
    224 	isc_nmhandle_t *sendhandle;
    225 	ISC_LINK(dig_query_t) link;
    226 	ISC_LINK(dig_query_t) clink;
    227 	isc_sockaddr_t sockaddr;
    228 	isc_time_t time_sent;
    229 	isc_time_t time_recv;
    230 	uint64_t byte_count;
    231 	isc_timer_t *timer;
    232 };
    233 
    234 struct dig_server {
    235 	char servername[MXNAME];
    236 	char userarg[MXNAME];
    237 	ISC_LINK(dig_server_t) link;
    238 };
    239 
    240 struct dig_searchlist {
    241 	char origin[MXNAME];
    242 	ISC_LINK(dig_searchlist_t) link;
    243 };
    244 
    245 typedef ISC_LIST(dig_searchlist_t) dig_searchlistlist_t;
    246 typedef ISC_LIST(dig_lookup_t) dig_lookuplist_t;
    247 
    248 /*
    249  * Externals from dighost.c
    250  */
    251 
    252 extern dig_lookuplist_t lookup_list;
    253 extern dig_serverlist_t server_list;
    254 extern dig_searchlistlist_t search_list;
    255 extern unsigned int extrabytes;
    256 
    257 extern bool check_ra, have_ipv4, have_ipv6, specified_source, usesearch,
    258 	showsearch, yaml;
    259 extern in_port_t port;
    260 extern bool port_set;
    261 extern unsigned int timeout;
    262 extern isc_mem_t *mctx;
    263 extern isc_refcount_t sendcount;
    264 extern int ndots;
    265 extern int lookup_counter;
    266 extern int exitcode;
    267 extern isc_sockaddr_t localaddr;
    268 extern char keynametext[MXNAME];
    269 extern char keyfile[MXNAME];
    270 extern char keysecret[MXNAME];
    271 extern dst_algorithm_t hmac_alg;
    272 extern unsigned int digestbits;
    273 extern dns_tsigkey_t *tsigkey;
    274 extern bool validated;
    275 extern isc_loopmgr_t *loopmgr;
    276 extern isc_loop_t *mainloop;
    277 extern bool free_now;
    278 extern bool debugging, debugtiming, memdebugging;
    279 extern bool keep_open;
    280 
    281 extern char *progname;
    282 extern int tries;
    283 extern int fatalexit;
    284 extern bool verbose;
    285 
    286 /*
    287  * Routines in dighost.c.
    288  */
    289 isc_result_t
    290 get_address(char *host, in_port_t myport, isc_sockaddr_t *sockaddr);
    291 
    292 int
    293 getaddresses(dig_lookup_t *lookup, const char *host, isc_result_t *resultp);
    294 
    295 isc_result_t
    296 get_reverse(char *reverse, size_t len, char *value, bool strict);
    297 
    298 noreturn void
    299 fatal(const char *format, ...) ISC_FORMAT_PRINTF(1, 2);
    300 
    301 void
    302 warn(const char *format, ...) ISC_FORMAT_PRINTF(1, 2);
    303 
    304 noreturn void
    305 digexit(void);
    306 
    307 void
    308 cleanup_openssl_refs(void);
    309 
    310 void
    311 debug(const char *format, ...) ISC_FORMAT_PRINTF(1, 2);
    312 
    313 void
    314 check_result(isc_result_t result, const char *msg);
    315 
    316 bool
    317 setup_lookup(dig_lookup_t *lookup);
    318 
    319 void
    320 destroy_lookup(dig_lookup_t *lookup);
    321 
    322 void
    323 do_lookup(dig_lookup_t *lookup);
    324 
    325 void
    326 start_lookup(void);
    327 
    328 void
    329 onrun_callback(void *arg);
    330 
    331 void
    332 run_loop(void *arg);
    333 
    334 int
    335 dhmain(int argc, char **argv);
    336 
    337 void
    338 setup_libs(void);
    339 
    340 void
    341 setup_system(bool ipv4only, bool ipv6only);
    342 
    343 isc_result_t
    344 parse_uint(uint32_t *uip, const char *value, uint32_t max, const char *desc);
    345 
    346 isc_result_t
    347 parse_xint(uint32_t *uip, const char *value, uint32_t max, const char *desc);
    348 
    349 isc_result_t
    350 parse_netprefix(isc_sockaddr_t **sap, const char *value);
    351 
    352 void
    353 parse_hmac(const char *algname);
    354 
    355 dig_lookup_t *
    356 requeue_lookup(dig_lookup_t *lookold, bool servers);
    357 
    358 dig_lookup_t *
    359 make_empty_lookup(void);
    360 
    361 dig_lookup_t *
    362 clone_lookup(dig_lookup_t *lookold, bool servers);
    363 
    364 dig_server_t *
    365 make_server(const char *servname, const char *userarg);
    366 
    367 void
    368 flush_server_list(void);
    369 
    370 void
    371 set_nameserver(char *opt);
    372 
    373 void
    374 clone_server_list(dig_serverlist_t src, dig_serverlist_t *dest);
    375 
    376 void
    377 cancel_all(void);
    378 
    379 void
    380 destroy_libs(void);
    381 
    382 void
    383 set_search_domain(char *domain);
    384 
    385 /*
    386  * Routines to be defined in dig.c, host.c, and nslookup.c. and
    387  * then assigned to the appropriate function pointer
    388  */
    389 extern isc_result_t (*dighost_printmessage)(dig_query_t *query,
    390 					    const isc_buffer_t *msgbuf,
    391 					    dns_message_t *msg, bool headers);
    392 
    393 /*
    394  * Print an error message in the appropriate format.
    395  */
    396 extern void (*dighost_error)(const char *format, ...);
    397 
    398 /*
    399  * Print a warning message in the appropriate format.
    400  */
    401 extern void (*dighost_warning)(const char *format, ...);
    402 
    403 /*
    404  * Print a comment in the appropriate format.
    405  */
    406 extern void (*dighost_comments)(dig_lookup_t *lookup, const char *format, ...);
    407 
    408 /*%<
    409  * Print the final result of the lookup.
    410  */
    411 
    412 extern void (*dighost_received)(unsigned int bytes, isc_sockaddr_t *from,
    413 				dig_query_t *query);
    414 /*%<
    415  * Print a message about where and when the response
    416  * was received from, like the final comment in the
    417  * output of "dig".
    418  */
    419 
    420 extern void (*dighost_trying)(char *frm, dig_lookup_t *lookup);
    421 
    422 extern void (*dighost_shutdown)(void);
    423 
    424 extern void (*dighost_pre_exit_hook)(void);
    425 
    426 void
    427 save_opt(dig_lookup_t *lookup, char *code, char *value);
    428 
    429 void
    430 setup_file_key(void);
    431 void
    432 setup_text_key(void);
    433 
    434 /*
    435  * Routines exported from dig.c for use by dig for iOS
    436  */
    437 
    438 /*%
    439  * Call once only to set up libraries, parse global
    440  * parameters and initial command line query parameters
    441  */
    442 void
    443 dig_setup(int argc, char **argv);
    444 
    445 /*%
    446  * Call to supply new parameters for the next lookup
    447  */
    448 void
    449 dig_query_setup(bool, bool, int argc, char **argv);
    450 
    451 /*%
    452  * set the main application event cycle running
    453  */
    454 void
    455 dig_startup(void);
    456 
    457 /*%
    458  * Activate/deactivate IDN filtering of output.
    459  */
    460 void
    461 dig_idnsetup(dig_lookup_t *lookup, bool active);
    462 
    463 /*%
    464  * Cleans up the application
    465  */
    466 void
    467 dig_shutdown(void);
    468 
    469 bool
    470 dig_lookup_is_tls(const dig_lookup_t *lookup);
    471 
    472 ISC_LANG_ENDDECLS
    473