1 /* $MirOS: src/sbin/isakmpd/message.c,v 1.4 2005/11/23 16:43:58 tg Exp $ */
2 /* $OpenBSD: message.c,v 1.114 2005/07/20 16:50:43 moritz Exp $ */
3 /* $EOM: message.c,v 1.156 2000/10/10 12:36:39 provos Exp $ */
4
5 /*
6 * Copyright (c) 1998, 1999, 2000, 2001 Niklas Hallqvist. All rights reserved.
7 * Copyright (c) 1999 Angelos D. Keromytis. All rights reserved.
8 * Copyright (c) 1999, 2000, 2001, 2004 H�kan Olsson. All rights reserved.
9 *
10 * Redistribution and use in source and binary forms, with or without
11 * modification, are permitted provided that the following conditions
12 * are met:
13 * 1. Redistributions of source code must retain the above copyright
14 * notice, this list of conditions and the following disclaimer.
15 * 2. Redistributions in binary form must reproduce the above copyright
16 * notice, this list of conditions and the following disclaimer in the
17 * documentation and/or other materials provided with the distribution.
18 *
19 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR
20 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
21 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
22 * IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
23 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
24 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
25 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
26 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
27 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
28 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
29 */
30
31 /*
32 * This code was written under funding by Ericsson Radio Systems.
33 */
34
35 #include <sys/types.h>
36 #include <sys/socket.h>
37 #include <netinet/in.h>
38 #include <arpa/inet.h>
39 #include <stdlib.h>
40 #include <string.h>
41
42 #include "attribute.h"
43 #include "cert.h"
44 #include "constants.h"
45 #include "crypto.h"
46 #include "doi.h"
47 #include "dpd.h"
48 #include "exchange.h"
49 #include "field.h"
50 #include "hash.h"
51 #include "ipsec.h"
52 #include "ipsec_num.h"
53 #include "isakmp.h"
54 #include "log.h"
55 #include "message.h"
56 #include "nat_traversal.h"
57 #include "prf.h"
58 #include "sa.h"
59 #include "timer.h"
60 #include "transport.h"
61 #include "util.h"
62 #include "virtual.h"
63
64 __RCSID("$MirOS: src/sbin/isakmpd/message.c,v 1.4 2005/11/23 16:43:58 tg Exp $");
65
66 /* A local set datatype, coincidentally fd_set suits our purpose fine. */
67 typedef fd_set set;
68 #define ISSET FD_ISSET
69 #define SET FD_SET
70 #define ZERO FD_ZERO
71
72 static int message_check_duplicate(struct message *);
73 static int message_encrypt(struct message *);
74 static int message_index_payload(struct message *, struct payload *,
75 u_int8_t ,u_int8_t *);
76 static int message_parse_transform(struct message *, struct payload *,
77 u_int8_t, u_int8_t *);
78 static struct field *message_get_field(u_int8_t);
79 static int message_validate_payload(struct message *, struct payload *,
80 u_int8_t);
81 static u_int16_t message_payload_sz(u_int8_t);
82 static int message_validate_attribute(struct message *, struct payload *);
83 static int message_validate_cert(struct message *, struct payload *);
84 static int message_validate_cert_req(struct message *, struct payload *);
85 static int message_validate_delete(struct message *, struct payload *);
86 static int message_validate_hash(struct message *, struct payload *);
87 static int message_validate_id(struct message *, struct payload *);
88 static int message_validate_key_exch(struct message *, struct payload *);
89 static int message_validate_nat_d(struct message *, struct payload *);
90 static int message_validate_nat_oa(struct message *, struct payload *);
91 static int message_validate_nonce(struct message *, struct payload *);
92 static int message_validate_notify(struct message *, struct payload *);
93 static int message_validate_proposal(struct message *, struct payload *);
94 static int message_validate_sa(struct message *, struct payload *);
95 static int message_validate_sig(struct message *, struct payload *);
96 static int message_validate_transform(struct message *, struct payload *);
97 static int message_validate_vendor(struct message *, struct payload *);
98
99 static void message_packet_log(struct message *);
100
101 /*
102 * Fields used for checking monotonic increasing of proposal and transform
103 * numbers.
104 */
105 static u_int8_t *last_sa = 0;
106 static u_int32_t last_prop_no;
107 static u_int8_t *last_prop = 0;
108 static u_int32_t last_xf_no;
109
110 /*
111 * Allocate a message structure bound to transport T, and with a first
112 * segment buffer sized SZ, copied from BUF if given.
113 */
114 struct message *
message_alloc(struct transport * t,u_int8_t * buf,size_t sz)115 message_alloc(struct transport *t, u_int8_t *buf, size_t sz)
116 {
117 struct message *msg;
118 int i;
119
120 /*
121 * We use calloc(3) because it zeroes the structure which we rely on in
122 * message_free when determining what sub-allocations to free.
123 */
124 msg = (struct message *)calloc(1, sizeof *msg);
125 if (!msg)
126 return 0;
127 msg->iov = calloc(1, sizeof *msg->iov);
128 if (!msg->iov) {
129 message_free(msg);
130 return 0;
131 }
132 msg->iov[0].iov_len = sz;
133 msg->iov[0].iov_base = malloc(sz);
134 if (!msg->iov[0].iov_base) {
135 message_free(msg);
136 return 0;
137 }
138 msg->iovlen = 1;
139 if (buf)
140 memcpy(msg->iov[0].iov_base, buf, sz);
141 msg->nextp = (u_int8_t *)msg->iov[0].iov_base +
142 ISAKMP_HDR_NEXT_PAYLOAD_OFF;
143 msg->transport = t;
144 transport_reference(t);
145 msg->payload = (struct payload_head *)calloc(ISAKMP_PAYLOAD_MAX,
146 sizeof *msg->payload);
147 if (!msg->payload) {
148 message_free(msg);
149 return 0;
150 }
151 for (i = 0; i < ISAKMP_PAYLOAD_MAX; i++)
152 TAILQ_INIT(&msg->payload[i]);
153 TAILQ_INIT(&msg->post_send);
154 LOG_DBG((LOG_MESSAGE, 90, "message_alloc: allocated %p", msg));
155 return msg;
156 }
157
158 /*
159 * Allocate a message suitable for a reply to MSG. Just allocate an empty
160 * ISAKMP header as the first segment.
161 */
162 struct message *
message_alloc_reply(struct message * msg)163 message_alloc_reply(struct message *msg)
164 {
165 struct message *reply;
166
167 reply = message_alloc(msg->transport, 0, ISAKMP_HDR_SZ);
168 reply->exchange = msg->exchange;
169 reply->isakmp_sa = msg->isakmp_sa;
170 if (msg->isakmp_sa)
171 sa_reference(msg->isakmp_sa);
172 return reply;
173 }
174
175 /* Free up all resources used by the MSG message. */
176 void
message_free(struct message * msg)177 message_free(struct message *msg)
178 {
179 u_int32_t i;
180 struct payload *payload;
181
182 LOG_DBG((LOG_MESSAGE, 20, "message_free: freeing %p", msg));
183 if (!msg)
184 return;
185 if (msg->iov) {
186 if (msg->orig && msg->orig != (u_int8_t *)msg->iov[0].iov_base)
187 free(msg->orig);
188 for (i = 0; i < msg->iovlen; i++)
189 if (msg->iov[i].iov_base)
190 free(msg->iov[i].iov_base);
191 free(msg->iov);
192 }
193 if (msg->retrans)
194 timer_remove_event(msg->retrans);
195 if (msg->payload) {
196 for (i = 0; i < ISAKMP_PAYLOAD_MAX; i++)
197 while ((payload = TAILQ_FIRST(&msg->payload[i]))) {
198 TAILQ_REMOVE(&msg->payload[i], payload, link);
199 free(payload);
200 }
201 free(msg->payload);
202 }
203 while (TAILQ_FIRST(&msg->post_send) != 0)
204 TAILQ_REMOVE(&msg->post_send, TAILQ_FIRST(&msg->post_send),
205 link);
206
207 if (msg->transport) {
208 /* If we are on the send queue, remove us from there. */
209 if (msg->flags & MSG_IN_TRANSIT)
210 TAILQ_REMOVE(msg->transport->vtbl->get_queue(msg),
211 msg, link);
212
213 transport_release(msg->transport);
214 }
215
216 if (msg->isakmp_sa)
217 sa_release(msg->isakmp_sa);
218
219 free(msg);
220 }
221
222 /*
223 * Generic ISAKMP parser.
224 * MSG is the ISAKMP message to be parsed. NEXT is the type of the first
225 * payload to be parsed, and it's pointed to by BUF. ACCEPTED_PAYLOADS
226 * tells what payloads are accepted and FUNC is a pointer to a function
227 * to be called for each payload found. Returns the total length of the
228 * parsed payloads.
229 */
230 static int
message_parse_payloads(struct message * msg,struct payload * p,u_int8_t next,u_int8_t * buf,set * accepted_payloads,int (* func)(struct message *,struct payload *,u_int8_t,u_int8_t *))231 message_parse_payloads(struct message *msg, struct payload *p, u_int8_t next,
232 u_int8_t *buf, set *accepted_payloads, int (*func)(struct message *,
233 struct payload *, u_int8_t, u_int8_t *))
234 {
235 u_int8_t payload;
236 u_int16_t len;
237 int sz = 0;
238
239 do {
240 LOG_DBG((LOG_MESSAGE, 50,
241 "message_parse_payloads: offset %ld payload %s",
242 (long)(buf - (u_int8_t *) msg->iov[0].iov_base),
243 constant_name(isakmp_payload_cst, next)));
244
245 /* Does this payload's header fit? */
246 if (buf + ISAKMP_GEN_SZ > (u_int8_t *)msg->iov[0].iov_base +
247 msg->iov[0].iov_len) {
248 log_print("message_parse_payloads: short message");
249 message_drop(msg,
250 ISAKMP_NOTIFY_UNEQUAL_PAYLOAD_LENGTHS, 0, 1, 1);
251 return -1;
252 }
253 /* Ponder on the payload that is at BUF... */
254 payload = next;
255
256 /* Look at the next payload's type. */
257 next = GET_ISAKMP_GEN_NEXT_PAYLOAD(buf);
258 if (next >= ISAKMP_PAYLOAD_RESERVED_MIN &&
259 next <= ISAKMP_PAYLOAD_RESERVED_MAX) {
260 log_print("message_parse_payloads: invalid next "
261 "payload type %s in payload of type %d",
262 constant_name(isakmp_payload_cst, next), payload);
263 message_drop(msg, ISAKMP_NOTIFY_INVALID_PAYLOAD_TYPE,
264 0, 1, 1);
265 return -1;
266 }
267 /* Reserved fields in ISAKMP messages should be zero. */
268 if (GET_ISAKMP_GEN_RESERVED(buf) != 0) {
269 log_print("message_parse_payloads: reserved field "
270 "non-zero: %x", GET_ISAKMP_GEN_RESERVED(buf));
271 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED,
272 0, 1, 1);
273 return -1;
274 }
275 /*
276 * Decode and validate the payload length field.
277 */
278 len = GET_ISAKMP_GEN_LENGTH(buf);
279
280 if (message_payload_sz(payload) == 0) {
281 log_print("message_parse_payloads: unknown minimum "
282 "payload size for payload type %s",
283 constant_name(isakmp_payload_cst, payload));
284 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED,
285 0, 1, 1);
286 return -1;
287 }
288 if (len < message_payload_sz(payload)) {
289 log_print("message_parse_payloads: payload too "
290 "short: %u", len);
291 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED,
292 0, 1, 1);
293 return -1;
294 }
295 if (buf + len > (u_int8_t *)msg->iov[0].iov_base +
296 msg->iov[0].iov_len) {
297 log_print("message_parse_payloads: payload too "
298 "long: %u", len);
299 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED,
300 0, 1, 1);
301 return -1;
302 }
303 /* Ignore most private payloads. */
304 if (next >= ISAKMP_PAYLOAD_PRIVATE_MIN &&
305 next != ISAKMP_PAYLOAD_NAT_D_DRAFT &&
306 next != ISAKMP_PAYLOAD_NAT_OA_DRAFT) {
307 LOG_DBG((LOG_MESSAGE, 30, "message_parse_payloads: "
308 "private next payload type %s in payload of "
309 "type %d ignored",
310 constant_name(isakmp_payload_cst, next), payload));
311 goto next_payload;
312 }
313 /*
314 * Check if the current payload is one of the accepted ones at
315 * this stage.
316 */
317 if (!ISSET(payload, accepted_payloads)) {
318 log_print("message_parse_payloads: payload type %s "
319 "unexpected", constant_name(isakmp_payload_cst,
320 payload));
321 message_drop(msg, ISAKMP_NOTIFY_INVALID_PAYLOAD_TYPE,
322 0, 1, 1);
323 return -1;
324 }
325 /* Call the payload handler specified by the caller. */
326 if (func(msg, p, payload, buf))
327 return -1;
328
329 next_payload:
330 /* Advance to next payload. */
331 buf += len;
332 sz += len;
333 } while (next != ISAKMP_PAYLOAD_NONE);
334 return sz;
335 }
336
337 /*
338 * Parse a proposal payload found in message MSG. PAYLOAD is always
339 * ISAKMP_PAYLOAD_PROPOSAL and ignored in here. It's needed as the API for
340 * message_parse_payloads requires it. BUF points to the proposal's
341 * generic payload header.
342 */
343 static int
message_parse_proposal(struct message * msg,struct payload * p,u_int8_t payload,u_int8_t * buf)344 message_parse_proposal(struct message *msg, struct payload *p,
345 u_int8_t payload, u_int8_t *buf)
346 {
347 set payload_set;
348
349 /* Put the proposal into the proposal bucket. */
350 message_index_payload(msg, p, payload, buf);
351
352 ZERO(&payload_set);
353 SET(ISAKMP_PAYLOAD_TRANSFORM, &payload_set);
354 if (message_parse_payloads(msg,
355 TAILQ_LAST(&msg->payload[ISAKMP_PAYLOAD_PROPOSAL], payload_head),
356 ISAKMP_PAYLOAD_TRANSFORM, buf + ISAKMP_PROP_SPI_OFF +
357 GET_ISAKMP_PROP_SPI_SZ(buf), &payload_set, message_parse_transform)
358 == -1)
359 return -1;
360
361 return 0;
362 }
363
364 static int
message_parse_transform(struct message * msg,struct payload * p,u_int8_t payload,u_int8_t * buf)365 message_parse_transform(struct message *msg, struct payload *p,
366 u_int8_t payload, u_int8_t *buf)
367 {
368 /* Put the transform into the transform bucket. */
369 message_index_payload(msg, p, payload, buf);
370
371 LOG_DBG((LOG_MESSAGE, 50, "Transform %d's attributes",
372 GET_ISAKMP_TRANSFORM_NO(buf)));
373 attribute_map(buf + ISAKMP_TRANSFORM_SA_ATTRS_OFF,
374 GET_ISAKMP_GEN_LENGTH(buf) - ISAKMP_TRANSFORM_SA_ATTRS_OFF,
375 msg->exchange->doi->debug_attribute, msg);
376
377 return 0;
378 }
379
380 static struct field *
message_get_field(u_int8_t payload)381 message_get_field(u_int8_t payload)
382 {
383 switch (payload) {
384 case ISAKMP_PAYLOAD_SA:
385 return isakmp_sa_fld;
386 case ISAKMP_PAYLOAD_PROPOSAL:
387 return isakmp_prop_fld;
388 case ISAKMP_PAYLOAD_TRANSFORM:
389 return isakmp_transform_fld;
390 case ISAKMP_PAYLOAD_KEY_EXCH:
391 return isakmp_ke_fld;
392 case ISAKMP_PAYLOAD_ID:
393 return isakmp_id_fld;
394 case ISAKMP_PAYLOAD_CERT:
395 return isakmp_cert_fld;
396 case ISAKMP_PAYLOAD_CERT_REQ:
397 return isakmp_certreq_fld;
398 case ISAKMP_PAYLOAD_HASH:
399 return isakmp_hash_fld;
400 case ISAKMP_PAYLOAD_SIG:
401 return isakmp_sig_fld;
402 case ISAKMP_PAYLOAD_NONCE:
403 return isakmp_nonce_fld;
404 case ISAKMP_PAYLOAD_NOTIFY:
405 return isakmp_notify_fld;
406 case ISAKMP_PAYLOAD_DELETE:
407 return isakmp_delete_fld;
408 case ISAKMP_PAYLOAD_VENDOR:
409 return isakmp_vendor_fld;
410 case ISAKMP_PAYLOAD_ATTRIBUTE:
411 return isakmp_attribute_fld;
412 case ISAKMP_PAYLOAD_NAT_D:
413 case ISAKMP_PAYLOAD_NAT_D_DRAFT:
414 return isakmp_nat_d_fld;
415 case ISAKMP_PAYLOAD_NAT_OA:
416 case ISAKMP_PAYLOAD_NAT_OA_DRAFT:
417 return isakmp_nat_oa_fld;
418 /* Not yet supported and any other unknown payloads. */
419 case ISAKMP_PAYLOAD_SAK:
420 case ISAKMP_PAYLOAD_SAT:
421 case ISAKMP_PAYLOAD_KD:
422 case ISAKMP_PAYLOAD_SEQ:
423 case ISAKMP_PAYLOAD_POP:
424 default:
425 break;
426 }
427 return NULL;
428 }
429
430 static int
message_validate_payload(struct message * m,struct payload * p,u_int8_t payload)431 message_validate_payload(struct message *m, struct payload *p, u_int8_t payload)
432 {
433 switch (payload) {
434 case ISAKMP_PAYLOAD_SA:
435 return message_validate_sa(m, p);
436 case ISAKMP_PAYLOAD_PROPOSAL:
437 return message_validate_proposal(m, p);
438 case ISAKMP_PAYLOAD_TRANSFORM:
439 return message_validate_transform(m, p);
440 case ISAKMP_PAYLOAD_KEY_EXCH:
441 return message_validate_key_exch(m, p);
442 case ISAKMP_PAYLOAD_ID:
443 return message_validate_id(m, p);
444 case ISAKMP_PAYLOAD_CERT:
445 return message_validate_cert(m, p);
446 case ISAKMP_PAYLOAD_CERT_REQ:
447 return message_validate_cert_req(m, p);
448 case ISAKMP_PAYLOAD_HASH:
449 return message_validate_hash(m, p);
450 case ISAKMP_PAYLOAD_SIG:
451 return message_validate_sig(m, p);
452 case ISAKMP_PAYLOAD_NONCE:
453 return message_validate_nonce(m, p);
454 case ISAKMP_PAYLOAD_NOTIFY:
455 return message_validate_notify(m, p);
456 case ISAKMP_PAYLOAD_DELETE:
457 return message_validate_delete(m, p);
458 case ISAKMP_PAYLOAD_VENDOR:
459 return message_validate_vendor(m, p);
460 case ISAKMP_PAYLOAD_ATTRIBUTE:
461 return message_validate_attribute(m, p);
462 case ISAKMP_PAYLOAD_NAT_D:
463 case ISAKMP_PAYLOAD_NAT_D_DRAFT:
464 return message_validate_nat_d(m, p);
465 case ISAKMP_PAYLOAD_NAT_OA:
466 case ISAKMP_PAYLOAD_NAT_OA_DRAFT:
467 return message_validate_nat_oa(m, p);
468 /* Not yet supported and any other unknown payloads. */
469 case ISAKMP_PAYLOAD_SAK:
470 case ISAKMP_PAYLOAD_SAT:
471 case ISAKMP_PAYLOAD_KD:
472 case ISAKMP_PAYLOAD_SEQ:
473 case ISAKMP_PAYLOAD_POP:
474 default:
475 break;
476 }
477 return -1;
478 }
479
480 /* Check payloads for their required minimum size. */
481 static u_int16_t
message_payload_sz(u_int8_t payload)482 message_payload_sz(u_int8_t payload)
483 {
484 switch (payload) {
485 case ISAKMP_PAYLOAD_SA:
486 return ISAKMP_SA_SZ;
487 case ISAKMP_PAYLOAD_PROPOSAL:
488 return ISAKMP_PROP_SZ;
489 case ISAKMP_PAYLOAD_TRANSFORM:
490 return ISAKMP_TRANSFORM_SZ;
491 case ISAKMP_PAYLOAD_KEY_EXCH:
492 return ISAKMP_KE_SZ;
493 case ISAKMP_PAYLOAD_ID:
494 return ISAKMP_ID_SZ;
495 case ISAKMP_PAYLOAD_CERT:
496 return ISAKMP_CERT_SZ;
497 case ISAKMP_PAYLOAD_CERT_REQ:
498 return ISAKMP_CERTREQ_SZ;
499 case ISAKMP_PAYLOAD_HASH:
500 return ISAKMP_HASH_SZ;
501 case ISAKMP_PAYLOAD_SIG:
502 return ISAKMP_SIG_SZ;
503 case ISAKMP_PAYLOAD_NONCE:
504 return ISAKMP_NONCE_SZ;
505 case ISAKMP_PAYLOAD_NOTIFY:
506 return ISAKMP_NOTIFY_SZ;
507 case ISAKMP_PAYLOAD_DELETE:
508 return ISAKMP_DELETE_SZ;
509 case ISAKMP_PAYLOAD_VENDOR:
510 return ISAKMP_VENDOR_SZ;
511 case ISAKMP_PAYLOAD_ATTRIBUTE:
512 return ISAKMP_ATTRIBUTE_SZ;
513 case ISAKMP_PAYLOAD_NAT_D:
514 case ISAKMP_PAYLOAD_NAT_D_DRAFT:
515 return ISAKMP_NAT_D_SZ;
516 case ISAKMP_PAYLOAD_NAT_OA:
517 case ISAKMP_PAYLOAD_NAT_OA_DRAFT:
518 return ISAKMP_NAT_OA_SZ;
519 /* Not yet supported and any other unknown payloads. */
520 case ISAKMP_PAYLOAD_SAK:
521 case ISAKMP_PAYLOAD_SAT:
522 case ISAKMP_PAYLOAD_KD:
523 case ISAKMP_PAYLOAD_SEQ:
524 case ISAKMP_PAYLOAD_POP:
525 default:
526 return 0;
527 }
528 }
529
530 /* Validate the attribute payload P in message MSG. */
531 static int
message_validate_attribute(struct message * msg,struct payload * p)532 message_validate_attribute(struct message *msg, struct payload *p)
533 {
534 /* If we don't have an exchange yet, create one. */
535 if (!msg->exchange) {
536 if (zero_test((u_int8_t *) msg->iov[0].iov_base +
537 ISAKMP_HDR_MESSAGE_ID_OFF, ISAKMP_HDR_MESSAGE_ID_LEN))
538 msg->exchange = exchange_setup_p1(msg,
539 IPSEC_DOI_IPSEC);
540 else
541 msg->exchange = exchange_setup_p2(msg,
542 IPSEC_DOI_IPSEC);
543 if (!msg->exchange) {
544 log_print("message_validate_attribute: can not "
545 "create exchange");
546 message_free(msg);
547 return -1;
548 }
549 }
550 return 0;
551 }
552
553 /* Validate the certificate payload P in message MSG. */
554 static int
message_validate_cert(struct message * msg,struct payload * p)555 message_validate_cert(struct message *msg, struct payload *p)
556 {
557 if (GET_ISAKMP_CERT_ENCODING(p->p) >= ISAKMP_CERTENC_RESERVED_MIN) {
558 message_drop(msg, ISAKMP_NOTIFY_INVALID_CERT_ENCODING, 0, 1,
559 1);
560 return -1;
561 }
562 return 0;
563 }
564
565 /* Validate the certificate request payload P in message MSG. */
566 static int
message_validate_cert_req(struct message * msg,struct payload * p)567 message_validate_cert_req(struct message *msg, struct payload *p)
568 {
569 struct cert_handler *cert;
570 size_t len =
571 GET_ISAKMP_GEN_LENGTH(p->p) - ISAKMP_CERTREQ_AUTHORITY_OFF;
572
573 if (GET_ISAKMP_CERTREQ_TYPE(p->p) >= ISAKMP_CERTENC_RESERVED_MIN) {
574 message_drop(msg, ISAKMP_NOTIFY_INVALID_CERT_ENCODING, 0, 1,
575 1);
576 return -1;
577 }
578 /*
579 * Check the certificate types we support and if an acceptable
580 * authority is included in the payload check if it can be decoded
581 */
582 cert = cert_get(GET_ISAKMP_CERTREQ_TYPE(p->p));
583 if (!cert || (len && !cert->certreq_validate(p->p +
584 ISAKMP_CERTREQ_AUTHORITY_OFF, len))) {
585 message_drop(msg, ISAKMP_NOTIFY_CERT_TYPE_UNSUPPORTED, 0, 1,
586 1);
587 return -1;
588 }
589 return 0;
590 }
591
592 /*
593 * Validate the delete payload P in message MSG. As a side-effect, create
594 * an exchange if we do not have one already.
595 */
596 static int
message_validate_delete(struct message * msg,struct payload * p)597 message_validate_delete(struct message *msg, struct payload *p)
598 {
599 u_int8_t proto = GET_ISAKMP_DELETE_PROTO(p->p);
600 struct doi *doi;
601 struct sa *sa, *isakmp_sa;
602 struct sockaddr *dst, *dst_isa;
603 u_int32_t nspis = GET_ISAKMP_DELETE_NSPIS(p->p);
604 u_int8_t *spis = (u_int8_t *)p->p + ISAKMP_DELETE_SPI_OFF;
605 u_int32_t i;
606 char *addr;
607
608 /* Only accept authenticated DELETEs. */
609 if ((msg->flags & MSG_AUTHENTICATED) == 0) {
610 log_print("message_validate_delete: "
611 "got unauthenticated DELETE");
612 message_free(msg);
613 return -1;
614 }
615
616 doi = doi_lookup(GET_ISAKMP_DELETE_DOI(p->p));
617 if (!doi) {
618 log_print("message_validate_delete: DOI not supported");
619 message_free(msg);
620 return -1;
621 }
622 /* If we don't have an exchange yet, create one. */
623 if (!msg->exchange) {
624 if (zero_test((u_int8_t *) msg->iov[0].iov_base
625 + ISAKMP_HDR_MESSAGE_ID_OFF, ISAKMP_HDR_MESSAGE_ID_LEN))
626 msg->exchange = exchange_setup_p1(msg, doi->id);
627 else
628 msg->exchange = exchange_setup_p2(msg, doi->id);
629 if (!msg->exchange) {
630 log_print("message_validate_delete: can not create "
631 "exchange");
632 message_free(msg);
633 return -1;
634 }
635 }
636 /* Only accept DELETE as part of an INFORMATIONAL exchange. */
637 if (msg->exchange->type != ISAKMP_EXCH_INFO) {
638 log_print("message_validate_delete: delete in exchange other "
639 "than INFO: %s", constant_name(isakmp_exch_cst,
640 msg->exchange->type));
641 message_free(msg);
642 return -1;
643 }
644 if (proto != ISAKMP_PROTO_ISAKMP && doi->validate_proto(proto)) {
645 log_print("message_validate_delete: protocol not supported");
646 message_free(msg);
647 return -1;
648 }
649 /* Validate the SPIs. */
650 for (i = 0; i < nspis; i++) {
651 /* Get ISAKMP SA protecting this message. */
652 isakmp_sa = msg->isakmp_sa;
653 if (!isakmp_sa) {
654 /* XXX should not happen? */
655 log_print("message_validate_delete: invalid spi (no "
656 "valid ISAKMP SA found)");
657 message_free(msg);
658 return -1;
659 }
660 isakmp_sa->transport->vtbl->get_dst(isakmp_sa->transport,
661 &dst_isa);
662
663 /* Get SA to be deleted. */
664 msg->transport->vtbl->get_dst(msg->transport, &dst);
665 if (proto == ISAKMP_PROTO_ISAKMP)
666 sa = sa_lookup_isakmp_sa(dst, spis + i
667 * ISAKMP_HDR_COOKIES_LEN);
668 else
669 sa = ipsec_sa_lookup(dst, ((u_int32_t *) spis)[i],
670 proto);
671 if (!sa) {
672 LOG_DBG((LOG_MESSAGE, 50, "message_validate_delete: "
673 "invalid spi (no valid SA found)"));
674 message_free(msg);
675 return -1;
676 }
677 sa->transport->vtbl->get_dst(sa->transport, &dst);
678
679 /* Destination addresses must match. */
680 if (dst->sa_family != dst_isa->sa_family ||
681 memcmp(sockaddr_addrdata(dst_isa), sockaddr_addrdata(dst),
682 sockaddr_addrlen(dst))) {
683 sockaddr2text(dst_isa, &addr, 0);
684
685 log_print("message_validate_delete: invalid spi "
686 "(illegal delete request from %s)", addr);
687 free(addr);
688 message_free(msg);
689 return -1;
690 }
691 }
692
693 return 0;
694 }
695
696 /*
697 * Validate the hash payload P in message MSG.
698 */
699 static int
message_validate_hash(struct message * msg,struct payload * p)700 message_validate_hash(struct message *msg, struct payload *p)
701 {
702 struct sa *isakmp_sa = msg->isakmp_sa;
703 struct ipsec_sa *isa;
704 struct hash *hash;
705 struct payload *hashp = payload_first(msg, ISAKMP_PAYLOAD_HASH);
706 struct prf *prf;
707 u_int8_t *rest;
708 u_int8_t message_id[ISAKMP_HDR_MESSAGE_ID_LEN];
709 size_t rest_len;
710
711 /* active exchanges other than INFORMATIONAL validates hash payload. */
712 if (msg->exchange && (msg->exchange->type != ISAKMP_EXCH_INFO))
713 return 0;
714
715 if (isakmp_sa == NULL)
716 goto invalid;
717
718 isa = isakmp_sa->data;
719 hash = hash_get(isa->hash);
720 if (hash == NULL)
721 goto invalid;
722
723 /* If no SKEYID_a, we can not do anything (should not happen). */
724 if (!isa->skeyid_a)
725 goto invalid;
726
727 /* Allocate the prf and start calculating our HASH(1). */
728 LOG_DBG_BUF((LOG_MISC, 90, "message_validate_hash: SKEYID_a",
729 isa->skeyid_a, isa->skeyid_len));
730 prf = prf_alloc(isa->prf_type, hash->type, isa->skeyid_a,
731 isa->skeyid_len);
732 if (!prf) {
733 message_free(msg);
734 return -1;
735 }
736 /* This is not an active exchange. */
737 GET_ISAKMP_HDR_MESSAGE_ID(msg->iov[0].iov_base, message_id);
738
739 prf->Init(prf->prfctx);
740 LOG_DBG_BUF((LOG_MISC, 90, "message_validate_hash: message_id",
741 message_id, ISAKMP_HDR_MESSAGE_ID_LEN));
742 prf->Update(prf->prfctx, message_id, ISAKMP_HDR_MESSAGE_ID_LEN);
743 rest = hashp->p + GET_ISAKMP_GEN_LENGTH(hashp->p);
744 rest_len = (GET_ISAKMP_HDR_LENGTH(msg->iov[0].iov_base) - (rest -
745 (u_int8_t *)msg->iov[0].iov_base));
746 LOG_DBG_BUF((LOG_MISC, 90,
747 "message_validate_hash: payloads after HASH(1)", rest, rest_len));
748 prf->Update(prf->prfctx, rest, rest_len);
749 prf->Final(hash->digest, prf->prfctx);
750 prf_free(prf);
751
752 if (memcmp(hashp->p + ISAKMP_HASH_DATA_OFF, hash->digest,
753 hash->hashsize))
754 goto invalid;
755
756 /* Mark the HASH as handled. */
757 hashp->flags |= PL_MARK;
758
759 /* Mark message as authenticated. */
760 msg->flags |= MSG_AUTHENTICATED;
761
762 return 0;
763
764 invalid:
765 log_print("message_validate_hash: invalid hash information");
766 message_drop(msg, ISAKMP_NOTIFY_INVALID_HASH_INFORMATION, 0, 1, 1);
767 return -1;
768 }
769
770 /* Validate the identification payload P in message MSG. */
771 static int
message_validate_id(struct message * msg,struct payload * p)772 message_validate_id(struct message *msg, struct payload *p)
773 {
774 struct exchange *exchange = msg->exchange;
775 size_t len = GET_ISAKMP_GEN_LENGTH(p->p);
776
777 if (!exchange) {
778 /* We should have an exchange at this point. */
779 log_print("message_validate_id: payload out of sequence");
780 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
781 return -1;
782 }
783 if (exchange->doi &&
784 exchange->doi->validate_id_information(GET_ISAKMP_ID_TYPE(p->p),
785 p->p + ISAKMP_ID_DOI_DATA_OFF, p->p + ISAKMP_ID_DATA_OFF,
786 len - ISAKMP_ID_DATA_OFF, exchange)) {
787 message_drop(msg, ISAKMP_NOTIFY_INVALID_ID_INFORMATION, 0, 1,
788 1);
789 return -1;
790 }
791 return 0;
792 }
793
794 /* Validate the key exchange payload P in message MSG. */
795 static int
message_validate_key_exch(struct message * msg,struct payload * p)796 message_validate_key_exch(struct message *msg, struct payload *p)
797 {
798 struct exchange *exchange = msg->exchange;
799 size_t len = GET_ISAKMP_GEN_LENGTH(p->p);
800
801 if (!exchange) {
802 /* We should have an exchange at this point. */
803 log_print("message_validate_key_exch: "
804 "payload out of sequence");
805 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
806 return -1;
807 }
808 if (exchange->doi && exchange->doi->validate_key_information(p->p +
809 ISAKMP_KE_DATA_OFF, len - ISAKMP_KE_DATA_OFF)) {
810 message_drop(msg, ISAKMP_NOTIFY_INVALID_KEY_INFORMATION,
811 0, 1, 1);
812 return -1;
813 }
814 return 0;
815 }
816
817 /* Validate the NAT-D payload P in message MSG. */
818 static int
message_validate_nat_d(struct message * msg,struct payload * p)819 message_validate_nat_d(struct message *msg, struct payload *p)
820 {
821 struct exchange *exchange = msg->exchange;
822
823 if (!exchange) {
824 /* We should have an exchange at this point. */
825 log_print("message_validate_nat_d: payload out of sequence");
826 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
827 return -1;
828 }
829
830 if (exchange->phase != 1) {
831 log_print("message_validate_nat_d: "
832 "NAT-D payload must be in phase 1");
833 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
834 return -1;
835 }
836
837 /* Mark as handled. */
838 p->flags |= PL_MARK;
839
840 return 0;
841 }
842
843 /* Validate the NAT-OA payload P in message MSG. */
844 static int
message_validate_nat_oa(struct message * msg,struct payload * p)845 message_validate_nat_oa(struct message *msg, struct payload *p)
846 {
847 struct exchange *exchange = msg->exchange;
848
849 if (!exchange) {
850 /* We should have an exchange at this point. */
851 log_print("message_validate_nat_d: payload out of sequence");
852 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
853 return -1;
854 }
855
856 #ifdef notyet /* XXX Probably never, due to patent issues. */
857 /* Mark as handled. */
858 p->flags |= PL_MARK;
859 #endif
860
861 return 0;
862 }
863
864 /* Validate the nonce payload P in message MSG. */
865 static int
message_validate_nonce(struct message * msg,struct payload * p)866 message_validate_nonce(struct message *msg, struct payload *p)
867 {
868 if (!msg->exchange) {
869 /* We should have an exchange at this point. */
870 log_print("message_validate_nonce: payload out of sequence");
871 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
872 return -1;
873 }
874 /* Nonces require no specific validation. */
875 return 0;
876 }
877
878 /*
879 * Validate the notify payload P in message MSG. As a side-effect, create
880 * an exchange if we do not have one already.
881 */
882 static int
message_validate_notify(struct message * msg,struct payload * p)883 message_validate_notify(struct message *msg, struct payload *p)
884 {
885 u_int8_t proto = GET_ISAKMP_NOTIFY_PROTO(p->p);
886 u_int16_t type = GET_ISAKMP_NOTIFY_MSG_TYPE(p->p);
887 struct doi *doi;
888
889 doi = doi_lookup(GET_ISAKMP_NOTIFY_DOI(p->p));
890 if (!doi) {
891 log_print("message_validate_notify: DOI not supported");
892 message_free(msg);
893 return -1;
894 }
895 /* If we don't have an exchange yet, create one. */
896 if (!msg->exchange) {
897 if (zero_test((u_int8_t *) msg->iov[0].iov_base +
898 ISAKMP_HDR_MESSAGE_ID_OFF, ISAKMP_HDR_MESSAGE_ID_LEN))
899 msg->exchange = exchange_setup_p1(msg, doi->id);
900 else
901 msg->exchange = exchange_setup_p2(msg, doi->id);
902 if (!msg->exchange) {
903 log_print("message_validate_notify: can not create "
904 "exchange");
905 message_free(msg);
906 return -1;
907 }
908 }
909 if (proto != ISAKMP_PROTO_ISAKMP && doi->validate_proto(proto)) {
910 log_print("message_validate_notify: protocol not supported");
911 message_free(msg);
912 return -1;
913 }
914
915 /* Validate the SPI. XXX Just ISAKMP for now. */
916 if (proto == ISAKMP_PROTO_ISAKMP &&
917 GET_ISAKMP_NOTIFY_SPI_SZ(p->p) == ISAKMP_HDR_COOKIES_LEN &&
918 msg->isakmp_sa &&
919 memcmp(p->p + ISAKMP_NOTIFY_SPI_OFF, msg->isakmp_sa->cookies,
920 ISAKMP_HDR_COOKIES_LEN) != 0) {
921 log_print("message_validate_notify: bad cookies");
922 message_drop(msg, ISAKMP_NOTIFY_INVALID_SPI, 0, 1, 0);
923 return -1;
924 }
925
926 if (type < ISAKMP_NOTIFY_INVALID_PAYLOAD_TYPE ||
927 (type >= ISAKMP_NOTIFY_RESERVED_MIN &&
928 type < ISAKMP_NOTIFY_PRIVATE_MIN) ||
929 (type >= ISAKMP_NOTIFY_STATUS_RESERVED1_MIN &&
930 type <= ISAKMP_NOTIFY_STATUS_RESERVED1_MAX) ||
931 (type >= ISAKMP_NOTIFY_STATUS_DOI_MIN &&
932 type <= ISAKMP_NOTIFY_STATUS_DOI_MAX &&
933 doi->validate_notification(type)) ||
934 type >= ISAKMP_NOTIFY_STATUS_RESERVED2_MIN) {
935 log_print("message_validate_notify: "
936 "message type not supported");
937 message_free(msg);
938 return -1;
939 }
940
941 return 0;
942 }
943
944 /* Validate the proposal payload P in message MSG. */
945 static int
message_validate_proposal(struct message * msg,struct payload * p)946 message_validate_proposal(struct message *msg, struct payload *p)
947 {
948 u_int8_t proto = GET_ISAKMP_PROP_PROTO(p->p);
949 u_int8_t *sa = p->context->p;
950
951 if (!msg->exchange) {
952 /* We should have an exchange at this point. */
953 log_print("message_validate_proposal: "
954 "payload out of sequence");
955 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
956 return -1;
957 }
958 if (proto != ISAKMP_PROTO_ISAKMP &&
959 msg->exchange->doi->validate_proto(proto)) {
960 message_drop(msg, ISAKMP_NOTIFY_INVALID_PROTOCOL_ID, 0, 1, 1);
961 return -1;
962 }
963 /* Check that we get monotonically increasing proposal IDs per SA. */
964 if (sa != last_sa)
965 last_sa = sa;
966 else if (GET_ISAKMP_PROP_NO(p->p) < last_prop_no) {
967 message_drop(msg, ISAKMP_NOTIFY_BAD_PROPOSAL_SYNTAX, 0, 1, 1);
968 return -1;
969 }
970 last_prop_no = GET_ISAKMP_PROP_NO(p->p);
971
972 /* XXX Validate the SPI, and other syntactic things. */
973
974 return 0;
975 }
976
977 /*
978 * Validate the SA payload P in message MSG.
979 * Aside from normal validation, note what DOI is in use for other
980 * validation routines to look at. Also index the proposal payloads
981 * on the fly.
982 * XXX This assumes PAYLOAD_SA is always the first payload
983 * to be validated, which is true for IKE, except for quick mode where
984 * a PAYLOAD_HASH comes first, but in that specific case it does not matter.
985 * XXX Make sure the above comment is relevant, isn't SA always checked
986 * first due to the IANA assigned payload number?
987 */
988 static int
message_validate_sa(struct message * msg,struct payload * p)989 message_validate_sa(struct message *msg, struct payload *p)
990 {
991 set payload_set;
992 size_t len;
993 u_int32_t doi_id;
994 struct exchange *exchange = msg->exchange;
995 u_int8_t *pkt = msg->iov[0].iov_base;
996
997 doi_id = GET_ISAKMP_SA_DOI(p->p);
998 if (!doi_lookup(doi_id)) {
999 log_print("message_validate_sa: DOI not supported");
1000 message_drop(msg, ISAKMP_NOTIFY_DOI_NOT_SUPPORTED, 0, 1, 1);
1001 return -1;
1002 }
1003 /*
1004 * It's time to figure out what SA this message is about. If it is
1005 * already set, then we are creating a new phase 1 SA. Otherwise,
1006 * lookup the SA using the cookies and the message ID. If we cannot
1007 * find it, and the phase 1 SA is ready, setup a phase 2 SA.
1008 */
1009 if (!exchange) {
1010 if (zero_test(pkt + ISAKMP_HDR_RCOOKIE_OFF,
1011 ISAKMP_HDR_RCOOKIE_LEN))
1012 exchange = exchange_setup_p1(msg, doi_id);
1013 else if (msg->isakmp_sa->flags & SA_FLAG_READY)
1014 exchange = exchange_setup_p2(msg, doi_id);
1015 else {
1016 /* XXX What to do here? */
1017 message_free(msg);
1018 return -1;
1019 }
1020 if (!exchange) {
1021 /* XXX Log? */
1022 message_free(msg);
1023 return -1;
1024 }
1025 }
1026 msg->exchange = exchange;
1027
1028 /*
1029 * Create a struct sa for each SA payload handed to us unless we are
1030 * the initiator where we only will count them.
1031 */
1032 if (exchange->initiator) {
1033 /* XXX Count SA payloads. */
1034 } else if (sa_create(exchange, msg->transport)) {
1035 /* XXX Remove exchange if we just created it? */
1036 message_free(msg);
1037 return -1;
1038 }
1039 if (exchange->phase == 1) {
1040 msg->isakmp_sa = TAILQ_FIRST(&exchange->sa_list);
1041 if (msg->isakmp_sa)
1042 sa_reference(msg->isakmp_sa);
1043 }
1044 /*
1045 * Let the DOI validate the situation, at the same time it tells us
1046 * what the length of the situation field is.
1047 */
1048 if (exchange->doi->validate_situation(p->p + ISAKMP_SA_SIT_OFF, &len,
1049 GET_ISAKMP_GEN_LENGTH(p->p) - ISAKMP_SA_SIT_OFF)) {
1050 log_print("message_validate_sa: situation not supported");
1051 message_drop(msg, ISAKMP_NOTIFY_SITUATION_NOT_SUPPORTED,
1052 0, 1, 1);
1053 return -1;
1054 }
1055 /*
1056 * Reset the fields we base our proposal & transform number checks
1057 * on.
1058 */
1059 last_sa = last_prop = 0;
1060 last_prop_no = last_xf_no = 0;
1061
1062 /* Go through the PROPOSAL payloads. */
1063 ZERO(&payload_set);
1064 SET(ISAKMP_PAYLOAD_PROPOSAL, &payload_set);
1065 if (message_parse_payloads(msg, p, ISAKMP_PAYLOAD_PROPOSAL,
1066 p->p + ISAKMP_SA_SIT_OFF + len, &payload_set,
1067 message_parse_proposal) == -1)
1068 return -1;
1069
1070 return 0;
1071 }
1072
1073 /* Validate the signature payload P in message MSG. */
1074 static int
message_validate_sig(struct message * msg,struct payload * p)1075 message_validate_sig(struct message *msg, struct payload *p)
1076 {
1077 if (!msg->exchange) {
1078 /* We should have an exchange at this point. */
1079 log_print("message_validate_sig: payload out of sequence");
1080 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
1081 return -1;
1082 }
1083 /* XXX Not implemented yet. */
1084 return 0;
1085 }
1086
1087 /* Validate the transform payload P in message MSG. */
1088 static int
message_validate_transform(struct message * msg,struct payload * p)1089 message_validate_transform(struct message *msg, struct payload *p)
1090 {
1091 u_int8_t proto = GET_ISAKMP_PROP_PROTO(p->context->p);
1092 u_int8_t *prop = p->context->p;
1093
1094 if (!msg->exchange) {
1095 /* We should have an exchange at this point. */
1096 log_print("message_validate_transform: "
1097 "payload out of sequence");
1098 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
1099 return -1;
1100 }
1101 if (msg->exchange->doi
1102 ->validate_transform_id(proto, GET_ISAKMP_TRANSFORM_ID(p->p))) {
1103 message_drop(msg, ISAKMP_NOTIFY_INVALID_TRANSFORM_ID, 0, 1, 1);
1104 return -1;
1105 }
1106 /* Check that the reserved field is zero. */
1107 if (!zero_test(p->p + ISAKMP_TRANSFORM_RESERVED_OFF,
1108 ISAKMP_TRANSFORM_RESERVED_LEN)) {
1109 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
1110 return -1;
1111 }
1112 /*
1113 * Check that we get monotonically increasing transform numbers per
1114 * proposal.
1115 */
1116 if (prop != last_prop)
1117 last_prop = prop;
1118 else if (GET_ISAKMP_TRANSFORM_NO(p->p) <= last_xf_no) {
1119 message_drop(msg, ISAKMP_NOTIFY_BAD_PROPOSAL_SYNTAX, 0, 1, 1);
1120 return -1;
1121 }
1122 last_xf_no = GET_ISAKMP_TRANSFORM_NO(p->p);
1123
1124 /* Validate the attributes. */
1125 if (attribute_map(p->p + ISAKMP_TRANSFORM_SA_ATTRS_OFF,
1126 GET_ISAKMP_GEN_LENGTH(p->p) - ISAKMP_TRANSFORM_SA_ATTRS_OFF,
1127 msg->exchange->doi->validate_attribute, msg)) {
1128 message_drop(msg, ISAKMP_NOTIFY_ATTRIBUTES_NOT_SUPPORTED,
1129 0, 1, 1);
1130 return -1;
1131 }
1132 return 0;
1133 }
1134
1135 /* Validate the vendor payload P in message MSG. */
1136 static int
message_validate_vendor(struct message * msg,struct payload * p)1137 message_validate_vendor(struct message *msg, struct payload *p)
1138 {
1139 if (!msg->exchange) {
1140 /* We should have an exchange at this point. */
1141 log_print("message_validate_vendor: payload out of sequence");
1142 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
1143 return -1;
1144 }
1145 /* Vendor IDs are only allowed in phase 1. */
1146 if (msg->exchange->phase != 1) {
1147 message_drop(msg, ISAKMP_NOTIFY_INVALID_PAYLOAD_TYPE, 0, 1, 1);
1148 return -1;
1149 }
1150 dpd_check_vendor_payload(msg, p);
1151 nat_t_check_vendor_payload(msg, p);
1152 if (!(p->flags & PL_MARK))
1153 LOG_DBG((LOG_MESSAGE, 40, "message_validate_vendor: "
1154 "vendor ID seen"));
1155 return 0;
1156 }
1157
1158 /*
1159 * Add an index-record pointing to the payload at BUF in message MSG
1160 * to the PAYLOAD bucket of payloads. This allows us to quickly reference
1161 * payloads by type. Also stash the parent payload P link into the new
1162 * node so we can go from transforms -> payloads -> SAs.
1163 */
1164 static int
message_index_payload(struct message * msg,struct payload * p,u_int8_t payload,u_int8_t * buf)1165 message_index_payload(struct message *msg, struct payload *p, u_int8_t payload,
1166 u_int8_t *buf)
1167 {
1168 struct payload *payload_node;
1169
1170 /* Put the payload pointer into the right bucket. */
1171 payload_node = malloc(sizeof *payload_node);
1172 if (!payload_node)
1173 return -1;
1174 payload_node->p = buf;
1175 payload_node->context = p;
1176 payload_node->flags = 0;
1177 TAILQ_INSERT_TAIL(&msg->payload[payload], payload_node, link);
1178 return 0;
1179 }
1180
1181 /*
1182 * Group each payload found in MSG by type for easy reference later.
1183 * While doing this, validate the generic parts of the message structure too.
1184 * NEXT is the 1st payload's type. This routine will also register the
1185 * computed message length (i.e. without padding) in msg->iov[0].iov_len.
1186 */
1187 static int
message_sort_payloads(struct message * msg,u_int8_t next)1188 message_sort_payloads(struct message *msg, u_int8_t next)
1189 {
1190 set payload_set;
1191 int i, sz;
1192
1193 ZERO(&payload_set);
1194 for (i = ISAKMP_PAYLOAD_SA; i < ISAKMP_PAYLOAD_MAX; i++)
1195 if (i != ISAKMP_PAYLOAD_PROPOSAL && i !=
1196 ISAKMP_PAYLOAD_TRANSFORM)
1197 SET(i, &payload_set);
1198 sz = message_parse_payloads(msg, 0, next,
1199 (u_int8_t *)msg->iov[0].iov_base + ISAKMP_HDR_SZ, &payload_set,
1200 message_index_payload);
1201 if (sz == -1)
1202 return -1;
1203 msg->iov[0].iov_len = ISAKMP_HDR_SZ + sz;
1204 SET_ISAKMP_HDR_LENGTH(msg->iov[0].iov_base, ISAKMP_HDR_SZ + sz);
1205 return 0;
1206 }
1207
1208 /* Run all the generic payload tests that the drafts specify. */
1209 static int
message_validate_payloads(struct message * msg)1210 message_validate_payloads(struct message *msg)
1211 {
1212 int i;
1213 struct payload *p;
1214 struct field *f;
1215
1216 for (i = ISAKMP_PAYLOAD_SA; i < ISAKMP_PAYLOAD_MAX; i++)
1217 TAILQ_FOREACH(p, &msg->payload[i], link) {
1218 LOG_DBG((LOG_MESSAGE, 60, "message_validate_payloads: "
1219 "payload %s at %p of message %p",
1220 constant_name(isakmp_payload_cst, i), p->p, msg));
1221 if ((f = message_get_field(i)) != NULL)
1222 field_dump_payload(f, p->p);
1223 if (message_validate_payload(msg, p, i))
1224 return -1;
1225 }
1226 return 0;
1227 }
1228
1229 /*
1230 * All incoming messages go through here. We do generic validity checks
1231 * and try to find or establish SAs. Last but not least we try to find
1232 * the exchange this message, MSG, is part of, and feed it there.
1233 */
1234 int
message_recv(struct message * msg)1235 message_recv(struct message *msg)
1236 {
1237 u_int8_t *buf = msg->iov[0].iov_base;
1238 size_t sz = msg->iov[0].iov_len;
1239 u_int8_t exch_type;
1240 int setup_isakmp_sa, msgid_is_zero;
1241 u_int8_t flags;
1242 struct keystate *ks = 0;
1243 struct proto tmp_proto;
1244 struct sa tmp_sa;
1245 struct transport *t;
1246
1247 /* Messages shorter than an ISAKMP header are bad. */
1248 if (sz < ISAKMP_HDR_SZ || sz != GET_ISAKMP_HDR_LENGTH(buf)) {
1249 log_print("message_recv: bad message length");
1250 message_drop(msg, 0, 0, 1, 1);
1251 return -1;
1252 }
1253 /* Possibly dump a raw hex image of the message to the log channel. */
1254 message_dump_raw("message_recv", msg, LOG_MESSAGE);
1255
1256 /*
1257 * If the responder cookie is zero, this is a request to setup an
1258 * ISAKMP SA. Otherwise the cookies should refer to an existing
1259 * ISAKMP SA.
1260 *
1261 * XXX This is getting ugly, please reread later to see if it can be
1262 * made nicer.
1263 */
1264 setup_isakmp_sa = zero_test(buf + ISAKMP_HDR_RCOOKIE_OFF,
1265 ISAKMP_HDR_RCOOKIE_LEN);
1266 if (setup_isakmp_sa) {
1267 /*
1268 * This might be a retransmission of a former ISAKMP SA setup
1269 * message. If so, just drop it.
1270 * XXX Must we really look in both the SA and exchange pools?
1271 */
1272 if (exchange_lookup_from_icookie(buf + ISAKMP_HDR_ICOOKIE_OFF) ||
1273 sa_lookup_from_icookie(buf + ISAKMP_HDR_ICOOKIE_OFF)) {
1274 /*
1275 * XXX Later we should differentiate between
1276 * retransmissions and potential replay attacks.
1277 */
1278 LOG_DBG((LOG_MESSAGE, 90,
1279 "message_recv: dropping setup for existing SA"));
1280 message_free(msg);
1281 return -1;
1282 }
1283 } else {
1284 msg->isakmp_sa = sa_lookup_by_header(buf, 0);
1285 if (msg->isakmp_sa)
1286 sa_reference(msg->isakmp_sa);
1287
1288 /*
1289 * If we cannot find an ISAKMP SA out of the cookies, this is
1290 * either a responder's first reply, and we need to upgrade
1291 * our exchange, or it's just plain invalid cookies.
1292 */
1293 if (!msg->isakmp_sa) {
1294 msg->exchange = exchange_lookup_from_icookie(buf +
1295 ISAKMP_HDR_ICOOKIE_OFF);
1296 if (msg->exchange && msg->exchange->phase == 1 &&
1297 zero_test(msg->exchange->cookies +
1298 ISAKMP_HDR_RCOOKIE_OFF, ISAKMP_HDR_RCOOKIE_LEN))
1299 exchange_upgrade_p1(msg);
1300 else {
1301 log_print("message_recv: invalid cookie(s) "
1302 "%08x%08x %08x%08x",
1303 decode_32(buf + ISAKMP_HDR_ICOOKIE_OFF),
1304 decode_32(buf + ISAKMP_HDR_ICOOKIE_OFF + 4),
1305 decode_32(buf + ISAKMP_HDR_RCOOKIE_OFF),
1306 decode_32(buf + ISAKMP_HDR_RCOOKIE_OFF + 4));
1307 tmp_proto.sa = &tmp_sa;
1308 tmp_sa.doi = doi_lookup(ISAKMP_DOI_ISAKMP);
1309 tmp_proto.proto = ISAKMP_PROTO_ISAKMP;
1310 tmp_proto.spi_sz[1] = ISAKMP_HDR_COOKIES_LEN;
1311 tmp_proto.spi[1] =
1312 buf + ISAKMP_HDR_COOKIES_OFF;
1313 message_drop(msg, ISAKMP_NOTIFY_INVALID_COOKIE,
1314 &tmp_proto, 1, 1);
1315 return -1;
1316 }
1317 #if 0
1318 msg->isakmp_sa = sa_lookup_from_icookie(buf +
1319 ISAKMP_HDR_ICOOKIE_OFF);
1320 if (msg->isakmp_sa)
1321 sa_isakmp_upgrade(msg);
1322 #endif
1323 }
1324 msg->exchange = exchange_lookup(buf, 1);
1325 }
1326
1327 if (message_check_duplicate(msg))
1328 return -1;
1329
1330 if (GET_ISAKMP_HDR_NEXT_PAYLOAD(buf) >= ISAKMP_PAYLOAD_RESERVED_MIN) {
1331 log_print("message_recv: invalid payload type %d in ISAKMP "
1332 "header (check passphrases, if applicable and in Phase 1)",
1333 GET_ISAKMP_HDR_NEXT_PAYLOAD(buf));
1334 message_drop(msg, ISAKMP_NOTIFY_INVALID_PAYLOAD_TYPE, 0, 1, 1);
1335 return -1;
1336 }
1337 /* Validate that the message is of version 1.0. */
1338 if (ISAKMP_VERSION_MAJOR(GET_ISAKMP_HDR_VERSION(buf)) != 1) {
1339 log_print("message_recv: invalid version major %d",
1340 ISAKMP_VERSION_MAJOR(GET_ISAKMP_HDR_VERSION(buf)));
1341 message_drop(msg, ISAKMP_NOTIFY_INVALID_MAJOR_VERSION, 0, 1,
1342 1);
1343 return -1;
1344 }
1345 if (ISAKMP_VERSION_MINOR(GET_ISAKMP_HDR_VERSION(buf)) != 0) {
1346 log_print("message_recv: invalid version minor %d",
1347 ISAKMP_VERSION_MINOR(GET_ISAKMP_HDR_VERSION(buf)));
1348 message_drop(msg, ISAKMP_NOTIFY_INVALID_MINOR_VERSION, 0, 1,
1349 1);
1350 return -1;
1351 }
1352 /*
1353 * Validate the exchange type. If it's a DOI-specified exchange wait
1354 * until after all payloads have been seen for the validation as the
1355 * SA payload might not yet have been parsed, thus the DOI might be
1356 * unknown.
1357 */
1358 exch_type = GET_ISAKMP_HDR_EXCH_TYPE(buf);
1359 if (exch_type == ISAKMP_EXCH_NONE ||
1360 (exch_type >= ISAKMP_EXCH_FUTURE_MIN &&
1361 exch_type <= ISAKMP_EXCH_FUTURE_MAX) ||
1362 (setup_isakmp_sa && exch_type >= ISAKMP_EXCH_DOI_MIN)) {
1363 log_print("message_recv: invalid exchange type %s",
1364 constant_name(isakmp_exch_cst, exch_type));
1365 message_drop(msg, ISAKMP_NOTIFY_INVALID_EXCHANGE_TYPE, 0, 1,
1366 1);
1367 return -1;
1368 }
1369 /*
1370 * Check for unrecognized flags, or the encryption flag when we don't
1371 * have an ISAKMP SA to decrypt with.
1372 */
1373 flags = GET_ISAKMP_HDR_FLAGS(buf);
1374 if (flags & ~(ISAKMP_FLAGS_ENC | ISAKMP_FLAGS_COMMIT |
1375 ISAKMP_FLAGS_AUTH_ONLY)) {
1376 log_print("message_recv: invalid flags 0x%x",
1377 GET_ISAKMP_HDR_FLAGS(buf));
1378 message_drop(msg, ISAKMP_NOTIFY_INVALID_FLAGS, 0, 1, 1);
1379 return -1;
1380 }
1381 /*
1382 * If we are about to setup an ISAKMP SA, the message ID must be
1383 * zero.
1384 */
1385 msgid_is_zero = zero_test(buf + ISAKMP_HDR_MESSAGE_ID_OFF,
1386 ISAKMP_HDR_MESSAGE_ID_LEN);
1387 if (setup_isakmp_sa && !msgid_is_zero) {
1388 log_print("message_recv: invalid message id");
1389 message_drop(msg, ISAKMP_NOTIFY_INVALID_MESSAGE_ID, 0, 1, 1);
1390 return -1;
1391 }
1392 if (!setup_isakmp_sa && msgid_is_zero) {
1393 /*
1394 * XXX Very likely redundant, look at the else clause of the
1395 * if (setup_isakmp_sa) statement above.
1396 */
1397 msg->exchange = exchange_lookup(buf, 0);
1398 if (!msg->exchange) {
1399 log_print("message_recv: phase 1 message after "
1400 "ISAKMP SA is ready");
1401 message_free(msg);
1402 return -1;
1403 } else if (msg->exchange->last_sent) {
1404 LOG_DBG((LOG_MESSAGE, 80, "message_recv: resending "
1405 "last message from phase 1"));
1406 message_send(msg->exchange->last_sent);
1407 }
1408 }
1409 if (flags & ISAKMP_FLAGS_ENC) {
1410 if (!msg->isakmp_sa) {
1411 LOG_DBG((LOG_MISC, 10, "message_recv: no isakmp_sa "
1412 "for encrypted message"));
1413 message_free(msg);
1414 return -1;
1415 }
1416 /* Decrypt rest of message using a DOI-specified IV. */
1417 ks = msg->isakmp_sa->doi->get_keystate(msg);
1418 if (!ks) {
1419 message_free(msg);
1420 return -1;
1421 }
1422 msg->orig = malloc(sz);
1423 if (!msg->orig) {
1424 message_free(msg);
1425 free(ks);
1426 return -1;
1427 }
1428 memcpy(msg->orig, buf, sz);
1429 crypto_decrypt(ks, buf + ISAKMP_HDR_SZ, sz - ISAKMP_HDR_SZ);
1430 } else
1431 msg->orig = buf;
1432 msg->orig_sz = sz;
1433
1434 /* IKE packet capture */
1435 message_packet_log(msg);
1436
1437 /*
1438 * Check the overall payload structure at the same time as indexing
1439 * them by type.
1440 */
1441 if (GET_ISAKMP_HDR_NEXT_PAYLOAD(buf) != ISAKMP_PAYLOAD_NONE &&
1442 message_sort_payloads(msg, GET_ISAKMP_HDR_NEXT_PAYLOAD(buf))) {
1443 if (ks)
1444 free(ks);
1445 return -1;
1446 }
1447 /*
1448 * Run generic payload tests now. If anything fails these checks, the
1449 * message needs either to be retained for later duplicate checks or
1450 * freed entirely.
1451 * XXX Should SAs and even transports be cleaned up then too?
1452 */
1453 if (message_validate_payloads(msg)) {
1454 if (ks)
1455 free(ks);
1456 return -1;
1457 }
1458 /*
1459 * If we have not found an exchange by now something is definitely
1460 * wrong.
1461 */
1462 if (!msg->exchange) {
1463 log_print("message_recv: no exchange");
1464 message_drop(msg, ISAKMP_NOTIFY_PAYLOAD_MALFORMED, 0, 1, 1);
1465 if (ks)
1466 free(ks);
1467 return -1;
1468 }
1469 /*
1470 * NAT-T may have switched ports for us. We need to replace the
1471 * old ISAKMP SA transport here with one that contains the proper
1472 * (i.e translated) ports.
1473 */
1474 if (msg->isakmp_sa && msg->exchange->phase == 1) {
1475 t = msg->isakmp_sa->transport;
1476 msg->isakmp_sa->transport = msg->transport;
1477 transport_reference(msg->transport);
1478 transport_release(t);
1479 }
1480
1481 /*
1482 * Now we can validate DOI-specific exchange types. If we have no SA
1483 * DOI-specific exchange types are definitely wrong.
1484 */
1485 if (exch_type >= ISAKMP_EXCH_DOI_MIN &&
1486 msg->exchange->doi->validate_exchange(exch_type)) {
1487 log_print("message_recv: invalid DOI exchange type %d",
1488 exch_type);
1489 message_drop(msg, ISAKMP_NOTIFY_INVALID_EXCHANGE_TYPE, 0, 1,
1490 1);
1491 if (ks)
1492 free(ks);
1493 return -1;
1494 }
1495 /* Make sure the IV we used gets saved in the proper SA. */
1496 if (ks) {
1497 if (!msg->exchange->keystate) {
1498 msg->exchange->keystate = ks;
1499 msg->exchange->crypto = ks->xf;
1500 } else
1501 free(ks);
1502 }
1503 /* Handle the flags. */
1504 if (flags & ISAKMP_FLAGS_ENC)
1505 msg->exchange->flags |= EXCHANGE_FLAG_ENCRYPT;
1506 if ((msg->exchange->flags & EXCHANGE_FLAG_COMMITTED) == 0 &&
1507 (flags & ISAKMP_FLAGS_COMMIT))
1508 msg->exchange->flags |= EXCHANGE_FLAG_HE_COMMITTED;
1509
1510 /*
1511 * Except for the 3rd Aggressive Mode message, require encryption
1512 * as soon as we have the keystate for it.
1513 */
1514 if ((flags & ISAKMP_FLAGS_ENC) == 0 &&
1515 (msg->exchange->phase == 2 ||
1516 (msg->exchange->keystate &&
1517 msg->exchange->type != ISAKMP_EXCH_AGGRESSIVE))) {
1518 log_print("message_recv: cleartext phase %d message",
1519 msg->exchange->phase);
1520 message_drop(msg, ISAKMP_NOTIFY_INVALID_FLAGS, 0, 1, 1);
1521 return -1;
1522 }
1523
1524 /* OK let the exchange logic do the rest. */
1525 exchange_run(msg);
1526
1527 return 0;
1528 }
1529
1530 void
message_send_expire(struct message * msg)1531 message_send_expire(struct message *msg)
1532 {
1533 msg->retrans = 0;
1534
1535 message_send(msg);
1536 }
1537
1538 /* Queue up message MSG for transmittal. */
1539 void
message_send(struct message * msg)1540 message_send(struct message *msg)
1541 {
1542 struct exchange *exchange = msg->exchange;
1543 struct message *m;
1544 struct msg_head *q;
1545
1546 /* Remove retransmissions on this message */
1547 if (msg->retrans) {
1548 timer_remove_event(msg->retrans);
1549 msg->retrans = 0;
1550 }
1551 /* IKE packet capture */
1552 message_packet_log(msg);
1553
1554 /*
1555 * If the ISAKMP SA has set up encryption, encrypt the message.
1556 * However, in a retransmit, it is already encrypted.
1557 */
1558 if ((msg->flags & MSG_ENCRYPTED) == 0 &&
1559 exchange->flags & EXCHANGE_FLAG_ENCRYPT) {
1560 if (!exchange->keystate) {
1561 exchange->keystate = exchange->doi->get_keystate(msg);
1562 if (!exchange->keystate)
1563 return;
1564 exchange->crypto = exchange->keystate->xf;
1565 exchange->flags |= EXCHANGE_FLAG_ENCRYPT;
1566 }
1567 if (message_encrypt(msg)) {
1568 /* XXX Log. */
1569 return;
1570 }
1571 }
1572 /* Keep the COMMIT bit on. */
1573 if (exchange->flags & EXCHANGE_FLAG_COMMITTED)
1574 SET_ISAKMP_HDR_FLAGS(msg->iov[0].iov_base,
1575 GET_ISAKMP_HDR_FLAGS(msg->iov[0].iov_base)
1576 | ISAKMP_FLAGS_COMMIT);
1577
1578 message_dump_raw("message_send", msg, LOG_MESSAGE);
1579 msg->flags |= MSG_IN_TRANSIT;
1580 exchange->in_transit = msg;
1581
1582 /*
1583 * If we get a retransmission of a message before our response
1584 * has left the queue, don't queue it again, as it will result
1585 * in a circular list.
1586 */
1587 q = msg->transport->vtbl->get_queue(msg);
1588 for (m = TAILQ_FIRST(q); m; m = TAILQ_NEXT(m, link))
1589 if (m == msg) {
1590 LOG_DBG((LOG_MESSAGE, 60,
1591 "message_send: msg %p already on sendq %p", m, q));
1592 return;
1593 }
1594 TAILQ_INSERT_TAIL(q, msg, link);
1595 }
1596
1597 /*
1598 * Setup the ISAKMP message header for message MSG. EXCHANGE is the exchange
1599 * type, FLAGS are the ISAKMP header flags and MSG_ID is message ID
1600 * identifying the exchange.
1601 */
1602 void
message_setup_header(struct message * msg,u_int8_t exchange,u_int8_t flags,u_int8_t * msg_id)1603 message_setup_header(struct message *msg, u_int8_t exchange, u_int8_t flags,
1604 u_int8_t *msg_id)
1605 {
1606 u_int8_t *buf = msg->iov[0].iov_base;
1607
1608 SET_ISAKMP_HDR_ICOOKIE(buf, msg->exchange->cookies);
1609 SET_ISAKMP_HDR_RCOOKIE(buf, msg->exchange->cookies +
1610 ISAKMP_HDR_ICOOKIE_LEN);
1611 SET_ISAKMP_HDR_NEXT_PAYLOAD(buf, ISAKMP_PAYLOAD_NONE);
1612 SET_ISAKMP_HDR_VERSION(buf, ISAKMP_VERSION_MAKE(1, 0));
1613 SET_ISAKMP_HDR_EXCH_TYPE(buf, exchange);
1614 SET_ISAKMP_HDR_FLAGS(buf, flags);
1615 SET_ISAKMP_HDR_MESSAGE_ID(buf, msg_id);
1616 SET_ISAKMP_HDR_LENGTH(buf, msg->iov[0].iov_len);
1617 }
1618
1619 /*
1620 * Add the payload of type PAYLOAD in BUF sized SZ to the MSG message.
1621 * The caller thereby is released from the responsibility of freeing BUF,
1622 * unless we return a failure of course. If LINK is set the former
1623 * payload's "next payload" field to PAYLOAD.
1624 *
1625 * XXX We might want to resize the iov array several slots at a time.
1626 */
1627 int
message_add_payload(struct message * msg,u_int8_t payload,u_int8_t * buf,size_t sz,int link)1628 message_add_payload(struct message *msg, u_int8_t payload, u_int8_t *buf,
1629 size_t sz, int link)
1630 {
1631 struct iovec *new_iov;
1632 struct payload *payload_node;
1633
1634 payload_node = calloc(1, sizeof *payload_node);
1635 if (!payload_node) {
1636 log_error("message_add_payload: calloc (1, %lu) failed",
1637 (unsigned long)sizeof *payload_node);
1638 return -1;
1639 }
1640 new_iov = (struct iovec *) realloc(msg->iov, (msg->iovlen + 1) *
1641 sizeof *msg->iov);
1642 if (!new_iov) {
1643 log_error("message_add_payload: realloc (%p, %lu) failed",
1644 msg->iov, (msg->iovlen + 1) *
1645 (unsigned long)sizeof *msg->iov);
1646 free(payload_node);
1647 return -1;
1648 }
1649 msg->iov = new_iov;
1650 new_iov[msg->iovlen].iov_base = buf;
1651 new_iov[msg->iovlen].iov_len = sz;
1652 msg->iovlen++;
1653 if (link)
1654 *msg->nextp = payload;
1655 msg->nextp = buf + ISAKMP_GEN_NEXT_PAYLOAD_OFF;
1656 *msg->nextp = ISAKMP_PAYLOAD_NONE;
1657 SET_ISAKMP_GEN_RESERVED(buf, 0);
1658 SET_ISAKMP_GEN_LENGTH(buf, sz);
1659 SET_ISAKMP_HDR_LENGTH(msg->iov[0].iov_base,
1660 GET_ISAKMP_HDR_LENGTH(msg->iov[0].iov_base) + sz);
1661
1662 /*
1663 * For the sake of exchange_validate we index the payloads even in
1664 * outgoing messages, however context and flags are uninteresting in
1665 * this situation.
1666 */
1667 payload_node->p = buf;
1668 TAILQ_INSERT_TAIL(&msg->payload[payload], payload_node, link);
1669 return 0;
1670 }
1671
1672 /* XXX Move up when ready. */
1673 struct info_args {
1674 char discr;
1675 u_int32_t doi;
1676 u_int8_t proto;
1677 u_int16_t spi_sz;
1678 union {
1679 struct {
1680 u_int16_t msg_type;
1681 u_int8_t *spi;
1682 } n;
1683 struct {
1684 u_int16_t nspis;
1685 u_int8_t *spis;
1686 } d;
1687 struct {
1688 u_int16_t msg_type;
1689 u_int8_t *spi;
1690 u_int32_t seq;
1691 } dpd;
1692 } u;
1693 };
1694
1695 /*
1696 * As a reaction to the incoming message MSG create an informational exchange
1697 * protected by ISAKMP_SA and send a notify payload of type NOTIFY, with
1698 * fields initialized from SA. INCOMING is true if the SPI field should be
1699 * filled with the incoming SPI and false if it is to be filled with the
1700 * outgoing one.
1701 *
1702 * XXX Should we handle sending multiple notify payloads? The draft allows
1703 * it, but do we need it? Furthermore, should we not return a success
1704 * status value?
1705 */
1706 void
message_send_notification(struct message * msg,struct sa * isakmp_sa,u_int16_t notify,struct proto * proto,int incoming)1707 message_send_notification(struct message *msg, struct sa *isakmp_sa,
1708 u_int16_t notify, struct proto *proto, int incoming)
1709 {
1710 struct info_args args;
1711 struct sa *doi_sa = proto ? proto->sa : isakmp_sa;
1712
1713 args.discr = 'N';
1714 args.doi = doi_sa ? doi_sa->doi->id : ISAKMP_DOI_ISAKMP;
1715 args.proto = proto ? proto->proto : ISAKMP_PROTO_ISAKMP;
1716 args.spi_sz = proto ? proto->spi_sz[incoming] : 0;
1717 args.u.n.msg_type = notify;
1718 args.u.n.spi = proto ? proto->spi[incoming] : 0;
1719 if (isakmp_sa && (isakmp_sa->flags & SA_FLAG_READY))
1720 exchange_establish_p2(isakmp_sa, ISAKMP_EXCH_INFO, 0, &args,
1721 0, 0);
1722 else
1723 exchange_establish_p1(msg->transport, ISAKMP_EXCH_INFO,
1724 msg->exchange ? msg->exchange->doi->id : ISAKMP_DOI_ISAKMP,
1725 0, &args, 0, 0);
1726 }
1727
1728 /* Send a DELETE inside an informational exchange for each protocol in SA. */
1729 void
message_send_delete(struct sa * sa)1730 message_send_delete(struct sa *sa)
1731 {
1732 struct info_args args;
1733 struct proto *proto;
1734 struct sa *isakmp_sa;
1735 struct sockaddr *dst;
1736
1737 sa->transport->vtbl->get_dst(sa->transport, &dst);
1738 isakmp_sa = sa_isakmp_lookup_by_peer(dst, SA_LEN(dst));
1739 if (!isakmp_sa) {
1740 /*
1741 * XXX We ought to setup an ISAKMP SA with our peer here and
1742 * send the DELETE over that one.
1743 */
1744 return;
1745 }
1746 args.discr = 'D';
1747 args.doi = sa->doi->id;
1748 args.u.d.nspis = 1;
1749 for (proto = TAILQ_FIRST(&sa->protos); proto;
1750 proto = TAILQ_NEXT(proto, link)) {
1751 if (proto->proto == ISAKMP_PROTO_ISAKMP) {
1752 args.spi_sz = ISAKMP_HDR_COOKIES_LEN;
1753 args.u.d.spis = sa->cookies;
1754 } else {
1755 args.spi_sz = proto->spi_sz[1];
1756 args.u.d.spis = proto->spi[1];
1757 }
1758 args.proto = proto->proto;
1759 exchange_establish_p2(isakmp_sa, ISAKMP_EXCH_INFO, 0, &args,
1760 0, 0);
1761 }
1762 }
1763
1764 void
message_send_dpd_notify(struct sa * isakmp_sa,u_int16_t notify,u_int32_t seq)1765 message_send_dpd_notify(struct sa* isakmp_sa, u_int16_t notify, u_int32_t seq)
1766 {
1767 struct info_args args;
1768
1769 args.discr = 'P';
1770 args.doi = IPSEC_DOI_IPSEC;
1771 args.proto = ISAKMP_PROTO_ISAKMP;
1772 args.spi_sz = ISAKMP_HDR_COOKIES_LEN;
1773 args.u.dpd.msg_type = notify;
1774 args.u.dpd.spi = isakmp_sa->cookies;
1775 args.u.dpd.seq = htonl(seq);
1776
1777 exchange_establish_p2(isakmp_sa, ISAKMP_EXCH_INFO, 0, &args, 0, 0);
1778 }
1779
1780 /* Build the informational message into MSG. */
1781 int
message_send_info(struct message * msg)1782 message_send_info(struct message *msg)
1783 {
1784 u_int8_t *buf;
1785 size_t sz = 0;
1786 struct info_args *args = msg->extra;
1787 u_int8_t payload;
1788
1789 /* Let the DOI get the first hand on the message. */
1790 if (msg->exchange->doi->informational_pre_hook)
1791 if (msg->exchange->doi->informational_pre_hook(msg))
1792 return -1;
1793
1794 switch (args->discr) {
1795 case 'P':
1796 sz = sizeof args->u.dpd.seq;
1797 /* FALLTHROUGH */
1798 case 'N':
1799 sz += ISAKMP_NOTIFY_SPI_OFF + args->spi_sz;
1800 break;
1801 case 'D':
1802 default: /* Silence gcc */
1803 sz = ISAKMP_DELETE_SPI_OFF + args->u.d.nspis * args->spi_sz;
1804 break;
1805 }
1806
1807 buf = calloc(1, sz);
1808 if (!buf) {
1809 log_error("message_send_info: calloc (1, %lu) failed",
1810 (unsigned long)sz);
1811 message_free(msg);
1812 return -1;
1813 }
1814 switch (args->discr) {
1815 case 'P':
1816 memcpy(buf + ISAKMP_NOTIFY_SPI_OFF + args->spi_sz,
1817 &args->u.dpd.seq, sizeof args->u.dpd.seq);
1818 /* FALLTHROUGH */
1819 case 'N':
1820 /* Build the NOTIFY payload. */
1821 payload = ISAKMP_PAYLOAD_NOTIFY;
1822 SET_ISAKMP_NOTIFY_DOI(buf, args->doi);
1823 SET_ISAKMP_NOTIFY_PROTO(buf, args->proto);
1824 SET_ISAKMP_NOTIFY_SPI_SZ(buf, args->spi_sz);
1825 SET_ISAKMP_NOTIFY_MSG_TYPE(buf, args->u.n.msg_type);
1826 memcpy(buf + ISAKMP_NOTIFY_SPI_OFF, args->u.n.spi,
1827 args->spi_sz);
1828 break;
1829
1830 case 'D':
1831 default: /* Silence GCC. */
1832 /* Build the DELETE payload. */
1833 payload = ISAKMP_PAYLOAD_DELETE;
1834 SET_ISAKMP_DELETE_DOI(buf, args->doi);
1835 SET_ISAKMP_DELETE_PROTO(buf, args->proto);
1836 SET_ISAKMP_DELETE_SPI_SZ(buf, args->spi_sz);
1837 SET_ISAKMP_DELETE_NSPIS(buf, args->u.d.nspis);
1838 memcpy(buf + ISAKMP_DELETE_SPI_OFF, args->u.d.spis,
1839 args->u.d.nspis * args->spi_sz);
1840 msg->flags |= MSG_PRIORITIZED;
1841 break;
1842 }
1843
1844 if (message_add_payload(msg, payload, buf, sz, 1)) {
1845 free(buf);
1846 message_free(msg);
1847 return -1;
1848 }
1849 /* Let the DOI get the last hand on the message. */
1850 if (msg->exchange->doi->informational_post_hook)
1851 if (msg->exchange->doi->informational_post_hook(msg)) {
1852 message_free(msg);
1853 return -1;
1854 }
1855 return 0;
1856 }
1857
1858 /*
1859 * Drop the MSG message due to reason given in NOTIFY. If NOTIFY is set
1860 * send out a notification to the originator. Fill this notification with
1861 * values from PROTO. INCOMING decides which SPI to include. If CLEAN is
1862 * set, free the message when ready with it.
1863 */
1864 void
message_drop(struct message * msg,int notify,struct proto * proto,int incoming,int clean)1865 message_drop(struct message *msg, int notify, struct proto *proto,
1866 int incoming, int clean)
1867 {
1868 struct transport *t = msg->transport;
1869 struct sockaddr *dst;
1870 char *address;
1871 short port = 0;
1872
1873 t->vtbl->get_dst(t, &dst);
1874 if (sockaddr2text(dst, &address, 0)) {
1875 log_error("message_drop: sockaddr2text () failed");
1876 address = 0;
1877 }
1878 switch (dst->sa_family) {
1879 case AF_INET:
1880 port = ((struct sockaddr_in *)dst)->sin_port;
1881 break;
1882 case AF_INET6:
1883 port = ((struct sockaddr_in6 *)dst)->sin6_port;
1884 break;
1885 default:
1886 log_print("message_drop: unknown protocol family %d",
1887 dst->sa_family);
1888 }
1889
1890 log_print("dropped message from %s port %d due to notification type "
1891 "%s", address ? address : "<unknown>", htons(port),
1892 constant_name(isakmp_notify_cst, notify));
1893
1894 if (address)
1895 free(address);
1896
1897 /* If specified, return a notification. */
1898 if (notify)
1899 message_send_notification(msg, msg->isakmp_sa, notify, proto,
1900 incoming);
1901 if (clean)
1902 message_free(msg);
1903 }
1904
1905 /*
1906 * If the user demands debug printouts, printout MSG with as much detail
1907 * as we can without resorting to per-payload handling.
1908 */
1909 void
message_dump_raw(char * header,struct message * msg,int class)1910 message_dump_raw(char *header, struct message *msg, int class)
1911 {
1912 u_int32_t i, j, k = 0;
1913 char buf[80], *p = buf;
1914
1915 LOG_DBG((class, 70, "%s: message %p", header, msg));
1916 field_dump_payload(isakmp_hdr_fld, msg->iov[0].iov_base);
1917 for (i = 0; i < msg->iovlen; i++)
1918 for (j = 0; j < msg->iov[i].iov_len; j++) {
1919 snprintf(p, sizeof buf - (int) (p - buf), "%02x",
1920 ((u_int8_t *) msg->iov[i].iov_base)[j]);
1921 p += 2;
1922 if (++k % 32 == 0) {
1923 *p = '\0';
1924 LOG_DBG((class, 70, "%s: %s", header, buf));
1925 p = buf;
1926 } else if (k % 4 == 0)
1927 *p++ = ' ';
1928 }
1929 *p = '\0';
1930 if (p != buf)
1931 LOG_DBG((class, 70, "%s: %s", header, buf));
1932 }
1933
1934 static void
message_packet_log(struct message * msg)1935 message_packet_log(struct message *msg)
1936 {
1937 struct sockaddr *src, *dst;
1938 struct transport *t = msg->transport;
1939
1940 /* Don't log retransmissions. Redundant for incoming packets... */
1941 if (msg->xmits > 0)
1942 return;
1943
1944 if (msg->exchange && msg->exchange->flags & EXCHANGE_FLAG_NAT_T_ENABLE)
1945 t = ((struct virtual_transport *)msg->transport)->encap;
1946
1947 /* Figure out direction. */
1948 if (msg->exchange &&
1949 msg->exchange->initiator ^ (msg->exchange->step % 2)) {
1950 t->vtbl->get_src(t, &src);
1951 t->vtbl->get_dst(t, &dst);
1952 } else {
1953 t->vtbl->get_src(t, &dst);
1954 t->vtbl->get_dst(t, &src);
1955 }
1956
1957 log_packet_iov(src, dst, msg->iov, msg->iovlen);
1958 }
1959
1960 /*
1961 * Encrypt an outgoing message MSG. As outgoing messages are represented
1962 * with an iovec with one segment per payload, we need to coalesce them
1963 * into just une buffer containing all payloads and some padding before
1964 * we encrypt.
1965 */
1966 static int
message_encrypt(struct message * msg)1967 message_encrypt(struct message *msg)
1968 {
1969 struct exchange *exchange = msg->exchange;
1970 size_t i, sz = 0;
1971 u_int8_t *buf;
1972
1973 /* If no payloads, nothing to do. */
1974 if (msg->iovlen == 1)
1975 return 0;
1976
1977 /*
1978 * For encryption we need to put all payloads together in a single
1979 * buffer. This buffer should be padded to the current crypto
1980 * transform's blocksize.
1981 */
1982 for (i = 1; i < msg->iovlen; i++)
1983 sz += msg->iov[i].iov_len;
1984 sz = ((sz + exchange->crypto->blocksize - 1) /
1985 exchange->crypto->blocksize) * exchange->crypto->blocksize;
1986 buf = realloc(msg->iov[1].iov_base, sz);
1987 if (!buf) {
1988 log_error("message_encrypt: realloc (%p, %lu) failed",
1989 msg->iov[1].iov_base, (unsigned long) sz);
1990 return -1;
1991 }
1992 msg->iov[1].iov_base = buf;
1993 for (i = 2; i < msg->iovlen; i++) {
1994 memcpy(buf + msg->iov[1].iov_len, msg->iov[i].iov_base,
1995 msg->iov[i].iov_len);
1996 msg->iov[1].iov_len += msg->iov[i].iov_len;
1997 free(msg->iov[i].iov_base);
1998 }
1999
2000 /* Pad with zeroes. */
2001 memset(buf + msg->iov[1].iov_len, '\0', sz - msg->iov[1].iov_len);
2002 msg->iov[1].iov_len = sz;
2003 msg->iovlen = 2;
2004
2005 SET_ISAKMP_HDR_FLAGS(msg->iov[0].iov_base,
2006 GET_ISAKMP_HDR_FLAGS(msg->iov[0].iov_base) | ISAKMP_FLAGS_ENC);
2007 SET_ISAKMP_HDR_LENGTH(msg->iov[0].iov_base, ISAKMP_HDR_SZ + sz);
2008 crypto_encrypt(exchange->keystate, buf, msg->iov[1].iov_len);
2009 msg->flags |= MSG_ENCRYPTED;
2010
2011 /* Update the IV so we can decrypt the next incoming message. */
2012 crypto_update_iv(exchange->keystate);
2013
2014 return 0;
2015 }
2016
2017 /*
2018 * Check whether the message MSG is a duplicate of the last one negotiating
2019 * this specific SA.
2020 */
2021 static int
message_check_duplicate(struct message * msg)2022 message_check_duplicate(struct message *msg)
2023 {
2024 struct exchange *exchange = msg->exchange;
2025 size_t sz = msg->iov[0].iov_len;
2026 u_int8_t *pkt = msg->iov[0].iov_base;
2027
2028 /* If no SA has been found, we cannot test, thus it's good. */
2029 if (!exchange)
2030 return 0;
2031
2032 LOG_DBG((LOG_MESSAGE, 90, "message_check_duplicate: last_received %p",
2033 exchange->last_received));
2034 if (exchange->last_received) {
2035 LOG_DBG_BUF((LOG_MESSAGE, 95,
2036 "message_check_duplicate: last_received",
2037 exchange->last_received->orig,
2038 exchange->last_received->orig_sz));
2039 /* Is it a duplicate, lose the new one. */
2040 if (sz == exchange->last_received->orig_sz &&
2041 memcmp(pkt, exchange->last_received->orig, sz) == 0) {
2042 LOG_DBG((LOG_MESSAGE, 80,
2043 "message_check_duplicate: dropping dup"));
2044
2045 /*
2046 * Retransmit if the previos sent message was the last
2047 * of an exchange, otherwise just wait for the
2048 * ordinary retransmission.
2049 */
2050 if (exchange->last_sent && (exchange->last_sent->flags
2051 & MSG_LAST))
2052 message_send(exchange->last_sent);
2053 message_free(msg);
2054 return -1;
2055 }
2056 }
2057 /*
2058 * As this new message is an indication that state is moving forward
2059 * at the peer, remove the retransmit timer on our last message.
2060 */
2061 if (exchange->last_sent) {
2062 if (exchange->last_sent == exchange->in_transit) {
2063 struct message *m = exchange->in_transit;
2064 TAILQ_REMOVE(m->transport->vtbl->get_queue(m), m,
2065 link);
2066 exchange->in_transit = 0;
2067 }
2068 message_free(exchange->last_sent);
2069 exchange->last_sent = 0;
2070 }
2071 return 0;
2072 }
2073
2074 /* Helper to message_negotiate_sa. */
2075 static __inline struct payload *
step_transform(struct payload * tp,struct payload ** propp,struct payload ** sap)2076 step_transform(struct payload *tp, struct payload **propp,
2077 struct payload **sap)
2078 {
2079 tp = TAILQ_NEXT(tp, link);
2080 if (tp) {
2081 *propp = tp->context;
2082 *sap = (*propp)->context;
2083 }
2084 return tp;
2085 }
2086
2087 /*
2088 * Pick out the first transforms out of MSG (which should contain at least one
2089 * SA payload) we accept as a full protection suite.
2090 */
2091 int
message_negotiate_sa(struct message * msg,int (* validate)(struct exchange *,struct sa *,struct sa *))2092 message_negotiate_sa(struct message *msg, int (*validate)(struct exchange *,
2093 struct sa *, struct sa *))
2094 {
2095 struct payload *tp, *propp, *sap, *next_tp = 0, *next_propp, *next_sap;
2096 struct payload *saved_tp = 0, *saved_propp = 0, *saved_sap = 0;
2097 struct sa *sa;
2098 struct proto *proto;
2099 int suite_ok_so_far = 0;
2100 struct exchange *exchange = msg->exchange;
2101
2102 /*
2103 * This algorithm is a weird bottom-up thing... mostly due to the
2104 * payload links pointing upwards.
2105 *
2106 * The algorithm goes something like this:
2107 * Foreach transform
2108 * If transform is compatible
2109 * Remember that this protocol can work
2110 * Skip to last transform of this protocol
2111 * If next transform belongs to a new protocol inside the same suite
2112 * If no transform was found for the current protocol
2113 * Forget all earlier transforms for protocols in this suite
2114 * Skip to last transform of this suite
2115 * If next transform belongs to a new suite
2116 * If the current protocol had an OK transform
2117 * Skip to the last transform of this SA
2118 * If the next transform belongs to a new SA
2119 * If no transforms have been chosen
2120 * Issue a NO_PROPOSAL_CHOSEN notification
2121 */
2122
2123 sa = TAILQ_FIRST(&exchange->sa_list);
2124 for (tp = payload_first(msg, ISAKMP_PAYLOAD_TRANSFORM); tp;
2125 tp = next_tp) {
2126 propp = tp->context;
2127 sap = propp->context;
2128 sap->flags |= PL_MARK;
2129 next_tp = step_transform(tp, &next_propp, &next_sap);
2130
2131 /* For each transform, see if it is compatible. */
2132 if (!attribute_map(tp->p + ISAKMP_TRANSFORM_SA_ATTRS_OFF,
2133 GET_ISAKMP_GEN_LENGTH(tp->p) -
2134 ISAKMP_TRANSFORM_SA_ATTRS_OFF,
2135 exchange->doi->is_attribute_incompatible, msg)) {
2136 LOG_DBG((LOG_NEGOTIATION, 30, "message_negotiate_sa: "
2137 "transform %d proto %d proposal %d ok",
2138 GET_ISAKMP_TRANSFORM_NO(tp->p),
2139 GET_ISAKMP_PROP_PROTO(propp->p),
2140 GET_ISAKMP_PROP_NO(propp->p)));
2141 if (sa_add_transform(sa, tp, exchange->initiator,
2142 &proto))
2143 goto cleanup;
2144 suite_ok_so_far = 1;
2145
2146 saved_tp = next_tp;
2147 saved_propp = next_propp;
2148 saved_sap = next_sap;
2149 /* Skip to last transform of this protocol proposal. */
2150 while ((next_tp = step_transform(tp, &next_propp,
2151 &next_sap)) && next_propp == propp)
2152 tp = next_tp;
2153 }
2154 retry_transform:
2155 /*
2156 * Figure out if we will be looking at a new protocol proposal
2157 * inside the current protection suite.
2158 */
2159 if (next_tp && propp != next_propp && sap == next_sap &&
2160 (GET_ISAKMP_PROP_NO(propp->p) ==
2161 GET_ISAKMP_PROP_NO(next_propp->p))) {
2162 if (!suite_ok_so_far) {
2163 LOG_DBG((LOG_NEGOTIATION, 30,
2164 "message_negotiate_sa: proto %d proposal "
2165 "%d failed",
2166 GET_ISAKMP_PROP_PROTO(propp->p),
2167 GET_ISAKMP_PROP_NO(propp->p)));
2168 /*
2169 * Remove potentially succeeded choices from
2170 * the SA.
2171 */
2172 while (TAILQ_FIRST(&sa->protos))
2173 TAILQ_REMOVE(&sa->protos,
2174 TAILQ_FIRST(&sa->protos), link);
2175
2176 /*
2177 * Skip to the last transform of this
2178 * protection suite.
2179 */
2180 while ((next_tp = step_transform(tp,
2181 &next_propp, &next_sap)) &&
2182 (GET_ISAKMP_PROP_NO(next_propp->p) ==
2183 GET_ISAKMP_PROP_NO(propp->p)) &&
2184 next_sap == sap)
2185 tp = next_tp;
2186 }
2187 suite_ok_so_far = 0;
2188 }
2189 /*
2190 * Figure out if we will be looking at a new protection
2191 * suite.
2192 */
2193 if (!next_tp ||
2194 (propp != next_propp && (GET_ISAKMP_PROP_NO(propp->p) !=
2195 GET_ISAKMP_PROP_NO(next_propp->p))) ||
2196 sap != next_sap) {
2197 /*
2198 * Check if the suite we just considered was OK, if so
2199 * we check it against the accepted ones.
2200 */
2201 if (suite_ok_so_far) {
2202 if (!validate || validate(exchange, sa,
2203 msg->isakmp_sa)) {
2204 LOG_DBG((LOG_NEGOTIATION, 30,
2205 "message_negotiate_sa: proposal "
2206 "%d succeeded",
2207 GET_ISAKMP_PROP_NO(propp->p)));
2208
2209 /*
2210 * Skip to the last transform of this
2211 * SA.
2212 */
2213 while ((next_tp = step_transform(tp,
2214 &next_propp, &next_sap)) &&
2215 next_sap == sap)
2216 tp = next_tp;
2217 } else {
2218 /* Backtrack. */
2219 LOG_DBG((LOG_NEGOTIATION, 30,
2220 "message_negotiate_sa: proposal "
2221 "%d failed",
2222 GET_ISAKMP_PROP_NO(propp->p)));
2223 next_tp = saved_tp;
2224 next_propp = saved_propp;
2225 next_sap = saved_sap;
2226 suite_ok_so_far = 0;
2227
2228 /*
2229 * Remove potentially succeeded
2230 * choices from the SA.
2231 */
2232 while (TAILQ_FIRST(&sa->protos))
2233 TAILQ_REMOVE(&sa->protos,
2234 TAILQ_FIRST(&sa->protos),
2235 link);
2236 goto retry_transform;
2237 }
2238 }
2239 }
2240 /* Have we walked all the proposals of an SA? */
2241 if (!next_tp || sap != next_sap) {
2242 if (!suite_ok_so_far) {
2243 /*
2244 * XXX We cannot possibly call this a drop...
2245 * seeing we just turn down one of the offers,
2246 * can we? I suggest renaming message_drop to
2247 * something else.
2248 */
2249 log_print("message_negotiate_sa: no "
2250 "compatible proposal found");
2251 message_drop(msg,
2252 ISAKMP_NOTIFY_NO_PROPOSAL_CHOSEN, 0, 1, 0);
2253 }
2254 sa = TAILQ_NEXT(sa, next);
2255 }
2256 }
2257 return 0;
2258
2259 cleanup:
2260 /*
2261 * Remove potentially succeeded choices from the SA.
2262 * XXX Do we leak struct protos and related data here?
2263 */
2264 while (TAILQ_FIRST(&sa->protos))
2265 TAILQ_REMOVE(&sa->protos, TAILQ_FIRST(&sa->protos), link);
2266 return -1;
2267 }
2268
2269 /*
2270 * Add SA, proposal and transform payload(s) to MSG out of information
2271 * found in the exchange MSG is part of..
2272 */
2273 int
message_add_sa_payload(struct message * msg)2274 message_add_sa_payload(struct message *msg)
2275 {
2276 struct exchange *exchange = msg->exchange;
2277 u_int8_t *sa_buf, *saved_nextp_sa, *saved_nextp_prop;
2278 size_t sa_len, extra_sa_len;
2279 int i, nprotos = 0;
2280 struct proto *proto;
2281 u_int8_t **transforms = 0, **proposals = 0;
2282 size_t *transform_lens = 0, *proposal_lens = 0;
2283 struct sa *sa;
2284 struct doi *doi = exchange->doi;
2285 u_int8_t *spi = 0;
2286 size_t spi_sz;
2287
2288 /*
2289 * Generate SA payloads.
2290 */
2291 for (sa = TAILQ_FIRST(&exchange->sa_list); sa;
2292 sa = TAILQ_NEXT(sa, next)) {
2293 /* Setup a SA payload. */
2294 sa_len = ISAKMP_SA_SIT_OFF + doi->situation_size();
2295 extra_sa_len = 0;
2296 sa_buf = malloc(sa_len);
2297 if (!sa_buf) {
2298 log_error("message_add_sa_payload: "
2299 "malloc (%lu) failed", (unsigned long)sa_len);
2300 goto cleanup;
2301 }
2302 SET_ISAKMP_SA_DOI(sa_buf, doi->id);
2303 doi->setup_situation(sa_buf);
2304
2305 /* Count transforms. */
2306 nprotos = 0;
2307 for (proto = TAILQ_FIRST(&sa->protos); proto;
2308 proto = TAILQ_NEXT(proto, link))
2309 nprotos++;
2310
2311 /*
2312 * Allocate transient transform and proposal payload/size
2313 * vectors.
2314 */
2315 transforms = calloc(nprotos, sizeof *transforms);
2316 if (!transforms) {
2317 log_error("message_add_sa_payload: calloc (%d, %lu) "
2318 "failed", nprotos,
2319 (unsigned long)sizeof *transforms);
2320 goto cleanup;
2321 }
2322 transform_lens = calloc(nprotos, sizeof *transform_lens);
2323 if (!transform_lens) {
2324 log_error("message_add_sa_payload: calloc (%d, %lu) "
2325 "failed", nprotos,
2326 (unsigned long) sizeof *transform_lens);
2327 goto cleanup;
2328 }
2329 proposals = calloc(nprotos, sizeof *proposals);
2330 if (!proposals) {
2331 log_error("message_add_sa_payload: calloc (%d, %lu) "
2332 "failed", nprotos,
2333 (unsigned long)sizeof *proposals);
2334 goto cleanup;
2335 }
2336 proposal_lens = calloc(nprotos, sizeof *proposal_lens);
2337 if (!proposal_lens) {
2338 log_error("message_add_sa_payload: calloc (%d, %lu) "
2339 "failed", nprotos,
2340 (unsigned long)sizeof *proposal_lens);
2341 goto cleanup;
2342 }
2343 /* Pick out the chosen transforms. */
2344 for (proto = TAILQ_FIRST(&sa->protos), i = 0; proto;
2345 proto = TAILQ_NEXT(proto, link), i++) {
2346 transform_lens[i] =
2347 GET_ISAKMP_GEN_LENGTH(proto->chosen->p);
2348 transforms[i] = malloc(transform_lens[i]);
2349 if (!transforms[i]) {
2350 log_error("message_add_sa_payload: malloc "
2351 "(%lu) failed",
2352 (unsigned long)transform_lens[i]);
2353 goto cleanup;
2354 }
2355 /* Get incoming SPI from application. */
2356 if (doi->get_spi) {
2357 spi = doi->get_spi(&spi_sz,
2358 GET_ISAKMP_PROP_PROTO(proto->chosen->context->p),
2359 msg);
2360 if (spi_sz && !spi)
2361 goto cleanup;
2362 proto->spi[1] = spi;
2363 proto->spi_sz[1] = spi_sz;
2364 } else
2365 spi_sz = 0;
2366
2367 proposal_lens[i] = ISAKMP_PROP_SPI_OFF + spi_sz;
2368 proposals[i] = malloc(proposal_lens[i]);
2369 if (!proposals[i]) {
2370 log_error("message_add_sa_payload: malloc "
2371 "(%lu) failed",
2372 (unsigned long)proposal_lens[i]);
2373 goto cleanup;
2374 }
2375 memcpy(transforms[i], proto->chosen->p,
2376 transform_lens[i]);
2377 memcpy(proposals[i], proto->chosen->context->p,
2378 ISAKMP_PROP_SPI_OFF);
2379 SET_ISAKMP_PROP_NTRANSFORMS(proposals[i], 1);
2380 SET_ISAKMP_PROP_SPI_SZ(proposals[i], spi_sz);
2381 if (spi_sz)
2382 memcpy(proposals[i] + ISAKMP_PROP_SPI_OFF, spi,
2383 spi_sz);
2384 extra_sa_len += proposal_lens[i] + transform_lens[i];
2385 }
2386
2387 /*
2388 * Add the payloads. As this is a SA, we need to recompute the
2389 * lengths of the payloads containing others. We also need to
2390 * reset these payload's "next payload type" field.
2391 */
2392 if (message_add_payload(msg, ISAKMP_PAYLOAD_SA, sa_buf,
2393 sa_len, 1))
2394 goto cleanup;
2395 SET_ISAKMP_GEN_LENGTH(sa_buf, sa_len + extra_sa_len);
2396 sa_buf = 0;
2397
2398 saved_nextp_sa = msg->nextp;
2399 for (proto = TAILQ_FIRST(&sa->protos), i = 0; proto;
2400 proto = TAILQ_NEXT(proto, link), i++) {
2401 if (message_add_payload(msg, ISAKMP_PAYLOAD_PROPOSAL,
2402 proposals[i], proposal_lens[i], i > 1))
2403 goto cleanup;
2404 SET_ISAKMP_GEN_LENGTH(proposals[i], proposal_lens[i] +
2405 transform_lens[i]);
2406 proposals[i] = 0;
2407
2408 saved_nextp_prop = msg->nextp;
2409 if (message_add_payload(msg, ISAKMP_PAYLOAD_TRANSFORM,
2410 transforms[i], transform_lens[i], 0))
2411 goto cleanup;
2412 msg->nextp = saved_nextp_prop;
2413 transforms[i] = 0;
2414 }
2415 msg->nextp = saved_nextp_sa;
2416
2417 /* Free the temporary allocations made above. */
2418 free(transforms);
2419 free(transform_lens);
2420 free(proposals);
2421 free(proposal_lens);
2422 }
2423 return 0;
2424
2425 cleanup:
2426 if (sa_buf)
2427 free(sa_buf);
2428 for (i = 0; i < nprotos; i++) {
2429 if (transforms[i])
2430 free(transforms[i]);
2431 if (proposals[i])
2432 free(proposals[i]);
2433 }
2434 if (transforms)
2435 free(transforms);
2436 if (transform_lens)
2437 free(transform_lens);
2438 if (proposals)
2439 free(proposals);
2440 if (proposal_lens)
2441 free(proposal_lens);
2442 return -1;
2443 }
2444
2445 /*
2446 * Return a copy of MSG's constants starting from OFFSET and stash the size
2447 * in SZP. It is the callers responsibility to free this up.
2448 */
2449 u_int8_t *
message_copy(struct message * msg,size_t offset,size_t * szp)2450 message_copy(struct message *msg, size_t offset, size_t *szp)
2451 {
2452 int skip = 0;
2453 size_t i, sz = 0;
2454 ssize_t start = -1;
2455 u_int8_t *buf, *p;
2456
2457 /* Calculate size of message and where we want to start to copy. */
2458 for (i = 1; i < msg->iovlen; i++) {
2459 sz += msg->iov[i].iov_len;
2460 if (sz <= offset)
2461 skip = i;
2462 else if (start < 0)
2463 start = offset - (sz - msg->iov[i].iov_len);
2464 }
2465
2466 /* Allocate and copy. */
2467 *szp = sz - offset;
2468 buf = malloc(*szp);
2469 if (!buf)
2470 return 0;
2471 p = buf;
2472 for (i = skip + 1; i < msg->iovlen; i++) {
2473 memcpy(p, (u_int8_t *) msg->iov[i].iov_base + start,
2474 msg->iov[i].iov_len - start);
2475 p += msg->iov[i].iov_len - start;
2476 start = 0;
2477 }
2478 return buf;
2479 }
2480
2481 /* Register a post-send function POST_SEND with message MSG. */
2482 int
message_register_post_send(struct message * msg,void (* post_send)(struct message *))2483 message_register_post_send(struct message *msg,
2484 void (*post_send)(struct message *))
2485 {
2486 struct post_send *node;
2487
2488 node = malloc(sizeof *node);
2489 if (!node)
2490 return -1;
2491 node->func = post_send;
2492 TAILQ_INSERT_TAIL(&msg->post_send, node, link);
2493 return 0;
2494 }
2495
2496 /* Run the post-send functions of message MSG. */
2497 void
message_post_send(struct message * msg)2498 message_post_send(struct message *msg)
2499 {
2500 struct post_send *node;
2501
2502 while ((node = TAILQ_FIRST(&msg->post_send)) != 0) {
2503 TAILQ_REMOVE(&msg->post_send, node, link);
2504 node->func(msg);
2505 free(node);
2506 }
2507 }
2508
2509 struct payload *
payload_first(struct message * msg,u_int8_t payload)2510 payload_first(struct message *msg, u_int8_t payload)
2511 {
2512 return TAILQ_FIRST(&msg->payload[payload]);
2513 }
2514