2000-05-09 18:05:13 +00:00
|
|
|
/*
|
|
|
|
* Copyright (C) 2000 Internet Software Consortium.
|
2000-08-01 01:33:37 +00:00
|
|
|
*
|
2000-05-09 18:05:13 +00:00
|
|
|
* Permission to use, copy, modify, and distribute this software for any
|
|
|
|
* purpose with or without fee is hereby granted, provided that the above
|
|
|
|
* copyright notice and this permission notice appear in all copies.
|
2000-08-01 01:33:37 +00:00
|
|
|
*
|
2000-07-27 09:55:03 +00:00
|
|
|
* THE SOFTWARE IS PROVIDED "AS IS" AND INTERNET SOFTWARE CONSORTIUM
|
|
|
|
* DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE INCLUDING ALL
|
|
|
|
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL
|
|
|
|
* INTERNET SOFTWARE CONSORTIUM BE LIABLE FOR ANY SPECIAL, DIRECT,
|
|
|
|
* INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING
|
|
|
|
* FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT,
|
|
|
|
* NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION
|
|
|
|
* WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
2000-05-09 18:05:13 +00:00
|
|
|
*/
|
|
|
|
|
2000-09-14 20:11:48 +00:00
|
|
|
/* $Id: nslookup.c,v 1.43 2000/09/14 20:11:48 mws Exp $ */
|
2000-06-06 18:49:06 +00:00
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
#include <config.h>
|
|
|
|
|
|
|
|
#include <stdlib.h>
|
|
|
|
|
|
|
|
extern int h_errno;
|
|
|
|
|
2000-06-21 17:48:32 +00:00
|
|
|
#include <isc/app.h>
|
|
|
|
#include <isc/buffer.h>
|
|
|
|
#include <isc/commandline.h>
|
2000-09-01 23:43:55 +00:00
|
|
|
#include <isc/event.h>
|
2000-06-21 17:48:32 +00:00
|
|
|
#include <isc/string.h>
|
|
|
|
#include <isc/timer.h>
|
|
|
|
#include <isc/util.h>
|
2000-06-30 14:11:49 +00:00
|
|
|
#include <isc/task.h>
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-07-18 01:28:20 +00:00
|
|
|
#include <dns/message.h>
|
|
|
|
#include <dns/name.h>
|
|
|
|
#include <dns/rdata.h>
|
|
|
|
#include <dns/rdataclass.h>
|
|
|
|
#include <dns/rdataset.h>
|
|
|
|
#include <dns/rdatatype.h>
|
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
#include <dig/dig.h>
|
|
|
|
|
|
|
|
extern ISC_LIST(dig_lookup_t) lookup_list;
|
|
|
|
extern ISC_LIST(dig_server_t) server_list;
|
|
|
|
extern ISC_LIST(dig_searchlist_t) search_list;
|
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
extern isc_boolean_t have_ipv6, show_details,
|
2000-06-21 01:40:42 +00:00
|
|
|
usesearch, trace, qr, debugging;
|
2000-05-09 18:05:13 +00:00
|
|
|
extern in_port_t port;
|
|
|
|
extern unsigned int timeout;
|
|
|
|
extern isc_mem_t *mctx;
|
|
|
|
extern dns_messageid_t id;
|
|
|
|
extern char *rootspace[BUFSIZE];
|
|
|
|
extern isc_buffer_t rootbuf;
|
|
|
|
extern int sendcount;
|
|
|
|
extern int ndots;
|
|
|
|
extern int tries;
|
|
|
|
extern int lookup_counter;
|
|
|
|
extern char fixeddomain[MXNAME];
|
|
|
|
extern int exitcode;
|
2000-06-30 14:11:49 +00:00
|
|
|
extern isc_taskmgr_t *taskmgr;
|
2000-09-01 23:43:55 +00:00
|
|
|
extern isc_task_t *global_task;
|
2000-07-05 23:28:32 +00:00
|
|
|
extern char *progname;
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-05-16 17:53:35 +00:00
|
|
|
isc_boolean_t short_form = ISC_TRUE, printcmd = ISC_TRUE,
|
2000-05-12 01:02:37 +00:00
|
|
|
filter = ISC_FALSE, showallsoa = ISC_FALSE,
|
2000-06-15 18:24:08 +00:00
|
|
|
tcpmode = ISC_FALSE, deprecation_msg = ISC_TRUE;
|
2000-05-09 18:05:13 +00:00
|
|
|
|
|
|
|
isc_uint16_t bufsize = 0;
|
|
|
|
isc_boolean_t identify = ISC_FALSE,
|
|
|
|
trace = ISC_FALSE, ns_search_only = ISC_FALSE,
|
|
|
|
forcecomment = ISC_FALSE, stats = ISC_TRUE,
|
|
|
|
comments = ISC_TRUE, section_question = ISC_TRUE,
|
|
|
|
section_answer = ISC_TRUE, section_authority = ISC_TRUE,
|
|
|
|
section_additional = ISC_TRUE, recurse = ISC_TRUE,
|
|
|
|
defname = ISC_TRUE, aaonly = ISC_FALSE;
|
2000-05-12 01:02:37 +00:00
|
|
|
isc_boolean_t busy = ISC_FALSE, in_use = ISC_FALSE;
|
|
|
|
char defclass[MXRD] = "IN";
|
|
|
|
char deftype[MXRD] = "A";
|
2000-09-01 23:43:55 +00:00
|
|
|
isc_event_t *global_event = NULL;
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-06-06 00:43:17 +00:00
|
|
|
static const char *rcodetext[] = {
|
2000-05-09 18:05:13 +00:00
|
|
|
"NOERROR",
|
|
|
|
"FORMERR",
|
|
|
|
"SERVFAIL",
|
|
|
|
"NXDOMAIN",
|
|
|
|
"NOTIMPL",
|
|
|
|
"REFUSED",
|
|
|
|
"YXDOMAIN",
|
|
|
|
"YXRRSET",
|
|
|
|
"NXRRSET",
|
|
|
|
"NOTAUTH",
|
|
|
|
"NOTZONE",
|
|
|
|
"RESERVED11",
|
|
|
|
"RESERVED12",
|
|
|
|
"RESERVED13",
|
|
|
|
"RESERVED14",
|
|
|
|
"RESERVED15",
|
|
|
|
"BADVERS"
|
|
|
|
};
|
|
|
|
|
2000-06-06 00:43:17 +00:00
|
|
|
static const char *rtypetext[] = {
|
2000-05-12 01:02:37 +00:00
|
|
|
"rtype_0 = ", /* 0 */
|
|
|
|
"internet address = ", /* 1 */
|
|
|
|
"nameserver = ", /* 2 */
|
|
|
|
"md = ", /* 3 */
|
|
|
|
"mf = ", /* 4 */
|
|
|
|
"canonical name = ", /* 5 */
|
|
|
|
"soa = ", /* 6 */
|
2000-08-01 01:33:37 +00:00
|
|
|
"mb = ", /* 7 */
|
2000-05-12 01:02:37 +00:00
|
|
|
"mg = ", /* 8 */
|
|
|
|
"mr = ", /* 9 */
|
|
|
|
"rtype_10 = ", /* 10 */
|
|
|
|
"protocol = ", /* 11 */
|
|
|
|
"name = ", /* 12 */
|
|
|
|
"hinfo = ", /* 13 */
|
|
|
|
"minfo = ", /* 14 */
|
|
|
|
"mail exchanger = ", /* 15 */
|
|
|
|
"text = ", /* 16 */
|
|
|
|
"rp = ", /* 17 */
|
|
|
|
"afsdb = ", /* 18 */
|
|
|
|
"x25 address = ", /* 19 */
|
|
|
|
"isdn address = ", /* 20 */
|
2000-08-15 18:44:05 +00:00
|
|
|
"rt = ", /* 21 */
|
2000-05-12 01:02:37 +00:00
|
|
|
"nsap = ", /* 22 */
|
|
|
|
"nsap_ptr = ", /* 23 */
|
|
|
|
"signature = ", /* 24 */
|
|
|
|
"key = ", /* 25 */
|
|
|
|
"px = ", /* 26 */
|
|
|
|
"gpos = ", /* 27 */
|
|
|
|
"has AAAA address", /* 28 */
|
|
|
|
"loc = ", /* 29 */
|
|
|
|
"next = ", /* 30 */
|
|
|
|
"rtype_31 = ", /* 31 */
|
|
|
|
"rtype_32 = ", /* 32 */
|
|
|
|
"service = ", /* 33 */
|
|
|
|
"rtype_34 = ", /* 34 */
|
|
|
|
"naptr = ", /* 35 */
|
|
|
|
"kx = ", /* 36 */
|
|
|
|
"cert = ", /* 37 */
|
|
|
|
"v6 address = ", /* 38 */
|
|
|
|
"dname = ", /* 39 */
|
|
|
|
"rtype_40 = ", /* 40 */
|
|
|
|
"optional = "}; /* 41 */
|
|
|
|
|
|
|
|
|
2000-09-01 23:43:55 +00:00
|
|
|
static void flush_lookup_list(void);
|
|
|
|
static void getinput(isc_task_t *task, isc_event_t *event);
|
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
static void
|
2000-06-19 18:54:45 +00:00
|
|
|
show_usage(void) {
|
2000-08-07 23:54:46 +00:00
|
|
|
fputs("Usage:\n", stderr);
|
2000-08-01 01:33:37 +00:00
|
|
|
}
|
2000-05-09 18:05:13 +00:00
|
|
|
|
|
|
|
void
|
2000-05-12 01:02:37 +00:00
|
|
|
dighost_shutdown(void) {
|
2000-09-01 23:43:55 +00:00
|
|
|
isc_event_t *event = global_event;
|
|
|
|
|
|
|
|
flush_lookup_list();
|
2000-09-01 21:54:23 +00:00
|
|
|
debug("dighost_shutdown()");
|
2000-09-01 23:43:55 +00:00
|
|
|
|
|
|
|
if (!in_use) {
|
|
|
|
isc_app_shutdown();
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
|
|
|
|
isc_task_send(global_task, &event);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
2000-09-01 21:54:23 +00:00
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
void
|
|
|
|
received(int bytes, int frmsize, char *frm, dig_query_t *query) {
|
2000-08-07 23:54:46 +00:00
|
|
|
UNUSED(bytes);
|
|
|
|
UNUSED(frmsize);
|
|
|
|
UNUSED(frm);
|
|
|
|
UNUSED(query);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
void
|
|
|
|
trying(int frmsize, char *frm, dig_lookup_t *lookup) {
|
2000-08-07 23:54:46 +00:00
|
|
|
UNUSED(frmsize);
|
|
|
|
UNUSED(frm);
|
|
|
|
UNUSED(lookup);
|
2000-05-09 18:05:13 +00:00
|
|
|
|
|
|
|
}
|
|
|
|
|
|
|
|
static isc_result_t
|
2000-05-12 01:02:37 +00:00
|
|
|
printsection(dig_query_t *query, dns_message_t *msg, isc_boolean_t headers,
|
|
|
|
dns_section_t section) {
|
2000-05-09 18:05:13 +00:00
|
|
|
isc_result_t result, loopresult;
|
2000-05-12 01:02:37 +00:00
|
|
|
isc_buffer_t *b = NULL;
|
|
|
|
dns_name_t *name;
|
|
|
|
dns_rdataset_t *rdataset = NULL;
|
2000-05-09 18:05:13 +00:00
|
|
|
dns_rdata_t rdata;
|
2000-05-12 01:02:37 +00:00
|
|
|
char *ptr;
|
|
|
|
|
2000-08-07 23:54:46 +00:00
|
|
|
UNUSED(query);
|
|
|
|
UNUSED(headers);
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
debug("printsection()");
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
result = dns_message_firstname(msg, section);
|
2000-05-09 18:05:13 +00:00
|
|
|
if (result == ISC_R_NOMORE)
|
|
|
|
return (ISC_R_SUCCESS);
|
|
|
|
else if (result != ISC_R_SUCCESS)
|
|
|
|
return (result);
|
2000-05-12 01:02:37 +00:00
|
|
|
result = isc_buffer_allocate(mctx, &b, MXNAME);
|
|
|
|
check_result(result, "isc_buffer_allocate");
|
2000-05-09 18:05:13 +00:00
|
|
|
for (;;) {
|
|
|
|
name = NULL;
|
2000-08-01 01:33:37 +00:00
|
|
|
dns_message_currentname(msg, section,
|
2000-05-12 01:02:37 +00:00
|
|
|
&name);
|
2000-05-09 18:05:13 +00:00
|
|
|
for (rdataset = ISC_LIST_HEAD(name->list);
|
|
|
|
rdataset != NULL;
|
|
|
|
rdataset = ISC_LIST_NEXT(rdataset, link)) {
|
2000-05-12 01:02:37 +00:00
|
|
|
loopresult = dns_rdataset_first(rdataset);
|
|
|
|
while (loopresult == ISC_R_SUCCESS) {
|
2000-08-07 23:54:46 +00:00
|
|
|
dns_rdataset_current(rdataset, &rdata);
|
|
|
|
switch (rdata.type) {
|
2000-05-12 01:02:37 +00:00
|
|
|
case dns_rdatatype_a:
|
|
|
|
if (section != DNS_SECTION_ANSWER)
|
|
|
|
goto def_short_section;
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
result = dns_name_totext(name,
|
|
|
|
ISC_TRUE,
|
|
|
|
b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_name_totext");
|
|
|
|
printf("Name:\t%.*s\n",
|
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
result = dns_rdata_totext(&rdata,
|
|
|
|
NULL,
|
|
|
|
b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_rdata_totext");
|
|
|
|
printf("Address: %.*s\n",
|
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
|
|
|
break;
|
|
|
|
case dns_rdatatype_soa:
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
result = dns_name_totext(name,
|
|
|
|
ISC_TRUE,
|
|
|
|
b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_name_totext");
|
|
|
|
printf("%.*s\n",
|
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
result = dns_rdata_totext(&rdata,
|
|
|
|
NULL,
|
|
|
|
b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_rdata_totext");
|
2000-06-06 00:43:17 +00:00
|
|
|
((char *)isc_buffer_used(b))[0]=0;
|
2000-05-12 01:02:37 +00:00
|
|
|
ptr = strtok(isc_buffer_base(b),
|
|
|
|
" \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\torigin = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tmail addr = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tserial = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\trefresh = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tretry = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\texpire = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tminimum = %s\n",
|
|
|
|
ptr);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
def_short_section:
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
result = dns_name_totext(name,
|
|
|
|
ISC_TRUE,
|
|
|
|
b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_name_totext");
|
|
|
|
if (rdata.type <= 41)
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("%.*s\t%s",
|
2000-05-12 01:02:37 +00:00
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b),
|
|
|
|
rtypetext[rdata.type]);
|
|
|
|
else
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("%.*s\trdata_%d = ",
|
2000-05-12 01:02:37 +00:00
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b),
|
|
|
|
rdata.type);
|
|
|
|
isc_buffer_clear(b);
|
2000-08-01 01:33:37 +00:00
|
|
|
result = dns_rdata_totext(&rdata,
|
2000-05-12 01:02:37 +00:00
|
|
|
NULL, b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_rdata_totext");
|
|
|
|
printf("%.*s\n",
|
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
2000-08-01 01:33:37 +00:00
|
|
|
}
|
2000-05-12 01:02:37 +00:00
|
|
|
loopresult = dns_rdataset_next(rdataset);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
|
|
|
}
|
2000-05-12 01:02:37 +00:00
|
|
|
result = dns_message_nextname(msg, section);
|
2000-05-09 18:05:13 +00:00
|
|
|
if (result == ISC_R_NOMORE)
|
|
|
|
break;
|
2000-05-12 01:02:37 +00:00
|
|
|
else if (result != ISC_R_SUCCESS) {
|
|
|
|
isc_buffer_free (&b);
|
2000-05-09 18:05:13 +00:00
|
|
|
return (result);
|
2000-05-12 01:02:37 +00:00
|
|
|
}
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
2000-05-12 01:02:37 +00:00
|
|
|
isc_buffer_free(&b);
|
2000-05-09 18:05:13 +00:00
|
|
|
return (ISC_R_SUCCESS);
|
|
|
|
}
|
|
|
|
|
2000-05-16 17:53:35 +00:00
|
|
|
static isc_result_t
|
|
|
|
detailsection(dig_query_t *query, dns_message_t *msg, isc_boolean_t headers,
|
|
|
|
dns_section_t section) {
|
|
|
|
isc_result_t result, loopresult;
|
|
|
|
isc_buffer_t *b = NULL;
|
|
|
|
dns_name_t *name;
|
|
|
|
dns_rdataset_t *rdataset = NULL;
|
|
|
|
dns_rdata_t rdata;
|
|
|
|
char *ptr;
|
|
|
|
|
2000-08-07 23:54:46 +00:00
|
|
|
UNUSED(query);
|
2000-05-16 17:53:35 +00:00
|
|
|
|
2000-07-05 23:28:32 +00:00
|
|
|
debug("detailsection()");
|
2000-05-16 17:53:35 +00:00
|
|
|
|
|
|
|
if (headers) {
|
|
|
|
switch (section) {
|
|
|
|
case DNS_SECTION_QUESTION:
|
2000-08-07 23:54:46 +00:00
|
|
|
puts(" QUESTIONS:");
|
2000-05-16 17:53:35 +00:00
|
|
|
break;
|
|
|
|
case DNS_SECTION_ANSWER:
|
2000-08-07 23:54:46 +00:00
|
|
|
puts(" ANSWERS:");
|
2000-05-16 17:53:35 +00:00
|
|
|
break;
|
|
|
|
case DNS_SECTION_AUTHORITY:
|
2000-08-07 23:54:46 +00:00
|
|
|
puts(" AUTHORITY RECORDS:");
|
2000-05-16 17:53:35 +00:00
|
|
|
break;
|
|
|
|
case DNS_SECTION_ADDITIONAL:
|
2000-08-07 23:54:46 +00:00
|
|
|
puts(" ADDITIONAL RECORDS:");
|
2000-05-16 17:53:35 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
result = dns_message_firstname(msg, section);
|
|
|
|
if (result == ISC_R_NOMORE)
|
|
|
|
return (ISC_R_SUCCESS);
|
|
|
|
else if (result != ISC_R_SUCCESS)
|
|
|
|
return (result);
|
|
|
|
result = isc_buffer_allocate(mctx, &b, MXNAME);
|
|
|
|
check_result(result, "isc_buffer_allocate");
|
|
|
|
for (;;) {
|
|
|
|
name = NULL;
|
2000-08-01 01:33:37 +00:00
|
|
|
dns_message_currentname(msg, section,
|
2000-05-16 17:53:35 +00:00
|
|
|
&name);
|
|
|
|
for (rdataset = ISC_LIST_HEAD(name->list);
|
|
|
|
rdataset != NULL;
|
|
|
|
rdataset = ISC_LIST_NEXT(rdataset, link)) {
|
|
|
|
loopresult = dns_rdataset_first(rdataset);
|
|
|
|
while (loopresult == ISC_R_SUCCESS) {
|
|
|
|
dns_rdataset_current(rdataset, &rdata);
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
result = dns_name_totext(name,
|
|
|
|
ISC_TRUE,
|
|
|
|
b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_name_totext");
|
|
|
|
printf(" -> %.*s\n",
|
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
|
|
|
switch (rdata.type) {
|
|
|
|
case dns_rdatatype_soa:
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
result = dns_rdata_totext(&rdata,
|
|
|
|
NULL,
|
|
|
|
b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_rdata_totext");
|
2000-06-06 00:43:17 +00:00
|
|
|
((char *)isc_buffer_used(b))[0]=0;
|
2000-05-16 17:53:35 +00:00
|
|
|
ptr = strtok(isc_buffer_base(b),
|
|
|
|
" \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\torigin = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tmail addr = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tserial = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\trefresh = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tretry = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\texpire = %s\n",
|
|
|
|
ptr);
|
|
|
|
ptr = strtok(NULL, " \t\r\n");
|
|
|
|
if (ptr == NULL)
|
|
|
|
break;
|
|
|
|
printf("\tminimum = %s\n",
|
|
|
|
ptr);
|
|
|
|
break;
|
|
|
|
default:
|
|
|
|
isc_buffer_clear(b);
|
|
|
|
if (rdata.type <= 41)
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("\t%s",
|
2000-05-16 17:53:35 +00:00
|
|
|
rtypetext[rdata.type]);
|
|
|
|
else
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("\trdata_%d = ",
|
2000-05-16 17:53:35 +00:00
|
|
|
rdata.type);
|
|
|
|
isc_buffer_clear(b);
|
2000-08-01 01:33:37 +00:00
|
|
|
result = dns_rdata_totext(&rdata,
|
2000-05-16 17:53:35 +00:00
|
|
|
NULL, b);
|
|
|
|
check_result(result,
|
|
|
|
"dns_rdata_totext");
|
|
|
|
printf("%.*s\n",
|
|
|
|
(int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
2000-08-01 01:33:37 +00:00
|
|
|
}
|
2000-05-16 17:53:35 +00:00
|
|
|
loopresult = dns_rdataset_next(rdataset);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
result = dns_message_nextname(msg, section);
|
|
|
|
if (result == ISC_R_NOMORE)
|
|
|
|
break;
|
|
|
|
else if (result != ISC_R_SUCCESS) {
|
|
|
|
isc_buffer_free (&b);
|
|
|
|
return (result);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
isc_buffer_free(&b);
|
|
|
|
return (ISC_R_SUCCESS);
|
|
|
|
}
|
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
isc_result_t
|
|
|
|
printmessage(dig_query_t *query, dns_message_t *msg, isc_boolean_t headers) {
|
2000-05-12 01:02:37 +00:00
|
|
|
isc_buffer_t *b = NULL;
|
|
|
|
isc_region_t r;
|
2000-05-09 18:05:13 +00:00
|
|
|
isc_result_t result;
|
|
|
|
|
2000-08-07 23:54:46 +00:00
|
|
|
debug("printmessage()");
|
2000-09-14 20:11:48 +00:00
|
|
|
debug("continuing on with rcode != 0");
|
|
|
|
result = isc_buffer_allocate(mctx, &b, MXNAME);
|
|
|
|
check_result(result, "isc_buffer_allocate");
|
|
|
|
printf("Server:\t\t%s\n", query->servname);
|
|
|
|
result = isc_sockaddr_totext(&query->sockaddr, b);
|
|
|
|
check_result(result, "isc_sockaddr_totext");
|
|
|
|
printf("Address:\t%.*s\n", (int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
|
|
|
isc_buffer_free(&b);
|
|
|
|
puts("");
|
2000-05-12 01:02:37 +00:00
|
|
|
|
|
|
|
if (msg->rcode != 0) {
|
|
|
|
result = isc_buffer_allocate(mctx, &b, MXNAME);
|
|
|
|
check_result(result, "isc_buffer_allocate");
|
|
|
|
result = dns_name_totext(query->lookup->name, ISC_FALSE,
|
|
|
|
b);
|
|
|
|
check_result(result, "dns_name_totext");
|
|
|
|
isc_buffer_usedregion(b, &r);
|
|
|
|
printf("** server can't find %.*s: %s\n",
|
|
|
|
(int)r.length, (char*)r.base,
|
|
|
|
rcodetext[msg->rcode]);
|
|
|
|
isc_buffer_free(&b);
|
2000-08-07 23:54:46 +00:00
|
|
|
debug("returning with rcode == 0");
|
2000-05-12 01:02:37 +00:00
|
|
|
return (ISC_R_SUCCESS);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
2000-05-16 17:53:35 +00:00
|
|
|
if (!short_form){
|
2000-08-07 23:54:46 +00:00
|
|
|
puts("------------");
|
2000-05-16 17:53:35 +00:00
|
|
|
/* detailheader(query, msg);*/
|
|
|
|
detailsection(query, msg, headers, DNS_SECTION_QUESTION);
|
|
|
|
detailsection(query, msg, headers, DNS_SECTION_ANSWER);
|
|
|
|
detailsection(query, msg, headers, DNS_SECTION_AUTHORITY);
|
|
|
|
detailsection(query, msg, headers, DNS_SECTION_ADDITIONAL);
|
2000-08-07 23:54:46 +00:00
|
|
|
puts("------------");
|
2000-05-16 17:53:35 +00:00
|
|
|
}
|
2000-08-01 01:33:37 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
if ((msg->flags & DNS_MESSAGEFLAG_AA) == 0)
|
2000-08-07 23:54:46 +00:00
|
|
|
puts("Non-authorative answer:");
|
2000-05-12 01:02:37 +00:00
|
|
|
printsection(query, msg, headers, DNS_SECTION_ANSWER);
|
2000-08-01 01:33:37 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
if (((msg->flags & DNS_MESSAGEFLAG_AA) == 0) &&
|
2000-07-18 01:28:20 +00:00
|
|
|
(query->lookup->rdtype != dns_rdatatype_a)) {
|
2000-08-07 23:54:46 +00:00
|
|
|
puts("\nAuthorative answers can be found from:");
|
2000-05-16 17:53:35 +00:00
|
|
|
printsection(query, msg, headers,
|
|
|
|
DNS_SECTION_AUTHORITY);
|
|
|
|
printsection(query, msg, headers,
|
|
|
|
DNS_SECTION_ADDITIONAL);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
2000-05-12 01:02:37 +00:00
|
|
|
return (ISC_R_SUCCESS);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
2000-05-16 17:53:35 +00:00
|
|
|
show_settings(isc_boolean_t full) {
|
2000-05-12 01:02:37 +00:00
|
|
|
dig_server_t *srv;
|
2000-05-16 17:53:35 +00:00
|
|
|
isc_sockaddr_t sockaddr;
|
|
|
|
isc_buffer_t *b = NULL;
|
|
|
|
isc_result_t result;
|
2000-08-01 01:33:37 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
srv = ISC_LIST_HEAD(server_list);
|
2000-05-16 17:53:35 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
while (srv != NULL) {
|
2000-05-16 17:53:35 +00:00
|
|
|
result = isc_buffer_allocate(mctx, &b, MXNAME);
|
|
|
|
check_result(result, "isc_buffer_allocate");
|
2000-09-13 00:27:27 +00:00
|
|
|
get_address(srv->servername, 53, &sockaddr, ISC_FALSE);
|
2000-05-16 17:53:35 +00:00
|
|
|
result = isc_sockaddr_totext(&sockaddr, b);
|
|
|
|
check_result(result, "isc_sockaddr_totext");
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("Default server: %s\nAddress: %.*s\n",
|
2000-05-16 17:53:35 +00:00
|
|
|
srv->servername, (int)isc_buffer_usedlength(b),
|
|
|
|
(char*)isc_buffer_base(b));
|
|
|
|
isc_buffer_free(&b);
|
|
|
|
if (!full)
|
|
|
|
return;
|
2000-05-12 01:02:37 +00:00
|
|
|
srv = ISC_LIST_NEXT(srv, link);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("\n\tSet options:\n");
|
|
|
|
printf("\t %s\t\t\t%s\t\t%s\n",
|
2000-05-12 01:02:37 +00:00
|
|
|
tcpmode?"vc":"novc", short_form?"nodebug":"debug",
|
2000-06-21 01:40:42 +00:00
|
|
|
debugging?"d2":"nod2");
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("\t %s\t\t%s\t%s\n",
|
2000-05-16 17:53:35 +00:00
|
|
|
defname?"defname":"nodefname",
|
2000-07-18 01:28:20 +00:00
|
|
|
usesearch?"search ":"nosearch",
|
2000-06-21 01:40:42 +00:00
|
|
|
recurse?"recurse":"norecurse");
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("\t timeout = %d\t\tretry = %d\tport = %d\n",
|
2000-06-21 01:40:42 +00:00
|
|
|
timeout, tries, port);
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("\t querytype = %-8s\tclass = %s\n",deftype, defclass);
|
2000-06-21 01:40:42 +00:00
|
|
|
#if 0
|
2000-08-07 23:54:46 +00:00
|
|
|
printf("\t domain = %s\n", fixeddomain);
|
2000-06-21 01:40:42 +00:00
|
|
|
#endif
|
2000-05-12 01:02:37 +00:00
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
|
|
|
|
2000-07-18 01:28:20 +00:00
|
|
|
static isc_boolean_t
|
|
|
|
testtype(char *typetext) {
|
|
|
|
isc_result_t result;
|
|
|
|
isc_textregion_t tr;
|
|
|
|
dns_rdatatype_t rdtype;
|
|
|
|
|
|
|
|
tr.base = typetext;
|
|
|
|
tr.length = strlen(typetext);
|
|
|
|
result = dns_rdatatype_fromtext(&rdtype, &tr);
|
2000-08-02 19:53:33 +00:00
|
|
|
return (ISC_TF(result == ISC_R_SUCCESS));
|
2000-07-18 01:28:20 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
static isc_boolean_t
|
|
|
|
testclass(char *typetext) {
|
|
|
|
isc_result_t result;
|
|
|
|
isc_textregion_t tr;
|
|
|
|
dns_rdataclass_t rdclass;
|
|
|
|
|
|
|
|
tr.base = typetext;
|
|
|
|
tr.length = strlen(typetext);
|
|
|
|
result = dns_rdataclass_fromtext(&rdclass, &tr);
|
2000-08-02 19:53:33 +00:00
|
|
|
return (ISC_TF(result == ISC_R_SUCCESS));
|
2000-07-18 01:28:20 +00:00
|
|
|
}
|
|
|
|
|
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
static void
|
2000-05-12 01:02:37 +00:00
|
|
|
setoption(char *opt) {
|
2000-08-02 17:58:07 +00:00
|
|
|
dig_server_t *srv;
|
2000-05-12 01:02:37 +00:00
|
|
|
|
|
|
|
if (strncasecmp(opt,"all",4) == 0) {
|
2000-05-16 17:53:35 +00:00
|
|
|
show_settings(ISC_TRUE);
|
2000-05-12 01:02:37 +00:00
|
|
|
} else if (strncasecmp(opt, "class=", 6) == 0) {
|
|
|
|
strncpy(defclass, &opt[6], MXRD);
|
|
|
|
} else if (strncasecmp(opt, "cl=", 3) == 0) {
|
|
|
|
strncpy(defclass, &opt[3], MXRD);
|
|
|
|
} else if (strncasecmp(opt, "type=", 5) == 0) {
|
2000-07-18 01:28:20 +00:00
|
|
|
if (testtype(&opt[5]))
|
|
|
|
strncpy(deftype, &opt[5], MXRD);
|
2000-05-12 01:02:37 +00:00
|
|
|
} else if (strncasecmp(opt, "ty=", 3) == 0) {
|
2000-07-18 01:28:20 +00:00
|
|
|
if (testclass(&opt[3]))
|
|
|
|
strncpy(defclass, &opt[3], MXRD);
|
2000-05-12 01:02:37 +00:00
|
|
|
} else if (strncasecmp(opt, "querytype=", 10) == 0) {
|
|
|
|
strncpy(deftype, &opt[10], MXRD);
|
|
|
|
} else if (strncasecmp(opt, "query=", 6) == 0) {
|
|
|
|
strncpy(deftype, &opt[6], MXRD);
|
|
|
|
} else if (strncasecmp(opt, "qu=", 3) == 0) {
|
|
|
|
strncpy(deftype, &opt[3], MXRD);
|
2000-06-21 01:40:42 +00:00
|
|
|
#if 0
|
|
|
|
/* XXXMWS domain= doesn't work now. */
|
2000-05-12 01:02:37 +00:00
|
|
|
} else if (strncasecmp(opt, "domain=", 7) == 0) {
|
|
|
|
strncpy(fixeddomain, &opt[7], MXNAME);
|
|
|
|
} else if (strncasecmp(opt, "do=", 3) == 0) {
|
|
|
|
strncpy(fixeddomain, &opt[3], MXNAME);
|
2000-06-21 01:40:42 +00:00
|
|
|
#endif
|
2000-05-12 01:02:37 +00:00
|
|
|
} else if (strncasecmp(opt, "port=", 5) == 0) {
|
|
|
|
port = atoi(&opt[5]);
|
|
|
|
} else if (strncasecmp(opt, "po=", 3) == 0) {
|
|
|
|
port = atoi(&opt[3]);
|
|
|
|
} else if (strncasecmp(opt, "timeout=", 8) == 0) {
|
|
|
|
timeout = atoi(&opt[8]);
|
|
|
|
} else if (strncasecmp(opt, "t=", 2) == 0) {
|
|
|
|
timeout = atoi(&opt[2]);
|
|
|
|
} else if (strncasecmp(opt, "retry=", 6) == 0) {
|
|
|
|
tries = atoi(&opt[6]);
|
|
|
|
} else if (strncasecmp(opt, "ret=", 4) == 0) {
|
|
|
|
tries = atoi(&opt[4]);
|
|
|
|
} else if (strncasecmp(opt, "def", 3) == 0) {
|
|
|
|
defname = ISC_TRUE;
|
|
|
|
} else if (strncasecmp(opt, "nodef", 5) == 0) {
|
|
|
|
defname = ISC_FALSE;
|
|
|
|
} else if (strncasecmp(opt, "deb", 3) == 0) {
|
|
|
|
short_form = ISC_FALSE;
|
|
|
|
} else if (strncasecmp(opt, "nodeb", 5) == 0) {
|
|
|
|
short_form = ISC_TRUE;
|
2000-06-21 01:40:42 +00:00
|
|
|
} else if (strncasecmp(opt, "d2", 2) == 0) {
|
|
|
|
debugging = ISC_TRUE;
|
|
|
|
} else if (strncasecmp(opt, "nod2", 4) == 0) {
|
|
|
|
debugging = ISC_FALSE;
|
2000-06-15 00:22:21 +00:00
|
|
|
} else if (strncasecmp(opt, "sil",3) == 0) {
|
2000-06-15 18:24:08 +00:00
|
|
|
deprecation_msg = ISC_FALSE;
|
2000-08-02 17:58:07 +00:00
|
|
|
} else {
|
|
|
|
srv = make_server(opt);
|
|
|
|
debug("server is %s", srv->servername);
|
|
|
|
ISC_LIST_APPEND(server_list, srv, link);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2000-08-02 17:58:07 +00:00
|
|
|
static dig_lookup_t*
|
2000-05-12 01:02:37 +00:00
|
|
|
addlookup(char *opt) {
|
2000-05-09 18:05:13 +00:00
|
|
|
dig_lookup_t *lookup;
|
2000-07-18 01:28:20 +00:00
|
|
|
isc_result_t result;
|
|
|
|
isc_textregion_t tr;
|
|
|
|
dns_rdatatype_t rdtype;
|
|
|
|
dns_rdataclass_t rdclass;
|
2000-05-12 01:02:37 +00:00
|
|
|
|
2000-08-07 23:54:46 +00:00
|
|
|
debug("addlookup()");
|
2000-07-18 01:28:20 +00:00
|
|
|
tr.base = deftype;
|
|
|
|
tr.length = strlen(deftype);
|
|
|
|
result = dns_rdatatype_fromtext(&rdtype, &tr);
|
2000-09-14 20:11:48 +00:00
|
|
|
if (result != ISC_R_SUCCESS) {
|
|
|
|
printf ("unknown query type: %s\n",deftype);
|
|
|
|
rdclass = dns_rdatatype_a;
|
|
|
|
}
|
2000-07-18 01:28:20 +00:00
|
|
|
tr.base = defclass;
|
|
|
|
tr.length = strlen(defclass);
|
|
|
|
result = dns_rdataclass_fromtext(&rdclass, &tr);
|
2000-09-14 20:11:48 +00:00
|
|
|
if (result != ISC_R_SUCCESS) {
|
|
|
|
printf ("unknown query class: %s\n",defclass);
|
|
|
|
rdclass = dns_rdataclass_in;
|
|
|
|
}
|
2000-07-18 01:28:20 +00:00
|
|
|
lookup = make_empty_lookup();
|
2000-05-12 01:02:37 +00:00
|
|
|
strncpy(lookup->textname, opt, MXNAME-1);
|
2000-07-18 01:28:20 +00:00
|
|
|
lookup->rdtype = rdtype;
|
|
|
|
lookup->rdclass = rdclass;
|
2000-06-19 18:54:45 +00:00
|
|
|
lookup->trace = ISC_TF(trace || ns_search_only);
|
2000-05-12 01:02:37 +00:00
|
|
|
lookup->trace_root = trace;
|
|
|
|
lookup->ns_search_only = ns_search_only;
|
|
|
|
lookup->identify = identify;
|
|
|
|
lookup->recurse = recurse;
|
|
|
|
lookup->aaonly = aaonly;
|
2000-05-09 18:05:13 +00:00
|
|
|
lookup->retries = tries;
|
2000-05-12 01:02:37 +00:00
|
|
|
lookup->udpsize = bufsize;
|
|
|
|
lookup->comments = comments;
|
2000-05-12 18:45:38 +00:00
|
|
|
lookup->tcp_mode = tcpmode;
|
2000-05-12 01:02:37 +00:00
|
|
|
lookup->stats = stats;
|
|
|
|
lookup->section_question = section_question;
|
|
|
|
lookup->section_answer = section_answer;
|
|
|
|
lookup->section_authority = section_authority;
|
|
|
|
lookup->section_additional = section_additional;
|
2000-05-24 19:49:51 +00:00
|
|
|
lookup->new_search = ISC_TRUE;
|
2000-05-09 18:05:13 +00:00
|
|
|
ISC_LIST_INIT(lookup->q);
|
|
|
|
ISC_LIST_APPEND(lookup_list, lookup, link);
|
|
|
|
lookup->origin = NULL;
|
|
|
|
ISC_LIST_INIT(lookup->my_server_list);
|
2000-07-05 23:28:32 +00:00
|
|
|
debug("looking up %s", lookup->textname);
|
2000-08-02 17:58:07 +00:00
|
|
|
return (lookup);
|
2000-05-09 18:05:13 +00:00
|
|
|
}
|
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
static void
|
2000-06-19 18:54:45 +00:00
|
|
|
flush_server_list(void) {
|
2000-05-12 01:02:37 +00:00
|
|
|
dig_server_t *s, *ps;
|
|
|
|
|
2000-09-01 23:43:55 +00:00
|
|
|
debug("flush_server_list()");
|
2000-05-12 01:02:37 +00:00
|
|
|
s = ISC_LIST_HEAD(server_list);
|
|
|
|
while (s != NULL) {
|
|
|
|
ps = s;
|
|
|
|
s = ISC_LIST_NEXT(s, link);
|
|
|
|
ISC_LIST_DEQUEUE(server_list, ps, link);
|
|
|
|
isc_mem_free(mctx, ps);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2000-08-01 01:33:37 +00:00
|
|
|
/*
|
2000-05-12 01:02:37 +00:00
|
|
|
* This works on the global server list, instead of on a per-lookup
|
|
|
|
* server list, since the change is persistent.
|
|
|
|
*/
|
|
|
|
static void
|
|
|
|
setsrv(char *opt) {
|
|
|
|
dig_server_t *srv;
|
|
|
|
|
|
|
|
flush_server_list();
|
|
|
|
srv=isc_mem_allocate(mctx, sizeof(struct dig_server));
|
|
|
|
if (srv == NULL)
|
|
|
|
fatal("Memory allocation failure.");
|
|
|
|
strncpy(srv->servername, opt, MXNAME-1);
|
|
|
|
ISC_LIST_APPEND(server_list, srv, link);
|
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
2000-06-19 18:54:45 +00:00
|
|
|
get_next_command(void) {
|
2000-05-12 01:02:37 +00:00
|
|
|
char input[COMMSIZE];
|
|
|
|
char *ptr, *arg;
|
|
|
|
|
|
|
|
fputs("> ", stderr);
|
|
|
|
ptr = fgets(input, COMMSIZE, stdin);
|
|
|
|
if (ptr == NULL) {
|
|
|
|
in_use = ISC_FALSE;
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
ptr = strtok(input, " \t\r\n");
|
2000-09-01 22:45:16 +00:00
|
|
|
if (ptr == NULL)
|
2000-05-12 01:02:37 +00:00
|
|
|
return;
|
|
|
|
arg = strtok(NULL, " \t\r\n");
|
|
|
|
if ((strcasecmp(ptr, "set") == 0) &&
|
|
|
|
(arg != NULL))
|
|
|
|
setoption(arg);
|
|
|
|
else if ((strcasecmp(ptr, "server") == 0) ||
|
|
|
|
(strcasecmp(ptr, "lserver") == 0)) {
|
2000-08-01 01:33:37 +00:00
|
|
|
printf("Server:\t%s\n", arg);
|
2000-05-12 01:02:37 +00:00
|
|
|
setsrv(arg);
|
2000-09-01 22:14:32 +00:00
|
|
|
} else if (strcasecmp(ptr, "exit") == 0) {
|
|
|
|
in_use = ISC_FALSE;
|
|
|
|
return;
|
2000-09-01 22:45:16 +00:00
|
|
|
} else if (strcasecmp(ptr, "help") == 0 ||
|
|
|
|
strcasecmp(ptr, "?") == 0)
|
|
|
|
{
|
|
|
|
printf("The '%s' command is not yet implemented.\n", ptr);
|
|
|
|
return;
|
|
|
|
} else if (strcasecmp(ptr, "finger") == 0 ||
|
|
|
|
strcasecmp(ptr, "root") == 0 ||
|
|
|
|
strcasecmp(ptr, "ls") == 0 ||
|
|
|
|
strcasecmp(ptr, "view") == 0)
|
|
|
|
{
|
|
|
|
printf("The '%s' command is not implemented.\n", ptr);
|
|
|
|
return;
|
2000-08-01 01:33:37 +00:00
|
|
|
} else
|
2000-05-12 01:02:37 +00:00
|
|
|
addlookup(ptr);
|
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
|
|
|
parse_args(int argc, char **argv) {
|
|
|
|
dig_lookup_t *lookup = NULL;
|
2000-08-03 17:43:06 +00:00
|
|
|
isc_boolean_t have_lookup = ISC_FALSE;
|
2000-05-12 01:02:37 +00:00
|
|
|
|
|
|
|
for (argc--, argv++; argc > 0; argc--, argv++) {
|
2000-08-07 23:54:46 +00:00
|
|
|
debug("main parsing %s", argv[0]);
|
2000-05-12 01:02:37 +00:00
|
|
|
if (argv[0][0] == '-') {
|
|
|
|
if ((argv[0][1] == 'h') &&
|
|
|
|
(argv[0][2] == 0)) {
|
|
|
|
show_usage();
|
|
|
|
exit (1);
|
|
|
|
}
|
|
|
|
if (argv[0][1] != 0)
|
|
|
|
setoption(&argv[0][1]);
|
2000-08-03 17:43:06 +00:00
|
|
|
else
|
|
|
|
have_lookup = ISC_TRUE;
|
2000-05-12 01:02:37 +00:00
|
|
|
} else {
|
2000-08-03 17:43:06 +00:00
|
|
|
if (!have_lookup) {
|
|
|
|
have_lookup = ISC_TRUE;
|
2000-05-12 01:02:37 +00:00
|
|
|
in_use = ISC_TRUE;
|
2000-08-03 17:43:06 +00:00
|
|
|
lookup = addlookup(argv[0]);
|
2000-05-12 01:02:37 +00:00
|
|
|
}
|
|
|
|
else
|
|
|
|
setsrv(argv[0]);
|
|
|
|
}
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
static void
|
|
|
|
flush_lookup_list(void) {
|
|
|
|
dig_lookup_t *l, *lp;
|
|
|
|
dig_query_t *q, *qp;
|
|
|
|
dig_server_t *s, *sp;
|
|
|
|
|
|
|
|
lookup_counter = 0;
|
|
|
|
l = ISC_LIST_HEAD(lookup_list);
|
|
|
|
while (l != NULL) {
|
|
|
|
q = ISC_LIST_HEAD(l->q);
|
|
|
|
while (q != NULL) {
|
|
|
|
if (q->sock != NULL) {
|
|
|
|
isc_socket_cancel(q->sock, NULL,
|
|
|
|
ISC_SOCKCANCEL_ALL);
|
|
|
|
isc_socket_detach(&q->sock);
|
|
|
|
}
|
|
|
|
if (ISC_LINK_LINKED(&q->recvbuf, link))
|
|
|
|
ISC_LIST_DEQUEUE(q->recvlist, &q->recvbuf,
|
|
|
|
link);
|
|
|
|
if (ISC_LINK_LINKED(&q->lengthbuf, link))
|
|
|
|
ISC_LIST_DEQUEUE(q->lengthlist, &q->lengthbuf,
|
|
|
|
link);
|
|
|
|
isc_buffer_invalidate(&q->recvbuf);
|
|
|
|
isc_buffer_invalidate(&q->lengthbuf);
|
|
|
|
qp = q;
|
|
|
|
q = ISC_LIST_NEXT(q, link);
|
|
|
|
ISC_LIST_DEQUEUE(l->q, qp, link);
|
|
|
|
isc_mem_free(mctx, qp);
|
|
|
|
}
|
2000-07-14 16:35:30 +00:00
|
|
|
s = ISC_LIST_HEAD(l->my_server_list);
|
|
|
|
while (s != NULL) {
|
|
|
|
sp = s;
|
|
|
|
s = ISC_LIST_NEXT(s, link);
|
|
|
|
ISC_LIST_DEQUEUE(l->my_server_list, sp, link);
|
|
|
|
isc_mem_free(mctx, sp);
|
2000-08-01 01:33:37 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
}
|
|
|
|
if (l->sendmsg != NULL)
|
|
|
|
dns_message_destroy(&l->sendmsg);
|
|
|
|
if (l->timer != NULL)
|
|
|
|
isc_timer_detach(&l->timer);
|
|
|
|
lp = l;
|
|
|
|
l = ISC_LIST_NEXT(l, link);
|
|
|
|
ISC_LIST_DEQUEUE(lookup_list, lp, link);
|
|
|
|
isc_mem_free(mctx, lp);
|
|
|
|
}
|
2000-08-01 01:33:37 +00:00
|
|
|
}
|
2000-05-12 01:02:37 +00:00
|
|
|
|
2000-09-01 23:43:55 +00:00
|
|
|
static void
|
|
|
|
getinput(isc_task_t *task, isc_event_t *event) {
|
|
|
|
UNUSED(task);
|
|
|
|
if (global_event == NULL)
|
|
|
|
global_event = event;
|
|
|
|
isc_app_block();
|
|
|
|
get_next_command();
|
|
|
|
isc_app_unblock();
|
|
|
|
if (ISC_LIST_HEAD(lookup_list) != NULL)
|
|
|
|
start_lookup();
|
|
|
|
else
|
|
|
|
isc_app_shutdown();
|
|
|
|
}
|
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
int
|
|
|
|
main(int argc, char **argv) {
|
|
|
|
isc_result_t result;
|
|
|
|
|
|
|
|
ISC_LIST_INIT(lookup_list);
|
|
|
|
ISC_LIST_INIT(server_list);
|
|
|
|
ISC_LIST_INIT(search_list);
|
|
|
|
|
2000-09-01 23:43:55 +00:00
|
|
|
result = isc_app_start();
|
|
|
|
check_result(result, "isc_app_start");
|
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
setup_libs();
|
2000-07-05 23:28:32 +00:00
|
|
|
progname = argv[0];
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-05-12 01:02:37 +00:00
|
|
|
parse_args(argc, argv);
|
2000-06-15 00:22:21 +00:00
|
|
|
|
2000-06-15 18:24:08 +00:00
|
|
|
if (deprecation_msg) {
|
2000-08-09 18:35:40 +00:00
|
|
|
fputs(
|
2000-06-15 18:24:08 +00:00
|
|
|
"Note: nslookup is deprecated and may be removed from future releases.\n"
|
2000-06-20 00:21:15 +00:00
|
|
|
"Consider using the `dig' or `host' programs instead. Run nslookup with\n"
|
2000-08-09 18:35:40 +00:00
|
|
|
"the `-sil[ent]' option to prevent this message from appearing.\n", stderr);
|
2000-06-15 00:22:21 +00:00
|
|
|
}
|
2000-05-09 18:05:13 +00:00
|
|
|
setup_system();
|
|
|
|
|
2000-09-01 23:43:55 +00:00
|
|
|
if (in_use)
|
|
|
|
result = isc_app_onrun(mctx, global_task, onrun_callback,
|
|
|
|
NULL);
|
|
|
|
else
|
|
|
|
result = isc_app_onrun(mctx, global_task, getinput, NULL);
|
|
|
|
check_result(result, "isc_app_onrun");
|
|
|
|
in_use = ISC_TF(!in_use);
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-09-01 23:43:55 +00:00
|
|
|
(void)isc_app_run();
|
2000-05-09 18:05:13 +00:00
|
|
|
|
2000-08-07 23:54:46 +00:00
|
|
|
puts("");
|
|
|
|
debug("done, and starting to shut down");
|
2000-09-01 23:43:55 +00:00
|
|
|
if (global_event != NULL)
|
|
|
|
isc_event_free(&global_event);
|
2000-07-18 01:28:20 +00:00
|
|
|
destroy_libs();
|
2000-06-29 05:21:12 +00:00
|
|
|
isc_app_finish();
|
2000-08-01 01:33:37 +00:00
|
|
|
|
2000-05-09 18:05:13 +00:00
|
|
|
return (0);
|
|
|
|
}
|