diff --git a/proto/snmp/snmp.c b/proto/snmp/snmp.c index 347521eb..ee868825 100644 --- a/proto/snmp/snmp.c +++ b/proto/snmp/snmp.c @@ -257,7 +257,6 @@ snmp_sock_err(sock *sk, int UNUSED err) { snmp_log("socket error '%s' (errno: %d)", strerror(err), err); struct snmp_proto *p = sk->data; - p->errs++; snmp_sock_disconnect(p, 1); } @@ -280,10 +279,6 @@ snmp_start_locked(struct object_lock *lock) p->state = SNMP_LOCKED; sock *s = p->sock; - p->to_send = 0; - p->errs = 0; - - if (!p->bgp_trie) p->bgp_trie = f_new_trie(p->lp, 0); // TODO user-data attachment size @@ -303,9 +298,6 @@ snmp_start_locked(struct object_lock *lock) p->sock = s; s->data = p; - - p->to_send = 0; - p->errs = 0; } /* Try opening the socket, schedule a retry on fail */ @@ -478,6 +470,7 @@ snmp_start(struct proto *P) } } + p->last_header = NULL; snmp_startup(p); return PS_START; } @@ -651,9 +644,9 @@ snmp_shutdown(struct proto *P) */ struct protocol proto_snmp = { - .name = "Snmp", + .name = "SNMP", .template = "snmp%d", - .channel_mask = NB_ANY, + .channel_mask = 0, .proto_size = sizeof(struct snmp_proto), .config_size = sizeof(struct snmp_config), .postconfig = snmp_postconfig, diff --git a/proto/snmp/snmp.h b/proto/snmp/snmp.h index f8e12f70..dc4b7506 100644 --- a/proto/snmp/snmp.h +++ b/proto/snmp/snmp.h @@ -116,6 +116,7 @@ struct snmp_proto { u32 bgp_local_as; sock *sock; + void *last_header; /* points to partial PDU header */ u8 timeout; /* timeout is part of MIB registration. It specifies how long should the master agent wait for request responses. */ @@ -139,9 +140,6 @@ struct snmp_proto { uint startup_delay; timer *startup_timer; u8 state; - - uint to_send; - uint errs; }; //void snmp_tx(sock *sk); diff --git a/proto/snmp/subagent.c b/proto/snmp/subagent.c index 72880b8f..05585ec2 100644 --- a/proto/snmp/subagent.c +++ b/proto/snmp/subagent.c @@ -339,7 +339,7 @@ snmp_notify_pdu(struct snmp_proto *p, struct oid *oid, void *data, uint size, in memcpy(c.buffer, data, size); ADVANCE(c.buffer, c.size, size); - uint s = update_packet_size(p, sk->tbuf, c.buffer); + uint s = update_packet_size(p, sk->tpos, c.buffer); sk_send(sk, s); #undef TRAP0_HEADER_SIZE @@ -1522,15 +1522,23 @@ parse_gets2_pdu(struct snmp_proto *p, byte * const pkt_start, uint size, uint *s has_any = 0; for (bulk_state.index = 0; bulk_state.index < bulk_state.repeaters; bulk_state.repeaters++) - has_any = has_any || snmp_get_bulk2(p, start, end, &bulk_state, &c); + has_any = snmp_get_bulk2(p, start, end, &bulk_state, &c) || has_any; } } /* send the constructed packet */ - struct agentx_response *res = (void *) sk->tbuf; + struct agentx_response *res; + if (p->last_header) + { + res = p->last_header; + p->last_header = NULL; + } + else + res = response_header; + /* We update the error, index pair on the beginning of the packet. */ response_err_ind(res, c.error, c.index + 1); - uint s = update_packet_size(p, (byte *) response_header, c.buffer); + uint s = update_packet_size(p, (byte *) res, c.buffer); /* We send the message in TX-buffer. */ sk_send(sk, s); @@ -1542,8 +1550,9 @@ parse_gets2_pdu(struct snmp_proto *p, byte * const pkt_start, uint size, uint *s partial: /* need to tweak RX buffer packet size */ - (c.byte_ord) ? put_u32(&h->payload, pkt_size) : (h->payload = pkt_size); + STORE_U32(h->payload, pkt_size); *skip = AGENTX_HEADER_SIZE; + p->last_header = h; /* number of bytes parsed from RX-buffer */ ret = pkt - pkt_start; @@ -1897,6 +1906,9 @@ snmp_manage_tbuf(struct snmp_proto UNUSED *p, struct snmp_pdu *c) static struct agentx_response * prepare_response(struct snmp_proto *p, struct snmp_pdu *c) { + if (p->last_header) + return p->last_header; + struct agentx_response *r = (void *) c->buffer; struct agentx_header *h = &r->h;