1/**
2 * @file
3 * SNMP Agent message handling structures.
4 */
5
6/*
7 * Copyright (c) 2006 Axon Digital Design B.V., The Netherlands.
8 * All rights reserved.
9 *
10 * Redistribution and use in source and binary forms, with or without modification,
11 * are permitted provided that the following conditions are met:
12 *
13 * 1. Redistributions of source code must retain the above copyright notice,
14 *    this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright notice,
16 *    this list of conditions and the following disclaimer in the documentation
17 *    and/or other materials provided with the distribution.
18 * 3. The name of the author may not be used to endorse or promote products
19 *    derived from this software without specific prior written permission.
20 *
21 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
22 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
23 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT
24 * SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
25 * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT
26 * OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
27 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
28 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
29 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY
30 * OF SUCH DAMAGE.
31 *
32 * Author: Christiaan Simons <christiaan.simons@axon.tv>
33 */
34
35#ifndef __LWIP_SNMP_MSG_H__
36#define __LWIP_SNMP_MSG_H__
37
38#include "lwip/opt.h"
39#include "lwip/snmp.h"
40#include "lwip/snmp_structs.h"
41
42#if LWIP_SNMP
43
44#if SNMP_PRIVATE_MIB
45#include "private_mib.h"
46#endif
47
48#ifdef __cplusplus
49extern "C" {
50#endif
51
52/* The listen port of the SNMP agent. Clients have to make their requests to
53   this port. Most standard clients won't work if you change this! */
54#ifndef SNMP_IN_PORT
55#define SNMP_IN_PORT 161
56#endif
57/* The remote port the SNMP agent sends traps to. Most standard trap sinks won't
58   work if you change this! */
59#ifndef SNMP_TRAP_PORT
60#define SNMP_TRAP_PORT 162
61#endif
62
63#define SNMP_ES_NOERROR 0
64#define SNMP_ES_TOOBIG 1
65#define SNMP_ES_NOSUCHNAME 2
66#define SNMP_ES_BADVALUE 3
67#define SNMP_ES_READONLY 4
68#define SNMP_ES_GENERROR 5
69
70#define SNMP_GENTRAP_COLDSTART 0
71#define SNMP_GENTRAP_WARMSTART 1
72#define SNMP_GENTRAP_AUTHFAIL 4
73#define SNMP_GENTRAP_ENTERPRISESPC 6
74
75    struct snmp_varbind {
76        /* next pointer, NULL for last in list */
77        struct snmp_varbind *next;
78        /* previous pointer, NULL for first in list */
79        struct snmp_varbind *prev;
80
81        /* object identifier length (in s32_t) */
82        u8_t ident_len;
83        /* object identifier array */
84        s32_t *ident;
85
86        /* object value ASN1 type */
87        u8_t value_type;
88        /* object value length (in u8_t) */
89        u8_t value_len;
90        /* object value */
91        void *value;
92
93        /* encoding varbind seq length length */
94        u8_t seqlenlen;
95        /* encoding object identifier length length */
96        u8_t olenlen;
97        /* encoding object value length length */
98        u8_t vlenlen;
99        /* encoding varbind seq length */
100        u16_t seqlen;
101        /* encoding object identifier length */
102        u16_t olen;
103        /* encoding object value length */
104        u16_t vlen;
105    };
106
107    struct snmp_varbind_root {
108        struct snmp_varbind *head;
109        struct snmp_varbind *tail;
110        /* number of variable bindings in list */
111        u8_t count;
112        /* encoding varbind-list seq length length */
113        u8_t seqlenlen;
114        /* encoding varbind-list seq length */
115        u16_t seqlen;
116    };
117
118/** output response message header length fields */
119    struct snmp_resp_header_lengths {
120        /* encoding error-index length length */
121        u8_t erridxlenlen;
122        /* encoding error-status length length */
123        u8_t errstatlenlen;
124        /* encoding request id length length */
125        u8_t ridlenlen;
126        /* encoding pdu length length */
127        u8_t pdulenlen;
128        /* encoding community length length */
129        u8_t comlenlen;
130        /* encoding version length length */
131        u8_t verlenlen;
132        /* encoding sequence length length */
133        u8_t seqlenlen;
134
135        /* encoding error-index length */
136        u16_t erridxlen;
137        /* encoding error-status length */
138        u16_t errstatlen;
139        /* encoding request id length */
140        u16_t ridlen;
141        /* encoding pdu length */
142        u16_t pdulen;
143        /* encoding community length */
144        u16_t comlen;
145        /* encoding version length */
146        u16_t verlen;
147        /* encoding sequence length */
148        u16_t seqlen;
149    };
150
151/** output response message header length fields */
152    struct snmp_trap_header_lengths {
153        /* encoding timestamp length length */
154        u8_t tslenlen;
155        /* encoding specific-trap length length */
156        u8_t strplenlen;
157        /* encoding generic-trap length length */
158        u8_t gtrplenlen;
159        /* encoding agent-addr length length */
160        u8_t aaddrlenlen;
161        /* encoding enterprise-id length length */
162        u8_t eidlenlen;
163        /* encoding pdu length length */
164        u8_t pdulenlen;
165        /* encoding community length length */
166        u8_t comlenlen;
167        /* encoding version length length */
168        u8_t verlenlen;
169        /* encoding sequence length length */
170        u8_t seqlenlen;
171
172        /* encoding timestamp length */
173        u16_t tslen;
174        /* encoding specific-trap length */
175        u16_t strplen;
176        /* encoding generic-trap length */
177        u16_t gtrplen;
178        /* encoding agent-addr length */
179        u16_t aaddrlen;
180        /* encoding enterprise-id length */
181        u16_t eidlen;
182        /* encoding pdu length */
183        u16_t pdulen;
184        /* encoding community length */
185        u16_t comlen;
186        /* encoding version length */
187        u16_t verlen;
188        /* encoding sequence length */
189        u16_t seqlen;
190    };
191
192/* Accepting new SNMP messages. */
193#define SNMP_MSG_EMPTY                 0
194/* Search for matching object for variable binding. */
195#define SNMP_MSG_SEARCH_OBJ            1
196/* Perform SNMP operation on in-memory object.
197   Pass-through states, for symmetry only. */
198#define SNMP_MSG_INTERNAL_GET_OBJDEF   2
199#define SNMP_MSG_INTERNAL_GET_VALUE    3
200#define SNMP_MSG_INTERNAL_SET_TEST     4
201#define SNMP_MSG_INTERNAL_GET_OBJDEF_S 5
202#define SNMP_MSG_INTERNAL_SET_VALUE    6
203/* Perform SNMP operation on object located externally.
204   In theory this could be used for building a proxy agent.
205   Practical use is for an enterprise spc. app. gateway. */
206#define SNMP_MSG_EXTERNAL_GET_OBJDEF   7
207#define SNMP_MSG_EXTERNAL_GET_VALUE    8
208#define SNMP_MSG_EXTERNAL_SET_TEST     9
209#define SNMP_MSG_EXTERNAL_GET_OBJDEF_S 10
210#define SNMP_MSG_EXTERNAL_SET_VALUE    11
211
212#define SNMP_COMMUNITY_STR_LEN 64
213    struct snmp_msg_pstat {
214        /* lwIP local port (161) binding */
215        struct udp_pcb *pcb;
216        /* source IP address */
217        struct ip_addr sip;
218        /* source UDP port */
219        u16_t sp;
220        /* request type */
221        u8_t rt;
222        /* request ID */
223        s32_t rid;
224        /* error status */
225        s32_t error_status;
226        /* error index */
227        s32_t error_index;
228        /* community name (zero terminated) */
229        u8_t community[SNMP_COMMUNITY_STR_LEN + 1];
230        /* community string length (exclusive zero term) */
231        u8_t com_strlen;
232        /* one out of MSG_EMPTY, MSG_DEMUX, MSG_INTERNAL, MSG_EXTERNAL_x */
233        u8_t state;
234        /* saved arguments for MSG_EXTERNAL_x */
235        struct mib_external_node *ext_mib_node;
236        struct snmp_name_ptr ext_name_ptr;
237        struct obj_def ext_object_def;
238        struct snmp_obj_id ext_oid;
239        /* index into input variable binding list */
240        u8_t vb_idx;
241        /* ptr into input variable binding list */
242        struct snmp_varbind *vb_ptr;
243        /* list of variable bindings from input */
244        struct snmp_varbind_root invb;
245        /* list of variable bindings to output */
246        struct snmp_varbind_root outvb;
247        /* output response lengths used in ASN encoding */
248        struct snmp_resp_header_lengths rhl;
249    };
250
251    struct snmp_msg_trap {
252        /* lwIP local port (161) binding */
253        struct udp_pcb *pcb;
254        /* destination IP address in network order */
255        struct ip_addr dip;
256
257        /* source enterprise ID (sysObjectID) */
258        struct snmp_obj_id *enterprise;
259        /* source IP address, raw network order format */
260        u8_t sip_raw[4];
261        /* generic trap code */
262        u32_t gen_trap;
263        /* specific trap code */
264        u32_t spc_trap;
265        /* timestamp */
266        u32_t ts;
267        /* list of variable bindings to output */
268        struct snmp_varbind_root outvb;
269        /* output trap lengths used in ASN encoding */
270        struct snmp_trap_header_lengths thl;
271    };
272
273/** Agent Version constant, 0 = v1 oddity */
274    extern const s32_t snmp_version;
275/** Agent default "public" community string */
276    extern const char snmp_publiccommunity[7];
277
278    extern struct snmp_msg_trap trap_msg;
279
280/** Agent setup, start listening to port 161. */
281    void snmp_init(void);
282    void snmp_trap_dst_enable(u8_t dst_idx, u8_t enable);
283    void snmp_trap_dst_ip_set(u8_t dst_idx, struct ip_addr *dst);
284
285/** Varbind-list functions. */
286    struct snmp_varbind *snmp_varbind_alloc(struct snmp_obj_id *oid, u8_t type,
287                                            u8_t len);
288    void snmp_varbind_free(struct snmp_varbind *vb);
289    void snmp_varbind_list_free(struct snmp_varbind_root *root);
290    void snmp_varbind_tail_add(struct snmp_varbind_root *root,
291                               struct snmp_varbind *vb);
292    struct snmp_varbind *snmp_varbind_tail_remove(struct snmp_varbind_root
293                                                  *root);
294
295/** Handle an internal (recv) or external (private response) event. */
296    void snmp_msg_event(u8_t request_id);
297    err_t snmp_send_response(struct snmp_msg_pstat *m_stat);
298    err_t snmp_send_trap(s8_t generic_trap, struct snmp_obj_id *eoid,
299                         s32_t specific_trap);
300    void snmp_coldstart_trap(void);
301    void snmp_authfail_trap(void);
302
303#ifdef __cplusplus
304}
305#endif
306#endif                          /* LWIP_SNMP */
307#endif                          /* __LWIP_SNMP_MSG_H__ */
308