]> git.ipfire.org Git - thirdparty/ldns.git/commitdiff
added new test that reads packet from drill-formatted hexdump
authorJelte Jansen <jeltejan@NLnetLabs.nl>
Fri, 24 Dec 2004 11:34:38 +0000 (11:34 +0000)
committerJelte Jansen <jeltejan@NLnetLabs.nl>
Fri, 24 Dec 2004 11:34:38 +0000 (11:34 +0000)
(which can be created with drill -w <file> <query>), for wire2host
and host2str testing)

added example hexdump packet (which is read if no filename is given)

fixed bug when reading bad rcode

Makefile.in
host2str.c
packetdump.txt [new file with mode: 0644]
run-test2.c [new file with mode: 0644]

index 41fa9c6753a8a12560eb5f77dc542a7451263247..0e2796196ba0603373493a36b6d5059475aa766a 100644 (file)
@@ -34,7 +34,7 @@ LIBDNS_HEADERS        =       ldns/error.h            \
                        util.h
 LIBDNS_OBJECTS =       $(LIBDNS_SOURCES:.c=.o)
 
-ALL_SOURCES    =       run-test0.c run-test1.c $(LIBDNS_SOURCES)
+ALL_SOURCES    =       run-test0.c run-test1.c run-test2.c $(LIBDNS_SOURCES)
 
 COMPILE                = $(CC) $(CPPFLAGS) $(CFLAGS)
 LINK           = $(CC) $(CFLAGS) $(LDFLAGS)
@@ -44,7 +44,7 @@ LINK          = $(CC) $(CFLAGS) $(LDFLAGS)
 
 .PHONY:        clean realclean docclean doc lint
 
-all:   run-test0 run-test1
+all:   run-test0 run-test1 run-test2
 
 run-test0:     run-test0.o $(LIBDNS_OBJECTS) $(LIBOBJS)
                $(LINK) -o $@ $+
@@ -52,12 +52,17 @@ run-test0:  run-test0.o $(LIBDNS_OBJECTS) $(LIBOBJS)
 run-test1:     run-test1.o $(LIBDNS_OBJECTS) $(LIBOBJS)
                $(LINK) -o $@ $+
 
+run-test2:     run-test2.o $(LIBDNS_OBJECTS) $(LIBOBJS)
+               $(LINK) -o $@ $+
+
 doc:   
        doxygen libdns.doxygen
 
 clean: 
        rm -f *.o *.d
        rm -f run-test0
+       rm -f run-test1
+       rm -f run-test2
        rm -rf autom4te.cache/
        rm -f aclocal.m4
 
@@ -78,7 +83,10 @@ test0: run-test0
 test1: run-test1
        ./run-test1
 
-test: test0 test1
+test2: run-test2
+       ./run-test2
+
+test: test0 test1 test2
 
 lint:
        for i in $(ALL_SOURCES); do \
