xref: /freebsd/contrib/tcpdump/print-ssh.c (revision 2008043f386721d58158e37e0d7e50df8095942d)
1 /*
2  * Redistribution and use in source and binary forms, with or without
3  * modification, are permitted provided that: (1) source code
4  * distributions retain the above copyright notice and this paragraph
5  * in its entirety, and (2) distributions including binary code include
6  * the above copyright notice and this paragraph in its entirety in
7  * the documentation or other materials provided with the distribution.
8  * THIS SOFTWARE IS PROVIDED ``AS IS'' AND
9  * WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, WITHOUT
10  * LIMITATION, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
11  * FOR A PARTICULAR PURPOSE.
12  */
13 
14 /* \summary: Secure Shell (SSH) printer */
15 
16 #ifdef HAVE_CONFIG_H
17 #include <config.h>
18 #endif
19 
20 #include "netdissect-stdinc.h"
21 #include "netdissect-ctype.h"
22 
23 #include "netdissect.h"
24 #include "extract.h"
25 
26 static int
27 ssh_print_version(netdissect_options *ndo, const u_char *pptr, u_int len)
28 {
29 	u_int idx = 0;
30 
31 	if ( GET_U_1(pptr+idx) != 'S' )
32 		return 0;
33 	idx++;
34 	if ( GET_U_1(pptr+idx) != 'S' )
35 		return 0;
36 	idx++;
37 	if ( GET_U_1(pptr+idx) != 'H' )
38 		return 0;
39 	idx++;
40 	if ( GET_U_1(pptr+idx) != '-' )
41 		return 0;
42 	idx++;
43 
44 	while (idx < len) {
45 		u_char c;
46 
47 		c = GET_U_1(pptr + idx);
48 		if (c == '\n') {
49 			/*
50 			 * LF without CR; end of line.
51 			 * Skip the LF and print the line, with the
52 			 * exception of the LF.
53 			 */
54 			goto print;
55 		} else if (c == '\r') {
56 			/* CR - any LF? */
57 			if ((idx+1) >= len) {
58 				/* not in this packet */
59 				goto trunc;
60 			}
61 			if (GET_U_1(pptr + idx + 1) == '\n') {
62 				/*
63 				 * CR-LF; end of line.
64 				 * Skip the CR-LF and print the line, with
65 				 * the exception of the CR-LF.
66 				 */
67 				goto print;
68 			}
69 
70 			/*
71 			 * CR followed by something else; treat this as
72 			 * if it were binary data and don't print it.
73 			 */
74 			goto trunc;
75 		} else if (!ND_ASCII_ISPRINT(c) ) {
76 			/*
77 			 * Not a printable ASCII character; treat this
78 			 * as if it were binary data and don't print it.
79 			 */
80 			goto trunc;
81 		}
82 		idx++;
83 	}
84 trunc:
85 	return -1;
86 print:
87 	ND_PRINT(": ");
88 	nd_print_protocol_caps(ndo);
89 	ND_PRINT(": %.*s", (int)idx, pptr);
90 	return idx;
91 }
92 
93 void
94 ssh_print(netdissect_options *ndo, const u_char *pptr, u_int len)
95 {
96 	ndo->ndo_protocol = "ssh";
97 
98 	ssh_print_version(ndo, pptr, len);
99 }
100