|
|
1.1 root 1: /*
2: * Copyright (c) 1985 Regents of the University of California.
3: * All rights reserved.
4: *
5: * Redistribution and use in source and binary forms are permitted
6: * provided that the above copyright notice and this paragraph are
7: * duplicated in all such forms and that any documentation,
8: * advertising materials, and other materials related to such
9: * distribution and use acknowledge that the software was developed
10: * by the University of California, Berkeley. The name of the
11: * University may not be used to endorse or promote products derived
12: * from this software without specific prior written permission.
13: * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR
14: * IMPLIED WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED
15: * WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR A PARTICULAR PURPOSE.
16: */
17:
18: #if defined(LIBC_SCCS) && !defined(lint)
19: static char sccsid[] = "@(#)res_debug.c 5.24 (Berkeley) 6/27/88";
20: #endif /* LIBC_SCCS and not lint */
21:
22: #if defined(lint) && !defined(DEBUG)
23: #define DEBUG
24: #endif
25:
26: #include <sys/types.h>
27: #include <netinet/in.h>
28: #include <stdio.h>
29: #include <arpa/nameser.h>
30:
31: extern char *p_cdname(), *p_rr(), *p_type(), *p_class(), *p_time();
32: extern char *inet_ntoa();
33:
34: char *_res_opcodes[] = {
35: "QUERY",
36: "IQUERY",
37: "CQUERYM",
38: "CQUERYU",
39: "4",
40: "5",
41: "6",
42: "7",
43: "8",
44: "UPDATEA",
45: "UPDATED",
46: "UPDATEDA",
47: "UPDATEM",
48: "UPDATEMA",
49: "ZONEINIT",
50: "ZONEREF",
51: };
52:
53: char *_res_resultcodes[] = {
54: "NOERROR",
55: "FORMERR",
56: "SERVFAIL",
57: "NXDOMAIN",
58: "NOTIMP",
59: "REFUSED",
60: "6",
61: "7",
62: "8",
63: "9",
64: "10",
65: "11",
66: "12",
67: "13",
68: "14",
69: "NOCHANGE",
70: };
71:
72: p_query(msg)
73: char *msg;
74: {
75: #ifdef DEBUG
76: fp_query(msg,stdout);
77: #endif
78: }
79:
80: /*
81: * Print the contents of a query.
82: * This is intended to be primarily a debugging routine.
83: */
84: fp_query(msg,file)
85: char *msg;
86: FILE *file;
87: {
88: #ifdef DEBUG
89: register char *cp;
90: register HEADER *hp;
91: register int n;
92:
93: /*
94: * Print header fields.
95: */
96: hp = (HEADER *)msg;
97: cp = msg + sizeof(HEADER);
98: fprintf(file,"HEADER:\n");
99: fprintf(file,"\topcode = %s", _res_opcodes[hp->opcode]);
100: fprintf(file,", id = %d", ntohs(hp->id));
101: fprintf(file,", rcode = %s\n", _res_resultcodes[hp->rcode]);
102: fprintf(file,"\theader flags: ");
103: if (hp->qr)
104: fprintf(file," qr");
105: if (hp->aa)
106: fprintf(file," aa");
107: if (hp->tc)
108: fprintf(file," tc");
109: if (hp->rd)
110: fprintf(file," rd");
111: if (hp->ra)
112: fprintf(file," ra");
113: if (hp->pr)
114: fprintf(file," pr");
115: fprintf(file,"\n\tqdcount = %d", ntohs(hp->qdcount));
116: fprintf(file,", ancount = %d", ntohs(hp->ancount));
117: fprintf(file,", nscount = %d", ntohs(hp->nscount));
118: fprintf(file,", arcount = %d\n\n", ntohs(hp->arcount));
119: /*
120: * Print question records.
121: */
122: if (n = ntohs(hp->qdcount)) {
123: fprintf(file,"QUESTIONS:\n");
124: while (--n >= 0) {
125: fprintf(file,"\t");
126: cp = p_cdname(cp, msg, file);
127: if (cp == NULL)
128: return;
129: fprintf(file,", type = %s", p_type(_getshort(cp)));
130: cp += sizeof(u_short);
131: fprintf(file,", class = %s\n\n", p_class(_getshort(cp)));
132: cp += sizeof(u_short);
133: }
134: }
135: /*
136: * Print authoritative answer records
137: */
138: if (n = ntohs(hp->ancount)) {
139: fprintf(file,"ANSWERS:\n");
140: while (--n >= 0) {
141: fprintf(file,"\t");
142: cp = p_rr(cp, msg, file);
143: if (cp == NULL)
144: return;
145: }
146: }
147: /*
148: * print name server records
149: */
150: if (n = ntohs(hp->nscount)) {
151: fprintf(file,"NAME SERVERS:\n");
152: while (--n >= 0) {
153: fprintf(file,"\t");
154: cp = p_rr(cp, msg, file);
155: if (cp == NULL)
156: return;
157: }
158: }
159: /*
160: * print additional records
161: */
162: if (n = ntohs(hp->arcount)) {
163: fprintf(file,"ADDITIONAL RECORDS:\n");
164: while (--n >= 0) {
165: fprintf(file,"\t");
166: cp = p_rr(cp, msg, file);
167: if (cp == NULL)
168: return;
169: }
170: }
171: #endif
172: }
173:
174: char *
175: p_cdname(cp, msg, file)
176: char *cp, *msg;
177: FILE *file;
178: {
179: #ifdef DEBUG
180: char name[MAXDNAME];
181: int n;
182:
183: if ((n = dn_expand(msg, msg + 512, cp, name, sizeof(name))) < 0)
184: return (NULL);
185: if (name[0] == '\0') {
186: name[0] = '.';
187: name[1] = '\0';
188: }
189: fputs(name, file);
190: return (cp + n);
191: #endif
192: }
193:
194: /*
195: * Print resource record fields in human readable form.
196: */
197: char *
198: p_rr(cp, msg, file)
199: char *cp, *msg;
200: FILE *file;
201: {
202: #ifdef DEBUG
203: int type, class, dlen, n, c;
204: struct in_addr inaddr;
205: char *cp1;
206:
207: if ((cp = p_cdname(cp, msg, file)) == NULL)
208: return (NULL); /* compression error */
209: fprintf(file,"\n\ttype = %s", p_type(type = _getshort(cp)));
210: cp += sizeof(u_short);
211: fprintf(file,", class = %s", p_class(class = _getshort(cp)));
212: cp += sizeof(u_short);
213: fprintf(file,", ttl = %s", p_time(cp));
214: cp += sizeof(u_long);
215: fprintf(file,", dlen = %d\n", dlen = _getshort(cp));
216: cp += sizeof(u_short);
217: cp1 = cp;
218: /*
219: * Print type specific data, if appropriate
220: */
221: switch (type) {
222: case T_A:
223: switch (class) {
224: case C_IN:
225: bcopy(cp, (char *)&inaddr, sizeof(inaddr));
226: if (dlen == 4) {
227: fprintf(file,"\tinternet address = %s\n",
228: inet_ntoa(inaddr));
229: cp += dlen;
230: } else if (dlen == 7) {
231: fprintf(file,"\tinternet address = %s",
232: inet_ntoa(inaddr));
233: fprintf(file,", protocol = %d", cp[4]);
234: fprintf(file,", port = %d\n",
235: (cp[5] << 8) + cp[6]);
236: cp += dlen;
237: }
238: break;
239: default:
240: cp += dlen;
241: }
242: break;
243: case T_CNAME:
244: case T_MB:
245: #ifdef OLDRR
246: case T_MD:
247: case T_MF:
248: #endif /* OLDRR */
249: case T_MG:
250: case T_MR:
251: case T_NS:
252: case T_PTR:
253: fprintf(file,"\tdomain name = ");
254: cp = p_cdname(cp, msg, file);
255: fprintf(file,"\n");
256: break;
257:
258: case T_HINFO:
259: if (n = *cp++) {
260: fprintf(file,"\tCPU=%.*s\n", n, cp);
261: cp += n;
262: }
263: if (n = *cp++) {
264: fprintf(file,"\tOS=%.*s\n", n, cp);
265: cp += n;
266: }
267: break;
268:
269: case T_SOA:
270: fprintf(file,"\torigin = ");
271: cp = p_cdname(cp, msg, file);
272: fprintf(file,"\n\tmail addr = ");
273: cp = p_cdname(cp, msg, file);
274: fprintf(file,"\n\tserial=%ld", _getlong(cp));
275: cp += sizeof(u_long);
276: fprintf(file,", refresh=%s", p_time(cp));
277: cp += sizeof(u_long);
278: fprintf(file,", retry=%s", p_time(cp));
279: cp += sizeof(u_long);
280: fprintf(file,", expire=%s", p_time(cp));
281: cp += sizeof(u_long);
282: fprintf(file,", min=%s\n", p_time(cp));
283: cp += sizeof(u_long);
284: break;
285:
286: case T_MX:
287: fprintf(file,"\tpreference = %ld,",_getshort(cp));
288: cp += sizeof(u_short);
289: fprintf(file," name = ");
290: cp = p_cdname(cp, msg, file);
291: break;
292:
293: case T_MINFO:
294: fprintf(file,"\trequests = ");
295: cp = p_cdname(cp, msg, file);
296: fprintf(file,"\n\terrors = ");
297: cp = p_cdname(cp, msg, file);
298: break;
299:
300: case T_UINFO:
301: fprintf(file,"\t%s\n", cp);
302: cp += dlen;
303: break;
304:
305: case T_UID:
306: case T_GID:
307: if (dlen == 4) {
308: fprintf(file,"\t%ld\n", _getlong(cp));
309: cp += sizeof(int);
310: }
311: break;
312:
313: case T_WKS:
314: if (dlen < sizeof(u_long) + 1)
315: break;
316: bcopy(cp, (char *)&inaddr, sizeof(inaddr));
317: cp += sizeof(u_long);
318: fprintf(file,"\tinternet address = %s, protocol = %d\n\t",
319: inet_ntoa(inaddr), *cp++);
320: n = 0;
321: while (cp < cp1 + dlen) {
322: c = *cp++;
323: do {
324: if (c & 0200)
325: fprintf(file," %d", n);
326: c <<= 1;
327: } while (++n & 07);
328: }
329: putc('\n',file);
330: break;
331:
332: #ifdef ALLOW_T_UNSPEC
333: case T_UNSPEC:
334: {
335: int NumBytes = 8;
336: char *DataPtr;
337: int i;
338:
339: if (dlen < NumBytes) NumBytes = dlen;
340: fprintf(file, "\tFirst %d bytes of hex data:",
341: NumBytes);
342: for (i = 0, DataPtr = cp; i < NumBytes; i++, DataPtr++)
343: fprintf(file, " %x", *DataPtr);
344: fputs("\n", file);
345: cp += dlen;
346: }
347: break;
348: #endif /* ALLOW_T_UNSPEC */
349:
350: default:
351: fprintf(file,"\t???\n");
352: cp += dlen;
353: }
354: if (cp != cp1 + dlen)
355: fprintf(file,"packet size error (%#x != %#x)\n", cp, cp1+dlen);
356: fprintf(file,"\n");
357: return (cp);
358: #endif
359: }
360:
361: static char nbuf[40];
362:
363: /*
364: * Return a string for the type
365: */
366: char *
367: p_type(type)
368: int type;
369: {
370: switch (type) {
371: case T_A:
372: return("A");
373: case T_NS: /* authoritative server */
374: return("NS");
375: #ifdef OLDRR
376: case T_MD: /* mail destination */
377: return("MD");
378: case T_MF: /* mail forwarder */
379: return("MF");
380: #endif /* OLDRR */
381: case T_CNAME: /* connonical name */
382: return("CNAME");
383: case T_SOA: /* start of authority zone */
384: return("SOA");
385: case T_MB: /* mailbox domain name */
386: return("MB");
387: case T_MG: /* mail group member */
388: return("MG");
389: case T_MX: /* mail routing info */
390: return("MX");
391: case T_MR: /* mail rename name */
392: return("MR");
393: case T_NULL: /* null resource record */
394: return("NULL");
395: case T_WKS: /* well known service */
396: return("WKS");
397: case T_PTR: /* domain name pointer */
398: return("PTR");
399: case T_HINFO: /* host information */
400: return("HINFO");
401: case T_MINFO: /* mailbox information */
402: return("MINFO");
403: case T_AXFR: /* zone transfer */
404: return("AXFR");
405: case T_MAILB: /* mail box */
406: return("MAILB");
407: case T_MAILA: /* mail address */
408: return("MAILA");
409: case T_ANY: /* matches any type */
410: return("ANY");
411: case T_UINFO:
412: return("UINFO");
413: case T_UID:
414: return("UID");
415: case T_GID:
416: return("GID");
417: #ifdef ALLOW_T_UNSPEC
418: case T_UNSPEC:
419: return("UNSPEC");
420: #endif /* ALLOW_T_UNSPEC */
421: default:
422: (void)sprintf(nbuf, "%d", type);
423: return(nbuf);
424: }
425: }
426:
427: /*
428: * Return a mnemonic for class
429: */
430: char *
431: p_class(class)
432: int class;
433: {
434:
435: switch (class) {
436: case C_IN: /* internet class */
437: return("IN");
438: case C_ANY: /* matches any class */
439: return("ANY");
440: default:
441: (void)sprintf(nbuf, "%d", class);
442: return(nbuf);
443: }
444: }
445:
446: /*
447: * Return a mnemonic for a time to live
448: */
449: char
450: *p_time(value)
451: u_long value;
452: {
453: int secs, mins, hours;
454: register char *p;
455:
456: secs = value % 60;
457: value /= 60;
458: mins = value % 60;
459: value /= 60;
460: hours = value % 24;
461: value /= 24;
462:
463: #define PLURALIZE(x) x, (x == 1) ? "" : "s"
464: p = nbuf;
465: if (value) {
466: (void)sprintf(p, "%d day%s", PLURALIZE(value));
467: while (*++p);
468: }
469: if (hours) {
470: if (p != nbuf)
471: *p++ = ' ';
472: (void)sprintf(p, "%d hour%s", PLURALIZE(hours));
473: while (*++p);
474: }
475: if (mins) {
476: if (p != nbuf)
477: *p++ = ' ';
478: (void)sprintf(p, "%d min%s", PLURALIZE(mins));
479: while (*++p);
480: }
481: if (secs) {
482: if (p != nbuf)
483: *p++ = ' ';
484: (void)sprintf(p, "%d sec%s", PLURALIZE(secs));
485: while (*++p);
486: }
487: return(nbuf);
488: }
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.