1b0453382SBill Fenner /* $NetBSD: print-ascii.c,v 1.1 1999/09/30 14:49:12 sjg Exp $ */ 2b0453382SBill Fenner 3b0453382SBill Fenner /*- 4b0453382SBill Fenner * Copyright (c) 1997, 1998 The NetBSD Foundation, Inc. 5b0453382SBill Fenner * All rights reserved. 6b0453382SBill Fenner * 7b0453382SBill Fenner * This code is derived from software contributed to The NetBSD Foundation 8b0453382SBill Fenner * by Alan Barrett and Simon J. Gerraty. 9b0453382SBill Fenner * 10b0453382SBill Fenner * Redistribution and use in source and binary forms, with or without 11b0453382SBill Fenner * modification, are permitted provided that the following conditions 12b0453382SBill Fenner * are met: 13b0453382SBill Fenner * 1. Redistributions of source code must retain the above copyright 14b0453382SBill Fenner * notice, this list of conditions and the following disclaimer. 15b0453382SBill Fenner * 2. Redistributions in binary form must reproduce the above copyright 16b0453382SBill Fenner * notice, this list of conditions and the following disclaimer in the 17b0453382SBill Fenner * documentation and/or other materials provided with the distribution. 18b0453382SBill Fenner * 3. All advertising materials mentioning features or use of this software 19b0453382SBill Fenner * must display the following acknowledgement: 20b0453382SBill Fenner * This product includes software developed by the NetBSD 21b0453382SBill Fenner * Foundation, Inc. and its contributors. 22b0453382SBill Fenner * 4. Neither the name of The NetBSD Foundation nor the names of its 23b0453382SBill Fenner * contributors may be used to endorse or promote products derived 24b0453382SBill Fenner * from this software without specific prior written permission. 25b0453382SBill Fenner * 26b0453382SBill Fenner * THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS 27b0453382SBill Fenner * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED 28b0453382SBill Fenner * TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 29b0453382SBill Fenner * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS 30b0453382SBill Fenner * BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 31b0453382SBill Fenner * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 32b0453382SBill Fenner * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 33b0453382SBill Fenner * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 34b0453382SBill Fenner * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 35b0453382SBill Fenner * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 36b0453382SBill Fenner * POSSIBILITY OF SUCH DAMAGE. 37b0453382SBill Fenner */ 38b0453382SBill Fenner 39*3340d773SGleb Smirnoff /* \summary: ASCII packet dump printer */ 40*3340d773SGleb Smirnoff 41b0453382SBill Fenner #ifdef HAVE_CONFIG_H 42b0453382SBill Fenner #include "config.h" 43b0453382SBill Fenner #endif 44b0453382SBill Fenner 45*3340d773SGleb Smirnoff #include <netdissect-stdinc.h> 46b0453382SBill Fenner #include <stdio.h> 47b0453382SBill Fenner 48*3340d773SGleb Smirnoff #include "netdissect.h" 49b0453382SBill Fenner 505b0fe478SBruce M Simpson #define ASCII_LINELENGTH 300 51b0453382SBill Fenner #define HEXDUMP_BYTES_PER_LINE 16 52b0453382SBill Fenner #define HEXDUMP_SHORTS_PER_LINE (HEXDUMP_BYTES_PER_LINE / 2) 53b0453382SBill Fenner #define HEXDUMP_HEXSTUFF_PER_SHORT 5 /* 4 hex digits and a space */ 54b0453382SBill Fenner #define HEXDUMP_HEXSTUFF_PER_LINE \ 55b0453382SBill Fenner (HEXDUMP_HEXSTUFF_PER_SHORT * HEXDUMP_SHORTS_PER_LINE) 56b0453382SBill Fenner 57b0453382SBill Fenner void 583c602fabSXin LI ascii_print(netdissect_options *ndo, 593c602fabSXin LI const u_char *cp, u_int length) 602ebc47dbSSam Leffler { 618bdc5a62SPatrick Kelsey u_int caplength; 623c602fabSXin LI register u_char s; 632ebc47dbSSam Leffler 648bdc5a62SPatrick Kelsey caplength = (ndo->ndo_snapend >= cp) ? ndo->ndo_snapend - cp : 0; 658bdc5a62SPatrick Kelsey if (length > caplength) 668bdc5a62SPatrick Kelsey length = caplength; 673c602fabSXin LI ND_PRINT((ndo, "\n")); 682ebc47dbSSam Leffler while (length > 0) { 692ebc47dbSSam Leffler s = *cp++; 702ebc47dbSSam Leffler length--; 713c602fabSXin LI if (s == '\r') { 723c602fabSXin LI /* 733c602fabSXin LI * Don't print CRs at the end of the line; they 743c602fabSXin LI * don't belong at the ends of lines on UN*X, 753c602fabSXin LI * and the standard I/O library will give us one 763c602fabSXin LI * on Windows so we don't need to print one 773c602fabSXin LI * ourselves. 783c602fabSXin LI * 793c602fabSXin LI * In the middle of a line, just print a '.'. 803c602fabSXin LI */ 813c602fabSXin LI if (length > 1 && *cp != '\n') 823c602fabSXin LI ND_PRINT((ndo, ".")); 833c602fabSXin LI } else { 843c602fabSXin LI if (!ND_ISGRAPH(s) && 853c602fabSXin LI (s != '\t' && s != ' ' && s != '\n')) 863c602fabSXin LI ND_PRINT((ndo, ".")); 872ebc47dbSSam Leffler else 883c602fabSXin LI ND_PRINT((ndo, "%c", s)); 893c602fabSXin LI } 902ebc47dbSSam Leffler } 912ebc47dbSSam Leffler } 922ebc47dbSSam Leffler 932ebc47dbSSam Leffler void 943c602fabSXin LI hex_and_ascii_print_with_offset(netdissect_options *ndo, register const char *ident, 952ebc47dbSSam Leffler register const u_char *cp, register u_int length, register u_int oset) 96b0453382SBill Fenner { 978bdc5a62SPatrick Kelsey u_int caplength; 98b0453382SBill Fenner register u_int i; 99b0453382SBill Fenner register int s1, s2; 100b0453382SBill Fenner register int nshorts; 101b0453382SBill Fenner char hexstuff[HEXDUMP_SHORTS_PER_LINE*HEXDUMP_HEXSTUFF_PER_SHORT+1], *hsp; 1025b0fe478SBruce M Simpson char asciistuff[ASCII_LINELENGTH+1], *asp; 103b0453382SBill Fenner 1048bdc5a62SPatrick Kelsey caplength = (ndo->ndo_snapend >= cp) ? ndo->ndo_snapend - cp : 0; 1058bdc5a62SPatrick Kelsey if (length > caplength) 1068bdc5a62SPatrick Kelsey length = caplength; 107b0453382SBill Fenner nshorts = length / sizeof(u_short); 108b0453382SBill Fenner i = 0; 109b0453382SBill Fenner hsp = hexstuff; asp = asciistuff; 110b0453382SBill Fenner while (--nshorts >= 0) { 111b0453382SBill Fenner s1 = *cp++; 112b0453382SBill Fenner s2 = *cp++; 113685295f4SBill Fenner (void)snprintf(hsp, sizeof(hexstuff) - (hsp - hexstuff), 114685295f4SBill Fenner " %02x%02x", s1, s2); 115b0453382SBill Fenner hsp += HEXDUMP_HEXSTUFF_PER_SHORT; 1163c602fabSXin LI *(asp++) = (ND_ISGRAPH(s1) ? s1 : '.'); 1173c602fabSXin LI *(asp++) = (ND_ISGRAPH(s2) ? s2 : '.'); 1185b0fe478SBruce M Simpson i++; 1192ebc47dbSSam Leffler if (i >= HEXDUMP_SHORTS_PER_LINE) { 120b0453382SBill Fenner *hsp = *asp = '\0'; 1213c602fabSXin LI ND_PRINT((ndo, "%s0x%04x: %-*s %s", 1225b0fe478SBruce M Simpson ident, oset, HEXDUMP_HEXSTUFF_PER_LINE, 1233c602fabSXin LI hexstuff, asciistuff)); 124b0453382SBill Fenner i = 0; hsp = hexstuff; asp = asciistuff; 125b0453382SBill Fenner oset += HEXDUMP_BYTES_PER_LINE; 126b0453382SBill Fenner } 127b0453382SBill Fenner } 128b0453382SBill Fenner if (length & 1) { 129b0453382SBill Fenner s1 = *cp++; 130685295f4SBill Fenner (void)snprintf(hsp, sizeof(hexstuff) - (hsp - hexstuff), 131685295f4SBill Fenner " %02x", s1); 132b0453382SBill Fenner hsp += 3; 1333c602fabSXin LI *(asp++) = (ND_ISGRAPH(s1) ? s1 : '.'); 134b0453382SBill Fenner ++i; 135b0453382SBill Fenner } 136b0453382SBill Fenner if (i > 0) { 137b0453382SBill Fenner *hsp = *asp = '\0'; 1383c602fabSXin LI ND_PRINT((ndo, "%s0x%04x: %-*s %s", 1395b0fe478SBruce M Simpson ident, oset, HEXDUMP_HEXSTUFF_PER_LINE, 1403c602fabSXin LI hexstuff, asciistuff)); 141b0453382SBill Fenner } 142b0453382SBill Fenner } 143b0453382SBill Fenner 144b0453382SBill Fenner void 1453c602fabSXin LI hex_and_ascii_print(netdissect_options *ndo, register const char *ident, 1463c602fabSXin LI register const u_char *cp, register u_int length) 147b0453382SBill Fenner { 1483c602fabSXin LI hex_and_ascii_print_with_offset(ndo, ident, cp, length, 0); 149b0453382SBill Fenner } 150b0453382SBill Fenner 151b0453382SBill Fenner /* 152b0453382SBill Fenner * telnet_print() wants this. It is essentially default_print_unaligned() 153b0453382SBill Fenner */ 154b0453382SBill Fenner void 1553c602fabSXin LI hex_print_with_offset(netdissect_options *ndo, 1563c602fabSXin LI const char *ident, const u_char *cp, u_int length, 1573c602fabSXin LI u_int oset) 158b0453382SBill Fenner { 1598bdc5a62SPatrick Kelsey u_int caplength; 160b0453382SBill Fenner register u_int i, s; 161b0453382SBill Fenner register int nshorts; 162b0453382SBill Fenner 1638bdc5a62SPatrick Kelsey caplength = (ndo->ndo_snapend >= cp) ? ndo->ndo_snapend - cp : 0; 1648bdc5a62SPatrick Kelsey if (length > caplength) 1658bdc5a62SPatrick Kelsey length = caplength; 166b0453382SBill Fenner nshorts = (u_int) length / sizeof(u_short); 167b0453382SBill Fenner i = 0; 168b0453382SBill Fenner while (--nshorts >= 0) { 169b0453382SBill Fenner if ((i++ % 8) == 0) { 1703c602fabSXin LI ND_PRINT((ndo,"%s0x%04x: ", ident, oset)); 171b0453382SBill Fenner oset += HEXDUMP_BYTES_PER_LINE; 172b0453382SBill Fenner } 173b0453382SBill Fenner s = *cp++; 1743c602fabSXin LI ND_PRINT((ndo," %02x%02x", s, *cp++)); 175b0453382SBill Fenner } 176b0453382SBill Fenner if (length & 1) { 177b0453382SBill Fenner if ((i % 8) == 0) 1783c602fabSXin LI ND_PRINT((ndo,"%s0x%04x: ", ident, oset)); 1793c602fabSXin LI ND_PRINT((ndo," %02x", *cp)); 180b0453382SBill Fenner } 181b0453382SBill Fenner } 182b0453382SBill Fenner 183b0453382SBill Fenner /* 184b0453382SBill Fenner * just for completeness 185b0453382SBill Fenner */ 186b0453382SBill Fenner void 1873c602fabSXin LI hex_print(netdissect_options *ndo,const char *ident, const u_char *cp, u_int length) 188b0453382SBill Fenner { 1893c602fabSXin LI hex_print_with_offset(ndo, ident, cp, length, 0); 190b0453382SBill Fenner } 191b0453382SBill Fenner 192b0453382SBill Fenner #ifdef MAIN 193b0453382SBill Fenner int 194b0453382SBill Fenner main(int argc, char *argv[]) 195b0453382SBill Fenner { 1962ebc47dbSSam Leffler hex_print("\n\t", "Hello, World!\n", 14); 1972ebc47dbSSam Leffler printf("\n"); 1982ebc47dbSSam Leffler hex_and_ascii_print("\n\t", "Hello, World!\n", 14); 199b0453382SBill Fenner printf("\n"); 200b0453382SBill Fenner ascii_print("Hello, World!\n", 14); 201b0453382SBill Fenner printf("\n"); 202b0453382SBill Fenner #define TMSG "Now is the winter of our discontent...\n" 2032ebc47dbSSam Leffler hex_print_with_offset("\n\t", TMSG, sizeof(TMSG) - 1, 0x100); 2042ebc47dbSSam Leffler printf("\n"); 2052ebc47dbSSam Leffler hex_and_ascii_print_with_offset("\n\t", TMSG, sizeof(TMSG) - 1, 0x100); 206b0453382SBill Fenner printf("\n"); 207b0453382SBill Fenner exit(0); 208b0453382SBill Fenner } 209b0453382SBill Fenner #endif /* MAIN */ 210