Exemplo n.º 1
0
static int noit_snmp_handler(eventer_t e, int mask, void *closure,
                             struct timeval *now) {
  fd_set fdset;
  int fds, block = 0;
  struct timeval timeout = { 0, 0 };
  struct target_session *ts = closure;
  FD_ZERO(&fdset);
  FD_SET(e->fd, &fdset);
  fds = e->fd + 1;
  snmp_sess_read(ts->sess_handle, &fdset);
  if(noit_snmp_session_cleanse(ts))
    return 0;
  snmp_sess_select_info(ts->sess_handle, &fds, &fdset, &timeout, &block);
  _set_ts_timeout(ts, block ? &timeout : NULL);
  return EVENTER_READ | EVENTER_EXCEPTION;
}
Exemplo n.º 2
0
void mux_poller::poll()
{
   static const char *funcname {"snmp::mux_poller::poll"};
   if (0 == tasks.size()) return;

   int fds, block;
   fd_set fdset;
   timeval timeout;
   taskdata::iterator it = tasks.begin();

   for (unsigned active_hosts;;)
   {
      active_hosts = sessions.size();
      if (active_hosts < max_hosts)
      {
         if (0 == active_hosts and it == tasks.end()) return;
         unsigned delta = max_hosts - active_hosts;
         void *sessp;

         for (unsigned i = 0; it != tasks.end() and i < delta; ++i, ++it)
         {
            polltask &task = it->second;
            sessp = init_snmp_session(it->first.c_str(), task.community.c_str(),
                  task.version, callback_wrap, static_cast<void *>(&task));

            sessions.emplace_front(sessp);
            task.pdata = &(sessions.front());

            try { async_send(sessp, snmp_clone_pdu(task.request)); }
            catch (snmprun_error &error) { 
               throw snmprun_error {errtype::runtime, funcname, "poll failed: %s", error.what()}; }
         }
      }

      fds = block = 0;
      FD_ZERO(&fdset);
      
      for (auto &sess : sessions) snmp_sess_select_info(sess.sessp, &fds, &fdset, &timeout, &block);
      if (0 > (fds = select(fds, &fdset, nullptr, nullptr, &timeout)))
         throw snmprun_error {errtype::runtime, funcname, "select() failed: %s", strerror(errno)};

      if (fds) { for (auto &sess : sessions) snmp_sess_read(sess.sessp, &fdset); }
      else     { for (auto &sess : sessions) snmp_sess_timeout(sess.sessp);      }

      sessions.remove_if([](const polldata &p) { return (pollstate::finished == p.state); });
   }
}
Exemplo n.º 3
0
v8::Handle<v8::Value> Session::onData(const v8::Arguments& args) {

    fd_set fdset;
    struct timeval timeout;
    int block = 1;
    int numfds = 0;

    UNWRAP(Session, wrap, args.This());
    SwapScope scope(wrap, args);
    if(0 == wrap->session_) {
        return ThrowError("Session hasn't opened.");
    }

    if(2 != args.Length()) {
        return ThrowError("Must pass the msg and rinfo arguments to onData.");
    }

    FD_ZERO(&fdset);

    /**
    * block input:  set to 1 if input timeout value is undefined
    * set to 0 if input timeout value is defined
    * block output: set to 1 if output timeout value is undefined
    * set to 0 if output rimeout vlaue id defined
    */
    if(1 != snmp_sess_select_info(wrap->session_, &numfds, &fdset,
                                  &timeout, &block)) {
        return v8::Undefined();
    }


    if(-1 == snmp_sess_read(wrap->session_, &fdset)) {
        return ThrowError(snmp_api_errstring(wrap->arguments_.s_snmp_errno));
    }

    if(0 == block) {
        v8::Handle<v8::Object> ret = v8::Object::New();
        v8::Handle<v8::Object> timeout_v8 = v8::Object::New();
        timeout_v8->Set(tv_sec_symbol,  from_long(timeout.tv_sec));
        timeout_v8->Set(tv_usec_symbol, from_long(timeout.tv_usec));
        ret->Set(timeout_symbol, timeout_v8);
        return scope.Close(ret);
    } else {
        return v8::Undefined();
    }
}
Exemplo n.º 4
0
v8::Handle<v8::Value> Session::readData(const v8::Arguments& args) {

    fd_set fdset;
    struct timeval timeout;
    int block = 1;
    int numfds = 0;

    v8::HandleScope scope;
    UNWRAP(Session, wrap, args.This());
    if(0 == wrap->session_) {
        return ThrowError("Session hasn't opened.");
    }

    if(0 != args.Length()) {
        return ThrowError("Must not pass any arguments to readData.");
    }

    FD_ZERO(&fdset);

    /**
    * block input:  set to 1 if input timeout value is undefined
    * set to 0 if input timeout value is defined
    * block output: set to 1 if output timeout value is undefined
    * set to 0 if output rimeout vlaue id defined
    */
    if(0 == snmp_sess_select_info(wrap->session_, &numfds, &fdset,
		&timeout, &block)) {
		snmp_sess_timeout(wrap->session_);
		goto error;
	}

	if(0 == block) {
		int ret = select(numfds, &fdset, 0, 0, &timeout);
		if(SOCKET_ERROR == ret || 0 == ret) {
			snmp_sess_timeout(wrap->session_);
			goto error;
		}
	}

    if(-1 == snmp_sess_read(wrap->session_, &fdset)) {
        return ThrowError(snmp_api_errstring(wrap->arguments_.s_snmp_errno));
    }
error:
    return v8::Undefined();
}
Exemplo n.º 5
0
int
snmp_sess_synch_response(void *sessp,
                         netsnmp_pdu *pdu, netsnmp_pdu **response)
{
    netsnmp_session *ss;
    struct synch_state lstate, *state;
    snmp_callback   cbsav;
    void           *cbmagsav;
    int             numfds, count;
    fd_set          fdset;
    struct timeval  timeout, *tvp;
    int             block;

    ss = snmp_sess_session(sessp);
    memset((void *) &lstate, 0, sizeof(lstate));
    state = &lstate;
    cbsav = ss->callback;
    cbmagsav = ss->callback_magic;
    ss->callback = snmp_synch_input;
    ss->callback_magic = (void *) state;

    if ((state->reqid = snmp_sess_send(sessp, pdu)) == 0) {
        snmp_free_pdu(pdu);
        state->status = STAT_ERROR;
    } else
        state->waiting = 1;

    while (state->waiting) {
        numfds = 0;
        FD_ZERO(&fdset);
        block = SNMPBLOCK;
        tvp = &timeout;
        timerclear(tvp);
        snmp_sess_select_info(sessp, &numfds, &fdset, tvp, &block);
        if (block == 1)
            tvp = NULL;         /* block without timeout */
        count = select(numfds, &fdset, 0, 0, tvp);
        if (count > 0) {
            snmp_sess_read(sessp, &fdset);
        } else
            switch (count) {
            case 0:
                snmp_sess_timeout(sessp);
                break;
            case -1:
                if (errno == EINTR) {
                    continue;
                } else {
                    snmp_errno = SNMPERR_GENERR;
                    /*
                     * CAUTION! if another thread closed the socket(s)
                     * waited on here, the session structure was freed.
                     * It would be nice, but we can't rely on the pointer.
                     * ss->s_snmp_errno = SNMPERR_GENERR;
                     * ss->s_errno = errno;
                     */
                    snmp_set_detail(strerror(errno));
                }
                /*
                 * FALLTHRU 
                 */
            default:
                state->status = STAT_ERROR;
                state->waiting = 0;
            }
    }
    *response = state->pdu;
    ss->callback = cbsav;
    ss->callback_magic = cbmagsav;
    return state->status;
}
Exemplo n.º 6
0
int
main(int argc, char *argv[])
{
    int             arg;
    char           *prognam;
    char           *cp = NULL;
    const char*     sysUpTime = NULL;

    /* initialize tcpip, if necessary */
    SOCK_STARTUP;

    prognam = strrchr(argv[0], '/');
    if (prognam)
        ++prognam;
    else
        prognam = argv[0];

    putenv(strdup("POSIXLY_CORRECT=1"));

    netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID,
                           NETSNMP_DS_LIB_DISABLE_PERSISTENT_LOAD, 1);
    netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID,
                           NETSNMP_DS_LIB_DISABLE_PERSISTENT_SAVE, 1);

    while ((arg = getopt(argc, argv, ":Vhm:M:D:dP:L:U:c:x:")) != -1) {
        switch (arg) {
        case 'h':
            usage(prognam);
            result = 0;
            goto out;
        case 'm':
            setenv("MIBS", optarg, 1);
            break;
        case 'M':
            setenv("MIBDIRS", optarg, 1);
            break;
        case 'c':
            context = optarg;
            contextLen = strlen(context);
            break;
        case 'D':
            debug_register_tokens(optarg);
            snmp_set_do_debugging(1);
            break;
        case 'd':
            netsnmp_ds_set_boolean(NETSNMP_DS_LIBRARY_ID,
                                   NETSNMP_DS_LIB_DUMP_PACKET, 1);
            break;
        case 'U':
            sysUpTime = optarg;
            break;
        case 'V':
            fprintf(stderr, "NET-SNMP version: %s\n", netsnmp_get_version());
            result = 0;
            goto out;
#ifndef DISABLE_MIB_LOADING
        case 'P':
            cp = snmp_mib_toggle_options(optarg);
            if (cp != NULL) {
                fprintf(stderr, "Unknown parser option to -P: %c.\n", *cp);
                usage(prognam);
                goto out;
            }
            break;
#endif /* DISABLE_MIB_LOADING */
        case 'L':
            if (snmp_log_options(optarg, argc, argv) < 0)
                goto out;
            break;
        case 'x':
            if (optarg != NULL) {
                netsnmp_ds_set_string(NETSNMP_DS_APPLICATION_ID,
                                      NETSNMP_DS_AGENT_X_SOCKET, optarg);
            } else
                usage(argv[0]);
            break;

        case ':':
            fprintf(stderr, "Option -%c requires an operand\n", optopt);
            usage(prognam);
            goto out;
        case '?':
            fprintf(stderr, "Unrecognized option: -%c\n", optopt);
            usage(prognam);
            goto out;
        }
    }

    arg = optind;

    init_snmp(NETSNMP_APPLICATION_CONFIG_TYPE);
    agentx_config_init();

    /* NOTIFY varlist */
    pdu = pdu_create_opt_context(AGENTX_MSG_NOTIFY, context, contextLen);

    if (sysUpTime)
        snmp_add_var(pdu, sysuptime_oid, sysuptime_oid_len, 't', sysUpTime);

    if (arg == argc) {
        fprintf(stderr, "Missing trap-oid parameter\n");
        usage(prognam);
        goto out;
    }

    if (snmp_add_var(pdu, snmptrap_oid, snmptrap_oid_len, 'o', argv[arg])) {
        snmp_perror(argv[arg]);
        goto out;
    }
    ++arg;

    while (arg < argc) {
        oid    name[MAX_OID_LEN];
        size_t name_length = MAX_OID_LEN;
        arg += 3;
        if (arg > argc) {
            fprintf(stderr, "%s: Missing type/value for variable\n",
                    argv[arg - 3]);
            goto out;
        }
        if (!snmp_parse_oid(argv[arg - 3], name, &name_length)) {
            snmp_perror(argv[arg - 3]);
            goto out;
        }
        if (snmp_add_var(pdu, name, name_length, argv[arg - 2][0],
                         argv[arg - 1]) != 0) {
            snmp_perror(argv[arg - 3]);
            goto out;
        }
    }

    packetid = 0;

    state = &Connecting;
    next_state = NULL;
    if(state->entry) state->entry(state);

    /* main loop here... */
    for(;;) {
        int block = 1;
        int numfds = 0;
        int count;
        fd_set fdset;
        struct timeval timeout;

        while(next_state) {
            if(state->exit) state->exit(state);
            DEBUGMSGTL(("process", "State transition: %s -> %s\n",
                        state->name, next_state->name));
            state = next_state;
            next_state = NULL;
            if(state->entry) state->entry(state);
        }

        if(state == &Exit)
            break;

        FD_ZERO(&fdset);
        snmp_sess_select_info(sessp, &numfds, &fdset, &timeout, &block);
        count = select(numfds, &fdset, NULL, NULL, !block ? &timeout : NULL);
        if (count > 0)
            snmp_sess_read(sessp, &fdset);
        else if (count == 0)
            snmp_sess_timeout(sessp);
        else if (errno != EINTR) {
            snmp_log(LOG_ERR, "select error [%s]\n", strerror(errno));
            change_state(&Exit);
        }
    }

    /* at shutdown time */
    snmp_free_pdu(pdu);
    pdu = NULL;

    snmp_shutdown(NETSNMP_APPLICATION_CONFIG_TYPE);

out:
    SOCK_CLEANUP;
    return result;
}