home *** CD-ROM | disk | FTP | other *** search
- /*********************************************************************/
- /* */
- /* SNMP-DPI - SNMP Distributed Programming Interface */
- /* */
- /* May 1991 - Version 1.0 - SNMP-DPI Version 1.0 (RFC1228) */
- /* Created by IBM Research. */
- /* Feb 1992 - Version 1.1 - Allow enterpriseID to be passed with */
- /* a (enterprise specific) trap */
- /* - allow multiple variables to be passed */
- /* - Use 4 octets (INTEGER from RFC1157) */
- /* for generic and specific type. */
- /* Jun 1992 - Make it run on OS/2 as well */
- /* Note: dpisample = dpisampl on OS/2 */
- /* */
- /* Copyright None */
- /* */
- /* dpisample.c - a sample SNMP-DPI subagent */
- /* - can be used to test agent DPI implementations. */
- /* */
- /* For testing with XGMON and/or SQESERV (SNMP Query Engine) */
- /* it is best to keep the following define for OID in sync */
- /* with the dpiSample objectID in the MIB description file */
- /* (mib_desc for XGMON, MIB_DESC DATA for SQESERV on VM and */
- /* MIB@DESC.DATA for SQESERV on MVS, MIB2TBL on OS/2). */
- /* */
- /* See dpisample README file for more info. */
- /* */
- /*********************************************************************/
-
- #define OID "1.3.6.1.4.1.2.2.1.4."
- #define ENTERPRISE_OID "1.3.6.1.4.1.2.2.1.4" /* dpiSample */
- #define ifIndex "1.3.6.1.2.1.2.2.1.1.0"
- #define egpNeighAddr "1.3.6.1.2.8.5.1.2.0"
- #define PUBLIC_COMMUNITY_NAME "public"
-
- #if defined(VM) || defined(MVS)
-
- #define SNMPAGENTUSERID "SNMPD"
- #define SNMPIUCVNAME "SNMP_DPI"
- #pragma csect(CODE, "$DPISAMP")
- #pragma csect(STATIC,"#DPISAMP")
- #include <manifest.h> /* VM specific things */
- #include "snmpnms.h" /* short external names for VM/MVS */
- #include "snmp_vm.h" /* more of those short names */
- #include <saiucv.h>
- #include <bsdtime.h>
- #include <bsdtypes.h>
- #include <socket.h>
- #include <in.h>
- #include <netdb.h>
- #include <inet.h>
- extern char ebcdicto[], asciitoe[];
- #pragma linkage(cmxlate,OS)
- #define DO_ETOA(a) cmxlate((a),ebcdictoascii,strlen((a)))
- #define DO_ATOE(a) cmxlate((a),asciitoebcdic,strlen((a)))
- #define DO_ERROR(a) tcperror((a))
- #define LOOPBACK "loopback"
- #define IUCV TRUE
- #define max(a,b) (((a) > (b)) ? (a) : (b))
- #define min(a,b) (((a) < (b)) ? (a) : (b))
-
- #else /* we are not on VM or MVS */
-
- #ifdef OS2
- #include <stdlib.h>
- #include <types.h>
- #include <doscalls.h>
- #ifndef sleep
- #define sleep(a) DOSSLEEP(1000 * (a))
- #endif
- #define close soclose
- /*char * malloc(); */
- /*unsigned long strtoul(); */
- #endif
-
- #include <sys/time.h>
- #include <sys/types.h>
- #include <sys/socket.h>
- #include <netinet/in.h>
- #include <netdb.h>
- // #include <arpa/inet.h>
- #define DO_ETOA(a) ; /* no need for this */
- #define DO_ATOE(a) ; /* no need for this */
- #define DO_ERROR(a) perror((a))
- #define LOOPBACK "localhost"
- #define IUCV FALSE
- #ifdef AIX221
- #define isdigit(c) (((c) >= '0') && ((c) <= '9'))
- #else
- // #include <sys/select.h>
- #endif /* AIX221 */
-
- #endif /* defined(VM) || defined(MVS) */
-
- #include <stdio.h>
- #ifdef OS2
- #include <dpi/snmp_dpi.h>
- #else
- #include "snmp_dpi.h"
- #endif
-
- #define WAIT_FOR_AGENT 3 /* time to wait before closing agent fd */
-
- #ifndef TRUE
- #define TRUE 1
- #define FALSE 0
- #endif
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void check_arguments();
- static void send_packet();
- static void print_val();
- static void usage();
- static void init_connection();
- static void init_variables();
- static void await_and_read_packet();
- static void handle_packet();
- static void do_get();
- static void do_set();
- static void issue_traps();
- static void issue_one_trap();
- static void issue_one_trape();
- static void issue_std_traps();
- static void issue_ent_traps();
- static void issue_ent_trapse();
- static void do_register();
- static void dump_bfr();
- static struct dpi_set_packet *addtoset();
- extern unsigned long lookup_host();
-
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
-
- static void check_arguments(const int argc, char *argv[]);
- static void send_packet(const char * packet);
- static void print_val(const int index);
- static void usage(const char *progname, const int exit_rc);
- static void init_connection(void);
- static void init_variables(void);
- static void await_and_read_packet(void);
- static void handle_packet(void);
- static void do_get(void);
- static void do_set(void);
- static void issue_traps(void);
- static void issue_one_trap(void);
- static void issue_one_trape(void);
- static void issue_std_traps(void);
- static void issue_ent_traps(void);
- static void issue_ent_trapse(void);
- static void do_register(void);
- static void dump_bfr(const char *buf, const int len);
- static struct dpi_set_packet *addtoset(struct dpi_set_packet *data,
- int stype);
- extern unsigned long lookup_host(const char *hostname);
-
- #endif /* _NO_PROTO */
-
- #define OSTRING "hex01-04:"
- #define DSTRING "Initial Display String"
- #define COMMAND "None"
- #define BUFSIZE 4096
- #define TIMEOUT 3
- #define PACKET_LEN(packet) (((unsigned char)*(packet)) * 256 + \
- ((unsigned char)*((packet) + 1)) + 2)
-
- /* We have the following instances for OID.x variables */
- /* 0 - table */
- static long number = 0; /* 1 - a number */
- static unsigned char *ostring = 0; /* 2 - octet string */
- static int ostring_len = 0; /* and its length */
- static unsigned char *objectID = 0; /* 3 - objectID */
- static int objectID_len= 0; /* and its length */
- /* 4 - some empty variable */
- static unsigned long ipaddr = 0; /* 5 - ipaddress */
- static unsigned long counter = 1; /* 6 - a counter */
- static unsigned long gauge = 1; /* 7 - a gauge */
- static unsigned long ticks = 1; /* 8 - time ticks */
- static unsigned char *dstring = 0; /* 9 - display string */
- static unsigned char *command = 0; /* 10 - command */
-
- static char *DPI_var[] = {
- "dpiSample",
- "dpiSampleNumber",
- "dpiSampleOctetString",
- "dpiSampleObjectID",
- "dpiSampleEmpty",
- "dpiSampleInetAddress",
- "dpiSampleCounter",
- "dpiSampleGauge",
- "dpiSampleTimeTicks",
- "dpiSampleDisplayString",
- "dpiSampleCommand"
- };
-
- static short int valid_types[] = { /* SNMP_TYPEs accepted on SET */
- -1, /* 0 do not check type */
- SNMP_TYPE_NUMBER, /* 1 number */
- SNMP_TYPE_STRING, /* 2 octet string */
- SNMP_TYPE_OBJECT, /* 3 object identifier */
- -1, /* SNMP_TYPE_EMPTY */ /* 4 do not check type */
- SNMP_TYPE_INTERNET, /* 5 internet address */
- SNMP_TYPE_COUNTER, /* 6 counter */
- SNMP_TYPE_GAUGE, /* 7 gauge */
- SNMP_TYPE_TICKS, /* 8 time ticks */
- SNMP_TYPE_STRING, /* 9 display string */
- SNMP_TYPE_STRING /* 10 command (display string) */
- #define OID_COUNT_FOR_TRAPS 9
- #define OID_COUNT 10
- };
-
- static char *packet = NULL; /* ptr to send packet. */
- static char inbuf[BUFSIZE]; /* buffer for receive packets */
- static int dpi_fd; /* fd for socket to DPI agent */
- static short int dpi_port; /* DPI_port at agent */
- static unsigned long dpi_ipaddress; /* IP address of DPI agent */
- static char *dpi_hostname; /* hostname of DPI agent */
- static char *dpi_userid; /* userid of DPI agent VM/MVS */
- static char *var_gid; /* groupID received */
- static char *var_oid; /* objectID received */
- static int var_index; /* OID variable index */
- static unsigned char var_type; /* SET value type */
- static char *var_value; /* SET value */
- static short int var_value_len; /* SET value length */
- static int debug_lvl = 0; /* current debug level */
- static int use_iucv = IUCV; /* optional use of AF_IUCV */
- static int do_quit = FALSE;/* Quit in await loop */
- static int trap_gtype = 0; /* trap generic type */
- static int trap_stype = 0; /* trap specific type */
- static char *trap_data = NULL;/* trap data */
- static int do_trap = 0; /* switch for traps */
- #define ONE_TRAP 1
- #define ONE_TRAPE 2
- #define STD_TRAPS 3
- #define ENT_TRAPS 4
- #define ENT_TRAPSE 5
- #define ALL_TRAPS 6
- #define MAX_TRAPE_DATA 10 /* data for extended trap */
- static long trape_gtype = 6; /* trap generic type */
- static long trape_stype = 11; /* trap specific type */
- static char *trape_eprise = NULL; /* enterprise id */
- static char *trape_data[MAX_TRAPE_DATA]; /* pointers to data values */
- static int trape_datacnt; /* actual number of values */
-
- #ifdef _NO_PROTO /* for classic K&R C */
- main(argc, argv) /* main line */
- int argc;
- char *argv[];
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- main(const int argc, char *argv[]) /* main line */
- #endif /* _NO_PROTO */
- {
- check_arguments(argc, argv); /* check callers arguments */
- dpi_ipaddress = lookup_host(dpi_hostname); /* get ip address */
- init_connection(); /* connect to specified agent */
- init_variables(); /* initialize our variables */
- if (do_trap) { /* we just need to do traps */
- issue_traps(); /* issue the trap(s) */
- sleep(WAIT_FOR_AGENT); /* sleep a bit, so agent can */
- close(dpi_fd); /* read data before we close */
- exit(0); /* and that's it */
- } /* end if (do_trap) */
- do_register(); /* register our objectIDs */
- printf("%s ready and awaiting queries from agent\n",argv[0]);
- while (do_quit == FALSE) { /* forever until quit or error */
- await_and_read_packet(); /* wait for next packet */
- handle_packet(); /* handle it */
- if (do_trap) issue_traps(); /* request to issue traps */
- } /* while loop */
- sleep(WAIT_FOR_AGENT); /* allow agent to read response */
- printf("Quitting, %s set to: quit\n",DPI_var[10]);
- exit(2); /* sampleDisplayString == quit */
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void issue_traps()
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void issue_traps(void)
- #endif /* _NO_PROTO */
- {
- switch (do_trap) { /* let's see which one(s) */
- case ONE_TRAP: /* only need to issue one trap */
- issue_one_trap(); /* go issue the one trap */
- break;
- case ONE_TRAPE: /* only need to issue one trape */
- issue_one_trape(); /* go issue the one trape */
- break;
- case STD_TRAPS: /* only need to issue std traps */
- issue_std_traps(); /* standard traps gtypes 0-5 */
- break;
- case ENT_TRAPS: /* only need to issue ent traps */
- issue_ent_traps(); /* enterprise specific traps */
- break;
- case ENT_TRAPSE: /* only need to issue ent trapse */
- issue_ent_trapse(); /* enterprise specific trapse */
- break;
- case ALL_TRAPS: /* only need to issue std traps */
- issue_std_traps(); /* standard traps gtypes 0-5 */
- issue_ent_traps(); /* enterprise specific traps */
- issue_ent_trapse(); /* enterprise specific trapse */
- break;
- default:
- break;
- } /* end switch (do_trap) */
- do_trap = 0; /* reset do_trap switch */
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void await_and_read_packet() /* await packet from DPI agent */
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void await_and_read_packet(void)/* await packet from DPI agent */
- #endif /* _NO_PROTO */
- {
- int len, rc, bytes_to_read, bytes_read = 0;
- #ifdef OS2
- int socks[5];
- #else
- fd_set read_mask;
- #endif
- struct timeval timeout;
-
- #ifdef OS2
- socks[0] = dpi_fd;
- rc = select(socks, 1, 0, 0, -1L);
- #else
- FD_ZERO(&read_mask);
- FD_SET(dpi_fd, &read_mask); /* wait for data */
- rc = select(dpi_fd+1, &read_mask, NULL, NULL, NULL);
- #endif
- if (rc != 1) { /* exit on error */
- DO_ERROR("await_and_read_packet: select");
- close(dpi_fd);
- exit(1);
- }
- #ifdef OS2
- len = recv(dpi_fd, inbuf, 2, 0); /* read 2 bytes first */
- #else
- len = read(dpi_fd, inbuf, 2); /* read 2 bytes first */
- #endif
- if (len <= 0) { /* exit on error or EOF */
- if (len < 0) DO_ERROR("await_and_read_packet: read");
- else printf("Quitting, EOF received from DPI-agent\n");
- close(dpi_fd);
- exit(1);
- }
- bytes_to_read = (inbuf[0] << 8) + inbuf[1]; /* bytes to follow */
- if (BUFSIZE < (bytes_to_read + 2)) { /* exit if too much */
- printf("Quitting, packet larger than %d byte buffer\n",BUFSIZE);
- close(dpi_fd);
- exit(1);
- }
- while (bytes_to_read > 0) { /* while bytes to read */
- #ifdef OS2
- socks[0] = dpi_fd;
- len = select(socks, 1, 0, 0, 3000L);
- #else
- timeout.tv_sec = 3; /* wait max 3 seconds */
- timeout.tv_usec = 0;
- FD_SET(dpi_fd, &read_mask); /* check for data */
- len = select(dpi_fd+1, &read_mask, NULL, NULL, &timeout);
- #endif
- if (len == 1) { /* select returned OK */
- #ifdef OS2
- len = recv(dpi_fd, &inbuf[2] + bytes_read, bytes_to_read, 0);
- #else
- len = read(dpi_fd, &inbuf[2] + bytes_read, bytes_to_read);
- #endif
- } /* end if (len == 1) */
- if (len <= 0) { /* exit on error or EOF */
- if (len < 0) DO_ERROR("await_and_read_packet: read");
- printf("Can't read remainder of packet\n");
- close(dpi_fd);
- exit(1);
- } else { /* count bytes_read */
- bytes_read += len;
- bytes_to_read -= len;
- }
- } /* while (bytes_to_read > 0) */
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void handle_packet() /* handle DPI packet from agent */
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void handle_packet(void) /* handle DPI packet from agent */
- #endif /* _NO_PROTO */
- {
- struct snmp_dpi_hdr *hdr;
-
- if (debug_lvl > 2) {
- printf("Received following SNMP-DPI packet:\n");
- dump_bfr(inbuf, PACKET_LEN(inbuf));
- }
- hdr = pDPIpacket(inbuf); /* parse received packet */
- if (hdr == 0) { /* ignore if can't parse */
- printf("Ignore received packet, could not parse it!\n");
- return;
- }
- packet = NULL;
- var_type = 0;
- var_oid = "";
- var_gid = "";
- switch (hdr->packet_type) {
- /* extract pointers and/or data from specific packet types, */
- /* such that we can use them independent of packet type. */
- case SNMP_DPI_GET:
- if (debug_lvl > 0) printf("SNMP_DPI_GET for ");
- var_oid = hdr->packet_body.dpi_get->object_id;
- break;
- case SNMP_DPI_GET_NEXT:
- if (debug_lvl > 0) printf("SNMP_DPI_GET_NEXT for ");
- var_oid = hdr->packet_body.dpi_next->object_id;
- var_gid = hdr->packet_body.dpi_next->group_id;
- break;
- case SNMP_DPI_SET:
- if (debug_lvl > 0) printf("SNMP_DPI_SET for ");
- var_value_len = hdr->packet_body.dpi_set->value_len;
- var_value = hdr->packet_body.dpi_set->value;
- var_oid = hdr->packet_body.dpi_set->object_id;
- var_type = hdr->packet_body.dpi_set->type;
- break;
- default: /* Return a GEN_ERROR */
- if (debug_lvl > 0) printf("Unexpected packet_type %d, genErr\n",
- hdr->packet_type);
- packet = mkDPIresponse(SNMP_GEN_ERR, NULL);
- fDPIparse(hdr); /* return storage allocated by pDPIpacket() */
- send_packet(packet);
- return;
- break;
- } /* end switch(hdr->packet_type) */
- if (debug_lvl > 0) printf("objectID: %s \n",var_oid);
-
- if (strlen(var_oid) <= strlen(OID)) { /* not in our tree */
- if (hdr->packet_type == SNMP_DPI_GET_NEXT) var_index = 0; /* OK */
- else { /* cannot handle */
- if (debug_lvl>0) printf("...Ignored %s, noSuchName\n",var_oid);
- packet = mkDPIresponse(SNMP_NO_SUCH_NAME, NULL);
- fDPIparse(hdr); /* return storage allocated by pDPIpacket() */
- send_packet(packet);
- return;
- }
- } else { /* Extract our variable index (from OID.index.instance) */
- /* We handle any instance the same (we only have one instance) */
- var_index = atoi(&var_oid[strlen(OID)]);
- }
- if (debug_lvl > 1) {
- printf("...The groupID=%s\n",var_gid);
- printf("...Handle as if objectID=%s%d\n",OID,var_index);
- }
- switch (hdr->packet_type) {
- case SNMP_DPI_GET:
- do_get(); /* do a get to return response */
- break;
- case SNMP_DPI_GET_NEXT:
- { char toid[256]; /* space for temporary objectID */
- var_index++; /* do a get for the next variable */
- sprintf(toid,"%s%d",OID,var_index); /* construct objectID */
- var_oid = toid; /* point to it */
- do_get(); /* do a get to return response */
- } break;
- case SNMP_DPI_SET:
- if (debug_lvl > 1) printf("...value_type=%d\n",var_type);
- do_set(); /* set new value first */
- if (packet) break; /* some error response was generated */
- do_get(); /* do a get to return response */
- break;
- }
- fDPIparse(hdr); /* return storage allocated by pDPIpacket() */
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void do_get() /* handle SNMP_GET request */
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void do_get(void) /* handle SNMP_GET request */
- #endif /* _NO_PROTO */
- {
- struct dpi_set_packet *data = NULL;
-
- switch (var_index) {
- case 0: /* table, cannot be queried by itself */
- printf("...Should not issue GET for table %s.0\n", OID);
- break;
- case 1: /* a number */
- data = mkDPIset(var_oid,SNMP_TYPE_NUMBER,sizeof(number),&number);
- break;
- case 2: /* an octet_string (can have binary data) */
- data = mkDPIset(var_oid,SNMP_TYPE_STRING,ostring_len,ostring);
- break;
- case 3: /* object id */
- data = mkDPIset(var_oid,SNMP_TYPE_OBJECT,objectID_len,objectID);
- break;
- case 4: /* some empty variable */
- data = mkDPIset(var_oid,SNMP_TYPE_EMPTY,0,NULL);
- break;
- case 5: /* internet address */
- data = mkDPIset(var_oid,SNMP_TYPE_INTERNET,sizeof(ipaddr),&ipaddr);
- break;
- case 6: /* counter (unsigned) */
- data =mkDPIset(var_oid,SNMP_TYPE_COUNTER,sizeof(counter),&counter);
- break;
- case 7: /* gauge (unsigned) */
- data = mkDPIset(var_oid,SNMP_TYPE_GAUGE,sizeof(gauge),&gauge);
- break;
- case 8: /* time ticks (unsigned) */
- data = mkDPIset(var_oid,SNMP_TYPE_TICKS,sizeof(ticks),&ticks);
- break;
- case 9: /* a display_string (printable ascii only) */
- DO_ETOA(dstring);
- data = mkDPIset(var_oid,SNMP_TYPE_STRING,strlen(dstring),dstring);
- DO_ATOE(dstring);
- break;
- case 10: /* a command request (command is a display string) */
- DO_ETOA(command);
- data = mkDPIset(var_oid,SNMP_TYPE_STRING,strlen(command),command);
- DO_ATOE(command);
- break;
- default: /* Return a NoSuchName */
- if (debug_lvl > 1)
- printf("...GET[NEXT] for %s, not found\n", var_oid);
- break;
- } /* end switch (var_index) */
-
- if (data) {
- if (debug_lvl > 0) {
- printf("...Sending response oid: %s type: %d\n",
- var_oid, data->type);
- printf("......Current value: ");
- print_val(var_index); /* prints \n at end */
- }
- packet = mkDPIresponse(SNMP_NO_ERROR,data);
- } else { /* Could have been an error in mkDPIset though */
- if (debug_lvl > 0) printf("...Sending response noSuchName\n");
- packet = mkDPIresponse(SNMP_NO_SUCH_NAME,NULL);
- } /* end if (data) */
- if (packet) send_packet(packet);
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void do_set() /* handle SNMP_SET request */
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void do_set(void) /* handle SNMP_SET request */
- #endif /* _NO_PROTO */
- {
- unsigned long *ulp;
- long *lp;
-
- if (valid_types[var_index] != var_type &&
- valid_types[var_index] != -1) {
- printf("...Ignored set request with type %d, expect type %d,",
- var_type, valid_types[var_index]);
- printf(" Returning badValue\n");
- packet = mkDPIresponse(SNMP_BAD_VALUE, NULL);
- if (packet) send_packet(packet);
- return;
- }
- switch (var_index) {
- case 0: /* table, cannot set table. */
- if (debug_lvl > 0) printf("...Ignored set TABLE, noSuchName\n");
- packet = mkDPIresponse(SNMP_NO_SUCH_NAME,NULL);
- break;
- case 1: /* a number */
- lp = (long *)var_value;
- number = *lp;
- break;
- case 2: /* an octet_string (can have binary data) */
- free(ostring);
- ostring = (char *)malloc(var_value_len + 1);
- bcopy(var_value, ostring, var_value_len);
- ostring_len = var_value_len;
- ostring[var_value_len] = '\0'; /* so we can use it as a string */
- break;
- case 3: /* object id */
- free(objectID);
- objectID = (char *)malloc(var_value_len + 1);
- bcopy(var_value, objectID, var_value_len);
- objectID_len = var_value_len;
- if (objectID[objectID_len -1]) {
- objectID[objectID_len++] = '\0'; /* a valid one needs a null */
- if (debug_lvl > 0)
- printf("...added a terminating null to objectID\n");
- }
- break;
- case 4: /* an empty variable, cannot set */
- if (debug_lvl > 0) printf("...Ignored set EMPTY, readOnly\n");
- packet = mkDPIresponse(SNMP_READ_ONLY,NULL);
- break;
- case 5: /* Internet address */
- ulp = (unsigned long *)var_value;
- ipaddr = *ulp;
- break;
- case 6: /* counter (unsigned) */
- ulp = (unsigned long *)var_value;
- counter = *ulp;
- break;
- case 7: /* gauge (unsigned) */
- ulp = (unsigned long *)var_value;
- gauge = *ulp;
- break;
- case 8: /* time ticks (unsigned) */
- ulp = (unsigned long *)var_value;
- ticks = *ulp;
- break;
- case 9: /* a display_string (printable ascii only) */
- free(dstring);
- dstring = (char *)malloc(var_value_len + 1);
- bcopy(var_value, dstring, var_value_len);
- dstring[var_value_len] = '\0'; /* so we can use it as a string */
- DO_ATOE(dstring);
- break;
- case 10: /* a request to execute a command */
- free(command);
- command = (char *)malloc(var_value_len + 1);
- bcopy(var_value, command, var_value_len);
- command[var_value_len] = '\0'; /* so we can use it as a string */
- DO_ATOE(command);
- if (strcmp("all_traps",command) == 0) do_trap = ALL_TRAPS;
- else if (strcmp("std_traps",command) == 0) do_trap = STD_TRAPS;
- else if (strcmp("ent_traps",command) == 0) do_trap = ENT_TRAPS;
- else if (strcmp("ent_trapse",command) == 0) do_trap = ENT_TRAPSE;
- else if (strcmp("all_traps",command) == 0) do_trap = ALL_TRAPS;
- else if (strcmp("quit",command) == 0) do_quit = TRUE;
- else break;
- if (debug_lvl > 0)
- printf("...Action requested: %s set to: %s\n",
- DPI_var[10], command);
- break;
- default: /* NoSuchName */
- if (debug_lvl > 0)
- printf("...Ignored set for %s, noSuchName\n", var_oid);
- packet = mkDPIresponse(SNMP_NO_SUCH_NAME,NULL);
- break;
- } /* end switch (var_index) */
- if (packet) send_packet(packet);
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void issue_std_traps()
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void issue_std_traps(void)
- #endif /* _NO_PROTO */
- {
- trap_stype = 0;
- trap_data = dpi_hostname;
- for (trap_gtype=0; trap_gtype<6; trap_gtype++) {
- issue_one_trap();
- if (trap_gtype == 0) sleep(10); /* some managers purge cache */
- }
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void issue_ent_traps()
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void issue_ent_traps(void)
- #endif /* _NO_PROTO */
- {
- char temp_string[256];
-
- trap_gtype = 6;
- for (trap_stype = 1; trap_stype < 10; trap_stype++) {
- trap_data = temp_string;
- switch (trap_stype) {
- case 1 :
- sprintf(temp_string,"%ld",number);
- break;
- case 2 :
- sprintf(temp_string,"%s",ostring);
- break;
- case 3 :
- trap_data = objectID;
- break;
- case 4 :
- trap_data = "";
- break;
- case 5 :
- trap_data = dpi_hostname;
- break;
- case 6 :
- sleep(1); /* give manager a break */
- sprintf(temp_string,"%lu",counter);
- break;
- case 7 :
- sprintf(temp_string,"%lu",gauge);
- break;
- case 8 :
- sprintf(temp_string,"%lu",ticks);
- break;
- case 9 :
- trap_data = dstring;
- break;
- } /* end switch (trap_stype) */
- issue_one_trap();
- }
- }
-
- /* issue a set of extended traps, pass enterprise ID and multiple
- * variable (assume octect string) as passed by caller
- */
- #ifdef _NO_PROTO /* for classic K&R C */
- static void issue_ent_trapse()
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void issue_ent_trapse(void)
- #endif /* _NO_PROTO */
- {
- int i, n;
- struct dpi_set_packet *data = NULL;
- unsigned char *packet = NULL;
- unsigned long ipaddr, ulnum;
- char oid[256];
- char *cp;
-
- trape_gtype = 6;
- trape_eprise = ENTERPRISE_OID;
- for (n=11; n < (11+OID_COUNT_FOR_TRAPS); n++) {
- data = 0;
- trape_stype = n;
- for (i=1; i<=(n-10); i++)
- data = addtoset(data, i);
- if (data == 0) {
- printf("Could not make dpi_set_packet\n");
- return;
- }
- packet = mkDPItrape(trape_gtype,trape_stype,data,trape_eprise);
- if ((debug_lvl > 0) && (packet)) {
- printf("sending trape packet: %lu %lu enterprise=%s\n",
- trape_gtype, trape_stype, trape_eprise);
- }
- if (packet) send_packet(packet);
- else printf("Could not make trape packet\n");
- }
- }
-
- /* issue one extended trap, pass enterprise ID and multiple
- * variable (assume octect string) as passed by caller
- */
- #ifdef _NO_PROTO /* for classic K&R C */
- static void issue_one_trape()
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void issue_one_trape(void)
- #endif /* _NO_PROTO */
- {
- struct dpi_set_packet *data = NULL;
- unsigned char *packet = NULL;
- char oid[256];
- char *cp;
- int i;
-
- for (i=0; i<trape_datacnt; i++) {
- sprintf(oid,"%s2.%d",OID,i);
- /* assume an octet_string (could have hex data) */
- data = mkDPIlist(data, oid, SNMP_TYPE_STRING,
- strlen(trape_data[i]), trape_data[i]);
- if (data == 0) {
- printf("Could not make dpiset_packet\n");
- } else if (debug_lvl > 0) {
- printf("Preparing: [oid=%s] value: ", oid);
- printf("'");
- for (cp = trape_data[i]; *cp; cp++) /* loop through data */
- printf("%2.2x",*cp); /* hex print one byte */
- printf("'H\n");
- }
- }
- packet = mkDPItrape(trape_gtype,trape_stype,data,trape_eprise);
- if ((debug_lvl > 0) && (packet)) {
- printf("sending trape packet: %lu %lu enterprise=%s\n",
- trape_gtype, trape_stype, trape_eprise);
- }
- if (packet) send_packet(packet);
- else printf("Could not make trape packet\n");
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void issue_one_trap()
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void issue_one_trap(void)
- #endif /* _NO_PROTO */
- {
- long int num; /* must be 4 bytes */
- struct dpi_set_packet *data = NULL;
- unsigned char *packet = NULL;
- unsigned long ipaddr, ulnum;
- char oid[256];
- char *cp;
-
- switch (trap_gtype) {
- /* all traps are handled more or less the same sofar. */
- /* could put specific handling here if needed/wanted. */
- case 0: /* simulate cold start */
- case 1: /* simulate warm start */
- case 4: /* simulate authentication failure */
- strcpy(oid,"none");
- break;
- case 2: /* simulate link down */
- case 3: /* simulate link up */
- strcpy(oid,ifIndex);
- num = 1;
- data = mkDPIset(oid, SNMP_TYPE_NUMBER, sizeof(num), &num);
- break;
- case 5: /* simulate EGP neighbor loss */
- strcpy(oid,egpNeighAddr);
- ipaddr = lookup_host(trap_data);
- data = mkDPIset(oid, SNMP_TYPE_INTERNET, sizeof(ipaddr), &ipaddr);
- break;
- case 6: /* simulate enterprise specific trap */
- sprintf(oid,"%s%d.0",OID, trap_stype);
- switch (trap_stype) {
- case 1: /* a number */
- num = strtol(trap_data,(char **)0,10);
- data = mkDPIset(oid, SNMP_TYPE_NUMBER, sizeof(num), &num);
- break;
- case 2: /* an octet_string (could have hex data) */
- data = mkDPIset(oid,SNMP_TYPE_STRING,strlen(trap_data),trap_data);
- break;
- case 3: /* object id */
- data = mkDPIset(oid,SNMP_TYPE_OBJECT,strlen(trap_data) + 1,
- trap_data);
- break;
- case 4: /* an empty variable value */
- data = mkDPIset(oid, SNMP_TYPE_EMPTY, 0, 0);
- break;
- case 5: /* internet address */
- ipaddr = lookup_host(trap_data);
- data = mkDPIset(oid, SNMP_TYPE_INTERNET, sizeof(ipaddr), &ipaddr);
- break;
- case 6: /* counter (unsigned) */
- ulnum = strtoul(trap_data,(char **)0,10);
- data = mkDPIset(oid, SNMP_TYPE_COUNTER, sizeof(ulnum), &ulnum);
- break;
- case 7: /* gauge (unsigned) */
- ulnum = strtoul(trap_data,(char **)0,10);
- data = mkDPIset(oid, SNMP_TYPE_GAUGE, sizeof(ulnum), &ulnum);
- break;
- case 8: /* time ticks (unsigned) */
- ulnum = strtoul(trap_data,(char **)0,10);
- data = mkDPIset(oid, SNMP_TYPE_TICKS, sizeof(num), &ulnum);
- break;
- case 9: /* a display_string (ascii only) */
- DO_ETOA(trap_data);
- data = mkDPIset(oid,SNMP_TYPE_STRING,strlen(trap_data),trap_data);
- DO_ATOE(trap_data);
- break;
- default: /* handle as string */
- printf("Unknown specific trap type: %s, assume octet_string\n",
- trap_stype);
- data = mkDPIset(oid,SNMP_TYPE_STRING,strlen(trap_data),trap_data);
- break;
- } /* end switch (trap_stype) */
- break;
- default: /* unknown trap */
- printf("Unknown general trap type: %s\n", trap_gtype);
- return;
- break;
- } /* end switch (trap_gtype) */
-
- packet = mkDPItrap(trap_gtype,trap_stype,data);
- if ((debug_lvl > 0) && (packet)) {
- printf("sending trap packet: %u %u [oid=%s] value: ",
- trap_gtype, trap_stype, oid);
- if (trap_stype == 2) {
- printf("'");
- for (cp = trap_data; *cp; cp++) /* loop through data */
- printf("%2.2x",*cp); /* hex print one byte */
- printf("'H\n");
- } else printf("%s\n", trap_data);
- }
- if (packet) send_packet(packet);
- else printf("Could not make trap packet\n");
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void send_packet(packet) /* DPI packet to agent */
- char *packet;
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void send_packet(const char *packet) /* DPI packet to agent */
- #endif /* _NO_PROTO */
- {
- int rc;
-
- if (debug_lvl > 2) {
- printf("...Sending DPI packet:\n");
- dump_bfr(packet, PACKET_LEN(packet));
- }
- #ifdef OS2
- rc = send(dpi_fd,packet,PACKET_LEN(packet),0);
- #else
- rc = write(dpi_fd,packet,PACKET_LEN(packet));
- #endif
- if (rc != PACKET_LEN(packet)) DO_ERROR("send_packet: write");
- /* no need to free packet (static buffer in mkDPI.... routine) */
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void do_register() /* register our objectIDs with agent */
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void do_register(void) /* register our objectIDs with agent */
- #endif /* _NO_PROTO */
- {
- int i, rc;
- char toid[256];
-
- if (debug_lvl > 0) printf("Registering variables:\n");
- for (i=1; i<=OID_COUNT; i++) {
- sprintf(toid,"%s%d.",OID,i);
- packet = mkDPIregister(toid);
- #ifdef OS2
- rc = send(dpi_fd, packet, PACKET_LEN(packet),0);
- #else
- rc = write(dpi_fd, packet, PACKET_LEN(packet));
- #endif
- if (rc <= 0) {
- DO_ERROR("do_register: write");
- printf("Quitting, unsuccessful register for %s\n",toid);
- close(dpi_fd);
- exit(1);
- }
- if (debug_lvl > 0) {
- printf("...Registered: %-25s oid: %s\n",DPI_var[i],toid);
- printf("......Initial value: ");
- print_val(i); /* prints \n at end */
- }
- }
- }
-
- /* add specified variable to list of variable in the dpi_set_packet
- */
- #ifdef _NO_PROTO /* for classic K&R C */
- struct dpi_set_packet *addtoset(data, stype)
- struct dpi_set_packet *data;
- int stype;
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- struct dpi_set_packet *addtoset(struct dpi_set_packet *data, int stype)
- #endif /* _NO_PROTO */
- {
- char var_oid[256];
-
- sprintf(var_oid,"%s%d.0",OID, stype);
- switch (stype) {
- case 1: /* a number */
- data = mkDPIlist(data, var_oid, SNMP_TYPE_NUMBER,
- sizeof(number), &number);
- break;
- case 2: /* an octet_string (can have binary data) */
- data = mkDPIlist(data, var_oid, SNMP_TYPE_STRING,
- ostring_len, ostring);
- break;
- case 3: /* object id */
- data = mkDPIlist(data, var_oid, SNMP_TYPE_OBJECT,
- objectID_len, objectID);
- break;
- case 4: /* some empty variable */
- data = mkDPIlist(data, var_oid, SNMP_TYPE_EMPTY, 0, NULL);
- break;
- case 5: /* internet address */
- data = mkDPIlist(data, var_oid, SNMP_TYPE_INTERNET,
- sizeof(ipaddr), &ipaddr);
- break;
- case 6: /* counter (unsigned) */
- data =mkDPIlist(data, var_oid, SNMP_TYPE_COUNTER,
- sizeof(counter), &counter);
- break;
- case 7: /* gauge (unsigned) */
- data = mkDPIlist(data, var_oid, SNMP_TYPE_GAUGE,
- sizeof(gauge), &gauge);
- break;
- case 8: /* time ticks (unsigned) */
- data = mkDPIlist(data, var_oid, SNMP_TYPE_TICKS,
- sizeof(ticks), &ticks);
- break;
- case 9: /* a display_string (printable ascii only) */
- DO_ETOA(dstring);
- data = mkDPIlist(data, var_oid, SNMP_TYPE_STRING,
- strlen(dstring), dstring);
- DO_ATOE(dstring);
- break;
- } /* end switch (stype) */
- return(data);
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void print_val(index)
- int index;
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void print_val(const int index)
- #endif /* _NO_PROTO */
- {
- char *cp;
- struct in_addr display_ipaddr;
-
- switch (index) {
- case 1 :
- printf("%ld\n",number);
- break;
- case 2 :
- printf("'");
- for (cp = ostring; cp < ostring + ostring_len; cp++)
- printf("%2.2x",*cp);
- printf("'H\n");
- break;
- case 3 :
- printf("%*s\n", objectID_len, objectID);
- break;
- case 4 :
- printf("no value (EMPTY)\n");
- break;
- case 5 :
- display_ipaddr.s_addr = (u_long) ipaddr;
- printf("%s\n",inet_ntoa(display_ipaddr));
- /* This worked on VM, MVS and AIX, but not on OS/2
- * printf("%d.%d.%d.%d\n", (ipaddr >> 24), ((ipaddr << 8) >> 24),
- * ((ipaddr << 16) >> 24), ((ipaddr << 24) >> 24));
- */
- break;
- case 6 :
- printf("%lu\n",counter);
- break;
- case 7 :
- printf("%lu\n",gauge);
- break;
- case 8 :
- printf("%lu\n",ticks);
- break;
- case 9 :
- printf("%s\n",dstring);
- break;
- case 10 :
- printf("%s\n",command);
- break;
- } /* end switch(index) */
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void check_arguments(argc, argv) /* check arguments */
- int argc;
- char *argv[];
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void check_arguments(const int argc, char *argv[])
- #endif /* _NO_PROTO */
- {
- char *hname, *cname;
- int i, j;
-
- dpi_userid = hname = cname = NULL;
- for (i=1; argc > i; i++) {
- if (strcmp(argv[i],"-d") == 0) {
- i++;
- if (argc > i) {
- debug_lvl = atoi(argv[i]);
- if (debug_lvl >= 5) {
- DPIdebug(1);
- }
- }
- } else if (strcmp(argv[i],"-trap") == 0) {
- if (argc > i+3) {
- trap_gtype = atoi(argv[i+1]);
- trap_stype = atoi(argv[i+2]);
- trap_data = argv[i+3];
- i = i + 3;
- do_trap = ONE_TRAP;
- } else usage(argv[0], 1);
- } else if (strcmp(argv[i],"-trape") == 0) {
- if (argc > i+4) {
- trape_gtype = strtoul(argv[i+1],(char**)0,10);
- trape_stype = strtoul(argv[i+2],(char**)0,10);
- trape_eprise = argv[i+3];
- for (i = i + 4, j = 0;
- (argc > i) && (j < MAX_TRAPE_DATA);
- i++, j++) {
- trape_data[j] = argv[i];
- }
- trape_datacnt = j;
- do_trap = ONE_TRAPE;
- break; /* -trape must be last option */
- } else usage(argv[0], 1);
- } else if (strcmp(argv[i],"-all_traps") == 0) {
- do_trap = ALL_TRAPS;
- } else if (strcmp(argv[i],"-std_traps") == 0) {
- do_trap = STD_TRAPS;
- } else if (strcmp(argv[i],"-ent_traps") == 0) {
- do_trap = ENT_TRAPS;
- } else if (strcmp(argv[i],"-ent_trapse") == 0) {
- do_trap = ENT_TRAPSE;
- #if defined(VM) || defined(MVS)
- } else if (strcmp(argv[i],"-inet") == 0) {
- use_iucv = 0;
- } else if (strcmp(argv[i],"-iucv") == 0) {
- use_iucv = TRUE;
- } else if (strcmp(argv[i],"-u") == 0) {
- use_iucv = TRUE; /* -u implies -iucv */
- i++;
- if (argc > i) {
- dpi_userid = argv[i];
- }
- #endif
- } else if (strcmp(argv[i],"?") == 0) {
- usage(argv[0], 0);
- } else {
- if (hname == NULL) hname = argv[i];
- else if (cname == NULL) cname = argv[i];
- else usage(argv[0], 1);
- }
- }
- if (hname == NULL) hname = LOOPBACK; /* use default */
- if (cname == NULL) cname = PUBLIC_COMMUNITY_NAME; /* use default */
- #if defined(VM) || defined(MVS)
- if (dpi_userid == NULL) dpi_userid = SNMPAGENTUSERID;
- if (debug_lvl > 2)
- printf("hname=%s, cname=%s, userid=%s\n",hname,cname,dpi_userid);
- #else
- if (debug_lvl > 2)
- printf("hname=%s, cname=%s\n",hname,cname);
- #endif
- if (use_iucv != TRUE) {
- DO_ETOA(cname); /* for VM or MVS */
- dpi_port = query_DPI_port(hname,cname);
- DO_ATOE(cname); /* for VM or MVS */
- if (dpi_port == -1) {
- printf("No response from agent at %s(%s)\n",hname,cname);
- exit(1);
- }
- } else dpi_port == -1;
- dpi_hostname = hname;
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void usage(pname, exit_rc)
- char *pname;
- int exit_rc;
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void usage(const char *pname, const int exit_rc)
- #endif /* _NO_PROTO */
- {
- printf("Usage: %s [-d debug_lvl] [-trap g_type s_type data]", pname);
- printf(" [-all_traps]\n");
- printf("%*s[-trape g_type s_type enterprise data1 data2 .. datan]\n",
- strlen(pname)+8,"");
- printf("%*s[-std_traps] [-ent_traps] [-ent_trapse]\n",
- strlen(pname)+8,"");
- #if defined(VM) || defined(MVS)
- printf("%*s[-iucv] [-u agent_userid]\n",strlen(pname)+8, "");
- printf("%*s", strlen(pname)+8, "");
- printf("[-inet] [agent_hostname [community_name]]\n");
- printf("default: -d 0 -iucv -u %s\n", SNMPAGENTUSERID);
- printf(" -inet %s %s\n", LOOPBACK, PUBLIC_COMMUNITY_NAME);
- #else
- printf("%*s[agent_hostname [community_name]]\n",strlen(pname)+8,"");
- printf("default: -d 0 %s %s\n", LOOPBACK, PUBLIC_COMMUNITY_NAME);
- #endif
- exit(exit_rc);
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void init_variables() /* initialize our variables */
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void init_variables(void) /* initialize our variables */
- #endif /* _NO_PROTO */
- {
- char ch, *cp;
-
- ostring = (char *)malloc(strlen(OSTRING) + 4 + 1 );
- bcopy(OSTRING,ostring,strlen(OSTRING));
- ostring_len = strlen(OSTRING);
- for (ch=1;ch<5;ch++) /* add hex data 0x01020304 */
- ostring[ostring_len++] = ch;
- ostring[ostring_len] = '\0'; /* so we can use it as a string */
- objectID = (char *)malloc(strlen(OID));
- objectID_len = strlen(OID);
- bcopy(OID,objectID,strlen(OID));
- if (objectID[objectID_len - 1] == '.') /* if trailing dot, */
- objectID[objectID_len - 1] = '\0'; /* remove it */
- else objectID_len++; /* length includes null */
- dstring = (char *)malloc(strlen(DSTRING)+1);
- bcopy(DSTRING,dstring,strlen(DSTRING)+1);
- command = (char *)malloc(strlen(COMMAND)+1);
- bcopy(COMMAND,command,strlen(COMMAND)+1);
- ipaddr = dpi_ipaddress;
-
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void init_connection() /* connect to the DPI agent */
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void init_connection(void) /* connect to the DPI agent */
- #endif /* _NO_PROTO */
- {
- int rc;
- int sasize; /* size of socket structure */
- struct sockaddr_in sin; /* socket address AF_INET */
- struct sockaddr *sa; /* socket address general */
- #if defined(VM) || defined (MVS)
- struct sockaddr_iucv siu; /* socket address AF_IUCV */
-
- if (use_iucv == TRUE) {
- printf("Connecting to %s DPI_port %d userid %s (TCP, AF_IUCV)\n",
- dpi_hostname,dpi_port,dpi_userid);
- bzero(&siu,sizeof(siu));
- siu.siucv_family = AF_IUCV;
- siu.siucv_addr = dpi_ipaddress;
- siu.siucv_port = dpi_port;
- memset(siu.siucv_nodeid, ' ', sizeof(siu.siucv_nodeid));
- memset(siu.siucv_userid, ' ', sizeof(siu.siucv_userid));
- memset(siu.siucv_name, ' ', sizeof(siu.siucv_name));
- bcopy(dpi_userid, siu.siucv_userid, min(8,strlen(dpi_userid)));
- bcopy(SNMPIUCVNAME, siu.siucv_name, min(8,strlen(SNMPIUCVNAME)));
- dpi_fd = socket(AF_IUCV, SOCK_STREAM, 0);
- sa = (struct sockaddr *) &siu;
- sasize = sizeof(struct sockaddr_iucv);
- } else {
- #endif
- printf("Connecting to %s DPI_port %d (TCP, AF_INET)\n",
- dpi_hostname,dpi_port);
- bzero(&sin,sizeof(sin));
- sin.sin_family = AF_INET;
- sin.sin_port = htons(dpi_port);
- sin.sin_addr.s_addr = dpi_ipaddress;
- dpi_fd = socket(AF_INET, SOCK_STREAM, 0);
- sa = (struct sockaddr *) &sin;
- sasize = sizeof(struct sockaddr_in);
- #if defined(VM) || defined (MVS)
- }
- #endif
- if (dpi_fd < 0) { /* exit on error */
- DO_ERROR("init_connection: socket");
- exit(1);
- }
- rc = connect(dpi_fd, sa, sasize); /* connect to agent */
- if (rc != 0) { /* exit on error */
- DO_ERROR("init_connection: connect");
- close(dpi_fd);
- exit(1);
- }
- }
-
- #ifdef _NO_PROTO /* for classic K&R C */
- static void dump_bfr(buf, len) /* hex dump buffer */
- char *buf;
- int len;
- #else /* _NO_PROTO */ /* for ANSI-C compiler */
- static void dump_bfr(const char *buf, const int len)
- #endif /* _NO_PROTO */
- {
- register int i;
-
- if (len == 0) printf(" empty buffer\n"); /* buffer is empty */
- for (i=0;i<len;i++) { /* loop through buffer */
- if ((i&15) == 0) printf(" "); /* indent new line */
- printf("%2.2x",(unsigned char)buf[i]);/* hex print one byte */
- if ((i&15) == 15) printf("\n"); /* nl every 16 bytes */
- else if ((i&3) == 3) printf(" "); /* space every 4 bytes */
- }
- if (i&15) printf("\n"); /* always end with nl */
- }
-