index 9163d2cae514f5c456ebe4e833faa552e3a78146..8c207d5e3e5cc1cd775f4b1926225d215ac5fbde 100644 (file)
@@ -326,15 +326,28 @@ ldns_status
 ldns_pktheader2buffer(ldns_buffer *output, ldns_pkt *pkt)
 {
        /* TODO: strings for known names instead of numbers, flags etc */
+       const char *opcode_str, *rcode_str;
+       ldns_lookup_table *opcode = ldns_lookup_by_id(ldns_opcodes,
+                                           (int) ldns_pkt_opcode(pkt));
+       ldns_lookup_table *rcode = ldns_lookup_by_id(ldns_rcodes,
+                                           (int) ldns_pkt_rcode(pkt));
+
+       if (opcode) {
+               opcode_str = opcode->name;
+       } else {
+               opcode_str = "??";
+       }
+       if (rcode) {
+               rcode_str = rcode->name;
+       } else {
+               rcode_str = "??";
+       }
+       
        if (
            ldns_buffer_printf(output, ";; ->>HEADER<<- ") < 0 ||
-           ldns_buffer_printf(output, "opcode: %s, ", 
-                              ldns_lookup_by_id(ldns_opcodes,
-                                                 (int) ldns_pkt_opcode(pkt))->name
+           ldns_buffer_printf(output, "opcode: %s, ", opcode_str
                              ) < 0 ||
-           ldns_buffer_printf(output, "status: %s, ",
-                              ldns_lookup_by_id(ldns_rcodes,
-                                                (int) ldns_pkt_rcode(pkt))->name
+           ldns_buffer_printf(output, "rcode: %s, ", rcode_str
                              ) < 0 ||
            ldns_buffer_printf(output, "id %lu\n", ldns_pkt_id(pkt)) < 0 ||
            ldns_buffer_printf(output, ";; flags: ") < 0
diff --git a/packetdump.txt b/packetdump.txt
new file mode 100644 (file)
index 0000000..75278c3
--- /dev/null
@@ -0,0 +1,14 @@
+; 0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19 
+;-- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- -- 
+ 18 c4 81 80 00 01 00 01 00 02 00 02 03 77 77 77 0b 6b 61 6e   ;   0- 19
+ 61 72 69 65 70 69 65 74 03 63 6f 6d 00 00 01 00 01 03 77 77   ;  20- 39
+ 77 0b 6b 61 6e 61 72 69 65 70 69 65 74 03 63 6f 6d 00 00 01   ;  40- 59
+ 00 01 00 01 44 0a 00 04 d5 85 27 cf 0b 6b 61 6e 61 72 69 65   ;  60- 79
+ 70 69 65 74 03 63 6f 6d 00 00 02 00 01 00 01 44 0a 00 11 03   ;  80- 99
+ 6e 73 32 08 68 65 78 6f 6e 2d 69 73 02 6e 6c 00 0b 6b 61 6e   ; 100-119
+ 61 72 69 65 70 69 65 74 03 63 6f 6d 00 00 02 00 01 00 01 44   ; 120-139
+ 0a 00 11 03 6e 73 31 08 68 65 78 6f 6e 2d 69 73 02 6e 6c 00   ; 140-159
+ 03 6e 73 31 08 68 65 78 6f 6e 2d 69 73 02 6e 6c 00 00 01 00   ; 160-179
+ 01 00 00 5d 8c 00 04 d5 85 27 cb 03 6e 73 32 08 68 65 78 6f   ; 180-199
+ 6e 2d 69 73 02 6e 6c 00 00 01 00 01 00 00 5d 8c 00 04 d4 cc   ; 200-219
+ db 5b                                                         ; 220-221
diff --git a/run-test2.c b/run-test2.c
new file mode 100644 (file)
index 0000000..683a5c9
--- /dev/null
@@ -0,0 +1,196 @@
+/* 
+ * test2, read hexdump of file and print query
+ *
+ * reading code taken from drill, maybe put it in the library?
+ * (rewritten cleanly of course, and with error checking)
+ */
+
+#include <config.h>
+#include <ldns/ldns.h>
+#include <ldns/str2host.h>
+#include <ldns/host2str.h>
+#include <ldns/buffer.h>
+
+#include "util.h"
+
+#define MAX_PACKET 1000
+
+/**
+ * Converts a hex string to binary data
+ * len is the length of the string
+ * buf is the buffer to store the result in
+ * offset is the starting position in the result buffer
+ *
+ * This function returns the length of the result
+ */
+size_t
+hexstr2bin(char *hexstr, int len, uint8_t *buf, size_t offset)
+{
+       char c;
+       int i; 
+       uint8_t int8 = 0;
+       int sec = 0;
+       size_t bufpos = 0;
+       
+       if (len % 2 != 0) {
+               return 0;
+       }
+
+       for (i=0; i<len; i++) {
+               c = hexstr[i];
+
+               /* case insensitive, skip spaces */
+               if (c != ' ') {
+                       if (c >= '0' && c <= '9') {
+                               int8 += c & 0x0f;  
+                       } else if (c >= 'a' && c <= 'z') {
+                               int8 += (c & 0x0f) + 9;   
+                       } else if (c >= 'A' && c <= 'Z') {
+                               int8 += (c & 0x0f) + 9;   
+                       } else {
+                               printf("Error in reading hex data: \n");
+                               printf("%s ('%c' at %d, should read %d bytes)\n", hexstr, c, i, len);
+                               return 0;
+                       }
+                        
+                       if (sec == 0) {
+                               int8 = int8 << 4;
+                               sec = 1;
+                       } else {
+
+                               buf[bufpos+offset] = int8;
+                               int8 = 0;
+                               sec = 0; 
+                               bufpos++;
+                       }
+               }
+                 
+        }
+        return bufpos;        
+}
+
+
+ldns_pkt *
+file2pkt(const char *filename)
+{
+       ldns_pkt *pkt;
+       FILE *fp = NULL;
+       char c;
+       ldns_status status;
+       
+       /* stat hack
+        * 0 = normal
+        * 1 = comment (skip to end of line)
+        * 2 = unprintable character found, read binary data directly
+        */
+       int state = 0;
+       uint8_t *hexbuf = XMALLOC(uint8_t, MAX_PACKET);
+       int hexbufpos = 0;
+       size_t wirelen;
+       uint8_t *wire = XMALLOC(uint8_t, MAX_PACKET);
+       
+       if (strncmp(filename, "-", 2) == 0) {
+               fp = stdin;
+       } else {
+               fp = fopen(filename, "r");
+       }
+       if (fp == NULL) {
+               printf("Unable to open file for reading: %s\n", filename);
+               return NULL;
+       }
+
+       printf("Opened %s\n", filename);
+       
+       c = fgetc(fp);
+       while (c != EOF && hexbufpos < MAX_PACKET) {
+               if (state < 2 && !isascii(c)) {
+                       printf("non ascii character found in file: (%d) switching to raw mode\n", c);
+                       state = 2;
+               }
+               switch (state) {
+                       case 0:
+                               if (    (c >= '0' && c <= '9') ||
+                                       (c >= 'a' && c <= 'f') ||
+                                       (c >= 'A' && c <= 'F') )
+                               {
+                                       hexbuf[hexbufpos] = (uint8_t) c;
+                                       hexbufpos++;
+                               } else if (c == ';') {
+                                       state = 1;
+                               } else if (c == ' ' || c == '\t' || c == '\n') {
+                                       /* skip whitespace */
+                               } 
+                               break;
+                       case 1:
+                               if (c == '\n' || c == EOF) {
+                                       state = 0;
+                               }
+                               break;
+                       case 2:
+                               hexbuf[hexbufpos] = (uint8_t) c;
+                               hexbufpos++;
+                               break;
+                       default:
+                               printf("unknown state while reading file\n");
+                               return NULL;
+                               break;
+               }
+               c = fgetc(fp);
+       }
+       if (c == EOF) {
+               if (state < 2) {
+                       printf("read:\n");
+                       printf("%s\n", (char *)hexbuf);
+               } else {
+                       printf("Not printing wire because it contains non ascii data\n");
+               }
+       }
+       if (hexbufpos >= MAX_PACKET) {
+               printf("packet size reached\n");
+       }
+       
+       /* lenient mode: length must be multiple of 2 */
+       if (hexbufpos % 2 != 0) {
+               hexbuf[hexbufpos] = (uint8_t) '0';
+               hexbufpos++;
+       }
+
+       if (state < 2) {
+               wirelen = hexstr2bin((char *) hexbuf, hexbufpos, wire, 0);
+       } else {
+               memcpy(wire, hexbuf, (size_t) hexbufpos);
+               wirelen = (size_t) hexbufpos;
+       }
+       
+       status = ldns_wire2pkt(&pkt, wire, wirelen);
+       
+       if (status == LDNS_STATUS_OK) {
+               return pkt;
+       } else {
+               printf("error in wire2pkt: %d\n", status);
+               return NULL;
+       }
+}
+
+
+int
+main(int argc, char **argv)
+{
+       const char *file;
+       ldns_pkt *pkt;
+       if (argc == 2) {
+               file = argv[1];
+       } else {
+               file = "packetdump.txt";
+       }
+       
+       pkt = file2pkt(file);
+       if (pkt) {
+               printf("packet:\n");
+               printf("%s", ldns_pkt2str(pkt));
+       } else {
+               printf("\n");
+       }
+       return 0;
+}
+