1 /*
2  * CDDL HEADER START
3  *
4  * The contents of this file are subject to the terms of the
5  * Common Development and Distribution License, Version 1.0 only
6  * (the "License").  You may not use this file except in compliance
7  * with the License.
8  *
9  * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
10  * or http://www.opensolaris.org/os/licensing.
11  * See the License for the specific language governing permissions
12  * and limitations under the License.
13  *
14  * When distributing Covered Code, include this CDDL HEADER in each
15  * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
16  * If applicable, add the following below this CDDL HEADER, with the
17  * fields enclosed by brackets "[]" replaced with your own identifying
18  * information: Portions Copyright [yyyy] [name of copyright owner]
19  *
20  * CDDL HEADER END
21  */
22 /*
23  * Copyright (c) 1993, 1999 by Sun Microsystems, Inc.
24  * All rights reserved.
25  */
26 
27 #include <sys/types.h>
28 #include <sys/errno.h>
29 #include <setjmp.h>
30 #include <limits.h>
31 #include <netinet/in.h>
32 #include <string.h>
33 
34 #include <rpc/types.h>
35 #include <rpc/rpc.h>
36 #include <rpc/xdr.h>
37 #include <rpc/auth.h>
38 #include <rpc/clnt.h>
39 #include <rpc/rpc_msg.h>
40 #include <fw.h>
41 #include <fw_rpc.h>
42 #include "snoop.h"
43 
44 extern char *dlc_header;
45 extern jmp_buf xdr_err;
46 
47 static char *procnames_short[] = {
48 	"Null",		/*  0 */
49 	"INVOKE",	/*  1 */
50 	"MORE",		/*  2 */
51 	"KILL",		/*  3 */
52 };
53 
54 static char *procnames_long[] = {
55 	"Null procedure",	/*  0 */
56 	"Invoke operation",	/*  1 */
57 	"More data",		/*  2 */
58 	"Kill operation",	/*  3 */
59 };
60 
61 #define	MAXPROC	3
62 
63 enum Rec_type {
64 	REC_TYPE_NORM = 0,
65 	REC_TYPE_EOR = 1,
66 	REC_TYPE_EOF = 2
67 };
68 typedef enum Rec_type Rec_type;
69 
70 void
interpret_solarnet_fw(int flags,int type,int xid,int vers,int proc,char * data,int len)71 interpret_solarnet_fw(
72 	int flags,
73 	int type,
74 	int xid,
75 	int vers,
76 	int proc,
77 	char *data,
78 	int len)
79 {
80 	char *line;
81 	char buff[CTXTLEN + 1];
82 	ulong_t thresh;
83 	char op[CTXTLEN + 1];
84 	bool_t b;
85 	Fw_err e;
86 	Rec_type rt;
87 	int new_row = 1, row = 0;
88 
89 	if (proc < 0 || proc > MAXPROC)
90 		return;
91 
92 	if (flags & F_SUM) {
93 		if (setjmp(xdr_err)) {
94 			return;
95 		}
96 
97 		line = get_sum_line();
98 
99 		if (type == CALL) {
100 			(void) sprintf(line,
101 				"SOLARNET C %s",
102 				procnames_short[proc]);
103 			line += strlen(line);
104 
105 			switch (proc) {
106 			case FW_INVOKE:
107 				(void) sprintf(line, " %s",
108 				    getxdr_string(buff, CTXTLEN));
109 				line += strlen(line);
110 				(void) sprintf(line, "/%s",
111 				    getxdr_string(buff, CTXTLEN));
112 				line += strlen(line);
113 				getxdr_string(buff, CTXTLEN);
114 				if (strlen(buff) != 0) {
115 					(void) sprintf(line, ".%s", buff);
116 					line += strlen(line);
117 				}
118 				(void) getxdr_string(buff, CTXTLEN);
119 				thresh = getxdr_u_long();
120 				if (thresh == ULONG_MAX)
121 					(void) sprintf(line, " (all)");
122 				else
123 					(void) sprintf(line, " %lu", thresh);
124 				line += strlen(line);
125 				(void) getxdr_context(buff, CTXTLEN);
126 				break;
127 			case FW_MORE:
128 				(void) getxdr_context(buff, CTXTLEN);
129 				sscanf(buff, "%*s %*s %s.%*s", op);
130 				op[strlen(op)-1] = '\0';
131 				(void) sprintf(line, " %s", op);
132 				line += strlen(line);
133 				thresh = getxdr_u_long();
134 				if (thresh == ULONG_MAX)
135 					(void) sprintf(line, " (all)");
136 				else
137 					(void) sprintf(line, " %lu", thresh);
138 				line += strlen(line);
139 				break;
140 			case FW_KILL:
141 				(void) getxdr_context(buff, CTXTLEN);
142 				sscanf(buff, "%*s %*s %s.%*s", op);
143 				op[strlen(op)-1] = '\0';
144 				(void) sprintf(line, " %s", op);
145 				line += strlen(line);
146 				break;
147 			default:
148 				break;
149 			}
150 
151 			check_retransmit(line, xid);
152 		} else {
153 			(void) sprintf(line, "SOLARNET R %s",
154 			    procnames_short[proc]);
155 			line += strlen(line);
156 			b = getxdr_bool();
157 			if (b) {
158 				e = getxdr_enum();
159 				if (e == FW_ERR_FW)
160 					sprintf(line, " FW");
161 				else if (e == FW_ERR_OP)
162 					sprintf(line, " OP");
163 				else
164 					sprintf(line, " NOERR");
165 				line += strlen(line);
166 				if (e != FW_ERR_NONE) {
167 					sprintf(line, " %lu", getxdr_u_long());
168 					line += strlen(line);
169 					(void) getxdr_bool();
170 					sprintf(line, " %s",
171 					    getxdr_string(buff, CTXTLEN));
172 					line += strlen(line);
173 				}
174 			} else {
175 				sprintf(line, " Success");
176 				line += strlen(line);
177 			}
178 			b = getxdr_bool();
179 			if (b) {
180 				sprintf(line, " %lu rows", getxdr_u_long());
181 				line += strlen(line);
182 			} else {
183 				sprintf(line, " (No output)");
184 				line += strlen(line);
185 			}
186 		}
187 	}
188 
189 	if ((flags & F_DTAIL)) {
190 		show_header("SOLARNET:  ", "Solarnet Administration Service",
191 		    len);
192 		show_space();
193 		if (setjmp(xdr_err)) {
194 			return;
195 		}
196 		(void) sprintf(get_line(0, 0), "Proc = %d (%s)", proc,
197 		    procnames_long[proc]);
198 		if (type == CALL) {
199 			switch (proc) {
200 			case FW_INVOKE:
201 				(void) showxdr_string(CTXTLEN, "Category: %s");
202 				(void) showxdr_string(CTXTLEN, "Operation: %s");
203 				(void) showxdr_string(CTXTLEN, "Version: %s");
204 				(void) showxdr_string(CTXTLEN, "Locale: %s");
205 				(void) showxdr_u_long("Threshold: %lu rows");
206 				(void) showxdr_context("Context: %s");
207 				b = getxdr_bool();
208 				if (!b) {
209 					sprintf(get_line(0, 0),
210 					    "No input arguments");
211 					break;
212 				}
213 				thresh = showxdr_u_long("Input rows = %lu");
214 				(void) getxdr_bool();
215 				do {
216 					rt = getxdr_enum();
217 					if (rt == REC_TYPE_NORM) {
218 						if (new_row) {
219 							sprintf(get_line(0, 0),
220 							    "Row %d", ++row);
221 							new_row = 0;
222 						}
223 						(void) getxdr_string(buff,
224 						    CTXTLEN);
225 						(void) getxdr_string(op,
226 						    CTXTLEN);
227 						sprintf(get_line(0, 0),
228 						    "\t%s = %s", buff, op);
229 					} else if (rt == REC_TYPE_EOR) {
230 						new_row = 1;
231 					}
232 				} while (rt != REC_TYPE_EOF);
233 				break;
234 			case FW_MORE:
235 				(void) showxdr_context("Context: %s");
236 				(void) showxdr_u_long("Threshold: %lu rows");
237 				break;
238 			case FW_KILL:
239 				(void) showxdr_context("Context: %s");
240 				break;
241 			default:
242 				break;
243 			}
244 		} else {
245 			b = getxdr_bool();
246 			if (b) {
247 				e = getxdr_enum();
248 				if (e == FW_ERR_FW) {
249 					showxdr_u_long(
250 					    "Framework error code %lu");
251 				} else if (e == FW_ERR_OP) {
252 					showxdr_u_long(
253 					    "Operation error code %lu");
254 				} else {
255 					showxdr_u_long("No error %*lu");
256 				}
257 				(void) getxdr_bool();
258 				(void) getxdr_string(buff, CTXTLEN);
259 				if (e != FW_ERR_NONE) {
260 					sprintf(get_line(0, 0),
261 					    "Error message: %s", buff);
262 				} else {
263 				}
264 			} else {
265 				sprintf(get_line(0, 0),
266 				    "Operation was successful");
267 			}
268 			b = getxdr_bool();
269 			if (b) {
270 				showxdr_u_long("Output rows: %lu");
271 				(void) getxdr_bool();
272 				do {
273 					rt = getxdr_enum();
274 					if (rt == REC_TYPE_NORM) {
275 						if (new_row) {
276 							sprintf(get_line(0, 0),
277 							    "Row %d", ++row);
278 							new_row = 0;
279 						}
280 						(void) getxdr_string(buff,
281 						    CTXTLEN);
282 						(void) getxdr_string(op,
283 						    CTXTLEN);
284 						sprintf(get_line(0, 0),
285 						    "\t%s = %s", buff, op);
286 					} else if (rt == REC_TYPE_EOR) {
287 						new_row = 1;
288 					}
289 				} while (rt != REC_TYPE_EOF);
290 			} else {
291 				sprintf(get_line(0, 0), "No output");
292 			}
293 		}
294 		show_trailer();
295 	}
296 
297 }
298