xref: /freebsd/contrib/tcpdump/print-ssh.c (revision b64c5a0ace59af62eff52bfe110a521dc73c937b)
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 #include <config.h>
17 
18 #include "netdissect-stdinc.h"
19 #include "netdissect-ctype.h"
20 
21 #include "netdissect.h"
22 #include "extract.h"
23 
24 static int
25 ssh_print_version(netdissect_options *ndo, const u_char *pptr, u_int len)
26 {
27 	u_int idx = 0;
28 
29 	if ( GET_U_1(pptr+idx) != 'S' )
30 		return 0;
31 	idx++;
32 	if ( GET_U_1(pptr+idx) != 'S' )
33 		return 0;
34 	idx++;
35 	if ( GET_U_1(pptr+idx) != 'H' )
36 		return 0;
37 	idx++;
38 	if ( GET_U_1(pptr+idx) != '-' )
39 		return 0;
40 	idx++;
41 
42 	while (idx < len) {
43 		u_char c;
44 
45 		c = GET_U_1(pptr + idx);
46 		if (c == '\n') {
47 			/*
48 			 * LF without CR; end of line.
49 			 * Skip the LF and print the line, with the
50 			 * exception of the LF.
51 			 */
52 			goto print;
53 		} else if (c == '\r') {
54 			/* CR - any LF? */
55 			if ((idx+1) >= len) {
56 				/* not in this packet */
57 				goto trunc;
58 			}
59 			if (GET_U_1(pptr + idx + 1) == '\n') {
60 				/*
61 				 * CR-LF; end of line.
62 				 * Skip the CR-LF and print the line, with
63 				 * the exception of the CR-LF.
64 				 */
65 				goto print;
66 			}
67 
68 			/*
69 			 * CR followed by something else; treat this as
70 			 * if it were binary data and don't print it.
71 			 */
72 			goto trunc;
73 		} else if (!ND_ASCII_ISPRINT(c) ) {
74 			/*
75 			 * Not a printable ASCII character; treat this
76 			 * as if it were binary data and don't print it.
77 			 */
78 			goto trunc;
79 		}
80 		idx++;
81 	}
82 trunc:
83 	return -1;
84 print:
85 	ND_PRINT(": ");
86 	nd_print_protocol_caps(ndo);
87 	ND_PRINT(": %.*s", (int)idx, pptr);
88 	return idx;
89 }
90 
91 void
92 ssh_print(netdissect_options *ndo, const u_char *pptr, u_int len)
93 {
94 	ndo->ndo_protocol = "ssh";
95 
96 	ssh_print_version(ndo, pptr, len);
97 }
98