2 * Simple Network Management Protocol (RFC 1067).
5 /**********************************************************************
6 Copyright 1988, 1989, 1991, 1992 by Carnegie Mellon University
10 Permission to use, copy, modify, and distribute this software and its
11 documentation for any purpose and without fee is hereby granted,
12 provided that the above copyright notice appear in all copies and that
13 both that copyright notice and this permission notice appear in
14 supporting documentation, and that the name of CMU not be
15 used in advertising or publicity pertaining to distribution of the
16 software without specific, written prior permission.
18 CMU DISCLAIMS ALL WARRANTIES WITH REGARD TO THIS SOFTWARE, INCLUDING
19 ALL IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS, IN NO EVENT SHALL
20 CMU BE LIABLE FOR ANY SPECIAL, INDIRECT OR CONSEQUENTIAL DAMAGES OR
21 ANY DAMAGES WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS,
22 WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION,
23 ARISING OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS
25 ******************************************************************/
27 #include <net-snmp/net-snmp-config.h>
34 #include "fp4/cmdmacro.h"
42 #include <sys/types.h>
49 #include <netinet/in.h>
51 #ifdef HAVE_SYS_SELECT_H
52 #include <sys/select.h>
69 #include <net-snmp/types.h>
70 #include <net-snmp/output_api.h>
72 #include <net-snmp/library/asn1.h>
73 #include <net-snmp/library/snmp.h> /* for "internal" definitions */
74 #include <net-snmp/library/snmp_api.h>
75 #include <net-snmp/library/mib.h>
78 xdump(const u_char * cp, size_t length, const char *prefix)
83 buffer = (char *) malloc(strlen(prefix) + 80);
86 "xdump: malloc failed. packet-dump skipped\n");
91 while (count < (int) length) {
92 strcpy(buffer, prefix);
93 sprintf(buffer + strlen(buffer), "%.4d: ", count);
95 for (col = 0; ((count + col) < (int) length) && col < 16; col++) {
96 sprintf(buffer + strlen(buffer), "%02X ", cp[count + col]);
100 for (; col < 16; col++) { /* pad end of buffer with zeros */
106 for (col = 0; ((count + col) < (int) length) && col < 16; col++) {
108 isprint(cp[count + col]) ? cp[count + col] : '.';
110 buffer[col + 60] = '\n';
111 buffer[col + 60 + 1] = 0;
112 snmp_log(LOG_DEBUG, "%s", buffer);
115 snmp_log(LOG_DEBUG, "\n");
121 * u_char * snmp_parse_var_op(
122 * u_char *data IN - pointer to the start of object
123 * oid *var_name OUT - object id of variable
124 * int *var_name_len IN/OUT - length of variable name
125 * u_char *var_val_type OUT - type of variable (int or octet string) (one byte)
126 * int *var_val_len OUT - length of variable
127 * u_char **var_val OUT - pointer to ASN1 encoded value of variable
128 * int *listlength IN/OUT - number of valid bytes left in var_op_list
132 snmp_parse_var_op(u_char * data,
134 size_t * var_name_len,
135 u_char * var_val_type,
136 size_t * var_val_len,
137 u_char ** var_val, size_t * listlength)
140 size_t var_op_len = *listlength;
141 u_char *var_op_start = data;
143 data = asn_parse_sequence(data, &var_op_len, &var_op_type,
144 (ASN_SEQUENCE | ASN_CONSTRUCTOR), "var_op");
151 DEBUGDUMPHEADER("recv", "Name");
153 asn_parse_objid(data, &var_op_len, &var_op_type, var_name,
157 ERROR_MSG("No OID for variable");
161 (u_char) (ASN_UNIVERSAL | ASN_PRIMITIVE | ASN_OBJECT_ID))
163 *var_val = data; /* save pointer to this object */
165 * find out what type of object this is
167 data = asn_parse_header(data, &var_op_len, var_val_type);
169 ERROR_MSG("No header for value");
173 * XXX no check for type!
175 *var_val_len = var_op_len;
177 *listlength -= (int) (data - var_op_start);
182 * u_char * snmp_build_var_op(
183 * u_char *data IN - pointer to the beginning of the output buffer
184 * oid *var_name IN - object id of variable
185 * int *var_name_len IN - length of object id
186 * u_char var_val_type IN - type of variable
187 * int var_val_len IN - length of variable
188 * u_char *var_val IN - value of variable
189 * int *listlength IN/OUT - number of valid bytes left in
194 snmp_build_var_op(u_char * data,
196 size_t * var_name_len,
199 u_char * var_val, size_t * listlength)
201 size_t dummyLen, headerLen;
204 dummyLen = *listlength;
207 data = asn_build_sequence(data, &dummyLen,
208 (u_char) (ASN_SEQUENCE | ASN_CONSTRUCTOR),
219 headerLen = data - dataPtr;
220 *listlength -= headerLen;
221 DEBUGDUMPHEADER("send", "Name");
222 data = asn_build_objid(data, listlength,
223 (u_char) (ASN_UNIVERSAL | ASN_PRIMITIVE |
224 ASN_OBJECT_ID), var_name,
228 ERROR_MSG("Can't build OID for variable");
231 DEBUGDUMPHEADER("send", "Value");
232 switch (var_val_type) {
234 data = asn_build_int(data, listlength, var_val_type,
235 (long *) var_val, var_val_len);
241 data = asn_build_unsigned_int(data, listlength, var_val_type,
242 (u_long *) var_val, var_val_len);
244 #ifdef OPAQUE_SPECIAL_TYPES
245 case ASN_OPAQUE_COUNTER64:
248 #ifdef BRCM_SNMP_SUPPORT
250 data = asn_build_unsigned_int64(data, listlength, var_val_type,
251 (struct counter64 *) var_val,
253 #endif /* BRCM_SNMP_SUPPORT */
259 data = asn_build_string(data, listlength, var_val_type,
260 var_val, var_val_len);
263 data = asn_build_objid(data, listlength, var_val_type,
264 (oid *) var_val, var_val_len / sizeof(oid));
267 data = asn_build_null(data, listlength, var_val_type);
270 data = asn_build_bitstring(data, listlength, var_val_type,
271 var_val, var_val_len);
273 case SNMP_NOSUCHOBJECT:
274 case SNMP_NOSUCHINSTANCE:
275 case SNMP_ENDOFMIBVIEW:
276 data = asn_build_null(data, listlength, var_val_type);
278 #ifdef OPAQUE_SPECIAL_TYPES
279 case ASN_OPAQUE_FLOAT:
280 data = asn_build_float(data, listlength, var_val_type,
281 (float *) var_val, var_val_len);
283 case ASN_OPAQUE_DOUBLE:
284 data = asn_build_double(data, listlength, var_val_type,
285 (double *) var_val, var_val_len);
288 data = asn_build_signed_int64(data, listlength, var_val_type,
289 (struct counter64 *) var_val,
292 #endif /* OPAQUE_SPECIAL_TYPES */
294 ERROR_MSG("wrong type");
299 ERROR_MSG("Can't build value");
302 dummyLen = (data - dataPtr) - headerLen;
304 asn_build_sequence(dataPtr, &dummyLen,
305 (u_char) (ASN_SEQUENCE | ASN_CONSTRUCTOR),
310 #ifdef USE_REVERSE_ASNENCODING
312 snmp_realloc_rbuild_var_op(u_char ** pkt, size_t * pkt_len,
313 size_t * offset, int allow_realloc,
314 const oid * var_name, size_t * var_name_len,
316 u_char * var_val, size_t var_val_len)
318 size_t start_offset = *offset;
324 DEBUGDUMPHEADER("send", "Value");
326 switch (var_val_type) {
328 rc = asn_realloc_rbuild_int(pkt, pkt_len, offset, allow_realloc,
329 var_val_type, (long *) var_val,
337 rc = asn_realloc_rbuild_unsigned_int(pkt, pkt_len, offset,
338 allow_realloc, var_val_type,
343 #ifdef OPAQUE_SPECIAL_TYPES
344 case ASN_OPAQUE_COUNTER64:
347 #ifdef BRCM_SNMP_SUPPORT
349 rc = asn_realloc_rbuild_unsigned_int64(pkt, pkt_len, offset,
350 allow_realloc, var_val_type,
352 var_val, var_val_len);
360 rc = asn_realloc_rbuild_string(pkt, pkt_len, offset, allow_realloc,
361 var_val_type, var_val, var_val_len);
365 rc = asn_realloc_rbuild_objid(pkt, pkt_len, offset, allow_realloc,
366 var_val_type, (oid *) var_val,
367 var_val_len / sizeof(oid));
371 rc = asn_realloc_rbuild_null(pkt, pkt_len, offset, allow_realloc,
376 rc = asn_realloc_rbuild_bitstring(pkt, pkt_len, offset,
377 allow_realloc, var_val_type,
378 var_val, var_val_len);
381 case SNMP_NOSUCHOBJECT:
382 case SNMP_NOSUCHINSTANCE:
383 case SNMP_ENDOFMIBVIEW:
384 rc = asn_realloc_rbuild_null(pkt, pkt_len, offset, allow_realloc,
388 #ifdef OPAQUE_SPECIAL_TYPES
389 case ASN_OPAQUE_FLOAT:
390 rc = asn_realloc_rbuild_float(pkt, pkt_len, offset, allow_realloc,
391 var_val_type, (float *) var_val,
395 case ASN_OPAQUE_DOUBLE:
396 rc = asn_realloc_rbuild_double(pkt, pkt_len, offset, allow_realloc,
397 var_val_type, (double *) var_val,
402 rc = asn_realloc_rbuild_signed_int64(pkt, pkt_len, offset,
403 allow_realloc, var_val_type,
404 (struct counter64 *) var_val,
407 #endif /* OPAQUE_SPECIAL_TYPES */
409 ERROR_MSG("wrong type");
415 ERROR_MSG("Can't build value");
423 DEBUGDUMPHEADER("send", "Name");
424 rc = asn_realloc_rbuild_objid(pkt, pkt_len, offset, allow_realloc,
425 (u_char) (ASN_UNIVERSAL | ASN_PRIMITIVE |
426 ASN_OBJECT_ID), var_name,
430 ERROR_MSG("Can't build OID for variable");
435 * Build the sequence header.
438 rc = asn_realloc_rbuild_sequence(pkt, pkt_len, offset, allow_realloc,
439 (u_char) (ASN_SEQUENCE |
441 *offset - start_offset);
445 #endif /* USE_REVERSE_ASNENCODING */