1 #include <sys/socket.h>
2 #include <sys/types.h>
3 #include <sys/un.h>
4
5 #include <endian.h>
6 #include <err.h>
7 #include <poll.h>
8 #include <stdarg.h>
9 #include <stdint.h>
10 #include <stdio.h>
11 #include <stdlib.h>
12 #include <string.h>
13 #include <unistd.h>
14
15 #include "regress.h"
16
17 #define AGENTX_SOCKET "/tmp/agentx"
18
19 #define SUBAGENT_DESCR(name) name, strlen(name)
20
21 #define AGENTX_OPEN_PDU 1
22 #define AGENTX_CLOSE_PDU 2
23 #define AGENTX_REGISTER_PDU 3
24 #define AGENTX_UNREGISTER_PDU 4
25 #define AGENTX_GET_PDU 5
26 #define AGENTX_GETNEXT_PDU 6
27 #define AGENTX_GETBULK_PDU 7
28 #define AGENTX_TESTSET_PDU 8
29 #define AGENTX_COMMITSET_PDU 9
30 #define AGENTX_UNDOSET_PDU 10
31 #define AGENTX_CLEANUPSET_PDU 11
32 #define AGENTX_NOTIFY_PDU 12
33 #define AGENTX_PING_PDU 13
34 #define AGENTX_INDEXALLOCATE_PDU 14
35 #define AGENTX_INDEXDEALLOCATE_PDU 15
36 #define AGENTX_ADDAGENTCAPS_PDU 16
37 #define AGENTX_REMOVEAGENTCAPS_PDU 17
38 #define AGENTX_RESPONSE_PDU 18
39
40 #define NOAGENTXERROR 0
41 #define OPENFAILED 256
42 #define NOTOPEN 257
43 #define INDEXWRONGTYPE 258
44 #define INDEXALREADYALLOCATED 259
45 #define INDEXNONEAVAILABLE 260
46 #define INDEXNOTALLOCATED 261
47 #define UNSUPPORTEDCONTEXT 262
48 #define DUPLICATEREGISTRATION 263
49 #define UNKNOWNREGISTRATION 264
50 #define UNKNOWNAGENTCAPS 265
51 #define PARSEERROR 266
52 #define REQUESTDENIED 267
53 #define PROCESSINGERROR 268
54
55 #define INSTANCE_REGISTRATION (1 << 0)
56 #define NEW_INDEX (1 << 1)
57 #define ANY_INDEX (1 << 2)
58 #define NON_DEFAULT_CONTEXT (1 << 3)
59 #define NETWORK_BYTE_ORDER (1 << 4)
60
61 #define INTEGER 2
62 #define OCTETSTRING 4
63 #define AXNULL 5
64 #define OBJECTIDENTIFIER 6
65 #define IPADDRESS 64
66 #define COUNTER32 65
67 #define GAUGE32 66
68 #define TIMETICKS 67
69 #define OPAQUE 68
70 #define COUNTER64 70
71 #define NOSUCHOBJECT 128
72 #define NOSUCHINSTANCE 129
73 #define ENDOFMIBVIEW 130
74
75 #define MESSAGE_NBO(msg) (((const char *)msg->buf)[2] & NETWORK_BYTE_ORDER)
76
77 #define p16toh(header, value) (uint16_t)(header->flags & NETWORK_BYTE_ORDER ? \
78 be16toh(value) : le16toh(value))
79 #define p32toh(header, value) (uint32_t)(header->flags & NETWORK_BYTE_ORDER ? \
80 be32toh(value) : le32toh(value))
81 #define p64toh(header, value) (uint64_t)(header->flags & NETWORK_BYTE_ORDER ? \
82 be64toh(value) : le64toh(value))
83
84 struct header {
85 uint8_t version;
86 uint8_t type;
87 uint8_t flags;
88 uint8_t reserved;
89 uint32_t sessionid;
90 uint32_t transactionid;
91 uint32_t packetid;
92 uint32_t payload_length;
93 } __attribute__ ((packed));
94
95 struct message {
96 void *buf;
97 size_t len;
98 size_t size;
99 };
100
101 void agentx_close_validate(const char *, const void *,
102 size_t, uint8_t, uint8_t);
103 static void agentx_response_validate(const char *, const void *, size_t,
104 uint8_t, uint32_t, enum error, uint16_t, struct varbind *, size_t);
105 static void message_add_uint8(struct message *, uint8_t);
106 static void message_add_uint16(struct message *, uint16_t);
107 static void message_add_uint32(struct message *, uint32_t);
108 static void message_add_uint64(struct message *, uint64_t);
109 static void message_add_nstring(struct message *, const void *, uint32_t);
110 static void message_add_oid(struct message *, const uint32_t[], uint8_t,
111 uint8_t);
112 static void message_add_varbind(struct message *, struct varbind *);
113 static void message_add_header(struct message *, uint8_t, uint8_t, uint8_t,
114 uint32_t, uint32_t, uint32_t);
115 static void message_add(struct message *, const void *, size_t);
116 static void message_release(struct message *);
117 static size_t poid(const char *, const struct header *, const uint8_t *, size_t,
118 struct oid *);
119
120 void agentx_write(int, struct message *);
121
122 void
agentx_open_nnbo(void)123 agentx_open_nnbo(void)
124 {
125 int s;
126 struct message msg = {};
127 char zero[3] = {};
128 char repl[1024];
129 size_t n;
130 uint32_t packetid = arc4random();
131
132 s = agentx_connect(axsocket);
133 message_add_header(&msg, 1, AGENTX_OPEN_PDU, 0, 0, 0, packetid);
134 message_add_uint8(&msg, 0);
135 message_add(&msg, zero, 3);
136 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 1), 0);
137 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
138
139 agentx_write(s, &msg);
140
141 n = agentx_read(s, repl, sizeof(repl), 1000);
142
143 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
144 0, NULL, 0);
145 message_release(&msg);
146 close(s);
147 }
148
149 void
agentx_open_nbo(void)150 agentx_open_nbo(void)
151 {
152 int s;
153 struct message msg = {};
154 char zero[3] = {};
155 char repl[1024];
156 size_t n;
157 uint32_t packetid = arc4random();
158
159 s = agentx_connect(axsocket);
160 message_add_header(&msg, 1, AGENTX_OPEN_PDU, NETWORK_BYTE_ORDER, 0, 0,
161 packetid);
162 message_add_uint8(&msg, 0);
163 message_add(&msg, zero, 3);
164 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 2), 0);
165 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
166
167 agentx_write(s, &msg);
168
169 n = agentx_read(s, repl, sizeof(repl), 1000);
170
171 agentx_response_validate(__func__, repl, n, NETWORK_BYTE_ORDER,
172 packetid, NOAGENTXERROR, 0, NULL, 0);
173 message_release(&msg);
174 close(s);
175 }
176
177 /*
178 * The version byte is the only identifier we have to determine if we can
179 * "trust" the rest of the packet structure. If this doesn't match the server
180 * can't return a parseError message, because it doesn't know the packetid.
181 */
182 void
agentx_open_invalidversion(void)183 agentx_open_invalidversion(void)
184 {
185 int s;
186 struct message msg = {};
187 char zero[3] = {};
188 char repl[1024];
189 size_t n;
190 uint32_t packetid = arc4random();
191
192 s = agentx_connect(axsocket);
193 message_add_header(&msg, 0xFF, AGENTX_OPEN_PDU, 0, 0, 0, packetid);
194 message_add_uint8(&msg, 0);
195 message_add(&msg, zero, 3);
196 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 3), 0);
197 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
198
199 agentx_write(s, &msg);
200
201 if (agentx_read(s, repl, sizeof(repl), 1000) != 0)
202 errx(1, "%s: Unexpected reply", __func__);
203 close(s);
204 }
205
206 void
agentx_open_ignore_sessionid(void)207 agentx_open_ignore_sessionid(void)
208 {
209 int s1, s2;
210 struct message msg = {};
211 char zero[3] = {};
212 char repl[1024];
213 size_t n;
214 uint32_t packetid = arc4random();
215 uint32_t sessionid;
216 struct header *header = (struct header *)repl;
217
218 s1 = agentx_connect(axsocket);
219 message_add_header(&msg, 1, AGENTX_OPEN_PDU, 0, 0, 0, packetid);
220 message_add_uint8(&msg, 0);
221 message_add(&msg, zero, 3);
222 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 4, 1), 0);
223 message_add_nstring(&msg,
224 SUBAGENT_DESCR("agentx_open_ignore_sessionid.1"));
225
226 agentx_write(s1, &msg);
227
228 n = agentx_read(s1, repl, sizeof(repl), 1000);
229 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
230 0, NULL, 0);
231
232 sessionid = le32toh(header->sessionid);
233
234 s2 = agentx_connect(axsocket);
235 message_add_header(&msg, 1, AGENTX_OPEN_PDU, 0, sessionid, 0, packetid);
236 message_add_uint8(&msg, 0);
237 message_add(&msg, zero, 3);
238 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 4, 2), 0);
239 message_add_nstring(&msg,
240 SUBAGENT_DESCR("agentx_open_ignore_sessionid.2"));
241
242 agentx_write(s2, &msg);
243
244 n = agentx_read(s2, repl, sizeof(repl), 1000);
245
246 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
247 0, NULL, 0);
248 if (sessionid == le32toh(header->sessionid))
249 errx(1, "%s: sessionid not ignored", __func__);
250
251 message_release(&msg);
252 close(s1);
253 close(s2);
254 }
255
256 void
agentx_open_invalid_oid(void)257 agentx_open_invalid_oid(void)
258 {
259 int s;
260 struct message msg = {};
261 char zero[3] = {};
262 char repl[1024];
263 size_t n;
264 uint32_t packetid = arc4random();
265 uint32_t oid[129];
266
267 s = agentx_connect(axsocket);
268 message_add_header(&msg, 1, AGENTX_OPEN_PDU, 0, 0, 0, packetid);
269 message_add_uint8(&msg, 0);
270 message_add(&msg, zero, 3);
271 message_add_oid(&msg, oid, 129, 0);
272 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
273
274 agentx_write(s, &msg);
275
276 if ((n = agentx_read(s, repl, sizeof(repl), 1000)) != 0)
277 errx(1, "unexpected reply");
278
279 message_release(&msg);
280 close(s);
281 }
282
283 void
agentx_open_descr_too_long(void)284 agentx_open_descr_too_long(void)
285 {
286 int s;
287 struct message msg = {};
288 char zero[3] = {};
289 char repl[1024];
290 size_t n;
291 uint32_t packetid = arc4random();
292 char descr[256];
293
294 s = agentx_connect(axsocket);
295 message_add_header(&msg, 1, AGENTX_OPEN_PDU, 0, 0, 0, packetid);
296 message_add_uint8(&msg, 0);
297 message_add(&msg, zero, 3);
298 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 6), 0);
299 memset(descr, 'a', sizeof(descr));
300 message_add_nstring(&msg, descr, sizeof(descr));
301
302 agentx_write(s, &msg);
303
304 n = agentx_read(s, repl, sizeof(repl), 1000);
305
306 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR, 0,
307 NULL, 0);
308 message_release(&msg);
309 close(s);
310 }
311
312 void
agentx_open_descr_invalid(void)313 agentx_open_descr_invalid(void)
314 {
315 int s;
316 struct message msg = {};
317 char zero[3] = {};
318 char repl[1024];
319 size_t n;
320 uint32_t packetid = arc4random();
321
322 s = agentx_connect(axsocket);
323 message_add_header(&msg, 1, AGENTX_OPEN_PDU, 0, 0, 0, packetid);
324 message_add_uint8(&msg, 0);
325 message_add(&msg, zero, 3);
326 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 7), 0);
327 /* Too long start-byte (5 ones instead of max 4) followed by ascii */
328 message_add_nstring(&msg, SUBAGENT_DESCR("a\373a"));
329
330 agentx_write(s, &msg);
331
332 n = agentx_read(s, repl, sizeof(repl), 1000);
333
334 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR, 0,
335 NULL, 0);
336 message_release(&msg);
337 close(s);
338 }
339
340 void
agentx_open_context(void)341 agentx_open_context(void)
342 {
343 int s;
344 struct message msg = {};
345 char zero[3] = {};
346 char repl[1024];
347 size_t n;
348 uint32_t packetid = arc4random();
349
350 s = agentx_connect(axsocket);
351 message_add_header(&msg, 1, AGENTX_OPEN_PDU, NON_DEFAULT_CONTEXT, 0, 0,
352 packetid);
353 message_add_nstring(&msg, "ctx", 3);
354 message_add_uint8(&msg, 0);
355 message_add(&msg, zero, 3);
356 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 8), 0);
357 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
358
359 agentx_write(s, &msg);
360
361 n = agentx_read(s, repl, sizeof(repl), 1000);
362
363 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR, 0,
364 NULL, 0);
365 message_release(&msg);
366 close(s);
367 }
368
369 void
agentx_open_instance_registration(void)370 agentx_open_instance_registration(void)
371 {
372 int s;
373 struct message msg = {};
374 char zero[3] = {};
375 char repl[1024];
376 size_t n;
377 uint32_t packetid = arc4random();
378
379 s = agentx_connect(axsocket);
380 message_add_header(&msg, 1, AGENTX_OPEN_PDU, INSTANCE_REGISTRATION, 0,
381 0, packetid);
382 message_add_uint8(&msg, 0);
383 message_add(&msg, zero, 3);
384 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 9), 0);
385 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
386
387 agentx_write(s, &msg);
388
389 n = agentx_read(s, repl, sizeof(repl), 1000);
390
391 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR, 0,
392 NULL, 0);
393 message_release(&msg);
394 close(s);
395 }
396
397 void
agentx_open_new_index(void)398 agentx_open_new_index(void)
399 {
400 int s;
401 struct message msg = {};
402 char zero[3] = {};
403 char repl[1024];
404 size_t n;
405 uint32_t packetid = arc4random();
406
407 s = agentx_connect(axsocket);
408 message_add_header(&msg, 1, AGENTX_OPEN_PDU, NEW_INDEX, 0,
409 0, packetid);
410 message_add_uint8(&msg, 0);
411 message_add(&msg, zero, 3);
412 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 10), 0);
413 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
414
415 agentx_write(s, &msg);
416
417 n = agentx_read(s, repl, sizeof(repl), 1000);
418
419 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR, 0,
420 NULL, 0);
421 message_release(&msg);
422 close(s);
423 }
424
425 void
agentx_open_any_index(void)426 agentx_open_any_index(void)
427 {
428 int s;
429 struct message msg = {};
430 char zero[3] = {};
431 char repl[1024];
432 size_t n;
433 uint32_t packetid = arc4random();
434
435 s = agentx_connect(axsocket);
436 message_add_header(&msg, 1, AGENTX_OPEN_PDU, ANY_INDEX, 0,
437 0, packetid);
438 message_add_uint8(&msg, 0);
439 message_add(&msg, zero, 3);
440 message_add_oid(&msg, OID_ARG(MIB_SUBAGENT_OPEN, 11), 0);
441 message_add_nstring(&msg, SUBAGENT_DESCR(__func__));
442
443 agentx_write(s, &msg);
444
445 n = agentx_read(s, repl, sizeof(repl), 1000);
446
447 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR, 0,
448 NULL, 0);
449 message_release(&msg);
450 close(s);
451 }
452
453 void
agentx_ping_notopen(void)454 agentx_ping_notopen(void)
455 {
456 int s;
457 struct message msg = {};
458 char repl[1024];
459 size_t n;
460 uint32_t packetid = arc4random();
461
462 s = agentx_connect(axsocket);
463 message_add_header(&msg, 1, AGENTX_PING_PDU, 0, 0, 0, packetid);
464
465 agentx_write(s, &msg);
466
467 n = agentx_read(s, repl, sizeof(repl), 1000);
468
469 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
470 NULL, 0);
471 message_release(&msg);
472 close(s);
473 }
474
475 void
agentx_ping_invalid_sessionid(void)476 agentx_ping_invalid_sessionid(void)
477 {
478 int s;
479 struct message msg = {};
480 char repl[1024];
481 size_t n;
482 uint32_t packetid = arc4random();
483 uint32_t sessionid;
484
485 s = agentx_connect(axsocket);
486 sessionid = agentx_open(s, 0, 0,
487 OID_ARG(MIB_SUBAGENT_PING, 2), __func__);
488 message_add_header(&msg, 1, AGENTX_PING_PDU, 0,
489 sessionid + 1, 0, packetid);
490
491 agentx_write(s, &msg);
492
493 n = agentx_read(s, repl, sizeof(repl), 1000);
494
495 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
496 NULL, 0);
497 message_release(&msg);
498 close(s);
499 }
500
501 void
agentx_ping_default(void)502 agentx_ping_default(void)
503 {
504 int s;
505 struct message msg = {};
506 char repl[1024];
507 size_t n;
508 uint32_t packetid = arc4random();
509 uint32_t sessionid;
510
511 s = agentx_connect(axsocket);
512 sessionid = agentx_open(s, 0, 0,
513 OID_ARG(MIB_SUBAGENT_PING, 3), __func__);
514 message_add_header(&msg, 1, AGENTX_PING_PDU, 0,
515 sessionid, 0, packetid);
516
517 agentx_write(s, &msg);
518
519 n = agentx_read(s, repl, sizeof(repl), 1000);
520
521 agentx_response_validate(__func__, repl, n, 0,
522 packetid, NOAGENTXERROR, 0, NULL, 0);
523 message_release(&msg);
524 close(s);
525 }
526
527 void
agentx_ping_context(void)528 agentx_ping_context(void)
529 {
530 int s;
531 struct message msg = {};
532 char repl[1024];
533 size_t n;
534 uint32_t packetid = arc4random();
535 uint32_t sessionid;
536
537 s = agentx_connect(axsocket);
538 sessionid = agentx_open(s, 0, 0,
539 OID_ARG(MIB_SUBAGENT_PING, 4), __func__);
540 message_add_header(&msg, 1, AGENTX_PING_PDU, NON_DEFAULT_CONTEXT,
541 sessionid, 0, packetid);
542 message_add_nstring(&msg, "ctx", 3);
543
544 agentx_write(s, &msg);
545
546 n = agentx_read(s, repl, sizeof(repl), 1000);
547
548 agentx_response_validate(__func__, repl, n, 0,
549 packetid, UNSUPPORTEDCONTEXT, 0, NULL, 0);
550 message_release(&msg);
551 close(s);
552 }
553
554 void
agentx_ping_invalid_version(void)555 agentx_ping_invalid_version(void)
556 {
557 int s;
558 struct message msg = {};
559 char repl[1024];
560 size_t n;
561 uint32_t packetid = arc4random();
562 uint32_t sessionid;
563
564 s = agentx_connect(axsocket);
565 sessionid = agentx_open(s, 0, 0,
566 OID_ARG(MIB_SUBAGENT_PING, 5), __func__);
567 message_add_header(&msg, 0xFF, AGENTX_PING_PDU, INSTANCE_REGISTRATION,
568 sessionid, 0, packetid);
569
570 agentx_write(s, &msg);
571
572 n = agentx_read(s, repl, sizeof(repl), 1000);
573
574 agentx_close_validate(__func__, repl, n, 0, REASONPROTOCOLERROR);
575 message_release(&msg);
576 close(s);
577 }
578
579 void
agentx_ping_instance_registration(void)580 agentx_ping_instance_registration(void)
581 {
582 int s;
583 struct message msg = {};
584 char repl[1024];
585 size_t n;
586 uint32_t packetid = arc4random();
587 uint32_t sessionid;
588
589 s = agentx_connect(axsocket);
590 sessionid = agentx_open(s, 0, 0,
591 OID_ARG(MIB_SUBAGENT_PING, 6), __func__);
592 message_add_header(&msg, 1, AGENTX_PING_PDU, INSTANCE_REGISTRATION,
593 sessionid, 0, packetid);
594
595 agentx_write(s, &msg);
596
597 n = agentx_read(s, repl, sizeof(repl), 1000);
598
599 agentx_response_validate(__func__, repl, n, 0,
600 packetid, PARSEERROR, 0, NULL, 0);
601 message_release(&msg);
602 close(s);
603 }
604
605 void
agentx_ping_new_index(void)606 agentx_ping_new_index(void)
607 {
608 int s;
609 struct message msg = {};
610 char repl[1024];
611 size_t n;
612 uint32_t packetid = arc4random();
613 uint32_t sessionid;
614
615 s = agentx_connect(axsocket);
616 sessionid = agentx_open(s, 0, 0,
617 OID_ARG(MIB_SUBAGENT_PING, 7), __func__);
618 message_add_header(&msg, 1, AGENTX_PING_PDU, NEW_INDEX,
619 sessionid, 0, packetid);
620
621 agentx_write(s, &msg);
622
623 n = agentx_read(s, repl, sizeof(repl), 1000);
624
625 agentx_response_validate(__func__, repl, n, 0,
626 packetid, PARSEERROR, 0, NULL, 0);
627 message_release(&msg);
628 close(s);
629 }
630
631 void
agentx_ping_any_index(void)632 agentx_ping_any_index(void)
633 {
634 int s;
635 struct message msg = {};
636 char repl[1024];
637 size_t n;
638 uint32_t packetid = arc4random();
639 uint32_t sessionid;
640
641 s = agentx_connect(axsocket);
642 sessionid = agentx_open(s, 0, 0,
643 OID_ARG(MIB_SUBAGENT_PING, 8), __func__);
644 message_add_header(&msg, 1, AGENTX_PING_PDU, ANY_INDEX,
645 sessionid, 0, packetid);
646
647 agentx_write(s, &msg);
648
649 n = agentx_read(s, repl, sizeof(repl), 1000);
650
651 agentx_response_validate(__func__, repl, n, 0,
652 packetid, PARSEERROR, 0, NULL, 0);
653 message_release(&msg);
654 close(s);
655 }
656
657 void
agentx_ping_nbo_nnbo(void)658 agentx_ping_nbo_nnbo(void)
659 {
660 int s;
661 struct message msg = {};
662 char repl[1024];
663 size_t n;
664 uint32_t packetid = arc4random();
665 uint32_t sessionid;
666
667 s = agentx_connect(axsocket);
668 sessionid = agentx_open(s, 0, 0,
669 OID_ARG(MIB_SUBAGENT_PING, 9), __func__);
670 message_add_header(&msg, 1, AGENTX_PING_PDU, 0,
671 sessionid, 0, packetid);
672
673 agentx_write(s, &msg);
674
675 n = agentx_read(s, repl, sizeof(repl), 1000);
676
677 agentx_response_validate(__func__, repl, n, 0,
678 packetid, NOAGENTXERROR, 0, NULL, 0);
679 message_release(&msg);
680 close(s);
681 }
682
683 void
agentx_ping_nnbo_nbo(void)684 agentx_ping_nnbo_nbo(void)
685 {
686 int s;
687 struct message msg = {};
688 char repl[1024];
689 size_t n;
690 uint32_t packetid = arc4random();
691 uint32_t sessionid;
692
693 s = agentx_connect(axsocket);
694 sessionid = agentx_open(s, 0, 0,
695 OID_ARG(MIB_SUBAGENT_PING, 9), __func__);
696 message_add_header(&msg, 1, AGENTX_PING_PDU, NETWORK_BYTE_ORDER,
697 sessionid, 0, packetid);
698
699 agentx_write(s, &msg);
700
701 n = agentx_read(s, repl, sizeof(repl), 1000);
702
703 agentx_response_validate(__func__, repl, n, NETWORK_BYTE_ORDER,
704 packetid, NOAGENTXERROR, 0, NULL, 0);
705 message_release(&msg);
706 close(s);
707 }
708
709 /*
710 * Test that everything continues running in double exception condition
711 */
712 void
agentx_ping_invalid_version_close(void)713 agentx_ping_invalid_version_close(void)
714 {
715 struct sockaddr_storage ss;
716 struct message msg = {};
717 struct sockaddr *sa = (struct sockaddr *)&ss;
718 socklen_t salen;
719 int snmp_s, ax_s;
720 uint32_t sessionid, packetid;
721 struct varbind varbind = {
722 .type = TYPE_NULL,
723 .name = OID_STRUCT(MIB_SUBAGENT_PING, 10, 0),
724 };
725 int32_t requestid;
726 char buf[1024];
727 size_t n;
728
729 ax_s = agentx_connect(axsocket);
730 sessionid = agentx_open(ax_s, 0, 0,
731 OID_ARG(MIB_SUBAGENT_PING, 10), __func__);
732 message_add_header(&msg, 0xFF, AGENTX_PING_PDU, INSTANCE_REGISTRATION,
733 sessionid, 0, packetid);
734
735 agentx_write(ax_s, &msg);
736 close(ax_s);
737
738 salen = snmp_resolve(SOCK_DGRAM, hostname, servname, sa);
739 snmp_s = snmp_connect(SOCK_DGRAM, sa, salen);
740 requestid = snmpv2_get(snmp_s, community, 0, &varbind, 1);
741
742 varbind.type = TYPE_NOSUCHOBJECT;
743
744 snmpv2_response_validate(snmp_s, 1000, community, requestid, 0, 0,
745 &varbind, 1);
746 }
747
748 void
agentx_close_notopen(void)749 agentx_close_notopen(void)
750 {
751 int s;
752 struct message msg = {};
753 char repl[1024];
754 size_t n;
755 uint32_t packetid = arc4random();
756 const uint8_t reason = REASONOTHER, zero[3] = {0};
757
758 s = agentx_connect(axsocket);
759 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, 0, 0, packetid);
760 message_add(&msg, &reason, sizeof(reason));
761 message_add(&msg, zero, sizeof(zero));
762
763 agentx_write(s, &msg);
764
765 n = agentx_read(s, repl, sizeof(repl), 1000);
766
767 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
768 NULL, 0);
769 message_release(&msg);
770 close(s);
771 }
772
773 void
agentx_close_reasonother(void)774 agentx_close_reasonother(void)
775 {
776 int s;
777 struct message msg = {};
778 char repl[1024];
779 size_t n;
780 uint32_t packetid = arc4random();
781 uint32_t sessionid;
782 const uint8_t reason = REASONOTHER, zero[3] = {0};
783
784 s = agentx_connect(axsocket);
785
786 sessionid = agentx_open(s, 0, 0,
787 OID_ARG(MIB_SUBAGENT_CLOSE, 2), __func__);
788 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
789 packetid);
790 message_add(&msg, &reason, sizeof(reason));
791 message_add(&msg, zero, sizeof(zero));
792
793 agentx_write(s, &msg);
794
795 n = agentx_read(s, repl, sizeof(repl), 1000);
796
797 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
798 0, NULL, 0);
799 message_release(&msg);
800 close(s);
801 }
802
803 void
agentx_close_reasonparseerror(void)804 agentx_close_reasonparseerror(void)
805 {
806 int s;
807 struct message msg = {};
808 char repl[1024];
809 size_t n;
810 uint32_t packetid = arc4random();
811 uint32_t sessionid;
812 const uint8_t reason = REASONPARSEERROR, zero[3] = {0};
813
814 s = agentx_connect(axsocket);
815
816 sessionid = agentx_open(s, 0, 0,
817 OID_ARG(MIB_SUBAGENT_CLOSE, 3), __func__);
818 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
819 packetid);
820 message_add(&msg, &reason, sizeof(reason));
821 message_add(&msg, zero, sizeof(zero));
822
823 agentx_write(s, &msg);
824
825 n = agentx_read(s, repl, sizeof(repl), 1000);
826
827 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
828 0, NULL, 0);
829 message_release(&msg);
830 close(s);
831 }
832
833 void
agentx_close_reasonprotocolerror(void)834 agentx_close_reasonprotocolerror(void)
835 {
836 int s;
837 struct message msg = {};
838 char repl[1024];
839 size_t n;
840 uint32_t packetid = arc4random();
841 uint32_t sessionid;
842 const uint8_t reason = REASONPROTOCOLERROR, zero[3] = {0};
843
844 s = agentx_connect(axsocket);
845
846 sessionid = agentx_open(s, 0, 0,
847 OID_ARG(MIB_SUBAGENT_CLOSE, 4), __func__);
848 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
849 packetid);
850 message_add(&msg, &reason, sizeof(reason));
851 message_add(&msg, zero, sizeof(zero));
852
853 agentx_write(s, &msg);
854
855 n = agentx_read(s, repl, sizeof(repl), 1000);
856
857 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
858 0, NULL, 0);
859 message_release(&msg);
860 close(s);
861 }
862
863 void
agentx_close_reasontimouts(void)864 agentx_close_reasontimouts(void)
865 {
866 int s;
867 struct message msg = {};
868 char repl[1024];
869 size_t n;
870 uint32_t packetid = arc4random();
871 uint32_t sessionid;
872 const uint8_t reason = REASONTIMEOUTS, zero[3] = {0};
873
874 s = agentx_connect(axsocket);
875
876 sessionid = agentx_open(s, 0, 0,
877 OID_ARG(MIB_SUBAGENT_CLOSE, 5), __func__);
878 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
879 packetid);
880 message_add(&msg, &reason, sizeof(reason));
881 message_add(&msg, zero, sizeof(zero));
882
883 agentx_write(s, &msg);
884
885 n = agentx_read(s, repl, sizeof(repl), 1000);
886
887 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
888 0, NULL, 0);
889 message_release(&msg);
890 close(s);
891 }
892
893 void
agentx_close_reasonshutdown(void)894 agentx_close_reasonshutdown(void)
895 {
896 int s;
897 struct message msg = {};
898 char repl[1024];
899 size_t n;
900 uint32_t packetid = arc4random();
901 uint32_t sessionid;
902 const uint8_t reason = REASONSHUTDOWN, zero[3] = {0};
903
904 s = agentx_connect(axsocket);
905
906 sessionid = agentx_open(s, 0, 0,
907 OID_ARG(MIB_SUBAGENT_CLOSE, 6), __func__);
908 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
909 packetid);
910 message_add(&msg, &reason, sizeof(reason));
911 message_add(&msg, zero, sizeof(zero));
912
913 agentx_write(s, &msg);
914
915 n = agentx_read(s, repl, sizeof(repl), 1000);
916
917 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
918 0, NULL, 0);
919 message_release(&msg);
920 close(s);
921 }
922
923 void
agentx_close_reasonbymanager(void)924 agentx_close_reasonbymanager(void)
925 {
926 int s;
927 struct message msg = {};
928 char repl[1024];
929 size_t n;
930 uint32_t packetid = arc4random();
931 uint32_t sessionid;
932 const uint8_t reason = REASONBYMANAGER, zero[3] = {0};
933
934 s = agentx_connect(axsocket);
935
936 sessionid = agentx_open(s, 0, 0,
937 OID_ARG(MIB_SUBAGENT_CLOSE, 7), __func__);
938 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
939 packetid);
940 message_add(&msg, &reason, sizeof(reason));
941 message_add(&msg, zero, sizeof(zero));
942
943 agentx_write(s, &msg);
944
945 n = agentx_read(s, repl, sizeof(repl), 1000);
946
947 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR,
948 0, NULL, 0);
949 message_release(&msg);
950 close(s);
951 }
952
953 void
agentx_close_reasoninvalid(void)954 agentx_close_reasoninvalid(void)
955 {
956 int s;
957 struct message msg = {};
958 char repl[1024];
959 size_t n;
960 uint32_t packetid = arc4random();
961 uint32_t sessionid;
962 const uint8_t reason = 0xFF, zero[3] = {0};
963
964 s = agentx_connect(axsocket);
965
966 sessionid = agentx_open(s, 0, 0,
967 OID_ARG(MIB_SUBAGENT_CLOSE, 8), __func__);
968 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
969 packetid);
970 message_add(&msg, &reason, sizeof(reason));
971 message_add(&msg, zero, sizeof(zero));
972
973 agentx_write(s, &msg);
974
975 n = agentx_read(s, repl, sizeof(repl), 1000);
976
977 agentx_close_validate(__func__, repl, n, 0, REASONPROTOCOLERROR);
978 message_release(&msg);
979 close(s);
980 }
981
982 void
agentx_close_single(void)983 agentx_close_single(void)
984 {
985 int s;
986 struct message msg = {};
987 char repl[1024];
988 size_t n;
989 uint32_t packetid = arc4random();
990 uint32_t sessionid1, sessionid2;
991 const uint8_t reason = REASONOTHER, zero[3] = {0};
992
993 s = agentx_connect(axsocket);
994
995 sessionid1 = agentx_open(s, 0, 0,
996 OID_ARG(MIB_SUBAGENT_CLOSE, 9, 1), "agentx_close_single.1");
997 sessionid2 = agentx_open(s, 0, 0,
998 OID_ARG(MIB_SUBAGENT_CLOSE, 9, 2), "agentx_close_single.2");
999 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid1, 0, packetid);
1000 message_add(&msg, &reason, sizeof(reason));
1001 message_add(&msg, zero, sizeof(zero));
1002
1003 agentx_write(s, &msg);
1004
1005 n = agentx_read(s, repl, sizeof(repl), 1000);
1006
1007 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR,
1008 0, NULL, 0);
1009
1010 /* Test that only the second session is still open */
1011 packetid = arc4random();
1012 message_add_header(&msg, 1, AGENTX_PING_PDU, 0, sessionid2, 0, packetid);
1013 agentx_write(s, &msg);
1014 n = agentx_read(s, repl, sizeof(repl), 1000);
1015 agentx_response_validate(__func__, repl, n, 0,
1016 packetid, NOAGENTXERROR, 0, NULL, 0);
1017
1018 packetid = arc4random();
1019 message_add_header(&msg, 1, AGENTX_PING_PDU, 0, sessionid1, 0, packetid);
1020 agentx_write(s, &msg);
1021 n = agentx_read(s, repl, sizeof(repl), 1000);
1022 agentx_response_validate(__func__, repl, n, 0,
1023 packetid, NOTOPEN, 0, NULL, 0);
1024
1025 message_release(&msg);
1026 close(s);
1027 }
1028
1029 void
agentx_close_notowned(void)1030 agentx_close_notowned(void)
1031 {
1032 int s1, s2;
1033 struct message msg = {};
1034 char repl[1024];
1035 size_t n;
1036 uint32_t packetid = arc4random();
1037 uint32_t sessionid1, sessionid2;
1038 const uint8_t reason = REASONOTHER, zero[3] = {0};
1039
1040 s1 = agentx_connect(axsocket);
1041 s2 = agentx_connect(axsocket);
1042
1043 sessionid1 = agentx_open(s1, 0, 0,
1044 OID_ARG(MIB_SUBAGENT_CLOSE, 10, 1), "agentx_close_notowned.1");
1045 sessionid2 = agentx_open(s2, 0, 0,
1046 OID_ARG(MIB_SUBAGENT_CLOSE, 10, 2), "agentx_close_notowned.2");
1047 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid1, 0, packetid);
1048 message_add(&msg, &reason, sizeof(reason));
1049 message_add(&msg, zero, sizeof(zero));
1050
1051 agentx_write(s2, &msg);
1052
1053 n = agentx_read(s2, repl, sizeof(repl), 1000);
1054
1055 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN,
1056 0, NULL, 0);
1057
1058 /* Test that both sessions are still open */
1059 packetid = arc4random();
1060 message_add_header(&msg, 1, AGENTX_PING_PDU, 0, sessionid1, 0, packetid);
1061 agentx_write(s1, &msg);
1062 n = agentx_read(s1, repl, sizeof(repl), 1000);
1063 agentx_response_validate(__func__, repl, n, 0,
1064 packetid, NOAGENTXERROR, 0, NULL, 0);
1065
1066 packetid = arc4random();
1067 message_add_header(&msg, 1, AGENTX_PING_PDU, 0, sessionid2, 0, packetid);
1068 agentx_write(s2, &msg);
1069 n = agentx_read(s2, repl, sizeof(repl), 1000);
1070 agentx_response_validate(__func__, repl, n, 0,
1071 packetid, NOAGENTXERROR, 0, NULL, 0);
1072
1073 message_release(&msg);
1074 close(s1);
1075 close(s2);
1076 }
1077
1078 void
agentx_close_invalid_sessionid(void)1079 agentx_close_invalid_sessionid(void)
1080 {
1081 int s;
1082 struct message msg = {};
1083 char repl[1024];
1084 size_t n;
1085 uint32_t packetid = arc4random();
1086 uint32_t sessionid;
1087 const uint8_t reason = REASONOTHER, zero[3] = {0};
1088
1089 s = agentx_connect(axsocket);
1090 sessionid = agentx_open(s, 0, 0,
1091 OID_ARG(MIB_SUBAGENT_CLOSE, 11), __func__);
1092 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid + 1, 0, packetid);
1093 message_add(&msg, &reason, sizeof(reason));
1094 message_add(&msg, zero, sizeof(zero));
1095
1096 agentx_write(s, &msg);
1097
1098 n = agentx_read(s, repl, sizeof(repl), 1000);
1099
1100 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
1101 NULL, 0);
1102 message_release(&msg);
1103 close(s);
1104 }
1105
1106 void
agentx_close_context(void)1107 agentx_close_context(void)
1108 {
1109 int s;
1110 struct message msg = {};
1111 char repl[1024];
1112 size_t n;
1113 uint32_t packetid = arc4random();
1114 uint32_t sessionid;
1115 const uint8_t reason = REASONOTHER, zero[3] = {0};
1116
1117 s = agentx_connect(axsocket);
1118 sessionid = agentx_open(s, 0, 0,
1119 OID_ARG(MIB_SUBAGENT_CLOSE, 12), __func__);
1120 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, NON_DEFAULT_CONTEXT,
1121 sessionid, 0, packetid);
1122 message_add_nstring(&msg, "ctx", 3);
1123 message_add(&msg, &reason, sizeof(reason));
1124 message_add(&msg, zero, sizeof(zero));
1125
1126 agentx_write(s, &msg);
1127
1128 n = agentx_read(s, repl, sizeof(repl), 1000);
1129
1130 agentx_response_validate(__func__, repl, n, 0, packetid, PARSEERROR, 0,
1131 NULL, 0);
1132 message_release(&msg);
1133 close(s);
1134 }
1135
1136 void
agentx_close_invalid_version(void)1137 agentx_close_invalid_version(void)
1138 {
1139 int s;
1140 struct message msg = {};
1141 char repl[1024];
1142 size_t n;
1143 uint32_t packetid = arc4random();
1144 uint32_t sessionid;
1145 const uint8_t reason = REASONOTHER, zero[3] = {0};
1146
1147 s = agentx_connect(axsocket);
1148 sessionid = agentx_open(s, 0, 0,
1149 OID_ARG(MIB_SUBAGENT_CLOSE, 13), __func__);
1150 message_add_header(&msg, 0xFF, AGENTX_CLOSE_PDU, 0, sessionid, 0, packetid);
1151 message_add(&msg, &reason, sizeof(reason));
1152 message_add(&msg, zero, sizeof(zero));
1153
1154 agentx_write(s, &msg);
1155
1156 n = agentx_read(s, repl, sizeof(repl), 1000);
1157 agentx_close_validate(__func__, repl, n, 0, REASONPROTOCOLERROR);
1158
1159 message_release(&msg);
1160 close(s);
1161 }
1162
1163 void
agentx_close_instance_registration(void)1164 agentx_close_instance_registration(void)
1165 {
1166 int s;
1167 struct message msg = {};
1168 char repl[1024];
1169 size_t n;
1170 uint32_t packetid = arc4random();
1171 uint32_t sessionid;
1172 const uint8_t reason = REASONOTHER, zero[3] = {0};
1173
1174 s = agentx_connect(axsocket);
1175 sessionid = agentx_open(s, 0, 0,
1176 OID_ARG(MIB_SUBAGENT_CLOSE, 14), __func__);
1177 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, INSTANCE_REGISTRATION,
1178 sessionid, 0, packetid);
1179 message_add(&msg, &reason, sizeof(reason));
1180 message_add(&msg, zero, sizeof(zero));
1181
1182 agentx_write(s, &msg);
1183
1184 n = agentx_read(s, repl, sizeof(repl), 1000);
1185
1186 agentx_response_validate(__func__, repl, n, 0,
1187 packetid, PARSEERROR, 0, NULL, 0);
1188 message_release(&msg);
1189 close(s);
1190 }
1191
1192 void
agentx_close_new_index(void)1193 agentx_close_new_index(void)
1194 {
1195 int s;
1196 struct message msg = {};
1197 char repl[1024];
1198 size_t n;
1199 uint32_t packetid = arc4random();
1200 uint32_t sessionid;
1201 const uint8_t reason = REASONOTHER, zero[3] = {0};
1202
1203 s = agentx_connect(axsocket);
1204 sessionid = agentx_open(s, 0, 0,
1205 OID_ARG(MIB_SUBAGENT_CLOSE, 15), __func__);
1206 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, NEW_INDEX,
1207 sessionid, 0, packetid);
1208 message_add(&msg, &reason, sizeof(reason));
1209 message_add(&msg, zero, sizeof(zero));
1210
1211 agentx_write(s, &msg);
1212
1213 n = agentx_read(s, repl, sizeof(repl), 1000);
1214
1215 agentx_response_validate(__func__, repl, n, 0,
1216 packetid, PARSEERROR, 0, NULL, 0);
1217 message_release(&msg);
1218 close(s);
1219 }
1220
1221 void
agentx_close_any_index(void)1222 agentx_close_any_index(void)
1223 {
1224 int s;
1225 struct message msg = {};
1226 char repl[1024];
1227 size_t n;
1228 uint32_t packetid = arc4random();
1229 uint32_t sessionid;
1230 const uint8_t reason = REASONOTHER, zero[3] = {0};
1231
1232 s = agentx_connect(axsocket);
1233 sessionid = agentx_open(s, 0, 0,
1234 OID_ARG(MIB_SUBAGENT_CLOSE, 16), __func__);
1235 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, ANY_INDEX,
1236 sessionid, 0, packetid);
1237 message_add(&msg, &reason, sizeof(reason));
1238 message_add(&msg, zero, sizeof(zero));
1239
1240 agentx_write(s, &msg);
1241
1242 n = agentx_read(s, repl, sizeof(repl), 1000);
1243
1244 agentx_response_validate(__func__, repl, n, 0,
1245 packetid, PARSEERROR, 0, NULL, 0);
1246 message_release(&msg);
1247 close(s);
1248 }
1249
1250 void
agentx_close_nnbo_nbo(void)1251 agentx_close_nnbo_nbo(void)
1252 {
1253 int s;
1254 struct message msg = {};
1255 char repl[1024];
1256 size_t n;
1257 uint32_t packetid = arc4random();
1258 uint32_t sessionid;
1259 const uint8_t reason = REASONOTHER, zero[3] = {0};
1260
1261 s = agentx_connect(axsocket);
1262 sessionid = agentx_open(s, 0, 0,
1263 OID_ARG(MIB_SUBAGENT_CLOSE, 17), __func__);
1264 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, NETWORK_BYTE_ORDER,
1265 sessionid, 0, packetid);
1266 message_add(&msg, &reason, sizeof(reason));
1267 message_add(&msg, zero, sizeof(zero));
1268
1269 agentx_write(s, &msg);
1270
1271 n = agentx_read(s, repl, sizeof(repl), 1000);
1272
1273 agentx_response_validate(__func__, repl, n, NETWORK_BYTE_ORDER,
1274 packetid, NOAGENTXERROR, 0, NULL, 0);
1275 message_release(&msg);
1276 close(s);
1277 }
1278
1279 void
agentx_register_notopen(void)1280 agentx_register_notopen(void)
1281 {
1282 int s;
1283 struct message msg = {};
1284 char repl[1024];
1285 size_t n;
1286 uint32_t packetid = arc4random();
1287 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1288
1289 s = agentx_connect(axsocket);
1290 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, 0, 0, packetid);
1291 message_add(&msg, &timeout, sizeof(timeout));
1292 message_add(&msg, &priority, sizeof(priority));
1293 message_add(&msg, &range_subid, sizeof(range_subid));
1294 message_add(&msg, &reserved, sizeof(reserved));
1295 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 1, 0), 0);
1296
1297 agentx_write(s, &msg);
1298
1299 n = agentx_read(s, repl, sizeof(repl), 1000);
1300
1301 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
1302 NULL, 0);
1303 message_release(&msg);
1304 close(s);
1305 }
1306
1307 void
agentx_register_invalid_sessionid(void)1308 agentx_register_invalid_sessionid(void)
1309 {
1310 int s;
1311 struct message msg = {};
1312 char repl[1024];
1313 size_t n;
1314 uint32_t packetid = arc4random();
1315 uint32_t sessionid;
1316 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1317
1318 s = agentx_connect(axsocket);
1319 sessionid = agentx_open(s, 0, 0,
1320 OID_ARG(MIB_SUBAGENT_REGISTER, 2), __func__);
1321 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid + 1, 0,
1322 packetid);
1323 message_add(&msg, &timeout, sizeof(timeout));
1324 message_add(&msg, &priority, sizeof(priority));
1325 message_add(&msg, &range_subid, sizeof(range_subid));
1326 message_add(&msg, &reserved, sizeof(reserved));
1327 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 2, 0), 0);
1328
1329 agentx_write(s, &msg);
1330
1331 n = agentx_read(s, repl, sizeof(repl), 1000);
1332
1333 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
1334 NULL, 0);
1335 message_release(&msg);
1336 close(s);
1337 }
1338
1339 void
agentx_register_default(void)1340 agentx_register_default(void)
1341 {
1342 int s;
1343 struct message msg = {};
1344 char repl[1024];
1345 size_t n;
1346 uint32_t packetid = arc4random();
1347 uint32_t sessionid;
1348 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1349
1350 s = agentx_connect(axsocket);
1351 sessionid = agentx_open(s, 0, 0,
1352 OID_ARG(MIB_SUBAGENT_REGISTER, 3), __func__);
1353 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1354 packetid);
1355 message_add(&msg, &timeout, sizeof(timeout));
1356 message_add(&msg, &priority, sizeof(priority));
1357 message_add(&msg, &range_subid, sizeof(range_subid));
1358 message_add(&msg, &reserved, sizeof(reserved));
1359 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 3, 0), 0);
1360
1361 agentx_write(s, &msg);
1362
1363 n = agentx_read(s, repl, sizeof(repl), 1000);
1364
1365 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR, 0,
1366 NULL, 0);
1367 message_release(&msg);
1368 close(s);
1369 }
1370
1371 void
agentx_register_context(void)1372 agentx_register_context(void)
1373 {
1374 int s;
1375 struct message msg = {};
1376 char repl[1024];
1377 size_t n;
1378 uint32_t packetid = arc4random();
1379 uint32_t sessionid;
1380 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1381
1382 s = agentx_connect(axsocket);
1383 sessionid = agentx_open(s, 0, 0,
1384 OID_ARG(MIB_SUBAGENT_REGISTER, 4), __func__);
1385 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, NON_DEFAULT_CONTEXT,
1386 sessionid, 0, packetid);
1387 message_add_nstring(&msg, "ctx", 3);
1388 message_add(&msg, &timeout, sizeof(timeout));
1389 message_add(&msg, &priority, sizeof(priority));
1390 message_add(&msg, &range_subid, sizeof(range_subid));
1391 message_add(&msg, &reserved, sizeof(reserved));
1392 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 4, 0), 0);
1393
1394 agentx_write(s, &msg);
1395
1396 n = agentx_read(s, repl, sizeof(repl), 1000);
1397
1398 agentx_response_validate(__func__, repl, n, 0, packetid,
1399 UNSUPPORTEDCONTEXT, 0, NULL, 0);
1400 message_release(&msg);
1401 close(s);
1402 }
1403
1404 void
agentx_register_invalid_version(void)1405 agentx_register_invalid_version(void)
1406 {
1407 int s;
1408 struct message msg = {};
1409 char repl[1024];
1410 size_t n;
1411 uint32_t packetid = arc4random();
1412 uint32_t sessionid;
1413 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1414
1415 s = agentx_connect(axsocket);
1416 sessionid = agentx_open(s, 0, 0,
1417 OID_ARG(MIB_SUBAGENT_REGISTER, 5), __func__);
1418 message_add_header(&msg, 0xFF, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1419 packetid);
1420 message_add(&msg, &timeout, sizeof(timeout));
1421 message_add(&msg, &priority, sizeof(priority));
1422 message_add(&msg, &range_subid, sizeof(range_subid));
1423 message_add(&msg, &reserved, sizeof(reserved));
1424 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 5, 0), 0);
1425
1426 agentx_write(s, &msg);
1427
1428 n = agentx_read(s, repl, sizeof(repl), 1000);
1429
1430 agentx_close_validate(__func__, repl, n, 0, REASONPROTOCOLERROR);
1431 message_release(&msg);
1432 close(s);
1433 }
1434
1435 void
agentx_register_instance_registration(void)1436 agentx_register_instance_registration(void)
1437 {
1438 int s;
1439 struct message msg = {};
1440 char repl[1024];
1441 size_t n;
1442 uint32_t packetid = arc4random();
1443 uint32_t sessionid;
1444 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1445
1446 s = agentx_connect(axsocket);
1447 sessionid = agentx_open(s, 0, 0,
1448 OID_ARG(MIB_SUBAGENT_REGISTER, 6), __func__);
1449 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, INSTANCE_REGISTRATION,
1450 sessionid, 0, packetid);
1451 message_add(&msg, &timeout, sizeof(timeout));
1452 message_add(&msg, &priority, sizeof(priority));
1453 message_add(&msg, &range_subid, sizeof(range_subid));
1454 message_add(&msg, &reserved, sizeof(reserved));
1455 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 6, 0), 0);
1456
1457 agentx_write(s, &msg);
1458
1459 n = agentx_read(s, repl, sizeof(repl), 1000);
1460
1461 agentx_response_validate(__func__, repl, n, 0, packetid,
1462 NOAGENTXERROR, 0, NULL, 0);
1463 message_release(&msg);
1464 close(s);
1465 }
1466
1467 void
agentx_register_new_index(void)1468 agentx_register_new_index(void)
1469 {
1470 int s;
1471 struct message msg = {};
1472 char repl[1024];
1473 size_t n;
1474 uint32_t packetid = arc4random();
1475 uint32_t sessionid;
1476 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1477
1478 s = agentx_connect(axsocket);
1479 sessionid = agentx_open(s, 0, 0,
1480 OID_ARG(MIB_SUBAGENT_REGISTER, 7), __func__);
1481 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, NEW_INDEX,
1482 sessionid, 0, packetid);
1483 message_add(&msg, &timeout, sizeof(timeout));
1484 message_add(&msg, &priority, sizeof(priority));
1485 message_add(&msg, &range_subid, sizeof(range_subid));
1486 message_add(&msg, &reserved, sizeof(reserved));
1487 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 7, 0), 0);
1488
1489 agentx_write(s, &msg);
1490
1491 n = agentx_read(s, repl, sizeof(repl), 1000);
1492
1493 agentx_response_validate(__func__, repl, n, 0, packetid,
1494 PARSEERROR, 0, NULL, 0);
1495 message_release(&msg);
1496 close(s);
1497 }
1498
1499 void
agentx_register_any_index(void)1500 agentx_register_any_index(void)
1501 {
1502 int s;
1503 struct message msg = {};
1504 char repl[1024];
1505 size_t n;
1506 uint32_t packetid = arc4random();
1507 uint32_t sessionid;
1508 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1509
1510 s = agentx_connect(axsocket);
1511 sessionid = agentx_open(s, 0, 0,
1512 OID_ARG(MIB_SUBAGENT_REGISTER, 8), __func__);
1513 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, NEW_INDEX,
1514 sessionid, 0, packetid);
1515 message_add(&msg, &timeout, sizeof(timeout));
1516 message_add(&msg, &priority, sizeof(priority));
1517 message_add(&msg, &range_subid, sizeof(range_subid));
1518 message_add(&msg, &reserved, sizeof(reserved));
1519 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 8, 0), 0);
1520
1521 agentx_write(s, &msg);
1522
1523 n = agentx_read(s, repl, sizeof(repl), 1000);
1524
1525 agentx_response_validate(__func__, repl, n, 0, packetid,
1526 PARSEERROR, 0, NULL, 0);
1527 message_release(&msg);
1528 close(s);
1529 }
1530
1531 void
agentx_register_duplicate_self(void)1532 agentx_register_duplicate_self(void)
1533 {
1534 int s;
1535 struct message msg = {};
1536 char repl[1024];
1537 size_t n;
1538 uint32_t packetid = arc4random();
1539 uint32_t sessionid;
1540 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1541
1542 s = agentx_connect(axsocket);
1543 sessionid = agentx_open(s, 0, 0,
1544 OID_ARG(MIB_SUBAGENT_REGISTER, 9), __func__);
1545 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1546 packetid);
1547 message_add(&msg, &timeout, sizeof(timeout));
1548 message_add(&msg, &priority, sizeof(priority));
1549 message_add(&msg, &range_subid, sizeof(range_subid));
1550 message_add(&msg, &reserved, sizeof(reserved));
1551 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 9, 0), 0);
1552 agentx_write(s, &msg);
1553 n = agentx_read(s, repl, sizeof(repl), 1000);
1554 agentx_response_validate(__func__, repl, n, 0, packetid,
1555 NOAGENTXERROR, 0, NULL, 0);
1556
1557 packetid = arc4random();
1558 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1559 packetid);
1560 message_add(&msg, &timeout, sizeof(timeout));
1561 message_add(&msg, &priority, sizeof(priority));
1562 message_add(&msg, &range_subid, sizeof(range_subid));
1563 message_add(&msg, &reserved, sizeof(reserved));
1564 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 9, 0), 0);
1565 agentx_write(s, &msg);
1566 n = agentx_read(s, repl, sizeof(repl), 1000);
1567 agentx_response_validate(__func__, repl, n, 0, packetid,
1568 DUPLICATEREGISTRATION, 0, NULL, 0);
1569
1570 message_release(&msg);
1571 close(s);
1572 }
1573
1574 void
agentx_register_duplicate_twocon(void)1575 agentx_register_duplicate_twocon(void)
1576 {
1577 int s1, s2;
1578 struct message msg = {};
1579 char repl[1024];
1580 size_t n;
1581 uint32_t packetid = arc4random();
1582 uint32_t sessionid1, sessionid2;
1583 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1584
1585 s1 = agentx_connect(axsocket);
1586 s2 = agentx_connect(axsocket);
1587 sessionid1 = agentx_open(s1, 0, 0,
1588 OID_ARG(MIB_SUBAGENT_REGISTER, 10, 1),
1589 "agentx_register_duplicate_twocon.1");
1590 sessionid2 = agentx_open(s2, 0, 0,
1591 OID_ARG(MIB_SUBAGENT_REGISTER, 10, 2),
1592 "agentx_register_duplicate_twocon.2");
1593 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid1, 0,
1594 packetid);
1595 message_add(&msg, &timeout, sizeof(timeout));
1596 message_add(&msg, &priority, sizeof(priority));
1597 message_add(&msg, &range_subid, sizeof(range_subid));
1598 message_add(&msg, &reserved, sizeof(reserved));
1599 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 10, 0), 0);
1600 agentx_write(s1, &msg);
1601 n = agentx_read(s1, repl, sizeof(repl), 1000);
1602 agentx_response_validate(__func__, repl, n, 0, packetid,
1603 NOAGENTXERROR, 0, NULL, 0);
1604
1605 packetid = arc4random();
1606 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid2, 0,
1607 packetid);
1608 message_add(&msg, &timeout, sizeof(timeout));
1609 message_add(&msg, &priority, sizeof(priority));
1610 message_add(&msg, &range_subid, sizeof(range_subid));
1611 message_add(&msg, &reserved, sizeof(reserved));
1612 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 10, 0), 0);
1613 agentx_write(s2, &msg);
1614 n = agentx_read(s2, repl, sizeof(repl), 1000);
1615 agentx_response_validate(__func__, repl, n, 0, packetid,
1616 DUPLICATEREGISTRATION, 0, NULL, 0);
1617
1618 message_release(&msg);
1619 close(s1);
1620 close(s2);
1621 }
1622
1623 void
agentx_register_duplicate_priority(void)1624 agentx_register_duplicate_priority(void)
1625 {
1626 int s;
1627 struct message msg = {};
1628 char repl[1024];
1629 size_t n;
1630 uint32_t packetid = arc4random();
1631 uint32_t sessionid;
1632 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1633
1634 s = agentx_connect(axsocket);
1635 sessionid = agentx_open(s, 0, 0,
1636 OID_ARG(MIB_SUBAGENT_REGISTER, 11), __func__);
1637 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1638 packetid);
1639 message_add(&msg, &timeout, sizeof(timeout));
1640 message_add(&msg, &priority, sizeof(priority));
1641 message_add(&msg, &range_subid, sizeof(range_subid));
1642 message_add(&msg, &reserved, sizeof(reserved));
1643 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 11, 0), 0);
1644 agentx_write(s, &msg);
1645 n = agentx_read(s, repl, sizeof(repl), 1000);
1646 agentx_response_validate(__func__, repl, n, 0, packetid,
1647 NOAGENTXERROR, 0, NULL, 0);
1648
1649 packetid = arc4random();
1650 priority = 1;
1651 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1652 packetid);
1653 message_add(&msg, &timeout, sizeof(timeout));
1654 message_add(&msg, &priority, sizeof(priority));
1655 message_add(&msg, &range_subid, sizeof(range_subid));
1656 message_add(&msg, &reserved, sizeof(reserved));
1657 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 11, 0), 0);
1658 agentx_write(s, &msg);
1659 n = agentx_read(s, repl, sizeof(repl), 1000);
1660 agentx_response_validate(__func__, repl, n, 0, packetid,
1661 NOAGENTXERROR, 0, NULL, 0);
1662
1663 message_release(&msg);
1664 close(s);
1665 }
1666
1667 void
agentx_register_range(void)1668 agentx_register_range(void)
1669 {
1670 int s;
1671 struct message msg = {};
1672 char repl[1024];
1673 size_t n;
1674 uint32_t packetid = arc4random();
1675 uint32_t sessionid, upperbound = 10;
1676 uint8_t timeout = 0, priority = 127, range_subid = 11, reserved = 0;
1677
1678 s = agentx_connect(axsocket);
1679 sessionid = agentx_open(s, 0, 0,
1680 OID_ARG(MIB_SUBAGENT_REGISTER, 12), __func__);
1681 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1682 packetid);
1683 message_add(&msg, &timeout, sizeof(timeout));
1684 message_add(&msg, &priority, sizeof(priority));
1685 message_add(&msg, &range_subid, sizeof(range_subid));
1686 message_add(&msg, &reserved, sizeof(reserved));
1687 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 12, 1), 0);
1688 message_add_uint32(&msg, upperbound);
1689 agentx_write(s, &msg);
1690 n = agentx_read(s, repl, sizeof(repl), 1000);
1691 agentx_response_validate(__func__, repl, n, 0, packetid,
1692 NOAGENTXERROR, 0, NULL, 0);
1693
1694 message_release(&msg);
1695 close(s);
1696 }
1697
1698 void
agentx_register_range_invalidupperbound(void)1699 agentx_register_range_invalidupperbound(void)
1700 {
1701 int s;
1702 struct message msg = {};
1703 char repl[1024];
1704 size_t n;
1705 uint32_t packetid = arc4random();
1706 uint32_t sessionid, upperbound = 1;
1707 uint8_t timeout = 0, priority = 127, range_subid = 11, reserved = 0;
1708
1709 s = agentx_connect(axsocket);
1710 sessionid = agentx_open(s, 0, 0,
1711 OID_ARG(MIB_SUBAGENT_REGISTER, 13), __func__);
1712 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1713 packetid);
1714 message_add(&msg, &timeout, sizeof(timeout));
1715 message_add(&msg, &priority, sizeof(priority));
1716 message_add(&msg, &range_subid, sizeof(range_subid));
1717 message_add(&msg, &reserved, sizeof(reserved));
1718 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 13, 2), 0);
1719 message_add_uint32(&msg, upperbound);
1720 agentx_write(s, &msg);
1721 n = agentx_read(s, repl, sizeof(repl), 1000);
1722 agentx_response_validate(__func__, repl, n, 0, packetid,
1723 PARSEERROR, 0, NULL, 0);
1724
1725 message_release(&msg);
1726 close(s);
1727 }
1728
1729 void
agentx_register_range_single(void)1730 agentx_register_range_single(void)
1731 {
1732 int s;
1733 struct message msg = {};
1734 char repl[1024];
1735 size_t n;
1736 uint32_t packetid = arc4random();
1737 uint32_t sessionid, upperbound = 1;
1738 uint8_t timeout = 0, priority = 127, range_subid = 11, reserved = 0;
1739
1740 s = agentx_connect(axsocket);
1741 sessionid = agentx_open(s, 0, 0,
1742 OID_ARG(MIB_SUBAGENT_REGISTER, 14), __func__);
1743 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1744 packetid);
1745 message_add(&msg, &timeout, sizeof(timeout));
1746 message_add(&msg, &priority, sizeof(priority));
1747 message_add(&msg, &range_subid, sizeof(range_subid));
1748 message_add(&msg, &reserved, sizeof(reserved));
1749 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 14, 1), 0);
1750 message_add_uint32(&msg, upperbound);
1751 agentx_write(s, &msg);
1752 n = agentx_read(s, repl, sizeof(repl), 1000);
1753 agentx_response_validate(__func__, repl, n, 0, packetid,
1754 NOAGENTXERROR, 0, NULL, 0);
1755
1756 message_release(&msg);
1757 close(s);
1758 }
1759
1760 void
agentx_register_range_overlap_single(void)1761 agentx_register_range_overlap_single(void)
1762 {
1763 int s;
1764 struct message msg = {};
1765 char repl[1024];
1766 size_t n;
1767 uint32_t packetid = arc4random();
1768 uint32_t sessionid, upperbound = 10;
1769 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1770
1771 s = agentx_connect(axsocket);
1772 sessionid = agentx_open(s, 0, 0,
1773 OID_ARG(MIB_SUBAGENT_REGISTER, 15), __func__);
1774 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1775 packetid);
1776 message_add(&msg, &timeout, sizeof(timeout));
1777 message_add(&msg, &priority, sizeof(priority));
1778 message_add(&msg, &range_subid, sizeof(range_subid));
1779 message_add(&msg, &reserved, sizeof(reserved));
1780 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 15, 1), 0);
1781 agentx_write(s, &msg);
1782 n = agentx_read(s, repl, sizeof(repl), 1000);
1783 agentx_response_validate(__func__, repl, n, 0, packetid,
1784 NOAGENTXERROR, 0, NULL, 0);
1785
1786 packetid = arc4random();
1787 range_subid = 11;
1788 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1789 packetid);
1790 message_add(&msg, &timeout, sizeof(timeout));
1791 message_add(&msg, &priority, sizeof(priority));
1792 message_add(&msg, &range_subid, sizeof(range_subid));
1793 message_add(&msg, &reserved, sizeof(reserved));
1794 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 15, 1), 0);
1795 message_add_uint32(&msg, upperbound);
1796 agentx_write(s, &msg);
1797 n = agentx_read(s, repl, sizeof(repl), 1000);
1798 agentx_response_validate(__func__, repl, n, 0, packetid,
1799 DUPLICATEREGISTRATION, 0, NULL, 0);
1800
1801 message_release(&msg);
1802 close(s);
1803 }
1804
1805 void
agentx_register_single_overlap_range(void)1806 agentx_register_single_overlap_range(void)
1807 {
1808 int s;
1809 struct message msg = {};
1810 char repl[1024];
1811 size_t n;
1812 uint32_t packetid = arc4random();
1813 uint32_t sessionid, upperbound = 10;
1814 uint8_t timeout = 0, priority = 127, range_subid = 11, reserved = 0;
1815
1816 s = agentx_connect(axsocket);
1817 sessionid = agentx_open(s, 0, 0,
1818 OID_ARG(MIB_SUBAGENT_REGISTER, 16), __func__);
1819 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1820 packetid);
1821 message_add(&msg, &timeout, sizeof(timeout));
1822 message_add(&msg, &priority, sizeof(priority));
1823 message_add(&msg, &range_subid, sizeof(range_subid));
1824 message_add(&msg, &reserved, sizeof(reserved));
1825 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 16, 1), 0);
1826 message_add_uint32(&msg, upperbound);
1827 agentx_write(s, &msg);
1828 n = agentx_read(s, repl, sizeof(repl), 1000);
1829 agentx_response_validate(__func__, repl, n, 0, packetid,
1830 NOAGENTXERROR, 0, NULL, 0);
1831
1832 packetid = arc4random();
1833 range_subid = 0;
1834 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1835 packetid);
1836 message_add(&msg, &timeout, sizeof(timeout));
1837 message_add(&msg, &priority, sizeof(priority));
1838 message_add(&msg, &range_subid, sizeof(range_subid));
1839 message_add(&msg, &reserved, sizeof(reserved));
1840 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 16, 1), 0);
1841 agentx_write(s, &msg);
1842 n = agentx_read(s, repl, sizeof(repl), 1000);
1843 agentx_response_validate(__func__, repl, n, 0, packetid,
1844 DUPLICATEREGISTRATION, 0, NULL, 0);
1845
1846 message_release(&msg);
1847 close(s);
1848 }
1849
1850 void
agentx_register_range_overlap_range(void)1851 agentx_register_range_overlap_range(void)
1852 {
1853 int s;
1854 struct message msg = {};
1855 char repl[1024];
1856 size_t n;
1857 uint32_t packetid = arc4random();
1858 uint32_t sessionid, upperbound = 10;
1859 uint8_t timeout = 0, priority = 127, range_subid = 11, reserved = 0;
1860
1861 s = agentx_connect(axsocket);
1862 sessionid = agentx_open(s, 0, 0,
1863 OID_ARG(MIB_SUBAGENT_REGISTER, 17), __func__);
1864 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1865 packetid);
1866 message_add(&msg, &timeout, sizeof(timeout));
1867 message_add(&msg, &priority, sizeof(priority));
1868 message_add(&msg, &range_subid, sizeof(range_subid));
1869 message_add(&msg, &reserved, sizeof(reserved));
1870 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 17, 1), 0);
1871 message_add_uint32(&msg, upperbound);
1872 agentx_write(s, &msg);
1873 n = agentx_read(s, repl, sizeof(repl), 1000);
1874 agentx_response_validate(__func__, repl, n, 0, packetid,
1875 NOAGENTXERROR, 0, NULL, 0);
1876
1877 packetid = arc4random();
1878 upperbound = 15;
1879 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1880 packetid);
1881 message_add(&msg, &timeout, sizeof(timeout));
1882 message_add(&msg, &priority, sizeof(priority));
1883 message_add(&msg, &range_subid, sizeof(range_subid));
1884 message_add(&msg, &reserved, sizeof(reserved));
1885 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 17, 6), 0);
1886 message_add_uint32(&msg, upperbound);
1887 agentx_write(s, &msg);
1888 n = agentx_read(s, repl, sizeof(repl), 1000);
1889 agentx_response_validate(__func__, repl, n, 0, packetid,
1890 DUPLICATEREGISTRATION, 0, NULL, 0);
1891
1892 message_release(&msg);
1893 close(s);
1894 }
1895
1896 void
agentx_register_below(void)1897 agentx_register_below(void)
1898 {
1899 int s;
1900 struct message msg = {};
1901 char repl[1024];
1902 size_t n;
1903 uint32_t packetid = arc4random();
1904 uint32_t sessionid;
1905 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1906
1907 s = agentx_connect(axsocket);
1908 sessionid = agentx_open(s, 0, 0,
1909 OID_ARG(MIB_SUBAGENT_REGISTER, 18), __func__);
1910 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1911 packetid);
1912 message_add(&msg, &timeout, sizeof(timeout));
1913 message_add(&msg, &priority, sizeof(priority));
1914 message_add(&msg, &range_subid, sizeof(range_subid));
1915 message_add(&msg, &reserved, sizeof(reserved));
1916 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 18, 1), 0);
1917 agentx_write(s, &msg);
1918 n = agentx_read(s, repl, sizeof(repl), 1000);
1919 agentx_response_validate(__func__, repl, n, 0, packetid,
1920 NOAGENTXERROR, 0, NULL, 0);
1921
1922 packetid = arc4random();
1923 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1924 packetid);
1925 message_add(&msg, &timeout, sizeof(timeout));
1926 message_add(&msg, &priority, sizeof(priority));
1927 message_add(&msg, &range_subid, sizeof(range_subid));
1928 message_add(&msg, &reserved, sizeof(reserved));
1929 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 18, 1, 0), 0);
1930 agentx_write(s, &msg);
1931 n = agentx_read(s, repl, sizeof(repl), 1000);
1932 agentx_response_validate(__func__, repl, n, 0, packetid,
1933 NOAGENTXERROR, 0, NULL, 0);
1934
1935 message_release(&msg);
1936 close(s);
1937 }
1938
1939 void
agentx_register_above(void)1940 agentx_register_above(void)
1941 {
1942 int s;
1943 struct message msg = {};
1944 char repl[1024];
1945 size_t n;
1946 uint32_t packetid = arc4random();
1947 uint32_t sessionid;
1948 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1949
1950 s = agentx_connect(axsocket);
1951 sessionid = agentx_open(s, 0, 0,
1952 OID_ARG(MIB_SUBAGENT_REGISTER, 19), __func__);
1953 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1954 packetid);
1955 message_add(&msg, &timeout, sizeof(timeout));
1956 message_add(&msg, &priority, sizeof(priority));
1957 message_add(&msg, &range_subid, sizeof(range_subid));
1958 message_add(&msg, &reserved, sizeof(reserved));
1959 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 19, 1, 1), 0);
1960 agentx_write(s, &msg);
1961 n = agentx_read(s, repl, sizeof(repl), 1000);
1962 agentx_response_validate(__func__, repl, n, 0, packetid,
1963 NOAGENTXERROR, 0, NULL, 0);
1964
1965 packetid = arc4random();
1966 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1967 packetid);
1968 message_add(&msg, &timeout, sizeof(timeout));
1969 message_add(&msg, &priority, sizeof(priority));
1970 message_add(&msg, &range_subid, sizeof(range_subid));
1971 message_add(&msg, &reserved, sizeof(reserved));
1972 message_add_oid(&msg, OID_ARG(MIB_REGISTER, 19, 1), 0);
1973 agentx_write(s, &msg);
1974 n = agentx_read(s, repl, sizeof(repl), 1000);
1975 agentx_response_validate(__func__, repl, n, 0, packetid,
1976 NOAGENTXERROR, 0, NULL, 0);
1977
1978 message_release(&msg);
1979 close(s);
1980 }
1981
1982 void
agentx_register_restricted(void)1983 agentx_register_restricted(void)
1984 {
1985 int s;
1986 struct message msg = {};
1987 char repl[1024];
1988 size_t n;
1989 uint32_t packetid = arc4random();
1990 uint32_t sessionid;
1991 uint8_t timeout = 0, priority = 127, range_subid = 0, reserved = 0;
1992
1993 s = agentx_connect(axsocket);
1994 sessionid = agentx_open(s, 0, 0,
1995 OID_ARG(MIB_SUBAGENT_REGISTER, 20), __func__);
1996 message_add_header(&msg, 1, AGENTX_REGISTER_PDU, 0, sessionid, 0,
1997 packetid);
1998 message_add(&msg, &timeout, sizeof(timeout));
1999 message_add(&msg, &priority, sizeof(priority));
2000 message_add(&msg, &range_subid, sizeof(range_subid));
2001 message_add(&msg, &reserved, sizeof(reserved));
2002 message_add_oid(&msg, OID_ARG(SYSORTABLE, 1, 1), 0);
2003 agentx_write(s, &msg);
2004 n = agentx_read(s, repl, sizeof(repl), 1000);
2005 agentx_response_validate(__func__, repl, n, 0, packetid,
2006 REQUESTDENIED, 0, NULL, 0);
2007
2008 message_release(&msg);
2009 close(s);
2010 }
2011
2012 void
agentx_unregister_notopen(void)2013 agentx_unregister_notopen(void)
2014 {
2015 int s;
2016 struct message msg = {};
2017 char repl[1024];
2018 size_t n;
2019 uint32_t packetid = arc4random();
2020 uint8_t priority = 127, range_subid = 0, reserved = 0;
2021
2022 s = agentx_connect(axsocket);
2023 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, 0, 0, packetid);
2024 message_add(&msg, &reserved, sizeof(reserved));
2025 message_add(&msg, &priority, sizeof(priority));
2026 message_add(&msg, &range_subid, sizeof(range_subid));
2027 message_add(&msg, &reserved, sizeof(reserved));
2028 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 1, 0), 0);
2029
2030 agentx_write(s, &msg);
2031
2032 n = agentx_read(s, repl, sizeof(repl), 1000);
2033
2034 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
2035 NULL, 0);
2036 message_release(&msg);
2037 close(s);
2038 }
2039
2040 void
agentx_unregister_invalid_sessionid(void)2041 agentx_unregister_invalid_sessionid(void)
2042 {
2043 int s;
2044 struct message msg = {};
2045 char repl[1024];
2046 size_t n;
2047 uint32_t packetid = arc4random();
2048 uint32_t sessionid;
2049 uint8_t priority = 127, range_subid = 0, reserved = 0;
2050
2051 s = agentx_connect(axsocket);
2052 sessionid = agentx_open(s, 0, 0,
2053 OID_ARG(MIB_SUBAGENT_UNREGISTER, 2), __func__);
2054 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid + 1, 0,
2055 packetid);
2056 message_add(&msg, &reserved, sizeof(reserved));
2057 message_add(&msg, &priority, sizeof(priority));
2058 message_add(&msg, &range_subid, sizeof(range_subid));
2059 message_add(&msg, &reserved, sizeof(reserved));
2060 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 2, 0), 0);
2061
2062 agentx_write(s, &msg);
2063
2064 n = agentx_read(s, repl, sizeof(repl), 1000);
2065
2066 agentx_response_validate(__func__, repl, n, 0, packetid, NOTOPEN, 0,
2067 NULL, 0);
2068 message_release(&msg);
2069 close(s);
2070 }
2071
2072 void
agentx_unregister_notregistered(void)2073 agentx_unregister_notregistered(void)
2074 {
2075 int s;
2076 struct message msg = {};
2077 char repl[1024];
2078 size_t n;
2079 uint32_t packetid = arc4random();
2080 uint32_t sessionid;
2081 uint8_t priority = 127, range_subid = 0, reserved = 0;
2082
2083 s = agentx_connect(axsocket);
2084 sessionid = agentx_open(s, 0, 0,
2085 OID_ARG(MIB_SUBAGENT_UNREGISTER, 3), __func__);
2086 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid, 0,
2087 packetid);
2088 message_add(&msg, &reserved, sizeof(reserved));
2089 message_add(&msg, &priority, sizeof(priority));
2090 message_add(&msg, &range_subid, sizeof(range_subid));
2091 message_add(&msg, &reserved, sizeof(reserved));
2092 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 3), 0);
2093
2094 agentx_write(s, &msg);
2095
2096 n = agentx_read(s, repl, sizeof(repl), 1000);
2097
2098 agentx_response_validate(__func__, repl, n, 0, packetid,
2099 UNKNOWNREGISTRATION, 0, NULL, 0);
2100 message_release(&msg);
2101 close(s);
2102 }
2103
2104 void
agentx_unregister_single(void)2105 agentx_unregister_single(void)
2106 {
2107 int s;
2108 struct message msg = {};
2109 char repl[1024];
2110 size_t n;
2111 uint32_t packetid = arc4random();
2112 uint32_t sessionid;
2113 uint8_t priority = 127, range_subid = 0, reserved = 0;
2114
2115 s = agentx_connect(axsocket);
2116 sessionid = agentx_open(s, 0, 0,
2117 OID_ARG(MIB_SUBAGENT_UNREGISTER, 4), __func__);
2118 agentx_register(s, sessionid, 0, 0, 127, 0,
2119 OID_ARG(MIB_UNREGISTER, 4), 0);
2120 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid, 0,
2121 packetid);
2122 message_add(&msg, &reserved, sizeof(reserved));
2123 message_add(&msg, &priority, sizeof(priority));
2124 message_add(&msg, &range_subid, sizeof(range_subid));
2125 message_add(&msg, &reserved, sizeof(reserved));
2126 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 4), 0);
2127
2128 agentx_write(s, &msg);
2129
2130 n = agentx_read(s, repl, sizeof(repl), 1000);
2131
2132 agentx_response_validate(__func__, repl, n, 0, packetid,
2133 NOAGENTXERROR, 0, NULL, 0);
2134 message_release(&msg);
2135 close(s);
2136 }
2137
2138 void
agentx_unregister_single_notowned(void)2139 agentx_unregister_single_notowned(void)
2140 {
2141 int s;
2142 struct message msg = {};
2143 char repl[1024];
2144 size_t n;
2145 uint32_t packetid = arc4random();
2146 uint32_t sessionid1, sessionid2;
2147 uint8_t priority = 127, range_subid = 0, reserved = 0;
2148
2149 s = agentx_connect(axsocket);
2150 sessionid1 = agentx_open(s, 0, 0,
2151 OID_ARG(MIB_SUBAGENT_UNREGISTER, 5, 1),
2152 "agentx_unregister_single_notowned.1");
2153 sessionid2 = agentx_open(s, 0, 0,
2154 OID_ARG(MIB_SUBAGENT_UNREGISTER, 5, 2),
2155 "agentx_unregister_single_notowned.2");
2156 agentx_register(s, sessionid1, 0, 0, 127, 0,
2157 OID_ARG(MIB_UNREGISTER, 5, 1), 0);
2158 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid2, 0,
2159 packetid);
2160 message_add(&msg, &reserved, sizeof(reserved));
2161 message_add(&msg, &priority, sizeof(priority));
2162 message_add(&msg, &range_subid, sizeof(range_subid));
2163 message_add(&msg, &reserved, sizeof(reserved));
2164 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 5, 1), 0);
2165
2166 agentx_write(s, &msg);
2167
2168 n = agentx_read(s, repl, sizeof(repl), 1000);
2169
2170 agentx_response_validate(__func__, repl, n, 0, packetid,
2171 UNKNOWNREGISTRATION, 0, NULL, 0);
2172 message_release(&msg);
2173 close(s);
2174 }
2175
2176 void
agentx_unregister_range(void)2177 agentx_unregister_range(void)
2178 {
2179 int s;
2180 struct message msg = {};
2181 char repl[1024];
2182 size_t n;
2183 uint32_t packetid = arc4random();
2184 uint32_t sessionid;
2185 uint8_t priority = 127, range_subid = 11, reserved = 0;
2186 uint32_t upperbound = 10;
2187
2188 s = agentx_connect(axsocket);
2189 sessionid = agentx_open(s, 0, 0,
2190 OID_ARG(MIB_SUBAGENT_UNREGISTER, 6), __func__);
2191 agentx_register(s, sessionid, 0, 0, 127, 11,
2192 OID_ARG(MIB_UNREGISTER, 6, 1), 10);
2193 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid, 0,
2194 packetid);
2195 message_add(&msg, &reserved, sizeof(reserved));
2196 message_add(&msg, &priority, sizeof(priority));
2197 message_add(&msg, &range_subid, sizeof(range_subid));
2198 message_add(&msg, &reserved, sizeof(reserved));
2199 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 6, 1), 0);
2200 message_add_uint32(&msg, upperbound);
2201
2202 agentx_write(s, &msg);
2203
2204 n = agentx_read(s, repl, sizeof(repl), 1000);
2205
2206 agentx_response_validate(__func__, repl, n, 0, packetid,
2207 NOAGENTXERROR, 0, NULL, 0);
2208 message_release(&msg);
2209 close(s);
2210 }
2211
2212 void
agentx_unregister_range_single(void)2213 agentx_unregister_range_single(void)
2214 {
2215 int s;
2216 struct message msg = {};
2217 char repl[1024];
2218 size_t n;
2219 uint32_t packetid = arc4random();
2220 uint32_t sessionid;
2221 uint8_t priority = 127, range_subid = 0, reserved = 0;
2222
2223 s = agentx_connect(axsocket);
2224 sessionid = agentx_open(s, 0, 0,
2225 OID_ARG(MIB_SUBAGENT_UNREGISTER, 7), __func__);
2226 agentx_register(s, sessionid, 0, 0, 127, 11,
2227 OID_ARG(MIB_UNREGISTER, 6, 1), 10);
2228 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid, 0,
2229 packetid);
2230 message_add(&msg, &reserved, sizeof(reserved));
2231 message_add(&msg, &priority, sizeof(priority));
2232 message_add(&msg, &range_subid, sizeof(range_subid));
2233 message_add(&msg, &reserved, sizeof(reserved));
2234 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 7, 1), 0);
2235
2236 agentx_write(s, &msg);
2237
2238 n = agentx_read(s, repl, sizeof(repl), 1000);
2239
2240 agentx_response_validate(__func__, repl, n, 0, packetid,
2241 UNKNOWNREGISTRATION, 0, NULL, 0);
2242 message_release(&msg);
2243 close(s);
2244 }
2245
2246 void
agentx_unregister_range_subset(void)2247 agentx_unregister_range_subset(void)
2248 {
2249 int s;
2250 struct message msg = {};
2251 char repl[1024];
2252 size_t n;
2253 uint32_t packetid = arc4random();
2254 uint32_t sessionid;
2255 uint8_t priority = 127, range_subid = 11, reserved = 0;
2256 uint32_t upperbound = 5;
2257
2258 s = agentx_connect(axsocket);
2259 sessionid = agentx_open(s, 0, 0,
2260 OID_ARG(MIB_SUBAGENT_UNREGISTER, 8), __func__);
2261 agentx_register(s, sessionid, 0, 0, 127, 11,
2262 OID_ARG(MIB_UNREGISTER, 8, 1), 10);
2263 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid, 0,
2264 packetid);
2265 message_add(&msg, &reserved, sizeof(reserved));
2266 message_add(&msg, &priority, sizeof(priority));
2267 message_add(&msg, &range_subid, sizeof(range_subid));
2268 message_add(&msg, &reserved, sizeof(reserved));
2269 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 8, 1), 0);
2270 message_add_uint32(&msg, upperbound);
2271
2272 agentx_write(s, &msg);
2273
2274 n = agentx_read(s, repl, sizeof(repl), 1000);
2275
2276 agentx_response_validate(__func__, repl, n, 0, packetid,
2277 UNKNOWNREGISTRATION, 0, NULL, 0);
2278 message_release(&msg);
2279 close(s);
2280 }
2281
2282 void
agentx_unregister_range_extra(void)2283 agentx_unregister_range_extra(void)
2284 {
2285 int s;
2286 struct message msg = {};
2287 char repl[1024];
2288 size_t n;
2289 uint32_t packetid = arc4random();
2290 uint32_t sessionid;
2291 uint8_t priority = 127, range_subid = 11, reserved = 0;
2292 uint32_t upperbound = 10;
2293
2294 s = agentx_connect(axsocket);
2295 sessionid = agentx_open(s, 0, 0,
2296 OID_ARG(MIB_SUBAGENT_UNREGISTER, 9), __func__);
2297 agentx_register(s, sessionid, 0, 0, 127, 11,
2298 OID_ARG(MIB_UNREGISTER, 9, 1), upperbound);
2299 upperbound = 15;
2300 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid, 0,
2301 packetid);
2302 message_add(&msg, &reserved, sizeof(reserved));
2303 message_add(&msg, &priority, sizeof(priority));
2304 message_add(&msg, &range_subid, sizeof(range_subid));
2305 message_add(&msg, &reserved, sizeof(reserved));
2306 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 9, 1), 0);
2307 message_add_uint32(&msg, upperbound);
2308
2309 agentx_write(s, &msg);
2310
2311 n = agentx_read(s, repl, sizeof(repl), 1000);
2312
2313 agentx_response_validate(__func__, repl, n, 0, packetid,
2314 UNKNOWNREGISTRATION, 0, NULL, 0);
2315 message_release(&msg);
2316 close(s);
2317 }
2318
2319 void
agentx_unregister_range_priority(void)2320 agentx_unregister_range_priority(void)
2321 {
2322 int s;
2323 struct message msg = {};
2324 char repl[1024];
2325 size_t n;
2326 uint32_t packetid = arc4random();
2327 uint32_t sessionid;
2328 uint8_t priority = 127, range_subid = 11, reserved = 0;
2329 uint32_t upperbound = 10;
2330
2331 s = agentx_connect(axsocket);
2332 sessionid = agentx_open(s, 0, 0,
2333 OID_ARG(MIB_SUBAGENT_UNREGISTER, 10), __func__);
2334 agentx_register(s, sessionid, 0, 0, priority, 11,
2335 OID_ARG(MIB_UNREGISTER, 10, 1), upperbound);
2336 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid, 0,
2337 packetid);
2338 priority = 128;
2339 message_add(&msg, &reserved, sizeof(reserved));
2340 message_add(&msg, &priority, sizeof(priority));
2341 message_add(&msg, &range_subid, sizeof(range_subid));
2342 message_add(&msg, &reserved, sizeof(reserved));
2343 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 10, 1), 0);
2344 message_add_uint32(&msg, upperbound);
2345
2346 agentx_write(s, &msg);
2347
2348 n = agentx_read(s, repl, sizeof(repl), 1000);
2349
2350 agentx_response_validate(__func__, repl, n, 0, packetid,
2351 UNKNOWNREGISTRATION, 0, NULL, 0);
2352 message_release(&msg);
2353 close(s);
2354 }
2355
2356 void
agentx_unregister_range_notowned(void)2357 agentx_unregister_range_notowned(void)
2358 {
2359 int s;
2360 struct message msg = {};
2361 char repl[1024];
2362 size_t n;
2363 uint32_t packetid = arc4random();
2364 uint32_t sessionid1, sessionid2;
2365 uint8_t priority = 127, range_subid = 11, reserved = 0;
2366 uint32_t upperbound = 10;
2367
2368 s = agentx_connect(axsocket);
2369 sessionid1 = agentx_open(s, 0, 0,
2370 OID_ARG(MIB_SUBAGENT_UNREGISTER, 11, 1),
2371 "agentx_unregister_range_notowned.1");
2372 sessionid2 = agentx_open(s, 0, 0,
2373 OID_ARG(MIB_SUBAGENT_UNREGISTER, 11, 2),
2374 "agentx_unregister_range_notowned.2");
2375 agentx_register(s, sessionid1, 0, 0, priority, 11,
2376 OID_ARG(MIB_UNREGISTER, 11, 1), upperbound);
2377 message_add_header(&msg, 1, AGENTX_UNREGISTER_PDU, 0, sessionid2, 0,
2378 packetid);
2379 priority = 128;
2380 message_add(&msg, &reserved, sizeof(reserved));
2381 message_add(&msg, &priority, sizeof(priority));
2382 message_add(&msg, &range_subid, sizeof(range_subid));
2383 message_add(&msg, &reserved, sizeof(reserved));
2384 message_add_oid(&msg, OID_ARG(MIB_UNREGISTER, 10, 1), 0);
2385 message_add_uint32(&msg, upperbound);
2386
2387 agentx_write(s, &msg);
2388
2389 n = agentx_read(s, repl, sizeof(repl), 1000);
2390
2391 agentx_response_validate(__func__, repl, n, 0, packetid,
2392 UNKNOWNREGISTRATION, 0, NULL, 0);
2393 message_release(&msg);
2394 close(s);
2395 }
2396
2397 void
agentx_get_handle(const char * test,const void * buf,size_t len,uint8_t flags,uint32_t sessionid,struct varbind * varbind,size_t nvarbind)2398 agentx_get_handle(const char *test, const void *buf, size_t len,
2399 uint8_t flags, uint32_t sessionid, struct varbind *varbind,
2400 size_t nvarbind)
2401 {
2402 const struct header *header = buf;
2403 struct oid start, end, zero = {0};
2404 const uint8_t *u8;
2405 uint32_t u32;
2406 uint16_t u16;
2407 size_t sublen, i, j;
2408 char oid1[512], oid2[512];
2409 struct varbind *pool;
2410
2411 if (len < sizeof(*header))
2412 errx(1, "%s: unexpected pdu message size received: %zu", test, len);
2413 if (header->version != 1)
2414 errx(1, "%s: invalid pdu version", test);
2415 if (header->type != AGENTX_GET_PDU)
2416 errx(1, "%s: invalid pdu type received (%hhu/5)", test, header->type);
2417 if (header->flags != flags)
2418 errx(1, "%s: invalid get pdu flags received (%hhu/%hhu)",
2419 test, header->flags, flags);
2420 if (header->reserved != 0)
2421 errx(1, "%s: invalid get pdu reserved received", test);
2422 if (p32toh(header, header->sessionid) != sessionid)
2423 errx(1, "%s: unexpected get pdu sessionid (%u/%u)", test,
2424 p32toh(header, header->sessionid), sessionid);
2425 if (p32toh(header, header->payload_length) > len - sizeof(*header))
2426 errx(1, "%s: unexpected get pdu payload length received",
2427 test);
2428
2429 buf += sizeof(*header);
2430 len = p32toh(header, header->payload_length);
2431
2432 if ((pool = calloc(nvarbind, sizeof(*pool))) == NULL)
2433 err(1, NULL);
2434 memcpy(pool, varbind, nvarbind * sizeof(*pool));
2435
2436 for (i = 0; len > 0; i++) {
2437 sublen = poid(test, header, buf, len, &start);
2438 buf += sublen;
2439 len -= sublen;
2440 sublen = poid(test, header, buf, len, &end);
2441 buf += sublen;
2442 len -= sublen;
2443
2444 if (oid_cmp(&end, &zero) != 0)
2445 errx(1, "%s: unexpected searchrange end: (%s/%s)", test,
2446 oid_print(&end, oid1, sizeof(oid1)),
2447 oid_print(&zero, oid2, sizeof(oid2)));
2448 if (start.include != 0 || end.include != 0)
2449 errx(1, "%s: unexpected searchrange include: (%s)",
2450 test, oid_print(&start, oid1, sizeof(oid1)));
2451 for (j = 0; j < nvarbind; j++) {
2452 if (oid_cmp(&pool[j].name, &start) == 0)
2453 break;
2454 }
2455 if (j == nvarbind)
2456 warnx("%s: unexpected searchrange start: " "(%s)", test,
2457 oid_print(&start, oid1, sizeof(oid1)));
2458
2459 varbind[i] = pool[j];
2460 pool[j].name.n_subid = 0;
2461 }
2462 free(pool);
2463 }
2464
2465 void
agentx_getnext_handle(const char * test,const void * buf,size_t len,uint8_t flags,uint32_t sessionid,struct searchrange * searchrange,struct varbind * varbind,size_t nvarbind)2466 agentx_getnext_handle(const char *test, const void *buf, size_t len,
2467 uint8_t flags, uint32_t sessionid, struct searchrange *searchrange,
2468 struct varbind *varbind, size_t nvarbind)
2469 {
2470 const struct header *header = buf;
2471 struct oid start, end, zero = {0};
2472 const uint8_t *u8;
2473 uint32_t u32;
2474 uint16_t u16;
2475 size_t sublen, i, j, match;
2476 char oid1[512], oid2[512], oid3[512], oid4[512];
2477 struct varbind *pool;
2478
2479 if (len < sizeof(*header))
2480 errx(1, "%s: unexpected pdu message size received: %zu", test, len);
2481 if (header->version != 1)
2482 errx(1, "%s: invalid pdu version", test);
2483 if (header->type != AGENTX_GETNEXT_PDU)
2484 errx(1, "%s: invalid pdu type received (%hhu/6)", test, header->type);
2485 if (header->flags != flags)
2486 errx(1, "%s: invalid get pdu flags received (%hhu/%hhu)",
2487 test, header->flags, flags);
2488 if (header->reserved != 0)
2489 errx(1, "%s: invalid get pdu reserved received", test);
2490 if (p32toh(header, header->sessionid) != sessionid)
2491 errx(1, "%s: unexpected get pdu sessionid (%u/%u)", test,
2492 p32toh(header, header->sessionid), sessionid);
2493 if (p32toh(header, header->payload_length) > len - sizeof(*header))
2494 errx(1, "%s: unexpected get pdu payload length received",
2495 test);
2496
2497 buf += sizeof(*header);
2498 len = p32toh(header, header->payload_length);
2499
2500 if ((pool = calloc(nvarbind, sizeof(*pool))) == NULL)
2501 err(1, NULL);
2502 memcpy(pool, varbind, nvarbind * sizeof(*pool));
2503
2504 for (i = 0; len > 0; i++) {
2505 sublen = poid(test, header, buf, len, &start);
2506 buf += sublen;
2507 len -= sublen;
2508 sublen = poid(test, header, buf, len, &end);
2509 buf += sublen;
2510 len -= sublen;
2511
2512 if ((start.include != 1 && start.include != 0) ||
2513 end.include != 0)
2514 errx(1, "%s: unexpected searchrange include: (%s-%s)",
2515 test, oid_print(&start, oid1, sizeof(oid1)),
2516 oid_print(&end, oid2, sizeof(oid2)));
2517
2518 match = (size_t)-1;
2519 for (j = 0; j < nvarbind; j++) {
2520 if (oid_cmp(&pool[j].name, &start) == 0 &&
2521 pool[j].type == TYPE_ENDOFMIBVIEW) {
2522 match = j;
2523 } else if (oid_cmp(&pool[j].name, &start) < 0 ||
2524 (!start.include &&
2525 oid_cmp(&pool[j].name, &start) == 0) ||
2526 oid_cmp(&pool[j].name, &end) >= 0)
2527 continue;
2528 if (match == (size_t)-1)
2529 match = j;
2530 else {
2531 if (oid_cmp(&pool[j].name,
2532 &pool[match].name) < 0)
2533 match = j;
2534 }
2535 }
2536 if (match == (size_t)-1)
2537 errx(1, "%s: unexpected searchrange start: " "(%s-%s)",
2538 test,
2539 oid_print(&start, oid1, sizeof(oid1)),
2540 oid_print(&end, oid2, sizeof(oid2)));
2541 if (searchrange != NULL) {
2542 if (oid_cmp(&searchrange[match].start, &start) != 0 ||
2543 oid_cmp(&searchrange[match].end, &end) != 0 ||
2544 searchrange[match].end.include != end.include ||
2545 searchrange[match].start.include != start.include)
2546 errx(1, "%s: searchrange did not match "
2547 "(%s-%s/%s-%s)", test,
2548 oid_print(&start, oid1, sizeof(oid1)),
2549 oid_print(&end, oid2, sizeof(oid2)),
2550 oid_print(&searchrange[match].start, oid3,
2551 sizeof(oid3)),
2552 oid_print(&searchrange[match].end, oid4,
2553 sizeof(oid4)));
2554 }
2555
2556 varbind[i] = pool[match];
2557 pool[match].name.n_subid = 0;
2558 }
2559 free(pool);
2560 }
2561
2562 /*
2563 * Don't assume a specific sequence of requests here so we can more easily
2564 * migrate to getbulk in agentx.
2565 */
2566 size_t
agentx_getbulk_handle(const char * test,const void * buf,size_t len,uint8_t flags,int32_t sessionid,struct varbind * varbind,size_t nvarbind,struct varbind * outvarbind)2567 agentx_getbulk_handle(const char *test, const void *buf, size_t len,
2568 uint8_t flags, int32_t sessionid, struct varbind *varbind, size_t nvarbind,
2569 struct varbind *outvarbind)
2570 {
2571 const struct header *header = buf;
2572 struct oid start, end, zero = {0};
2573 const uint8_t *u8;
2574 uint16_t nonrep, maxrep;
2575 uint32_t u32;
2576 uint16_t u16;
2577 size_t sublen, i, j, match;
2578 size_t nout = 0;
2579 char oid1[512], oid2[512], oid3[512], oid4[512];
2580
2581 if (len < sizeof(*header))
2582 errx(1, "%s: unexpected pdu message size received: %zu", test, len);
2583 if (header->version != 1)
2584 errx(1, "%s: invalid pdu version", test);
2585 if (header->type != AGENTX_GETNEXT_PDU &&
2586 header->type != AGENTX_GETBULK_PDU)
2587 errx(1, "%s: invalid pdu type received (%hhu/[67])",
2588 test, header->type);
2589 if (header->flags != flags)
2590 errx(1, "%s: invalid get pdu flags received (%hhu/%hhu)",
2591 test, header->flags, flags);
2592 if (header->reserved != 0)
2593 errx(1, "%s: invalid get pdu reserved received", test);
2594 if (p32toh(header, header->sessionid) != sessionid)
2595 errx(1, "%s: unexpected get pdu sessionid (%u/%u)", test,
2596 p32toh(header, header->sessionid), sessionid);
2597 if (p32toh(header, header->payload_length) > len - sizeof(*header))
2598 errx(1, "%s: unexpected get pdu payload length received",
2599 test);
2600
2601 buf += sizeof(*header);
2602 len = p32toh(header, header->payload_length);
2603
2604 if (header->type == AGENTX_GETBULK_PDU) {
2605 if (len < 4)
2606 errx(1, "%s: missing non_repeaters/max_repititions",
2607 __func__);
2608 memcpy(&u16, buf, sizeof(u16));
2609 nonrep = p16toh(header, u16);
2610 memcpy(&u16, buf + sizeof(u16), sizeof(u16));
2611 maxrep = p16toh(header, u16);
2612 buf += 4;
2613 } else {
2614 nonrep = 0;
2615 maxrep = 1;
2616 }
2617 for (i = 0; len > 0; i++) {
2618 sublen = poid(test, header, buf, len, &start);
2619 buf += sublen;
2620 len -= sublen;
2621 sublen = poid(test, header, buf, len, &end);
2622 buf += sublen;
2623 len -= sublen;
2624
2625 if ((start.include != 1 && start.include != 0) ||
2626 end.include != 0)
2627 errx(1, "%s: unexpected searchrange include: (%s-%s)",
2628 test, oid_print(&start, oid1, sizeof(oid1)),
2629 oid_print(&end, oid2, sizeof(oid2)));
2630
2631 match = (size_t)-1;
2632 for (j = 0; j < nvarbind; j++) {
2633 if (oid_cmp(&varbind[j].name, &start) == 0 &&
2634 varbind[j].type == TYPE_ENDOFMIBVIEW) {
2635 match = j;
2636 } else if (oid_cmp(&varbind[j].name, &start) < 0 ||
2637 (!start.include &&
2638 oid_cmp(&varbind[j].name, &start) == 0) ||
2639 oid_cmp(&varbind[j].name, &end) >= 0)
2640 continue;
2641 if (match == (size_t)-1)
2642 match = j;
2643 else {
2644 if (oid_cmp(&varbind[j].name,
2645 &varbind[match].name) < 0)
2646 match = j;
2647 }
2648 }
2649 if (match == (size_t)-1)
2650 errx(1, "%s: unexpected searchrange start: " "(%s-%s)",
2651 test,
2652 oid_print(&start, oid1, sizeof(oid1)),
2653 oid_print(&end, oid2, sizeof(oid2)));
2654 outvarbind[nout++] = varbind[match];
2655 varbind[match] = varbind[--nvarbind];
2656 varbind[nvarbind] = (struct varbind){};
2657 }
2658 return nout;
2659 }
2660
2661 void
agentx_close_validate(const char * test,const void * buf,size_t len,uint8_t flags,uint8_t reason)2662 agentx_close_validate(const char *test, const void *buf, size_t len,
2663 uint8_t flags, uint8_t reason)
2664 {
2665 const struct header *header = buf;
2666 const uint8_t *u8;
2667 uint32_t u32;
2668 uint16_t u16;
2669
2670 if (len != sizeof(*header) + 4)
2671 errx(1, "%s: unexpected pdu message size received: %zu", test, len);
2672 if (header->version != 1)
2673 errx(1, "%s: invalid pdu version", test);
2674 if (header->type != AGENTX_CLOSE_PDU)
2675 errx(1, "%s: invalid pdu type received (%hhu/2)", test, header->type);
2676 if (header->flags != flags)
2677 errx(1, "%s: invalid close pdu flags received (%hhu/%hhu)",
2678 test, header->flags, flags);
2679 if (header->reserved != 0)
2680 errx(1, "%s: invalid close pdu reserved received", test);
2681 if (p32toh(header, header->payload_length) != 4)
2682 errx(1, "%s: unexpected response pdu payload length received",
2683 test);
2684
2685 u8 = buf + sizeof(*header);
2686 if (u8[0] != reason)
2687 errx(1, "%s: unexpected close reason (%hhu/%hhu)",
2688 test, u8[0], reason);
2689 if (u8[1] != 0 || u8[2] != 0 || u8[3] != 0)
2690 errx(1, "%s: invalid close pdu reserved received", test);
2691 }
2692
2693 void
agentx_response_validate(const char * test,const void * buf,size_t len,uint8_t flags,uint32_t packetid,enum error error,uint16_t index,struct varbind * varbindlist,size_t nvarbind)2694 agentx_response_validate(const char *test, const void *buf, size_t len,
2695 uint8_t flags, uint32_t packetid, enum error error, uint16_t index,
2696 struct varbind *varbindlist, size_t nvarbind)
2697 {
2698 const struct header *header = buf;
2699 struct oid name, oid;
2700 int32_t i32;
2701 uint32_t u32;
2702 uint16_t u16, type;
2703 size_t i, sublen;
2704
2705 if (len < sizeof(*header) + 8)
2706 errx(1, "%s: unexpected pdu message size received: %zu", test, len);
2707 if (header->version != 1)
2708 errx(1, "%s: invalid pdu version", test);
2709 if (header->type != AGENTX_RESPONSE_PDU)
2710 errx(1, "%s: invalid pdu type received (%hhu/18)", test, header->type);
2711 if (header->flags != flags)
2712 errx(1, "%s: invalid response pdu flags received (%hhu/%hhu)",
2713 test, header->flags, flags);
2714 if (header->reserved != 0)
2715 errx(1, "%s: invalid response pdu reserved received", test);
2716 if (p32toh(header, header->packetid) != packetid)
2717 errx(1, "%s: invalid response pdu packetid received", test);
2718 /*
2719 * Needs to be changed once we start validating responses with varbinds.
2720 */
2721 if (p32toh(header, header->payload_length) < 8 ||
2722 p32toh(header, header->payload_length) > len - sizeof(*header))
2723 errx(1, "%s: unexpected response pdu payload length received",
2724 test);
2725
2726 buf += sizeof(*header);
2727 len = p32toh(header, header->payload_length);
2728 memcpy(&u32, buf, sizeof(u32));
2729 if ((p32toh(header, u32) & 0xF0000000) != 0)
2730 errx(1, "%s: unexpected response pdu sysUptime received",
2731 test);
2732 buf += sizeof(u32);
2733 memcpy(&u16, buf, sizeof(u16));
2734 if (p16toh(header, u16) != error)
2735 errx(1, "%s: unexpected response pdu error (%hu/%u)",
2736 test, p16toh(header, u16), error);
2737 buf += sizeof(u16);
2738 memcpy(&u16, buf, sizeof(u16));
2739 if (p16toh(header, u16) != index)
2740 errx(1, "%s: unexpected response pdu index (%hu/%hu)",
2741 test, p16toh(header, u16), index);
2742 buf += sizeof(u16);
2743 len -= 8;
2744
2745 for (i = 0; len > 0; i++) {
2746 if (len < 4)
2747 errx(1,
2748 "%s: invalid response pdu varbind length", test);
2749 memcpy(&type, buf, sizeof(type));
2750 type = p16toh(header, type);
2751 if (i < nvarbind && type != varbindlist[i].type % 1000)
2752 errx(1, "%s: invalid response pdu varbind type", test);
2753 buf += sizeof(type);
2754 len -= sizeof(type);
2755 memcpy(&u16, buf, sizeof(u16));
2756 if (u16 != 0)
2757 errx(1, "%s: invalid response pdu varbind reserved",
2758 test);
2759 buf += sizeof(u16);
2760 len -= sizeof(u16);
2761 sublen = poid(test, header, buf, len, &name);
2762 if (i < nvarbind && oid_cmp(&varbindlist[i].name, &name) != 0)
2763 errx(1, "%s: invalid response pdu varbind name", test);
2764 buf += sublen;
2765 len -= sublen;
2766 switch (type % 1000) {
2767 case TYPE_INTEGER:
2768 if (len < sizeof(i32))
2769 errx(1,
2770 "%s: invalid response pdu varbind length",
2771 test);
2772 if (i < nvarbind && varbindlist[i].type / 1000 == 0) {
2773 memcpy(&i32, buf, sizeof(i32));
2774 i32 = p32toh(header, i32);
2775 if (i32 != varbindlist[i].data.int32)
2776 errx(1, "%s: invalid response pdu "
2777 "varbind integer", test);
2778 }
2779 break;
2780 default:
2781 errx(1, "%s: Regress test not implemented: %d", test, type);
2782 }
2783 }
2784
2785 if (i != nvarbind)
2786 errx(1, "%s: unexpected response pdu nvarbind: (%zu/%zu)",
2787 test, i, nvarbind);
2788 }
2789
2790 int
agentx_connect(const char * path)2791 agentx_connect(const char *path)
2792 {
2793 struct sockaddr_un sun;
2794 int s;
2795
2796 if (path == NULL)
2797 path = AGENTX_SOCKET;
2798
2799 sun.sun_len = sizeof(sun);
2800 sun.sun_family = AF_UNIX;
2801 strlcpy(sun.sun_path, path, sizeof(sun.sun_path));
2802
2803 if ((s = socket(AF_UNIX, SOCK_STREAM, 0)) == -1)
2804 err(1, "%s: socket", __func__);
2805 if (connect(s, (struct sockaddr *)&sun, sizeof(sun)) == -1)
2806 err(1, "%s: connect", __func__);
2807
2808 return s;
2809 }
2810
2811 uint32_t
agentx_open(int s,int nbo,uint8_t timeout,uint32_t oid[],size_t oidlen,const char * descr)2812 agentx_open(int s, int nbo, uint8_t timeout, uint32_t oid[], size_t oidlen,
2813 const char *descr)
2814 {
2815 struct message msg ={};
2816 char zero[3] = {};
2817 char repl[1024];
2818 size_t n;
2819 uint32_t packetid = arc4random();
2820 struct header *header = (struct header *)repl;
2821
2822 message_add_header(&msg, 1, AGENTX_OPEN_PDU,
2823 nbo ? NETWORK_BYTE_ORDER : 0, 0, 0, packetid);
2824 message_add_uint8(&msg, timeout);
2825 message_add(&msg, zero, 3);
2826 message_add_oid(&msg, oid, oidlen, 0);
2827 message_add_nstring(&msg, descr, strlen(descr));
2828
2829 agentx_write(s, &msg);
2830 n = agentx_read(s, repl, sizeof(repl), 1000);
2831
2832 agentx_response_validate(__func__, repl, n,
2833 nbo ? NETWORK_BYTE_ORDER : 0, packetid, 0, 0, NULL, 0);
2834
2835 message_release(&msg);
2836
2837 return p32toh(header, header->sessionid);
2838 }
2839
2840 void
agentx_close(int s,uint32_t sessionid,enum close_reason reason)2841 agentx_close(int s, uint32_t sessionid, enum close_reason reason)
2842 {
2843 struct message msg ={};
2844 char zero[3] = {};
2845 char repl[1024];
2846 size_t n;
2847 uint32_t packetid = arc4random();
2848 struct header *header = (struct header *)repl;
2849
2850 message_add_header(&msg, 1, AGENTX_CLOSE_PDU, 0, sessionid, 0,
2851 packetid);
2852 message_add_uint8(&msg, reason);
2853 message_add(&msg, zero, 3);
2854
2855 agentx_write(s, &msg);
2856 n = agentx_read(s, repl, sizeof(repl), 1000);
2857
2858 agentx_response_validate(__func__, repl, n, 0, packetid, 0, 0, NULL, 0);
2859
2860 message_release(&msg);
2861 }
2862
2863 void
agentx_register(int s,uint32_t sessionid,uint8_t instance,uint8_t timeout,uint8_t priority,uint8_t range_subid,uint32_t oid[],size_t oidlen,uint32_t upperbound)2864 agentx_register(int s, uint32_t sessionid, uint8_t instance, uint8_t timeout,
2865 uint8_t priority, uint8_t range_subid, uint32_t oid[], size_t oidlen,
2866 uint32_t upperbound)
2867 {
2868 struct message msg = {};
2869 char repl[1024];
2870 size_t n;
2871 uint32_t packetid = arc4random();
2872 uint8_t reserved = 0;
2873
2874 message_add_header(&msg, 1, AGENTX_REGISTER_PDU,
2875 instance ? INSTANCE_REGISTRATION : 0, sessionid, 0, packetid);
2876 message_add(&msg, &timeout, sizeof(timeout));
2877 message_add(&msg, &priority, sizeof(priority));
2878 message_add(&msg, &range_subid, sizeof(range_subid));
2879 message_add(&msg, &reserved, sizeof(reserved));
2880 message_add_oid(&msg, oid, oidlen, 0);
2881 if (range_subid != 0)
2882 message_add_uint32(&msg, upperbound);
2883
2884 agentx_write(s, &msg);
2885
2886 n = agentx_read(s, repl, sizeof(repl), 1000);
2887
2888 agentx_response_validate(__func__, repl, n, 0, packetid, NOAGENTXERROR, 0,
2889 NULL, 0);
2890 message_release(&msg);
2891 }
2892
2893 void
agentx_response(int s,void * buf,enum error error,uint16_t index,struct varbind * varbindlist,size_t nvarbind)2894 agentx_response(int s, void *buf, enum error error, uint16_t index,
2895 struct varbind *varbindlist, size_t nvarbind)
2896 {
2897 struct header *header = buf;
2898 struct message msg = {};
2899 char repl[1024];
2900 size_t n;
2901 uint32_t sysuptime = 0;
2902 uint16_t reserved = 0;
2903 size_t i;
2904
2905 message_add_header(&msg, 1, AGENTX_RESPONSE_PDU, 0,
2906 p32toh(header, header->sessionid),
2907 p32toh(header, header->transactionid),
2908 p32toh(header, header->packetid));
2909 message_add_uint32(&msg, sysuptime);
2910 message_add_uint16(&msg, error);
2911 message_add_uint16(&msg, index);
2912
2913 for (i = 0; i < nvarbind; i++)
2914 message_add_varbind(&msg, varbindlist + i);
2915
2916 agentx_write(s, &msg);
2917 message_release(&msg);
2918 }
2919
2920 static void
message_add_uint8(struct message * msg,uint8_t n)2921 message_add_uint8(struct message *msg, uint8_t n)
2922 {
2923 message_add(msg, &n, 1);
2924 }
2925
2926 static void
message_add_uint16(struct message * msg,uint16_t n)2927 message_add_uint16(struct message *msg, uint16_t n)
2928 {
2929 if (MESSAGE_NBO(msg))
2930 n = htobe16(n);
2931 else
2932 n = htole16(n);
2933
2934 message_add(msg, &n, sizeof(n));
2935 }
2936
2937 static void
message_add_uint32(struct message * msg,uint32_t n)2938 message_add_uint32(struct message *msg, uint32_t n)
2939 {
2940 if (MESSAGE_NBO(msg))
2941 n = htobe32(n);
2942 else
2943 n = htole32(n);
2944
2945 message_add(msg, &n, sizeof(n));
2946 }
2947
2948 static void
message_add_uint64(struct message * msg,uint64_t n)2949 message_add_uint64(struct message *msg, uint64_t n)
2950 {
2951 if (MESSAGE_NBO(msg))
2952 n = htobe64(n);
2953 else
2954 n = htole64(n);
2955
2956 message_add(msg, &n, sizeof(n));
2957 }
2958
2959 static void
message_add_nstring(struct message * msg,const void * src,uint32_t len)2960 message_add_nstring(struct message *msg, const void *src, uint32_t len)
2961 {
2962 char zero[3] = {};
2963
2964 message_add_uint32(msg, len);
2965 if (len == 0)
2966 return;
2967 message_add(msg, src, len);
2968 message_add(msg, zero, (4 - (len % 4)) % 4);
2969 }
2970
2971 static void
message_add_oid(struct message * msg,const uint32_t oid[],uint8_t n_subid,uint8_t include)2972 message_add_oid(struct message *msg, const uint32_t oid[], uint8_t n_subid,
2973 uint8_t include)
2974 {
2975 uint8_t prefix = 0;
2976 uint8_t i;
2977
2978 if (n_subid > 5 && oid[0] == 1 && oid[1] == 3 && oid[2] == 6 &&
2979 oid[3] == 1 && oid[4] < UINT8_MAX) {
2980 prefix = oid[4];
2981 oid += 5;
2982 n_subid -= 5;
2983 }
2984
2985 message_add_uint8(msg, n_subid);
2986 message_add_uint8(msg, prefix);
2987 message_add_uint8(msg, include);
2988 message_add_uint8(msg, 0);
2989 for (i = 0; i < n_subid; i++)
2990 message_add_uint32(msg, oid[i]);
2991 }
2992
2993 static void
message_add_varbind(struct message * msg,struct varbind * varbind)2994 message_add_varbind(struct message *msg, struct varbind *varbind)
2995 {
2996 uint64_t u64;
2997 uint32_t u32;
2998 size_t len;
2999 va_list ap;
3000
3001 message_add_uint16(msg, varbind->type);
3002 message_add_uint16(msg, 0);
3003 message_add_oid(msg, varbind->name.subid, varbind->name.n_subid, 0);
3004 switch (varbind->type) {
3005 case INTEGER:
3006 message_add_uint32(msg, varbind->data.int32);
3007 break;
3008 case COUNTER32:
3009 case GAUGE32:
3010 case TIMETICKS:
3011 message_add_uint32(msg, varbind->data.uint32);
3012 break;
3013 case OCTETSTRING:
3014 case IPADDRESS:
3015 case OPAQUE:
3016 message_add_nstring(msg, varbind->data.octetstring.string,
3017 varbind->data.octetstring.len);
3018 break;
3019 case OBJECTIDENTIFIER:
3020 message_add_oid(msg, varbind->data.oid.subid,
3021 varbind->data.oid.n_subid, 0);
3022 break;
3023 case COUNTER64:
3024 message_add_uint64(msg, varbind->data.uint64);
3025 break;
3026 case AXNULL:
3027 case NOSUCHOBJECT:
3028 case NOSUCHINSTANCE:
3029 case ENDOFMIBVIEW:
3030 break;
3031 default:
3032 errx(1, "%s: unsupported data type: %d", __func__,
3033 varbind->type);
3034 }
3035 }
3036
3037 static void
message_add_header(struct message * msg,uint8_t version,uint8_t type,uint8_t flags,uint32_t sessionid,uint32_t transactionid,uint32_t packetid)3038 message_add_header(struct message *msg, uint8_t version, uint8_t type,
3039 uint8_t flags, uint32_t sessionid, uint32_t transactionid,
3040 uint32_t packetid)
3041 {
3042 if (msg->len != 0)
3043 errx(1, "%s: message not new", __func__);
3044 message_add_uint8(msg, version);
3045 message_add_uint8(msg, type);
3046 message_add_uint8(msg, flags);
3047 message_add_uint8(msg, 0);
3048 message_add_uint32(msg, sessionid);
3049 message_add_uint32(msg, transactionid);
3050 message_add_uint32(msg, packetid);
3051 message_add_uint32(msg, 0); /* payload_length tbt */
3052 }
3053
3054 static void
message_add(struct message * msg,const void * src,size_t len)3055 message_add(struct message *msg, const void *src, size_t len)
3056 {
3057 if (len == 0)
3058 return;
3059 if (msg->len + len > msg->size) {
3060 if ((msg->buf = recallocarray(msg->buf, msg->size,
3061 (((msg->len + len) % 4096) + 1) * 4096, 1)) == NULL)
3062 err(1, NULL);
3063 msg->size = (((msg->len + len) % 4096) + 1) * 4096;
3064 }
3065 memcpy(msg->buf + msg->len, src, len);
3066 msg->len += len;
3067 }
3068
3069 static void
message_release(struct message * msg)3070 message_release(struct message *msg)
3071 {
3072 free(msg->buf);
3073 }
3074
3075 static size_t
poid(const char * test,const struct header * header,const uint8_t * buf,size_t len,struct oid * oid)3076 poid(const char *test, const struct header *header, const uint8_t *buf, size_t len,
3077 struct oid *oid)
3078 {
3079 uint8_t n_subid, i;
3080 uint32_t subid;
3081
3082 if (len < 4)
3083 errx(1, "%s: incomplete oid", test);
3084 n_subid = buf[0];
3085 if (buf[1] != 0) {
3086 *oid = OID_STRUCT(1, 3, 6, 1, buf[1]);
3087 } else
3088 *oid = OID_STRUCT();
3089 oid->include = buf[2];
3090 if (buf[3] != 0)
3091 errx(1, "%s: invalid oid reserved (%hhx)", test, buf[3]);
3092 buf += 4;
3093 len -= 4;
3094 if (oid->n_subid + n_subid > 128)
3095 errx(1, "%s: too many n_subid in oid", test);
3096 if (len < n_subid * sizeof(oid->subid[0]))
3097 errx(1, "%s: incomplete oid: (%zu/%zu)", test,
3098 n_subid * sizeof(oid->subid[0]), len);
3099 for (i = 0; i < n_subid; i++) {
3100 memcpy(&subid, buf, sizeof(subid));
3101 buf += 4;
3102 oid->subid[oid->n_subid++] = p32toh(header, subid);
3103 }
3104
3105 return 4 * (n_subid + 1);
3106 }
3107
3108 size_t
agentx_read(int s,void * buf,size_t len,int timeout)3109 agentx_read(int s, void *buf, size_t len, int timeout)
3110 {
3111 ssize_t n;
3112 size_t i;
3113 int ret;
3114 struct pollfd pfd = {
3115 .fd = s,
3116 .events = POLLIN
3117 };
3118
3119 if ((ret = poll(&pfd, 1, timeout)) == -1)
3120 err(1, "poll");
3121 if (ret == 0)
3122 errx(1, "%s: timeout", __func__);
3123 if ((n = read(s, buf, len)) == -1)
3124 err(1, "agentx read");
3125
3126 if (verbose && n != 0) {
3127 printf("AgentX received(%d):\n", s);
3128 for (i = 0; i < n; i++) {
3129 printf("%s%02hhx", i % 4 == 0 ? "" : " ",
3130 ((char *)buf)[i]);
3131 if (i % 4 == 3)
3132 printf("\n");
3133 }
3134 if (i % 4 != 0)
3135 printf("\n");
3136 }
3137 return n;
3138 }
3139
3140 void
agentx_timeout(int s,int timeout)3141 agentx_timeout(int s, int timeout)
3142 {
3143 int ret;
3144 struct pollfd pfd = {
3145 .fd = s,
3146 .events = POLLIN
3147 };
3148
3149 if ((ret = poll(&pfd, 1, timeout)) == -1)
3150 err(1, "poll");
3151 if (ret != 0)
3152 errx(1, "%s: unexpected agentx data", __func__);
3153 }
3154
3155 void
agentx_write(int s,struct message * msg)3156 agentx_write(int s, struct message *msg)
3157 {
3158 ssize_t n;
3159 char *buf = msg->buf;
3160 size_t len = msg->len;
3161 struct header *header = msg->buf;
3162 size_t i;
3163
3164 msg->len = 16;
3165 message_add_uint32(msg, len - sizeof(*header));
3166
3167 if (verbose) {
3168 printf("AgentX sending(%d):\n", s);
3169 for (i = 0; i < len; i++) {
3170 printf("%s%02hhx", i % 4 == 0 ? "" : " ", buf[i]);
3171 if (i % 4 == 3)
3172 printf("\n");
3173 }
3174 if (i % 4 != 0)
3175 printf("\n");
3176 }
3177
3178 while (len > 0) {
3179 if ((n = write(s, buf, len)) == -1)
3180 err(1, "agentx write");
3181 buf += n;
3182 len -= n;
3183 }
3184 msg->len = 0;
3185 }
3186