and added files
[bcm963xx.git] / userapps / opensource / net-snmp / apps / snmpgetnext.c
1 /*
2  * snmpgetnext.c - send snmp GETNEXT requests to a network entity.
3  *
4  */
5 /***********************************************************************
6         Copyright 1988, 1989, 1991, 1992 by Carnegie Mellon University
7
8                       All Rights Reserved
9
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.
17
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
24 SOFTWARE.
25 ******************************************************************/
26 #include <net-snmp/net-snmp-config.h>
27
28 #if HAVE_STDLIB_H
29 #include <stdlib.h>
30 #endif
31 #if HAVE_UNISTD_H
32 #include <unistd.h>
33 #endif
34 #if HAVE_STRING_H
35 #include <string.h>
36 #else
37 #include <strings.h>
38 #endif
39 #include <sys/types.h>
40 #if HAVE_NETINET_IN_H
41 #include <netinet/in.h>
42 #endif
43 #include <stdio.h>
44 #include <ctype.h>
45 #if TIME_WITH_SYS_TIME
46 # ifdef WIN32
47 #  include <sys/timeb.h>
48 # else
49 #  include <sys/time.h>
50 # endif
51 # include <time.h>
52 #else
53 # if HAVE_SYS_TIME_H
54 #  include <sys/time.h>
55 # else
56 #  include <time.h>
57 # endif
58 #endif
59 #if HAVE_SYS_SELECT_H
60 #include <sys/select.h>
61 #endif
62 #if HAVE_WINSOCK_H
63 #include <winsock.h>
64 #endif
65 #if HAVE_NETDB_H
66 #include <netdb.h>
67 #endif
68 #if HAVE_ARPA_INET_H
69 #include <arpa/inet.h>
70 #endif
71
72 #include <net-snmp/net-snmp-includes.h>
73
74 #define NETSNMP_DS_APP_DONT_FIX_PDUS 0
75
76 static void
77 optProc(int argc, char *const *argv, int opt)
78 {
79     switch (opt) {
80     case 'C':
81         while (*optarg) {
82             switch (*optarg++) {
83             case 'f':
84                 netsnmp_ds_toggle_boolean(NETSNMP_DS_APPLICATION_ID, 
85                                           NETSNMP_DS_APP_DONT_FIX_PDUS);
86                 break;
87             default:
88                 fprintf(stderr, "Unknown flag passed to -C: %c\n",
89                         optarg[-1]);
90                 exit(1);
91             }
92         }
93         break;
94     }
95 }
96
97 void
98 usage(void)
99 {
100     fprintf(stderr, "USAGE: snmpgetnext ");
101     snmp_parse_args_usage(stderr);
102     fprintf(stderr, " OID [OID]...\n\n");
103     snmp_parse_args_descriptions(stderr);
104     fprintf(stderr,
105             "  -C APPOPTS\t\tSet various application specific behaviours:\n");
106     fprintf(stderr,
107             "\t\t\t  f:  do not fix errors and retry the request\n");
108 }
109
110 int
111 main(int argc, char *argv[])
112 {
113     netsnmp_session session, *ss;
114     netsnmp_pdu    *pdu, *response;
115     netsnmp_variable_list *vars;
116     int             arg;
117     int             count;
118     int             current_name = 0;
119     char           *names[128];
120     oid             name[MAX_OID_LEN];
121     size_t          name_length;
122     int             status;
123     int             failures = 0;
124     int             exitval = 0;
125
126     /*
127      * get the common command line arguments 
128      */
129     switch (arg = snmp_parse_args(argc, argv, &session, "C:", &optProc)) {
130     case -2:
131         exit(0);
132     case -1:
133         usage();
134         exit(1);
135     default:
136         break;
137     }
138
139     if (arg >= argc) {
140         fprintf(stderr, "Missing object name\n");
141         usage();
142         exit(1);
143     }
144
145     /*
146      * get the object names 
147      */
148     for (; arg < argc; arg++)
149         names[current_name++] = argv[arg];
150
151     SOCK_STARTUP;
152
153     /*
154      * open an SNMP session 
155      */
156     ss = snmp_open(&session);
157     if (ss == NULL) {
158         /*
159          * diagnose snmp_open errors with the input netsnmp_session pointer 
160          */
161         snmp_sess_perror("snmpgetnext", &session);
162         SOCK_CLEANUP;
163         exit(1);
164     }
165
166     /*
167      * create PDU for GET request and add object names to request 
168      */
169     pdu = snmp_pdu_create(SNMP_MSG_GETNEXT);
170
171     for (count = 0; count < current_name; count++) {
172         name_length = MAX_OID_LEN;
173         if (snmp_parse_oid(names[count], name, &name_length) == NULL) {
174             snmp_perror(names[count]);
175             failures++;
176         } else
177             snmp_add_null_var(pdu, name, name_length);
178     }
179     if (failures) {
180         SOCK_CLEANUP;
181         exit(1);
182     }
183
184     /*
185      * do the request 
186      */
187   retry:
188     status = snmp_synch_response(ss, pdu, &response);
189     if (status == STAT_SUCCESS) {
190         if (response->errstat == SNMP_ERR_NOERROR) {
191             for (vars = response->variables; vars;
192                  vars = vars->next_variable)
193                 print_variable(vars->name, vars->name_length, vars);
194         } else {
195             fprintf(stderr, "Error in packet.\nReason: %s\n",
196                     snmp_errstring(response->errstat));
197             if (response->errindex != 0) {
198                 fprintf(stderr, "Failed object: ");
199                 for (count = 1, vars = response->variables;
200                      vars && count != response->errindex;
201                      vars = vars->next_variable, count++);
202                 if (vars)
203                     fprint_objid(stderr, vars->name, vars->name_length);
204                 fprintf(stderr, "\n");
205                 exitval = 2;
206             }
207
208             /*
209              * retry if the errored variable was successfully removed 
210              */
211             if (!netsnmp_ds_get_boolean(NETSNMP_DS_APPLICATION_ID, 
212                                         NETSNMP_DS_APP_DONT_FIX_PDUS)) {
213                 pdu = snmp_fix_pdu(response, SNMP_MSG_GETNEXT);
214                 snmp_free_pdu(response);
215                 response = NULL;
216                 if (pdu != NULL)
217                     goto retry;
218             }
219         }
220     } else if (status == STAT_TIMEOUT) {
221         fprintf(stderr, "Timeout: No Response from %s.\n",
222                 session.peername);
223         exitval = 1;
224     } else {                    /* status == STAT_ERROR */
225         snmp_sess_perror("snmpgetnext", ss);
226         exitval = 1;
227     }
228
229     if (response)
230         snmp_free_pdu(response);
231     snmp_close(ss);
232     SOCK_CLEANUP;
233     return exitval;
234 }