1 // SoftEther VPN Source Code - Developer Edition Master Branch
2 // Cedar Communication Module
3 
4 
5 // Proto_IkePacket.c
6 // IKE (ISAKMP) packet processing
7 
8 #include "Proto_IkePacket.h"
9 
10 #include "Mayaqua/Memory.h"
11 #include "Mayaqua/Str.h"
12 #include "Mayaqua/TcpIp.h"
13 
14 // Convert the string to a password
IkeStrToPassword(char * str)15 BUF *IkeStrToPassword(char *str)
16 {
17 	BUF *b;
18 	// Validate arguments
19 	if (str == NULL)
20 	{
21 		return NewBuf();
22 	}
23 
24 	if (StartWith(str, "0x") == false)
25 	{
26 		// Accept the string as is
27 		b = NewBuf();
28 		WriteBuf(b, str, StrLen(str));
29 	}
30 	else
31 	{
32 		// Interpret as a hexadecimal value
33 		b = StrToBin(str + 2);
34 	}
35 
36 	return b;
37 }
38 
39 // Build a data payload
IkeBuildDataPayload(IKE_PACKET_DATA_PAYLOAD * t)40 BUF *IkeBuildDataPayload(IKE_PACKET_DATA_PAYLOAD *t)
41 {
42 	BUF *b;
43 	// Validate arguments
44 	if (t == NULL)
45 	{
46 		return NULL;
47 	}
48 
49 	b = NewBuf();
50 	WriteBuf(b, t->Data->Buf, t->Data->Size);
51 
52 	return b;
53 }
54 
55 // Build a SA payload
IkeBuildSaPayload(IKE_PACKET_SA_PAYLOAD * t)56 BUF *IkeBuildSaPayload(IKE_PACKET_SA_PAYLOAD *t)
57 {
58 	IKE_SA_HEADER h;
59 	BUF *ret;
60 	BUF *b;
61 	// Validate arguments
62 	if (t == NULL)
63 	{
64 		return NULL;
65 	}
66 
67 	Zero(&h, sizeof(h));
68 	h.DoI = Endian32(IKE_SA_DOI_IPSEC);
69 	h.Situation = Endian32(IKE_SA_SITUATION_IDENTITY);
70 
71 	ret = NewBuf();
72 
73 	WriteBuf(ret, &h, sizeof(h));
74 
75 	b = IkeBuildPayloadList(t->PayloadList);
76 	WriteBufBuf(ret, b);
77 
78 	FreeBuf(b);
79 
80 	return ret;
81 }
82 
83 // Build a proposal payload
IkeBuildProposalPayload(IKE_PACKET_PROPOSAL_PAYLOAD * t)84 BUF *IkeBuildProposalPayload(IKE_PACKET_PROPOSAL_PAYLOAD *t)
85 {
86 	IKE_PROPOSAL_HEADER h;
87 	BUF *ret, *b;
88 	// Validate arguments
89 	if (t == NULL)
90 	{
91 		return NULL;
92 	}
93 
94 	Zero(&h, sizeof(h));
95 	h.Number = t->Number;
96 	h.NumTransforms = LIST_NUM(t->PayloadList);
97 	h.ProtocolId = t->ProtocolId;
98 	h.SpiSize = t->Spi->Size;
99 
100 	ret = NewBuf();
101 	WriteBuf(ret, &h, sizeof(h));
102 	WriteBufBuf(ret, t->Spi);
103 
104 	b = IkeBuildPayloadList(t->PayloadList);
105 	WriteBufBuf(ret, b);
106 
107 	FreeBuf(b);
108 
109 	return ret;
110 }
111 
112 // Build the transform value list
IkeBuildTransformValueList(LIST * o)113 BUF *IkeBuildTransformValueList(LIST *o)
114 {
115 	BUF *b;
116 	UINT i;
117 	// Validate arguments
118 	if (o == NULL)
119 	{
120 		return NULL;
121 	}
122 
123 	b = NewBuf();
124 
125 	for (i = 0;i < LIST_NUM(o);i++)
126 	{
127 		IKE_PACKET_TRANSFORM_VALUE *v = LIST_DATA(o, i);
128 		BUF *tmp = IkeBuildTransformValue(v);
129 
130 		WriteBufBuf(b, tmp);
131 
132 		FreeBuf(tmp);
133 	}
134 
135 	return b;
136 }
137 
138 // Build a transform value
IkeBuildTransformValue(IKE_PACKET_TRANSFORM_VALUE * v)139 BUF *IkeBuildTransformValue(IKE_PACKET_TRANSFORM_VALUE *v)
140 {
141 	BUF *b;
142 	UCHAR af_bit, type;
143 	USHORT size_or_value;
144 	// Validate arguments
145 	if (v == NULL)
146 	{
147 		return NULL;
148 	}
149 
150 	type = v->Type;
151 
152 	if (v->Value >= 65536)
153 	{
154 		// 32 bit
155 		af_bit = 0;
156 		size_or_value = Endian16(sizeof(UINT));
157 	}
158 	else
159 	{
160 		// 16 bit
161 		af_bit = 0x80;
162 		size_or_value = Endian16((USHORT)v->Value);
163 	}
164 
165 	b = NewBuf();
166 	WriteBuf(b, &af_bit, sizeof(af_bit));
167 	WriteBuf(b, &type, sizeof(type));
168 	WriteBuf(b, &size_or_value, sizeof(size_or_value));
169 
170 	if (af_bit == 0)
171 	{
172 		UINT value = Endian32(v->Value);
173 		WriteBuf(b, &value, sizeof(UINT));
174 	}
175 
176 	return b;
177 }
178 
179 // Build a transform payload
IkeBuildTransformPayload(IKE_PACKET_TRANSFORM_PAYLOAD * t)180 BUF *IkeBuildTransformPayload(IKE_PACKET_TRANSFORM_PAYLOAD *t)
181 {
182 	IKE_TRANSFORM_HEADER h;
183 	BUF *ret, *b;
184 	// Validate arguments
185 	if (t == NULL)
186 	{
187 		return NULL;
188 	}
189 
190 	Zero(&h, sizeof(h));
191 	h.Number = t->Number;
192 	h.TransformId = t->TransformId;
193 
194 	ret = NewBuf();
195 	WriteBuf(ret, &h, sizeof(h));
196 
197 	b = IkeBuildTransformValueList(t->ValueList);
198 	WriteBufBuf(ret, b);
199 
200 	FreeBuf(b);
201 
202 	return ret;
203 }
204 
205 // Get the value from the transform payload
IkeGetTransformValue(IKE_PACKET_TRANSFORM_PAYLOAD * t,UINT type,UINT index)206 UINT IkeGetTransformValue(IKE_PACKET_TRANSFORM_PAYLOAD *t, UINT type, UINT index)
207 {
208 	UINT i;
209 	UINT num;
210 	// Validate arguments
211 	if (t == NULL)
212 	{
213 		return 0;
214 	}
215 
216 	num = 0;
217 
218 	for (i = 0;i < LIST_NUM(t->ValueList);i++)
219 	{
220 		IKE_PACKET_TRANSFORM_VALUE *v = LIST_DATA(t->ValueList, i);
221 
222 		if (v->Type == type)
223 		{
224 			if (num == index)
225 			{
226 				return v->Value;
227 			}
228 
229 			num++;
230 		}
231 	}
232 
233 	return 0;
234 }
235 
236 // Get the number of values from the transform payload
IkeGetTransformValueNum(IKE_PACKET_TRANSFORM_PAYLOAD * t,UINT type)237 UINT IkeGetTransformValueNum(IKE_PACKET_TRANSFORM_PAYLOAD *t, UINT type)
238 {
239 	UINT i;
240 	UINT num;
241 	// Validate arguments
242 	if (t == NULL)
243 	{
244 		return 0;
245 	}
246 
247 	num = 0;
248 
249 	for (i = 0;i < LIST_NUM(t->ValueList);i++)
250 	{
251 		IKE_PACKET_TRANSFORM_VALUE *v = LIST_DATA(t->ValueList, i);
252 
253 		if (v->Type == type)
254 		{
255 			num++;
256 		}
257 	}
258 
259 	return num;
260 }
261 
262 // Build the ID payload
IkeBuildIdPayload(IKE_PACKET_ID_PAYLOAD * t)263 BUF *IkeBuildIdPayload(IKE_PACKET_ID_PAYLOAD *t)
264 {
265 	IKE_ID_HEADER h;
266 	BUF *ret;
267 	// Validate arguments
268 	if (t == NULL)
269 	{
270 		return NULL;
271 	}
272 
273 	Zero(&h, sizeof(h));
274 	h.IdType = t->Type;
275 	h.Port = Endian16(t->Port);
276 	h.ProtocolId = t->ProtocolId;
277 
278 	ret = NewBuf();
279 	WriteBuf(ret, &h, sizeof(h));
280 
281 	WriteBufBuf(ret, t->IdData);
282 
283 	return ret;
284 }
285 
286 // Build a certificate payload
IkeBuildCertPayload(IKE_PACKET_CERT_PAYLOAD * t)287 BUF *IkeBuildCertPayload(IKE_PACKET_CERT_PAYLOAD *t)
288 {
289 	IKE_CERT_HEADER h;
290 	BUF *ret;
291 	// Validate arguments
292 	if (t == NULL)
293 	{
294 		return NULL;
295 	}
296 
297 	Zero(&h, sizeof(h));
298 	h.CertType = t->CertType;
299 
300 	ret = NewBuf();
301 	WriteBuf(ret, &h, sizeof(h));
302 	WriteBufBuf(ret, t->CertData);
303 
304 	return ret;
305 }
306 
307 // Build a certificate request payload
IkeBuildCertRequestPayload(IKE_PACKET_CERT_REQUEST_PAYLOAD * t)308 BUF *IkeBuildCertRequestPayload(IKE_PACKET_CERT_REQUEST_PAYLOAD *t)
309 {
310 	IKE_CERT_REQUEST_HEADER h;
311 	BUF *ret;
312 	// Validate arguments
313 	if (t == NULL)
314 	{
315 		return NULL;
316 	}
317 
318 	Zero(&h, sizeof(h));
319 	h.CertType = t->CertType;
320 
321 	ret = NewBuf();
322 	WriteBuf(ret, &h, sizeof(h));
323 	WriteBufBuf(ret, t->Data);
324 
325 	return ret;
326 }
327 
328 // Build a notification payload
IkeBuildNoticePayload(IKE_PACKET_NOTICE_PAYLOAD * t)329 BUF *IkeBuildNoticePayload(IKE_PACKET_NOTICE_PAYLOAD *t)
330 {
331 	IKE_NOTICE_HEADER h;
332 	BUF *ret;
333 	// Validate arguments
334 	if (t == NULL)
335 	{
336 		return NULL;
337 	}
338 
339 	Zero(&h, sizeof(h));
340 	h.DoI = Endian32(IKE_SA_DOI_IPSEC);
341 	h.MessageType = Endian16(t->MessageType);
342 	h.ProtocolId = t->ProtocolId;
343 	h.SpiSize = t->Spi->Size;
344 
345 	ret = NewBuf();
346 	WriteBuf(ret, &h, sizeof(h));
347 	WriteBuf(ret, t->Spi->Buf, t->Spi->Size);
348 
349 	if (t->MessageData != NULL)
350 	{
351 		WriteBuf(ret, t->MessageData->Buf, t->MessageData->Size);
352 	}
353 
354 	return ret;
355 }
356 
357 // Build a NAT-OA payload
IkeBuildNatOaPayload(IKE_PACKET_NAT_OA_PAYLOAD * t)358 BUF *IkeBuildNatOaPayload(IKE_PACKET_NAT_OA_PAYLOAD *t)
359 {
360 	IKE_NAT_OA_HEADER h;
361 	BUF *ret;
362 	// Validate arguments
363 	if (t == NULL)
364 	{
365 		return NULL;
366 	}
367 
368 	Zero(&h, sizeof(h));
369 
370 	if (IsIP6(&t->IpAddress))
371 	{
372 		h.IdType = IKE_ID_IPV6_ADDR;
373 	}
374 	else
375 	{
376 		h.IdType = IKE_ID_IPV4_ADDR;
377 	}
378 
379 	ret = NewBuf();
380 
381 	WriteBuf(ret, &h, sizeof(h));
382 
383 	if (IsIP6(&t->IpAddress))
384 	{
385 		WriteBuf(ret, t->IpAddress.address, sizeof(t->IpAddress.address));
386 	}
387 	else
388 	{
389 		WriteBuf(ret, IPV4(t->IpAddress.address), IPV4_SIZE);
390 	}
391 
392 	return ret;
393 }
394 
395 // Build a deletion payload
IkeBuildDeletePayload(IKE_PACKET_DELETE_PAYLOAD * t)396 BUF *IkeBuildDeletePayload(IKE_PACKET_DELETE_PAYLOAD *t)
397 {
398 	IKE_DELETE_HEADER h;
399 	BUF *ret;
400 	UINT i;
401 	// Validate arguments
402 	if (t == NULL)
403 	{
404 		return NULL;
405 	}
406 
407 	Zero(&h, sizeof(h));
408 	h.DoI = Endian32(IKE_SA_DOI_IPSEC);
409 	h.NumSpis = Endian16(LIST_NUM(t->SpiList));
410 	h.ProtocolId = t->ProtocolId;
411 
412 	if (LIST_NUM(t->SpiList) >= 1)
413 	{
414 		BUF *b = LIST_DATA(t->SpiList, 0);
415 
416 		h.SpiSize = b->Size;
417 	}
418 
419 	ret = NewBuf();
420 	WriteBuf(ret, &h, sizeof(h));
421 
422 	for (i = 0;i < LIST_NUM(t->SpiList);i++)
423 	{
424 		BUF *b = LIST_DATA(t->SpiList, i);
425 
426 		WriteBuf(ret, b->Buf, b->Size);
427 	}
428 
429 	return ret;
430 }
431 
432 // Build a bit array from the payload
IkeBuildPayload(IKE_PACKET_PAYLOAD * p)433 BUF *IkeBuildPayload(IKE_PACKET_PAYLOAD *p)
434 {
435 	BUF *b = NULL;
436 	// Validate arguments
437 	if (p == NULL)
438 	{
439 		return NULL;
440 	}
441 
442 	switch (p->PayloadType)
443 	{
444 	case IKE_PAYLOAD_SA:					// SA payload
445 		b = IkeBuildSaPayload(&p->Payload.Sa);
446 		break;
447 
448 	case IKE_PAYLOAD_PROPOSAL:			// Proposal payload
449 		b = IkeBuildProposalPayload(&p->Payload.Proposal);
450 		break;
451 
452 	case IKE_PAYLOAD_TRANSFORM:			// Transform payload
453 		b = IkeBuildTransformPayload(&p->Payload.Transform);
454 		break;
455 
456 	case IKE_PAYLOAD_ID:					// ID payload
457 		b = IkeBuildIdPayload(&p->Payload.Id);
458 		break;
459 
460 	case IKE_PAYLOAD_CERT:				// Certificate payload
461 		b = IkeBuildCertPayload(&p->Payload.Cert);
462 		break;
463 
464 	case IKE_PAYLOAD_CERT_REQUEST:		// Certificate request payload
465 		b = IkeBuildCertRequestPayload(&p->Payload.CertRequest);
466 		break;
467 
468 	case IKE_PAYLOAD_NOTICE:			// Notification Payload
469 		b = IkeBuildNoticePayload(&p->Payload.Notice);
470 		break;
471 
472 	case IKE_PAYLOAD_DELETE:			// Deletion payload
473 		b = IkeBuildDeletePayload(&p->Payload.Delete);
474 		break;
475 
476 	case IKE_PAYLOAD_NAT_OA:			// NAT-OA payload
477 	case IKE_PAYLOAD_NAT_OA_DRAFT:
478 	case IKE_PAYLOAD_NAT_OA_DRAFT_2:
479 		b = IkeBuildNatOaPayload(&p->Payload.NatOa);
480 		break;
481 
482 	case IKE_PAYLOAD_KEY_EXCHANGE:		// Key exchange payload
483 	case IKE_PAYLOAD_HASH:				// Hash payload
484 	case IKE_PAYLOAD_SIGN:				// Signature payload
485 	case IKE_PAYLOAD_RAND:				// Random number payload
486 	case IKE_PAYLOAD_VENDOR_ID:			// Vendor ID payload
487 	case IKE_PAYLOAD_NAT_D:				// NAT-D payload
488 	case IKE_PAYLOAD_NAT_D_DRAFT:		// NAT-D payload (draft)
489 	default:
490 		b = IkeBuildDataPayload(&p->Payload.GeneralData);
491 		break;
492 	}
493 
494 	if (b != NULL)
495 	{
496 		if (p->BitArray != NULL)
497 		{
498 			FreeBuf(p->BitArray);
499 		}
500 		p->BitArray = CloneBuf(b);
501 	}
502 
503 	return b;
504 }
505 
506 // Get the payload type of the first item
IkeGetFirstPayloadType(LIST * o)507 UCHAR IkeGetFirstPayloadType(LIST *o)
508 {
509 	IKE_PACKET_PAYLOAD *p;
510 	// Validate arguments
511 	if (o == NULL)
512 	{
513 		return IKE_PAYLOAD_NONE;
514 	}
515 
516 	if (LIST_NUM(o) == 0)
517 	{
518 		return IKE_PAYLOAD_NONE;
519 	}
520 
521 	p = (IKE_PACKET_PAYLOAD *)LIST_DATA(o, 0);
522 
523 	return p->PayloadType;
524 }
525 
526 // Build a bit array from the payload list
IkeBuildPayloadList(LIST * o)527 BUF *IkeBuildPayloadList(LIST *o)
528 {
529 	BUF *b;
530 	UINT i;
531 	// Validate arguments
532 	if (o == NULL)
533 	{
534 		return NULL;
535 	}
536 
537 	b = NewBuf();
538 
539 	for (i = 0;i < LIST_NUM(o);i++)
540 	{
541 		IKE_PACKET_PAYLOAD *p = LIST_DATA(o, i);
542 		IKE_PACKET_PAYLOAD *next = NULL;
543 		IKE_COMMON_HEADER h;
544 		BUF *tmp;
545 
546 		if (i < (LIST_NUM(o) - 1))
547 		{
548 			next = LIST_DATA(o, i + 1);
549 		}
550 
551 		Zero(&h, sizeof(h));
552 		if (next != NULL)
553 		{
554 			h.NextPayload = next->PayloadType;
555 		}
556 		else
557 		{
558 			h.NextPayload = IKE_PAYLOAD_NONE;
559 		}
560 
561 		tmp = IkeBuildPayload(p);
562 		if (tmp != NULL)
563 		{
564 			h.PayloadSize = Endian16(tmp->Size + (USHORT)sizeof(h));
565 
566 			WriteBuf(b, &h, sizeof(h));
567 			WriteBuf(b, tmp->Buf, tmp->Size);
568 
569 			FreeBuf(tmp);
570 		}
571 	}
572 
573 	SeekBuf(b, 0, 0);
574 
575 	return b;
576 }
577 
578 // Get the specified payload
IkeGetPayload(LIST * o,UINT payload_type,UINT index)579 IKE_PACKET_PAYLOAD *IkeGetPayload(LIST *o, UINT payload_type, UINT index)
580 {
581 	UINT i, num;
582 	IKE_PACKET_PAYLOAD *ret = NULL;
583 	// Validate arguments
584 	if (o == NULL)
585 	{
586 		return 0;
587 	}
588 
589 	num = 0;
590 
591 	for (i = 0;i < LIST_NUM(o);i++)
592 	{
593 		IKE_PACKET_PAYLOAD *p = LIST_DATA(o, i);
594 
595 		if (p->PayloadType == payload_type)
596 		{
597 			if (num == index)
598 			{
599 				ret = p;
600 				break;
601 			}
602 
603 			num++;
604 		}
605 	}
606 
607 	return ret;
608 }
609 
610 // Get the number of the payload of the specified type
IkeGetPayloadNum(LIST * o,UINT payload_type)611 UINT IkeGetPayloadNum(LIST *o, UINT payload_type)
612 {
613 	UINT i, num;
614 	// Validate arguments
615 	if (o == NULL)
616 	{
617 		return 0;
618 	}
619 
620 	num = 0;
621 
622 	for (i = 0;i < LIST_NUM(o);i++)
623 	{
624 		IKE_PACKET_PAYLOAD *p = LIST_DATA(o, i);
625 
626 		if (p->PayloadType == payload_type)
627 		{
628 			num++;
629 		}
630 	}
631 
632 	return num;
633 }
634 
635 // Create a deletion payload
IkeNewDeletePayload(UCHAR protocol_id,LIST * spi_list)636 IKE_PACKET_PAYLOAD *IkeNewDeletePayload(UCHAR protocol_id, LIST *spi_list)
637 {
638 	IKE_PACKET_PAYLOAD *p;
639 	if (spi_list == NULL)
640 	{
641 		return NULL;
642 	}
643 
644 	p = IkeNewPayload(IKE_PAYLOAD_DELETE);
645 	p->Payload.Delete.ProtocolId = protocol_id;
646 	p->Payload.Delete.SpiList = spi_list;
647 
648 	return p;
649 }
650 
651 // Create a Notification payload
IkeNewNoticePayload(UCHAR protocol_id,USHORT message_type,void * spi,UINT spi_size,void * message,UINT message_size)652 IKE_PACKET_PAYLOAD *IkeNewNoticePayload(UCHAR protocol_id, USHORT message_type,
653 										void *spi, UINT spi_size,
654 										void *message, UINT message_size)
655 {
656 	IKE_PACKET_PAYLOAD *p;
657 	if (spi == NULL && spi_size != 0)
658 	{
659 		return NULL;
660 	}
661 	if (message == NULL && message_size != 0)
662 	{
663 		return NULL;
664 	}
665 
666 	p = IkeNewPayload(IKE_PAYLOAD_NOTICE);
667 	p->Payload.Notice.MessageType = message_type;
668 	p->Payload.Notice.MessageData = MemToBuf(message, message_size);
669 	p->Payload.Notice.Spi = MemToBuf(spi, spi_size);
670 	p->Payload.Notice.ProtocolId = protocol_id;
671 
672 	return p;
673 }
674 
675 // Create a Invalid Cookie Payload
IkeNewNoticeErrorInvalidCookiePayload(UINT64 init_cookie,UINT64 resp_cookie)676 IKE_PACKET_PAYLOAD *IkeNewNoticeErrorInvalidCookiePayload(UINT64 init_cookie, UINT64 resp_cookie)
677 {
678 	IKE_PACKET_PAYLOAD *ret;
679 	BUF *b = NewBuf();
680 
681 	WriteBufInt64(b, init_cookie);
682 	WriteBufInt64(b, resp_cookie);
683 
684 	ret = IkeNewNoticePayload(IKE_PROTOCOL_ID_IKE, IKE_NOTICE_ERROR_INVALID_COOKIE, b->Buf, b->Size,
685 		b->Buf, b->Size);
686 
687 	FreeBuf(b);
688 
689 	return ret;
690 }
691 
692 // Create an Invalid SPI payload
IkeNewNoticeErrorInvalidSpiPayload(UINT spi)693 IKE_PACKET_PAYLOAD *IkeNewNoticeErrorInvalidSpiPayload(UINT spi)
694 {
695 	IKE_PACKET_PAYLOAD *ret;
696 	spi = Endian32(spi);
697 
698 	ret = IkeNewNoticePayload(IKE_PROTOCOL_ID_IPSEC_ESP, IKE_NOTICE_ERROR_INVALID_SPI, &spi, sizeof(UINT),
699 		&spi, sizeof(UINT));
700 
701 	return ret;
702 }
703 
704 // Create a No Proposal Chosen payload
IkeNewNoticeErrorNoProposalChosenPayload(bool quick_mode,UINT64 init_cookie,UINT64 resp_cookie)705 IKE_PACKET_PAYLOAD *IkeNewNoticeErrorNoProposalChosenPayload(bool quick_mode, UINT64 init_cookie, UINT64 resp_cookie)
706 {
707 	BUF *b = NewBuf();
708 	IKE_PACKET_PAYLOAD *ret;
709 
710 	WriteBufInt64(b, init_cookie);
711 	WriteBufInt64(b, resp_cookie);
712 
713 	ret = IkeNewNoticePayload((quick_mode ? IKE_PROTOCOL_ID_IPSEC_ESP : IKE_PROTOCOL_ID_IKE),
714 		IKE_NOTICE_ERROR_NO_PROPOSAL_CHOSEN, b->Buf, b->Size,
715 		NULL, 0);
716 
717 	FreeBuf(b);
718 
719 	return ret;
720 }
721 
722 // Create a DPD payload
IkeNewNoticeDpdPayload(bool ack,UINT64 init_cookie,UINT64 resp_cookie,UINT seq_no)723 IKE_PACKET_PAYLOAD *IkeNewNoticeDpdPayload(bool ack, UINT64 init_cookie, UINT64 resp_cookie, UINT seq_no)
724 {
725 	IKE_PACKET_PAYLOAD *ret;
726 	BUF *b = NewBuf();
727 
728 	seq_no = Endian32(seq_no);
729 
730 	WriteBufInt64(b, init_cookie);
731 	WriteBufInt64(b, resp_cookie);
732 
733 	ret = IkeNewNoticePayload(IKE_PROTOCOL_ID_IKE, (ack ? IKE_NOTICE_DPD_RESPONSE : IKE_NOTICE_DPD_REQUEST),
734 		b->Buf, b->Size,
735 		&seq_no, sizeof(UINT));
736 
737 	FreeBuf(b);
738 
739 	return ret;
740 }
741 
742 // Create an ID payload
IkeNewIdPayload(UCHAR id_type,UCHAR protocol_id,USHORT port,void * id_data,UINT id_size)743 IKE_PACKET_PAYLOAD *IkeNewIdPayload(UCHAR id_type, UCHAR protocol_id, USHORT port, void *id_data, UINT id_size)
744 {
745 	IKE_PACKET_PAYLOAD *p;
746 	if (id_data == NULL && id_size != 0)
747 	{
748 		return NULL;
749 	}
750 
751 	p = IkeNewPayload(IKE_PAYLOAD_ID);
752 	p->Payload.Id.IdData = MemToBuf(id_data, id_size);
753 	p->Payload.Id.Port = port;
754 	p->Payload.Id.ProtocolId = protocol_id;
755 	p->Payload.Id.Type = id_type;
756 
757 	return p;
758 }
759 
760 // Create a transform payload
IkeNewTransformPayload(UCHAR number,UCHAR transform_id,LIST * value_list)761 IKE_PACKET_PAYLOAD *IkeNewTransformPayload(UCHAR number, UCHAR transform_id, LIST *value_list)
762 {
763 	IKE_PACKET_PAYLOAD *p;
764 	if (value_list == NULL)
765 	{
766 		return NULL;
767 	}
768 
769 	p = IkeNewPayload(IKE_PAYLOAD_TRANSFORM);
770 	p->Payload.Transform.Number = number;
771 	p->Payload.Transform.TransformId = transform_id;
772 	p->Payload.Transform.ValueList = value_list;
773 
774 	return p;
775 }
776 
777 // Create a proposal payload
IkeNewProposalPayload(UCHAR number,UCHAR protocol_id,void * spi,UINT spi_size,LIST * payload_list)778 IKE_PACKET_PAYLOAD *IkeNewProposalPayload(UCHAR number, UCHAR protocol_id, void *spi, UINT spi_size, LIST *payload_list)
779 {
780 	IKE_PACKET_PAYLOAD *p;
781 	if (payload_list == NULL || (spi == NULL && spi_size != 0))
782 	{
783 		return NULL;
784 	}
785 
786 	p = IkeNewPayload(IKE_PAYLOAD_PROPOSAL);
787 	p->Payload.Proposal.Number = number;
788 	p->Payload.Proposal.ProtocolId = protocol_id;
789 	p->Payload.Proposal.Spi = MemToBuf(spi, spi_size);
790 	p->Payload.Proposal.PayloadList = payload_list;
791 
792 	return p;
793 }
794 
795 // Create an SA payload
IkeNewSaPayload(LIST * payload_list)796 IKE_PACKET_PAYLOAD *IkeNewSaPayload(LIST *payload_list)
797 {
798 	IKE_PACKET_PAYLOAD *p;
799 	// Validate arguments
800 	if (payload_list == NULL)
801 	{
802 		return NULL;
803 	}
804 
805 	p = IkeNewPayload(IKE_PAYLOAD_SA);
806 	p->Payload.Sa.PayloadList = payload_list;
807 
808 	return p;
809 }
810 
811 // Create a NAT-OA payload
IkeNewNatOaPayload(UCHAR payload_type,IP * ip)812 IKE_PACKET_PAYLOAD *IkeNewNatOaPayload(UCHAR payload_type, IP *ip)
813 {
814 	IKE_PACKET_PAYLOAD *p;
815 	// Validate arguments
816 	if (ip == NULL)
817 	{
818 		return NULL;
819 	}
820 
821 	p = IkeNewPayload(payload_type);
822 	Copy(&p->Payload.NatOa.IpAddress, ip, sizeof(IP));
823 	p->PayloadType = payload_type;
824 
825 	return p;
826 }
827 
828 // Create a data payload
IkeNewDataPayload(UCHAR payload_type,void * data,UINT size)829 IKE_PACKET_PAYLOAD *IkeNewDataPayload(UCHAR payload_type, void *data, UINT size)
830 {
831 	IKE_PACKET_PAYLOAD *p;
832 	// Validate arguments
833 	if (data == NULL)
834 	{
835 		return NULL;
836 	}
837 
838 	p = IkeNewPayload(payload_type);
839 	p->Payload.GeneralData.Data = MemToBuf(data, size);
840 
841 	return p;
842 }
843 
844 // Create a new payload
IkeNewPayload(UINT payload_type)845 IKE_PACKET_PAYLOAD *IkeNewPayload(UINT payload_type)
846 {
847 	IKE_PACKET_PAYLOAD *p;
848 
849 	p = ZeroMalloc(sizeof(IKE_PACKET_PAYLOAD));
850 
851 	p->PayloadType = payload_type;
852 
853 	return p;
854 }
855 
856 // Analyse the IKE payload body
IkeParsePayload(UINT payload_type,BUF * b)857 IKE_PACKET_PAYLOAD *IkeParsePayload(UINT payload_type, BUF *b)
858 {
859 	IKE_PACKET_PAYLOAD *p = NULL;
860 	bool ok = true;
861 	// Validate arguments
862 	if (b == NULL)
863 	{
864 		return NULL;
865 	}
866 
867 	p = ZeroMalloc(sizeof(IKE_PACKET_PAYLOAD));
868 	p->PayloadType = payload_type;
869 
870 	switch (p->PayloadType)
871 	{
872 	case IKE_PAYLOAD_SA:					// SA payload
873 		ok = IkeParseSaPayload(&p->Payload.Sa, b);
874 		break;
875 
876 	case IKE_PAYLOAD_PROPOSAL:			// Proposal payload
877 		ok = IkeParseProposalPayload(&p->Payload.Proposal, b);
878 		break;
879 
880 	case IKE_PAYLOAD_TRANSFORM:			// Proposal payload
881 		ok = IkeParseTransformPayload(&p->Payload.Transform, b);
882 		break;
883 
884 	case IKE_PAYLOAD_ID:					// ID payload
885 		ok = IkeParseIdPayload(&p->Payload.Id, b);
886 		break;
887 
888 	case IKE_PAYLOAD_CERT:				// Certificate payload
889 		ok = IkeParseCertPayload(&p->Payload.Cert, b);
890 		break;
891 
892 	case IKE_PAYLOAD_CERT_REQUEST:		// Certificate request payload
893 		ok = IkeParseCertRequestPayload(&p->Payload.CertRequest, b);
894 		break;
895 
896 	case IKE_PAYLOAD_NOTICE:				// Notification Payload
897 		ok = IkeParseNoticePayload(&p->Payload.Notice, b);
898 		break;
899 
900 	case IKE_PAYLOAD_DELETE:				// Deletion payload
901 		ok = IkeParseDeletePayload(&p->Payload.Delete, b);
902 		break;
903 
904 	case IKE_PAYLOAD_NAT_OA:
905 	case IKE_PAYLOAD_NAT_OA_DRAFT:
906 	case IKE_PAYLOAD_NAT_OA_DRAFT_2:
907 		ok = IkeParseNatOaPayload(&p->Payload.NatOa, b);
908 		break;
909 
910 	case IKE_PAYLOAD_KEY_EXCHANGE:		// Key exchange payload
911 	case IKE_PAYLOAD_HASH:				// Hash payload
912 	case IKE_PAYLOAD_SIGN:				// Signature payload
913 	case IKE_PAYLOAD_RAND:				// Random number payload
914 	case IKE_PAYLOAD_VENDOR_ID:			// Vendor ID payload
915 	case IKE_PAYLOAD_NAT_D:				// NAT-D payload
916 	case IKE_PAYLOAD_NAT_D_DRAFT:		// NAT-D payload (draft)
917 	default:
918 		ok = IkeParseDataPayload(&p->Payload.GeneralData, b);
919 		break;
920 	}
921 
922 	if (ok == false)
923 	{
924 		Free(p);
925 		p = NULL;
926 	}
927 	else
928 	{
929 		p->BitArray = CloneBuf(b);
930 	}
931 
932 	return p;
933 }
934 
935 // Parse the SA payload
IkeParseSaPayload(IKE_PACKET_SA_PAYLOAD * t,BUF * b)936 bool IkeParseSaPayload(IKE_PACKET_SA_PAYLOAD *t, BUF *b)
937 {
938 	IKE_SA_HEADER *h;
939 	UCHAR *buf;
940 	UINT size;
941 	// Validate arguments
942 	if (t == NULL || b == NULL)
943 	{
944 		return false;
945 	}
946 
947 	if (b->Size < sizeof(IKE_SA_HEADER))
948 	{
949 		return false;
950 	}
951 
952 	h = (IKE_SA_HEADER *)b->Buf;
953 	buf = (UCHAR *)b->Buf;
954 	buf += sizeof(IKE_SA_HEADER);
955 	size = b->Size - sizeof(IKE_SA_HEADER);
956 
957 	if (Endian32(h->DoI) != IKE_SA_DOI_IPSEC)
958 	{
959 		Debug("ISAKMP: Invalid DoI Value: 0x%x\n", Endian32(h->DoI));
960 		return false;
961 	}
962 
963 	if (Endian32(h->Situation) != IKE_SA_SITUATION_IDENTITY)
964 	{
965 		Debug("ISAKMP: Invalid Situation Value: 0x%x\n", Endian32(h->Situation));
966 		return false;
967 	}
968 
969 	t->PayloadList = IkeParsePayloadList(buf, size, IKE_PAYLOAD_PROPOSAL);
970 
971 	return true;
972 }
973 
974 // Release the SA payload
IkeFreeSaPayload(IKE_PACKET_SA_PAYLOAD * t)975 void IkeFreeSaPayload(IKE_PACKET_SA_PAYLOAD *t)
976 {
977 	// Validate arguments
978 	if (t == NULL)
979 	{
980 		return;
981 	}
982 
983 	if (t->PayloadList != NULL)
984 	{
985 		IkeFreePayloadList(t->PayloadList);
986 		t->PayloadList = NULL;
987 	}
988 }
989 
990 // Parse the proposal payload
IkeParseProposalPayload(IKE_PACKET_PROPOSAL_PAYLOAD * t,BUF * b)991 bool IkeParseProposalPayload(IKE_PACKET_PROPOSAL_PAYLOAD *t, BUF *b)
992 {
993 	IKE_PROPOSAL_HEADER *h;
994 	UCHAR *buf;
995 	UINT size;
996 	// Validate arguments
997 	if (t == NULL || b == NULL)
998 	{
999 		return false;
1000 	}
1001 
1002 	if (b->Size < sizeof(IKE_PROPOSAL_HEADER))
1003 	{
1004 		return false;
1005 	}
1006 
1007 	h = (IKE_PROPOSAL_HEADER *)b->Buf;
1008 
1009 	t->Number = h->Number;
1010 	t->ProtocolId = h->ProtocolId;
1011 
1012 	buf = (UCHAR *)b->Buf;
1013 	buf += sizeof(IKE_PROPOSAL_HEADER);
1014 	size = b->Size - sizeof(IKE_PROPOSAL_HEADER);
1015 
1016 	if (size < (UINT)h->SpiSize)
1017 	{
1018 		return false;
1019 	}
1020 
1021 	t->Spi = MemToBuf(buf, h->SpiSize);
1022 
1023 	buf += h->SpiSize;
1024 	size -= h->SpiSize;
1025 
1026 	t->PayloadList = IkeParsePayloadList(buf, size, IKE_PAYLOAD_TRANSFORM);
1027 
1028 	return true;
1029 }
1030 
1031 // Release the proposal payload
IkeFreeProposalPayload(IKE_PACKET_PROPOSAL_PAYLOAD * t)1032 void IkeFreeProposalPayload(IKE_PACKET_PROPOSAL_PAYLOAD *t)
1033 {
1034 	// Validate arguments
1035 	if (t == NULL)
1036 	{
1037 		return;
1038 	}
1039 
1040 	if (t->Spi != NULL)
1041 	{
1042 		FreeBuf(t->Spi);
1043 		t->Spi = NULL;
1044 	}
1045 
1046 	if (t->PayloadList != NULL)
1047 	{
1048 		IkeFreePayloadList(t->PayloadList);
1049 		t->PayloadList = NULL;
1050 	}
1051 }
1052 
1053 // Parse the transform payload
IkeParseTransformPayload(IKE_PACKET_TRANSFORM_PAYLOAD * t,BUF * b)1054 bool IkeParseTransformPayload(IKE_PACKET_TRANSFORM_PAYLOAD *t, BUF *b)
1055 {
1056 	IKE_TRANSFORM_HEADER h;
1057 	// Validate arguments
1058 	if (t == NULL || b == NULL)
1059 	{
1060 		return false;
1061 	}
1062 
1063 	if (ReadBuf(b, &h, sizeof(h)) != sizeof(h))
1064 	{
1065 		return false;
1066 	}
1067 
1068 	t->Number = h.Number;
1069 	t->TransformId = h.TransformId;
1070 	t->ValueList = IkeParseTransformValueList(b);
1071 
1072 	return true;
1073 }
1074 
1075 // Create a new transform value
IkeNewTransformValue(UCHAR type,UINT value)1076 IKE_PACKET_TRANSFORM_VALUE *IkeNewTransformValue(UCHAR type, UINT value)
1077 {
1078 	IKE_PACKET_TRANSFORM_VALUE *v = ZeroMalloc(sizeof(IKE_PACKET_TRANSFORM_VALUE));
1079 
1080 	v->Type = type;
1081 	v->Value = value;
1082 
1083 	return v;
1084 }
1085 
1086 // Parse the transform value list
IkeParseTransformValueList(BUF * b)1087 LIST *IkeParseTransformValueList(BUF *b)
1088 {
1089 	LIST *o;
1090 	bool ok = true;
1091 	// Validate arguments
1092 	if (b == NULL)
1093 	{
1094 		return NULL;
1095 	}
1096 
1097 	o = NewListFast(NULL);
1098 
1099 	while (b->Current < b->Size)
1100 	{
1101 		UCHAR af_bit, type;
1102 		USHORT size;
1103 		UINT value = 0;
1104 		IKE_PACKET_TRANSFORM_VALUE *v;
1105 
1106 		if (ReadBuf(b, &af_bit, sizeof(af_bit)) != sizeof(af_bit))
1107 		{
1108 			ok = false;
1109 			break;
1110 		}
1111 
1112 		if (ReadBuf(b, &type, sizeof(type)) != sizeof(type))
1113 		{
1114 			ok = false;
1115 			break;
1116 		}
1117 
1118 		if (ReadBuf(b, &size, sizeof(size)) != sizeof(size))
1119 		{
1120 			ok = false;
1121 		}
1122 
1123 		size = Endian16(size);
1124 
1125 		if (af_bit == 0)
1126 		{
1127 			UCHAR *tmp = Malloc(size);
1128 
1129 			if (ReadBuf(b, tmp, size) != size)
1130 			{
1131 				ok = false;
1132 				Free(tmp);
1133 				break;
1134 			}
1135 
1136 			switch (size)
1137 			{
1138 			case sizeof(UINT):
1139 				value = READ_UINT(tmp);
1140 				break;
1141 
1142 			case sizeof(USHORT):
1143 				value = READ_USHORT(tmp);
1144 				break;
1145 
1146 			case sizeof(UCHAR):
1147 				value = *((UCHAR *)tmp);
1148 				break;
1149 			}
1150 
1151 			Free(tmp);
1152 		}
1153 		else
1154 		{
1155 			value = (UINT)size;
1156 		}
1157 
1158 		v = ZeroMalloc(sizeof(IKE_PACKET_TRANSFORM_VALUE));
1159 		v->Type = type;
1160 		v->Value = value;
1161 
1162 		Add(o, v);
1163 	}
1164 
1165 	if (ok == false)
1166 	{
1167 		IkeFreeTransformValueList(o);
1168 		o = NULL;
1169 	}
1170 
1171 	return o;
1172 }
1173 
1174 // Release the transform value list
IkeFreeTransformValueList(LIST * o)1175 void IkeFreeTransformValueList(LIST *o)
1176 {
1177 	UINT i;
1178 	// Validate arguments
1179 	if (o == NULL)
1180 	{
1181 		return;
1182 	}
1183 
1184 	for (i = 0;i < LIST_NUM(o);i++)
1185 	{
1186 		IKE_PACKET_TRANSFORM_VALUE *v = LIST_DATA(o, i);
1187 
1188 		Free(v);
1189 	}
1190 
1191 	ReleaseList(o);
1192 }
1193 
1194 // Release the transform payload
IkeFreeTransformPayload(IKE_PACKET_TRANSFORM_PAYLOAD * t)1195 void IkeFreeTransformPayload(IKE_PACKET_TRANSFORM_PAYLOAD *t)
1196 {
1197 	// Validate arguments
1198 	if (t == NULL)
1199 	{
1200 		return;
1201 	}
1202 
1203 	if (t->ValueList != NULL)
1204 	{
1205 		IkeFreeTransformValueList(t->ValueList);
1206 		t->ValueList = NULL;
1207 	}
1208 }
1209 
1210 // Parse the ID payload
IkeParseIdPayload(IKE_PACKET_ID_PAYLOAD * t,BUF * b)1211 bool IkeParseIdPayload(IKE_PACKET_ID_PAYLOAD *t, BUF *b)
1212 {
1213 	IKE_ID_HEADER h;
1214 	IP ip;
1215 	IP subnet;
1216 	// Validate arguments
1217 	if (t == NULL || b == NULL)
1218 	{
1219 		return false;
1220 	}
1221 
1222 	if (ReadBuf(b, &h, sizeof(h)) != sizeof(h))
1223 	{
1224 		return false;
1225 	}
1226 
1227 	t->Type = h.IdType;
1228 	t->ProtocolId = h.ProtocolId;
1229 	t->Port = Endian16(h.Port);
1230 	t->IdData = ReadRemainBuf(b);
1231 	if (t->IdData == NULL)
1232 	{
1233 		return false;
1234 	}
1235 
1236 	ZeroIP4(&ip);
1237 	ZeroIP4(&subnet);
1238 
1239 	// Convert to string
1240 	Zero(t->StrData, sizeof(t->StrData));
1241 	switch (t->Type)
1242 	{
1243 	case IKE_ID_FQDN:
1244 	case IKE_ID_USER_FQDN:
1245 	case IKE_ID_KEY_ID:
1246 		Copy(t->StrData, t->IdData->Buf, MIN(t->IdData->Size, sizeof(t->StrData) - 1));
1247 		break;
1248 
1249 	case IKE_ID_IPV4_ADDR:
1250 		if (t->IdData->Size == IPV4_SIZE)
1251 		{
1252 			Copy(IPV4(ip.address), t->IdData->Buf, IPV4_SIZE);
1253 
1254 			IPToStr(t->StrData, sizeof(t->StrData), &ip);
1255 		}
1256 		break;
1257 
1258 	case IKE_ID_IPV6_ADDR:
1259 		if (t->IdData->Size == 16)
1260 		{
1261 			SetIP6(&ip, t->IdData->Buf);
1262 
1263 			IPToStr(t->StrData, sizeof(t->StrData), &ip);
1264 		}
1265 		break;
1266 
1267 	case IKE_ID_IPV4_ADDR_SUBNET:
1268 		if (t->IdData->Size == IPV4_SIZE * 2)
1269 		{
1270 			char ipstr[MAX_SIZE];
1271 			char subnetstr[MAX_SIZE];
1272 			Copy(IPV4(ip.address), t->IdData->Buf, IPV4_SIZE);
1273 			Copy(IPV4(subnet.address), ((BYTE *)t->IdData->Buf) + IPV4_SIZE, IPV4_SIZE);
1274 
1275 			IPToStr(ipstr, sizeof(ipstr), &ip);
1276 			MaskToStr(subnetstr, sizeof(subnetstr), &subnet);
1277 
1278 			Format(t->StrData, sizeof(t->StrData), "%s/%s", ipstr, subnetstr);
1279 		}
1280 		break;
1281 
1282 	case IKE_ID_IPV6_ADDR_SUBNET:
1283 		if (t->IdData->Size == 32)
1284 		{
1285 			char ipstr[MAX_SIZE];
1286 			char subnetstr[MAX_SIZE];
1287 			SetIP6(&ip, t->IdData->Buf);
1288 			SetIP6(&subnet, ((UCHAR *)t->IdData->Buf) + 16);
1289 
1290 			IPToStr(ipstr, sizeof(ipstr), &ip);
1291 			MaskToStr(subnetstr, sizeof(subnetstr), &subnet);
1292 
1293 			Format(t->StrData, sizeof(t->StrData), "%s/%s", ipstr, subnetstr);
1294 		}
1295 		break;
1296 	}
1297 
1298 	return true;
1299 }
1300 
1301 // Release the ID payload
IkeFreeIdPayload(IKE_PACKET_ID_PAYLOAD * t)1302 void IkeFreeIdPayload(IKE_PACKET_ID_PAYLOAD *t)
1303 {
1304 	// Validate arguments
1305 	if (t == NULL)
1306 	{
1307 		return;
1308 	}
1309 
1310 	if (t->IdData != NULL)
1311 	{
1312 		FreeBuf(t->IdData);
1313 		t->IdData = NULL;
1314 	}
1315 }
1316 
1317 // Parse the certificate payload
IkeParseCertPayload(IKE_PACKET_CERT_PAYLOAD * t,BUF * b)1318 bool IkeParseCertPayload(IKE_PACKET_CERT_PAYLOAD *t, BUF *b)
1319 {
1320 	IKE_CERT_HEADER h;
1321 	// Validate arguments
1322 	if (t == NULL || b == NULL)
1323 	{
1324 		return false;
1325 	}
1326 
1327 	if (ReadBuf(b, &h, sizeof(h)) != sizeof(h))
1328 	{
1329 		return false;
1330 	}
1331 
1332 	t->CertType = h.CertType;
1333 	t->CertData = ReadRemainBuf(b);
1334 	if (t->CertData == NULL)
1335 	{
1336 		return false;
1337 	}
1338 
1339 	return true;
1340 }
1341 
1342 // Release the certificate payload
IkeFreeCertPayload(IKE_PACKET_CERT_PAYLOAD * t)1343 void IkeFreeCertPayload(IKE_PACKET_CERT_PAYLOAD *t)
1344 {
1345 	// Validate arguments
1346 	if (t == NULL)
1347 	{
1348 		return;
1349 	}
1350 
1351 	if (t->CertData != NULL)
1352 	{
1353 		FreeBuf(t->CertData);
1354 		t->CertData = NULL;
1355 	}
1356 }
1357 
1358 // Parse the certificate request payload
IkeParseCertRequestPayload(IKE_PACKET_CERT_REQUEST_PAYLOAD * t,BUF * b)1359 bool IkeParseCertRequestPayload(IKE_PACKET_CERT_REQUEST_PAYLOAD *t, BUF *b)
1360 {
1361 	IKE_CERT_REQUEST_HEADER h;
1362 	// Validate arguments
1363 	if (t == NULL || b == NULL)
1364 	{
1365 		return false;
1366 	}
1367 
1368 	if (ReadBuf(b, &h, sizeof(h)) != sizeof(h))
1369 	{
1370 		return false;
1371 	}
1372 
1373 	t->CertType = h.CertType;
1374 	t->Data = ReadRemainBuf(b);
1375 	if (t->Data == NULL)
1376 	{
1377 		return false;
1378 	}
1379 
1380 	return true;
1381 }
1382 
1383 // Release the certificate request payload
IkeFreeCertRequestPayload(IKE_PACKET_CERT_REQUEST_PAYLOAD * t)1384 void IkeFreeCertRequestPayload(IKE_PACKET_CERT_REQUEST_PAYLOAD *t)
1385 {
1386 	// Validate arguments
1387 	if (t == NULL)
1388 	{
1389 		return;
1390 	}
1391 
1392 	if (t->Data != NULL)
1393 	{
1394 		FreeBuf(t->Data);
1395 		t->Data = NULL;
1396 	}
1397 }
1398 
1399 // Parse the notification payload
IkeParseNoticePayload(IKE_PACKET_NOTICE_PAYLOAD * t,BUF * b)1400 bool IkeParseNoticePayload(IKE_PACKET_NOTICE_PAYLOAD *t, BUF *b)
1401 {
1402 	IKE_NOTICE_HEADER h;
1403 	// Validate arguments
1404 	if (t == NULL || b == NULL)
1405 	{
1406 		return false;
1407 	}
1408 
1409 	if (ReadBuf(b, &h, sizeof(h)) != sizeof(h))
1410 	{
1411 		return false;
1412 	}
1413 
1414 	if (Endian32(h.DoI) != IKE_SA_DOI_IPSEC)
1415 	{
1416 		Debug("ISAKMP: Invalid DoI Value: 0x%x\n", Endian32(h.DoI));
1417 		return false;
1418 	}
1419 
1420 	t->MessageType = Endian16(h.MessageType);
1421 	t->ProtocolId = h.ProtocolId;
1422 	t->Spi = ReadBufFromBuf(b, h.SpiSize);
1423 	if (t->Spi == NULL)
1424 	{
1425 		return false;
1426 	}
1427 	t->MessageData = ReadRemainBuf(b);
1428 
1429 	return true;
1430 }
1431 
1432 // Release the notification payload
IkeFreeNoticePayload(IKE_PACKET_NOTICE_PAYLOAD * t)1433 void IkeFreeNoticePayload(IKE_PACKET_NOTICE_PAYLOAD *t)
1434 {
1435 	// Validate arguments
1436 	if (t == NULL)
1437 	{
1438 		return;
1439 	}
1440 
1441 	if (t->MessageData != NULL)
1442 	{
1443 		FreeBuf(t->MessageData);
1444 		t->MessageData = NULL;
1445 	}
1446 
1447 	if (t->Spi != NULL)
1448 	{
1449 		FreeBuf(t->Spi);
1450 		t->Spi = NULL;
1451 	}
1452 }
1453 
1454 // Parse the NAT-OA payload
IkeParseNatOaPayload(IKE_PACKET_NAT_OA_PAYLOAD * t,BUF * b)1455 bool IkeParseNatOaPayload(IKE_PACKET_NAT_OA_PAYLOAD *t, BUF *b)
1456 {
1457 	IKE_NAT_OA_HEADER h;
1458 	UCHAR ip4[4];
1459 	UCHAR ip6[16];
1460 	IP ip;
1461 	// Validate arguments
1462 	if (t == NULL || b == NULL)
1463 	{
1464 		return false;
1465 	}
1466 
1467 	Zero(&ip, sizeof(ip));
1468 
1469 	if (ReadBuf(b, &h, sizeof(h)) != sizeof(h))
1470 	{
1471 		return false;
1472 	}
1473 
1474 	if (h.IdType != IKE_ID_IPV4_ADDR && h.IdType != IKE_ID_IPV6_ADDR)
1475 	{
1476 		return false;
1477 	}
1478 
1479 	switch (h.IdType)
1480 	{
1481 	case IKE_ID_IPV4_ADDR:	// IPv4
1482 		if (ReadBuf(b, ip4, sizeof(ip4)) != sizeof(ip4))
1483 		{
1484 			return false;
1485 		}
1486 
1487 		SetIP(&ip, ip4[0], ip4[1], ip4[2], ip4[3]);
1488 
1489 		break;
1490 
1491 	case IKE_ID_IPV6_ADDR:	// IPv6
1492 		if (ReadBuf(b, ip6, sizeof(ip6)) != sizeof(ip6))
1493 		{
1494 			return false;
1495 		}
1496 
1497 		SetIP6(&ip, ip6);
1498 
1499 		break;
1500 
1501 	default:
1502 		return false;
1503 	}
1504 
1505 	Copy(&t->IpAddress, &ip, sizeof(IP));
1506 
1507 	return true;
1508 }
1509 
1510 // Parse the deletion payload
IkeParseDeletePayload(IKE_PACKET_DELETE_PAYLOAD * t,BUF * b)1511 bool IkeParseDeletePayload(IKE_PACKET_DELETE_PAYLOAD *t, BUF *b)
1512 {
1513 	IKE_DELETE_HEADER h;
1514 	UINT num_spi;
1515 	UINT spi_size;
1516 	UINT i;
1517 	bool ok = true;
1518 	// Validate arguments
1519 	if (t == NULL || b == NULL)
1520 	{
1521 		return false;
1522 	}
1523 
1524 	if (ReadBuf(b, &h, sizeof(h)) != sizeof(h))
1525 	{
1526 		return false;
1527 	}
1528 
1529 	if (Endian32(h.DoI) != IKE_SA_DOI_IPSEC)
1530 	{
1531 		Debug("ISAKMP: Invalid DoI Value: 0x%x\n", Endian32(h.DoI));
1532 		return false;
1533 	}
1534 
1535 	t->ProtocolId = h.ProtocolId;
1536 	t->SpiList = NewListFast(NULL);
1537 	num_spi = Endian16(h.NumSpis);
1538 	spi_size = h.SpiSize;
1539 
1540 	for (i = 0;i < num_spi;i++)
1541 	{
1542 		BUF *spi = ReadBufFromBuf(b, spi_size);
1543 
1544 		if (spi == NULL)
1545 		{
1546 			ok = false;
1547 			break;
1548 		}
1549 
1550 		Add(t->SpiList, spi);
1551 	}
1552 
1553 	if (ok == false)
1554 	{
1555 		IkeFreeDeletePayload(t);
1556 		return false;
1557 	}
1558 
1559 	return true;
1560 }
1561 
1562 // Release the deletion payload
IkeFreeDeletePayload(IKE_PACKET_DELETE_PAYLOAD * t)1563 void IkeFreeDeletePayload(IKE_PACKET_DELETE_PAYLOAD *t)
1564 {
1565 	UINT i;
1566 	// Validate arguments
1567 	if (t == NULL)
1568 	{
1569 		return;
1570 	}
1571 
1572 	if (t->SpiList != NULL)
1573 	{
1574 		for (i = 0;i < LIST_NUM(t->SpiList);i++)
1575 		{
1576 			BUF *spi = LIST_DATA(t->SpiList, i);
1577 
1578 			FreeBuf(spi);
1579 		}
1580 
1581 		ReleaseList(t->SpiList);
1582 
1583 		t->SpiList = NULL;
1584 	}
1585 }
1586 
1587 // Check whether the hash matches
IkeCompareHash(IKE_PACKET_PAYLOAD * hash_payload,void * hash_data,UINT hash_size)1588 bool IkeCompareHash(IKE_PACKET_PAYLOAD *hash_payload, void *hash_data, UINT hash_size)
1589 {
1590 	//char tmp1[MAX_SIZE], tmp2[MAX_SIZE];
1591 	// Validate arguments
1592 	if (hash_payload == NULL || hash_data == NULL || hash_size == 0)
1593 	{
1594 		return false;
1595 	}
1596 
1597 	if (hash_payload->PayloadType != IKE_PAYLOAD_HASH)
1598 	{
1599 		return false;
1600 	}
1601 
1602 	if (hash_payload->Payload.Hash.Data == NULL)
1603 	{
1604 		return false;
1605 	}
1606 
1607 	if (hash_payload->Payload.Hash.Data->Size != hash_size)
1608 	{
1609 		return false;
1610 	}
1611 
1612 	//BinToStrEx(tmp1, sizeof(tmp1), hash_payload->Payload.Hash.Data->Buf, hash_size);
1613 	//BinToStrEx(tmp2, sizeof(tmp2), hash_data, hash_size);
1614 
1615 	//Debug("IkeCompareHash\n  1: %s\n  2: %s\n", tmp1, tmp2);
1616 
1617 	if (Cmp(hash_payload->Payload.Hash.Data->Buf, hash_data, hash_size) != 0)
1618 	{
1619 		return false;
1620 	}
1621 
1622 	return true;
1623 }
1624 
1625 // Parse the data payload
IkeParseDataPayload(IKE_PACKET_DATA_PAYLOAD * t,BUF * b)1626 bool IkeParseDataPayload(IKE_PACKET_DATA_PAYLOAD *t, BUF *b)
1627 {
1628 	// Validate arguments
1629 	if (t == NULL || b == NULL)
1630 	{
1631 		return false;
1632 	}
1633 
1634 	t->Data = MemToBuf(b->Buf, b->Size);
1635 
1636 	return true;
1637 }
1638 
1639 // Release the data payload
IkeFreeDataPayload(IKE_PACKET_DATA_PAYLOAD * t)1640 void IkeFreeDataPayload(IKE_PACKET_DATA_PAYLOAD *t)
1641 {
1642 	// Validate arguments
1643 	if (t == NULL)
1644 	{
1645 		return;
1646 	}
1647 
1648 	FreeBuf(t->Data);
1649 }
1650 
1651 // Release the IKE payload body
IkeFreePayload(IKE_PACKET_PAYLOAD * p)1652 void IkeFreePayload(IKE_PACKET_PAYLOAD *p)
1653 {
1654 	// Validate arguments
1655 	if (p == NULL)
1656 	{
1657 		return;
1658 	}
1659 
1660 	switch (p->PayloadType)
1661 	{
1662 	case IKE_PAYLOAD_SA:					// SA payload
1663 		IkeFreeSaPayload(&p->Payload.Sa);
1664 		break;
1665 
1666 	case IKE_PAYLOAD_PROPOSAL:			// Proposal payload
1667 		IkeFreeProposalPayload(&p->Payload.Proposal);
1668 		break;
1669 
1670 	case IKE_PAYLOAD_TRANSFORM:			// Proposal payload
1671 		IkeFreeTransformPayload(&p->Payload.Transform);
1672 		break;
1673 
1674 	case IKE_PAYLOAD_ID:					// ID payload
1675 		IkeFreeIdPayload(&p->Payload.Id);
1676 		break;
1677 
1678 	case IKE_PAYLOAD_CERT:				// Certificate payload
1679 		IkeFreeCertPayload(&p->Payload.Cert);
1680 		break;
1681 
1682 	case IKE_PAYLOAD_CERT_REQUEST:		// Certificate request payload
1683 		IkeFreeCertRequestPayload(&p->Payload.CertRequest);
1684 		break;
1685 
1686 	case IKE_PAYLOAD_NOTICE:				// Notification Payload
1687 		IkeFreeNoticePayload(&p->Payload.Notice);
1688 		break;
1689 
1690 	case IKE_PAYLOAD_DELETE:				// Deletion payload
1691 		IkeFreeDeletePayload(&p->Payload.Delete);
1692 		break;
1693 
1694 	case IKE_PAYLOAD_NAT_OA:				// NAT-OD payload
1695 	case IKE_PAYLOAD_NAT_OA_DRAFT:
1696 	case IKE_PAYLOAD_NAT_OA_DRAFT_2:
1697 		// Do Nothing
1698 		break;
1699 
1700 	case IKE_PAYLOAD_KEY_EXCHANGE:		// Key exchange payload
1701 	case IKE_PAYLOAD_HASH:				// Hash payload
1702 	case IKE_PAYLOAD_SIGN:				// Signature payload
1703 	case IKE_PAYLOAD_RAND:				// Random number payload
1704 	case IKE_PAYLOAD_VENDOR_ID:			// Vendor ID payload
1705 	case IKE_PAYLOAD_NAT_D:				// NAT-D payload
1706 	case IKE_PAYLOAD_NAT_D_DRAFT:		// NAT-D payload (draft)
1707 	default:
1708 		IkeFreeDataPayload(&p->Payload.GeneralData);
1709 		break;
1710 	}
1711 
1712 	if (p->BitArray != NULL)
1713 	{
1714 		FreeBuf(p->BitArray);
1715 	}
1716 
1717 	Free(p);
1718 }
1719 
1720 // Analyse the IKE payload list
IkeParsePayloadList(void * data,UINT size,UCHAR first_payload)1721 LIST *IkeParsePayloadList(void *data, UINT size, UCHAR first_payload)
1722 {
1723 	return IkeParsePayloadListEx(data, size, first_payload, NULL);
1724 }
IkeParsePayloadListEx(void * data,UINT size,UCHAR first_payload,UINT * total_read_size)1725 LIST *IkeParsePayloadListEx(void *data, UINT size, UCHAR first_payload, UINT *total_read_size)
1726 {
1727 	LIST *o;
1728 	BUF *b;
1729 	UCHAR payload_type = first_payload;
1730 	UINT total = 0;
1731 	// Validate arguments
1732 	if (data == NULL)
1733 	{
1734 		return NULL;
1735 	}
1736 
1737 	o = NewListFast(NULL);
1738 	b = MemToBuf(data, size);
1739 
1740 	while (payload_type != IKE_PAYLOAD_NONE)
1741 	{
1742 		// Read the common header
1743 		IKE_COMMON_HEADER header;
1744 		USHORT payload_size;
1745 		BUF *payload_data;
1746 		IKE_PACKET_PAYLOAD *pay;
1747 
1748 		if (ReadBuf(b, &header, sizeof(header)) != sizeof(header))
1749 		{
1750 			Debug("ISAKMP: Broken Packet (Invalid Payload Size)\n");
1751 
1752 LABEL_ERROR:
1753 			// Header reading failure
1754 			IkeFreePayloadList(o);
1755 			o = NULL;
1756 
1757 			break;
1758 		}
1759 
1760 		total += sizeof(header);
1761 
1762 		// Get the payload size
1763 		payload_size = Endian16(header.PayloadSize);
1764 
1765 		if (payload_size < sizeof(header))
1766 		{
1767 			Debug("ISAKMP: Broken Packet (Invalid Payload Size)\n");
1768 			goto LABEL_ERROR;
1769 		}
1770 
1771 		payload_size -= sizeof(header);
1772 
1773 		// Read the payload data
1774 		payload_data = ReadBufFromBuf(b, payload_size);
1775 		if (payload_data == NULL)
1776 		{
1777 			// Data read failure
1778 			Debug("ISAKMP: Broken Packet (Invalid Payload Data)\n");
1779 			goto LABEL_ERROR;
1780 		}
1781 
1782 		total += payload_size;
1783 
1784 		// Analyse the payload body
1785 		if (IKE_IS_SUPPORTED_PAYLOAD_TYPE(payload_type))
1786 		{
1787 			// Supported payload type
1788 			pay = IkeParsePayload(payload_type, payload_data);
1789 
1790 			if (pay == NULL)
1791 			{
1792 				FreeBuf(payload_data);
1793 				Debug("ISAKMP: Broken Packet (Payload Data Parse Failed)\n");
1794 				goto LABEL_ERROR;
1795 			}
1796 
1797 			Add(o, pay);
1798 		}
1799 		else
1800 		{
1801 			// Unsupported payload type
1802 			Debug("ISAKMP: Ignored Payload Type: %u\n", payload_type);
1803 			pay = IkeParsePayload(payload_type, payload_data);
1804 
1805 			if (pay == NULL)
1806 			{
1807 				FreeBuf(payload_data);
1808 				Debug("ISAKMP: Broken Packet (Payload Data Parse Failed)\n");
1809 				goto LABEL_ERROR;
1810 			}
1811 
1812 			Add(o, pay);
1813 		}
1814 
1815 		payload_type = header.NextPayload;
1816 
1817 		FreeBuf(payload_data);
1818 	}
1819 
1820 	FreeBuf(b);
1821 
1822 	if (total_read_size != NULL)
1823 	{
1824 		*total_read_size = total;
1825 	}
1826 
1827 	return o;
1828 }
1829 
1830 // Release the IKE payload list
IkeFreePayloadList(LIST * o)1831 void IkeFreePayloadList(LIST *o)
1832 {
1833 	UINT i;
1834 	// Validate arguments
1835 	if (o == NULL)
1836 	{
1837 		return;
1838 	}
1839 
1840 	for (i = 0;i < LIST_NUM(o);i++)
1841 	{
1842 		IKE_PACKET_PAYLOAD *p = LIST_DATA(o, i);
1843 
1844 		IkeFreePayload(p);
1845 	}
1846 
1847 	ReleaseList(o);
1848 }
1849 
1850 // Build an IKE packet
IkeBuild(IKE_PACKET * p,IKE_CRYPTO_PARAM * cparam)1851 BUF *IkeBuild(IKE_PACKET *p, IKE_CRYPTO_PARAM *cparam)
1852 {
1853 	return IkeBuildEx(p, cparam, false);
1854 }
IkeBuildEx(IKE_PACKET * p,IKE_CRYPTO_PARAM * cparam,bool use_original_decrypted)1855 BUF *IkeBuildEx(IKE_PACKET *p, IKE_CRYPTO_PARAM *cparam, bool use_original_decrypted)
1856 {
1857 	IKE_HEADER h;
1858 	BUF *msg_buf;
1859 	BUF *ret;
1860 	// Validate arguments
1861 	if (p == NULL)
1862 	{
1863 		return NULL;
1864 	}
1865 
1866 	if (p->PayloadList == NULL)
1867 	{
1868 		return NULL;
1869 	}
1870 
1871 	Zero(&h, sizeof(h));
1872 	h.InitiatorCookie = Endian64(p->InitiatorCookie);
1873 	h.ResponderCookie = Endian64(p->ResponderCookie);
1874 	h.NextPayload = IkeGetFirstPayloadType(p->PayloadList);
1875 	h.Version = IKE_VERSION;
1876 	h.ExchangeType = p->ExchangeType;
1877 	h.Flag = (p->FlagEncrypted ? IKE_HEADER_FLAG_ENCRYPTED : 0) |
1878 		(p->FlagCommit ? IKE_HEADER_FLAG_COMMIT : 0) |
1879 		(p->FlagAuthOnly ? IKE_HEADER_FLAG_AUTH_ONLY : 0);
1880 	h.MessageId = Endian32(p->MessageId);
1881 
1882 	if (p->DecryptedPayload != NULL && use_original_decrypted)
1883 	{
1884 		msg_buf = CloneBuf(p->DecryptedPayload);
1885 	}
1886 	else
1887 	{
1888 		msg_buf = IkeBuildPayloadList(p->PayloadList);
1889 	}
1890 
1891 	if (p->DecryptedPayload != NULL)
1892 	{
1893 		FreeBuf(p->DecryptedPayload);
1894 	}
1895 
1896 	p->DecryptedPayload = CloneBuf(msg_buf);
1897 
1898 	if (p->FlagEncrypted)
1899 	{
1900 		BUF *b;
1901 		// Encryption
1902 		b = IkeEncryptWithPadding(msg_buf->Buf, msg_buf->Size, cparam);
1903 
1904 		if (b == NULL)
1905 		{
1906 			Debug("ISAKMP: Packet Encrypt Failed\n");
1907 			FreeBuf(msg_buf);
1908 			return NULL;
1909 		}
1910 
1911 		FreeBuf(msg_buf);
1912 
1913 		msg_buf = b;
1914 	}
1915 
1916 	h.MessageSize = Endian32(msg_buf->Size + sizeof(h));
1917 
1918 	ret = NewBuf();
1919 	WriteBuf(ret, &h, sizeof(h));
1920 	WriteBufBuf(ret, msg_buf);
1921 
1922 	FreeBuf(msg_buf);
1923 
1924 	SeekBuf(ret, 0, 0);
1925 
1926 	return ret;
1927 }
1928 
1929 // Analyse the IKE packet
IkeParseEx(void * data,UINT size,IKE_CRYPTO_PARAM * cparam,bool header_only)1930 IKE_PACKET *IkeParseEx(void *data, UINT size, IKE_CRYPTO_PARAM *cparam, bool header_only)
1931 {
1932 	IKE_PACKET *p = NULL;
1933 	BUF *b;
1934 	// Validate arguments
1935 	if (data == NULL)
1936 	{
1937 		return NULL;
1938 	}
1939 
1940 	b = MemToBuf(data, size);
1941 
1942 	if (b->Size < sizeof(IKE_HEADER))
1943 	{
1944 		Debug("ISAKMP: Invalid Packet Size\n");
1945 	}
1946 	else
1947 	{
1948 		// Header analysis
1949 		IKE_HEADER *h = (IKE_HEADER *)b->Buf;
1950 
1951 		p = ZeroMalloc(sizeof(IKE_PACKET));
1952 
1953 		p->MessageSize = Endian32(h->MessageSize);
1954 		p->InitiatorCookie = Endian64(h->InitiatorCookie);
1955 		p->ResponderCookie = Endian64(h->ResponderCookie);
1956 		p->ExchangeType = h->ExchangeType;
1957 		p->FlagEncrypted = (h->Flag & IKE_HEADER_FLAG_ENCRYPTED) ? true : false;
1958 		p->FlagCommit = (h->Flag & IKE_HEADER_FLAG_COMMIT) ? true : false;
1959 		p->FlagAuthOnly = (h->Flag & IKE_HEADER_FLAG_AUTH_ONLY) ? true : false;
1960 		p->MessageId = Endian32(h->MessageId);
1961 
1962 		if (b->Size < Endian32(h->MessageSize) ||
1963 			Endian32(h->MessageSize) < sizeof(IKE_HEADER))
1964 		{
1965 			Debug("ISAKMP: Invalid Packet Size\n");
1966 
1967 			IkeFree(p);
1968 			p = NULL;
1969 		}
1970 		else
1971 		{
1972 			if (header_only == false)
1973 			{
1974 				bool ok = false;
1975 				UCHAR *payload_data;
1976 				UINT payload_size;
1977 				BUF *buf = NULL;
1978 
1979 				payload_data = ((UCHAR *)h) + sizeof(IKE_HEADER);
1980 				payload_size = Endian32(h->MessageSize) - sizeof(IKE_HEADER);
1981 
1982 				// Decrypt if it is encrypted
1983 				if (p->FlagEncrypted)
1984 				{
1985 					buf = IkeDecrypt(payload_data, payload_size, cparam);
1986 
1987 					if (buf != NULL)
1988 					{
1989 						ok = true;
1990 
1991 						payload_data = buf->Buf;
1992 						payload_size = buf->Size;
1993 
1994 						p->DecryptedPayload = CloneBuf(buf);
1995 					}
1996 				}
1997 				else
1998 				{
1999 					ok = true;
2000 				}
2001 
2002 				if (ok == false)
2003 				{
2004 					Debug("ISAKMP: Decrypt Failed\n");
2005 
2006 					IkeFree(p);
2007 					p = NULL;
2008 				}
2009 				else
2010 				{
2011 					UINT total_read_size;
2012 
2013 					// Payload analysis
2014 					p->PayloadList = IkeParsePayloadListEx(payload_data,
2015 						payload_size,
2016 						h->NextPayload,
2017 						&total_read_size);
2018 
2019 					if (p->DecryptedPayload != NULL)
2020 					{
2021 						p->DecryptedPayload->Size = MIN(p->DecryptedPayload->Size, total_read_size);
2022 					}
2023 					else
2024 					{
2025 						p->DecryptedPayload = MemToBuf(payload_data, payload_size);
2026 					}
2027 				}
2028 
2029 				if (buf != NULL)
2030 				{
2031 					FreeBuf(buf);
2032 				}
2033 			}
2034 		}
2035 	}
2036 
2037 	FreeBuf(b);
2038 
2039 	return p;
2040 }
IkeParseHeader(void * data,UINT size,IKE_CRYPTO_PARAM * cparam)2041 IKE_PACKET *IkeParseHeader(void *data, UINT size, IKE_CRYPTO_PARAM *cparam)
2042 {
2043 	return IkeParseEx(data, size, cparam, true);
2044 }
IkeParse(void * data,UINT size,IKE_CRYPTO_PARAM * cparam)2045 IKE_PACKET *IkeParse(void *data, UINT size, IKE_CRYPTO_PARAM *cparam)
2046 {
2047 	return IkeParseEx(data, size, cparam, false);
2048 }
2049 
2050 // Send packet for debugging by UDP (For debugging with Ethereal)
IkeDebugUdpSendRawPacket(IKE_PACKET * p)2051 void IkeDebugUdpSendRawPacket(IKE_PACKET *p)
2052 {
2053 	BUF *b;
2054 	IP ip;
2055 	SOCK *udp;
2056 	// Validate arguments
2057 	if (p == NULL)
2058 	{
2059 		return;
2060 	}
2061 
2062 	p->FlagEncrypted = false;
2063 
2064 	b = IkeBuildEx(p, NULL, true);
2065 
2066 	if (b == NULL)
2067 	{
2068 		return;
2069 	}
2070 
2071 	Zero(&ip, sizeof(ip));
2072 	SetIP(&ip, 1, 2, 3, 4);
2073 
2074 	udp = NewUDP(0);
2075 
2076 	SendTo(udp, &ip, 500, b->Buf, b->Size);
2077 
2078 	ReleaseSock(udp);
2079 	FreeBuf(b);
2080 }
2081 
2082 // Output the payload list
IkeDebugPrintPayloads(LIST * o,UINT depth)2083 void IkeDebugPrintPayloads(LIST *o, UINT depth)
2084 {
2085 	UINT i;
2086 	char space[MAX_SIZE];
2087 	// Validate arguments
2088 	if (o == NULL)
2089 	{
2090 		return;
2091 	}
2092 
2093 	MakeCharArray2(space, ' ', depth * 2);
2094 
2095 	for (i = 0;i < LIST_NUM(o);i++)
2096 	{
2097 		IKE_PACKET_PAYLOAD *payload = LIST_DATA(o, i);
2098 
2099 		Debug("%s%u: Type = %u, Size = %u\n", space, i, payload->PayloadType, payload->BitArray->Size);
2100 
2101 		switch (payload->PayloadType)
2102 		{
2103 		case IKE_PAYLOAD_SA:
2104 			IkeDebugPrintPayloads(payload->Payload.Sa.PayloadList, depth + 1);
2105 			break;
2106 
2107 		case IKE_PAYLOAD_PROPOSAL:
2108 			IkeDebugPrintPayloads(payload->Payload.Proposal.PayloadList, depth + 1);
2109 			break;
2110 		}
2111 	}
2112 }
2113 
2114 // Encryption (also with padding)
IkeEncryptWithPadding(void * data,UINT size,IKE_CRYPTO_PARAM * cparam)2115 BUF *IkeEncryptWithPadding(void *data, UINT size, IKE_CRYPTO_PARAM *cparam)
2116 {
2117 	UINT total_size;
2118 	UINT i;
2119 	UCHAR n = 0;
2120 	UCHAR *tmp;
2121 	BUF *ret;
2122 	UCHAR tmp1600[1600];
2123 	bool no_free = false;
2124 	// Validate arguments
2125 	if (data == NULL || cparam == NULL)
2126 	{
2127 		return NULL;
2128 	}
2129 
2130 	total_size = ((size / cparam->Key->Crypto->BlockSize) + ((size % cparam->Key->Crypto->BlockSize) == 0 ? 0 : 1))
2131 		* cparam->Key->Crypto->BlockSize;
2132 	if (total_size == 0)
2133 	{
2134 		total_size = cparam->Key->Crypto->BlockSize;
2135 	}
2136 
2137 	if (total_size > sizeof(tmp1600))
2138 	{
2139 		tmp = Malloc(total_size);
2140 	}
2141 	else
2142 	{
2143 		tmp = tmp1600;
2144 		no_free = true;
2145 	}
2146 
2147 	Copy(tmp, data, size);
2148 
2149 	for (i = size;i < total_size;i++)
2150 	{
2151 		tmp[i] = ++n;
2152 	}
2153 
2154 	ret = IkeEncrypt(tmp, total_size, cparam);
2155 
2156 	if (no_free == false)
2157 	{
2158 		Free(tmp);
2159 	}
2160 
2161 	return ret;
2162 }
2163 
2164 // Encryption
IkeEncrypt(void * data,UINT size,IKE_CRYPTO_PARAM * cparam)2165 BUF *IkeEncrypt(void *data, UINT size, IKE_CRYPTO_PARAM *cparam)
2166 {
2167 	void *tmp;
2168 	BUF *b;
2169 	UCHAR tmp1600[1600];
2170 	bool no_free = false;
2171 	// Validate arguments
2172 	if (data == NULL || cparam == NULL)
2173 	{
2174 		return NULL;
2175 	}
2176 
2177 	if ((size % cparam->Key->Crypto->BlockSize) != 0)
2178 	{
2179 		// Not an integral multiple of block size
2180 		return NULL;
2181 	}
2182 
2183 	if (size > sizeof(tmp1600))
2184 	{
2185 		tmp = Malloc(size);
2186 	}
2187 	else
2188 	{
2189 		tmp = tmp1600;
2190 		no_free = true;
2191 	}
2192 
2193 	IkeCryptoEncrypt(cparam->Key, tmp, data, size, cparam->Iv);
2194 
2195 	if (size >= cparam->Key->Crypto->BlockSize)
2196 	{
2197 		Copy(cparam->NextIv, ((UCHAR *)tmp) + (size - cparam->Key->Crypto->BlockSize), cparam->Key->Crypto->BlockSize);
2198 	}
2199 	else
2200 	{
2201 		Zero(cparam->NextIv, cparam->Key->Crypto->BlockSize);
2202 	}
2203 
2204 	b = MemToBuf(tmp, size);
2205 
2206 	if (no_free == false)
2207 	{
2208 		Free(tmp);
2209 	}
2210 
2211 	return b;
2212 }
2213 
2214 // Decryption
IkeDecrypt(void * data,UINT size,IKE_CRYPTO_PARAM * cparam)2215 BUF *IkeDecrypt(void *data, UINT size, IKE_CRYPTO_PARAM *cparam)
2216 {
2217 	void *tmp;
2218 	BUF *b;
2219 	UCHAR tmp1600[1600];
2220 	bool no_free = false;
2221 	// Validate arguments
2222 	if (data == NULL || cparam == NULL)
2223 	{
2224 		return NULL;
2225 	}
2226 
2227 	if ((size % cparam->Key->Crypto->BlockSize) != 0)
2228 	{
2229 		// Not an integral multiple of block size
2230 		return NULL;
2231 	}
2232 
2233 	if (size > sizeof(tmp1600))
2234 	{
2235 		tmp = Malloc(size);
2236 	}
2237 	else
2238 	{
2239 		tmp = tmp1600;
2240 		no_free = true;
2241 	}
2242 
2243 	IkeCryptoDecrypt(cparam->Key, tmp, data, size, cparam->Iv);
2244 
2245 	if (size >= cparam->Key->Crypto->BlockSize)
2246 	{
2247 		Copy(cparam->NextIv, ((UCHAR *)data) + (size - cparam->Key->Crypto->BlockSize), cparam->Key->Crypto->BlockSize);
2248 	}
2249 	else
2250 	{
2251 		Zero(cparam->NextIv, cparam->Key->Crypto->BlockSize);
2252 	}
2253 
2254 	b = MemToBuf(tmp, size);
2255 
2256 	if (no_free == false)
2257 	{
2258 		Free(tmp);
2259 	}
2260 
2261 	return b;
2262 }
2263 
2264 // Release the IKE packet
IkeFree(IKE_PACKET * p)2265 void IkeFree(IKE_PACKET *p)
2266 {
2267 	// Validate arguments
2268 	if (p == NULL)
2269 	{
2270 		return;
2271 	}
2272 
2273 	if (p->PayloadList != NULL)
2274 	{
2275 		IkeFreePayloadList(p->PayloadList);
2276 	}
2277 
2278 	if (p->DecryptedPayload != NULL)
2279 	{
2280 		FreeBuf(p->DecryptedPayload);
2281 	}
2282 
2283 	Free(p);
2284 }
2285 
2286 // Create an IKE packet
IkeNew(UINT64 init_cookie,UINT64 resp_cookie,UCHAR exchange_type,bool encrypted,bool commit,bool auth_only,UINT msg_id,LIST * payload_list)2287 IKE_PACKET *IkeNew(UINT64 init_cookie, UINT64 resp_cookie, UCHAR exchange_type,
2288 				   bool encrypted, bool commit, bool auth_only, UINT msg_id,
2289 				   LIST *payload_list)
2290 {
2291 	IKE_PACKET *p = ZeroMalloc(sizeof(IKE_PACKET));
2292 
2293 	p->InitiatorCookie = init_cookie;
2294 	p->ResponderCookie = resp_cookie;
2295 	p->ExchangeType = exchange_type;
2296 	p->FlagEncrypted = encrypted;
2297 	p->FlagCommit = commit;
2298 	p->FlagAuthOnly = auth_only;
2299 	p->MessageId = msg_id;
2300 	p->PayloadList = payload_list;
2301 
2302 	return p;
2303 }
2304 
2305 // Create an encryption engine for IKE
NewIkeEngine()2306 IKE_ENGINE *NewIkeEngine()
2307 {
2308 	IKE_ENGINE *e = ZeroMalloc(sizeof(IKE_ENGINE));
2309 	IKE_CRYPTO *des, *des3, *aes;
2310 	IKE_HASH *sha1, *md5, *sha2_256, *sha2_384, *sha2_512;
2311 	IKE_DH *dh1, *dh2, *dh5, *dh2048, *dh3072, *dh4096;
2312 	UINT des_key_sizes[] =
2313 	{
2314 		8,
2315 	};
2316 	UINT des3_key_sizes[] =
2317 	{
2318 		24,
2319 	};
2320 	UINT aes_key_sizes[] =
2321 	{
2322 		16, 24, 32,
2323 	};
2324 
2325 	e->CryptosList = NewListFast(NULL);
2326 	e->HashesList = NewListFast(NULL);
2327 	e->DhsList = NewListFast(NULL);
2328 
2329 	//// Encryption algorithm
2330 	// DES
2331 	des = NewIkeCrypto(e, IKE_CRYPTO_DES_ID, IKE_CRYPTO_DES_STRING,
2332 		des_key_sizes, sizeof(des_key_sizes) / sizeof(UINT), 8);
2333 
2334 	// 3DES
2335 	des3 = NewIkeCrypto(e, IKE_CRYPTO_3DES_ID, IKE_CRYPTO_3DES_STRING,
2336 		des3_key_sizes, sizeof(des3_key_sizes) / sizeof(UINT), 8);
2337 
2338 	// AES
2339 	aes = NewIkeCrypto(e, IKE_CRYPTO_AES_ID, IKE_CRYPTO_AES_STRING,
2340 		aes_key_sizes, sizeof(aes_key_sizes) / sizeof(UINT), 16);
2341 
2342 	//// Hash algorithm
2343 	// SHA-1
2344 	sha1 = NewIkeHash(e, IKE_HASH_SHA1_ID, IKE_HASH_SHA1_STRING, 20);
2345 
2346 	// SHA-2
2347 	// sha2-256
2348 	sha2_256 = NewIkeHash(e, IKE_HASH_SHA2_256_ID, IKE_HASH_SHA2_256_STRING, 32);
2349 	// sha2-384
2350 	sha2_384 = NewIkeHash(e, IKE_HASH_SHA2_384_ID, IKE_HASH_SHA2_384_STRING, 48);
2351 	// sha2-512
2352 	sha2_512 = NewIkeHash(e, IKE_HASH_SHA2_512_ID, IKE_HASH_SHA2_512_STRING, 64);
2353 
2354 	// MD5
2355 	md5 = NewIkeHash(e, IKE_HASH_MD5_ID, IKE_HASH_MD5_STRING, 16);
2356 
2357 	//// DH algorithm
2358 	dh1 = NewIkeDh(e, IKE_DH_1_ID, IKE_DH_1_STRING, 96);
2359 	dh2 = NewIkeDh(e, IKE_DH_2_ID, IKE_DH_2_STRING, 128);
2360 	dh5 = NewIkeDh(e, IKE_DH_5_ID, IKE_DH_5_STRING, 192);
2361 	dh2048 = NewIkeDh(e, IKE_DH_2048_ID, IKE_DH_2048_STRING, 256);
2362 	dh3072 = NewIkeDh(e, IKE_DH_3072_ID, IKE_DH_3072_STRING, 384);
2363 	dh4096 = NewIkeDh(e, IKE_DH_4096_ID, IKE_DH_4096_STRING, 512);
2364 
2365 	// Define the IKE algorithm
2366 	e->IkeCryptos[IKE_P1_CRYPTO_DES_CBC] = des;
2367 	e->IkeCryptos[IKE_P1_CRYPTO_3DES_CBC] = des3;
2368 	e->IkeCryptos[IKE_P1_CRYPTO_AES_CBC] = aes;
2369 	e->IkeHashes[IKE_P1_HASH_MD5] = md5;
2370 	e->IkeHashes[IKE_P1_HASH_SHA1] = sha1;
2371 	e->IkeHashes[IKE_P1_HASH_SHA2_256] = sha2_256;
2372 	e->IkeHashes[IKE_P1_HASH_SHA2_384] = sha2_384;
2373 	e->IkeHashes[IKE_P1_HASH_SHA2_512] = sha2_512;
2374 
2375 
2376 	// Definition of ESP algorithm
2377 	e->EspCryptos[IKE_TRANSFORM_ID_P2_ESP_DES] = des;
2378 	e->EspCryptos[IKE_TRANSFORM_ID_P2_ESP_3DES] = des3;
2379 	e->EspCryptos[IKE_TRANSFORM_ID_P2_ESP_AES] = aes;
2380 	e->EspHashes[IKE_P2_HMAC_MD5_96] = md5;
2381 	e->EspHashes[IKE_P2_HMAC_SHA1_96] = sha1;
2382 
2383 	// Definition of the DH algorithm
2384 	e->IkeDhs[IKE_P1_DH_GROUP_768_MODP] = e->EspDhs[IKE_P2_DH_GROUP_768_MODP] = dh1;
2385 	e->IkeDhs[IKE_P1_DH_GROUP_1024_MODP] = e->EspDhs[IKE_P2_DH_GROUP_1024_MODP] = dh2;
2386 	e->IkeDhs[IKE_P1_DH_GROUP_1536_MODP] = e->EspDhs[IKE_P2_DH_GROUP_1536_MODP] = dh5;
2387 	e->IkeDhs[IKE_P1_DH_GROUP_2048_MODP] = e->EspDhs[IKE_P2_DH_GROUP_2048_MODP] = dh2048;
2388 	e->IkeDhs[IKE_P1_DH_GROUP_3072_MODP] = e->EspDhs[IKE_P2_DH_GROUP_3072_MODP] = dh3072;
2389 	e->IkeDhs[IKE_P1_DH_GROUP_4096_MODP] = e->EspDhs[IKE_P2_DH_GROUP_4096_MODP] = dh4096;
2390 
2391 	return e;
2392 }
2393 
2394 // Release the encryption engine for IKE
FreeIkeEngine(IKE_ENGINE * e)2395 void FreeIkeEngine(IKE_ENGINE *e)
2396 {
2397 	UINT i;
2398 	// Validate arguments
2399 	if (e == NULL)
2400 	{
2401 		return;
2402 	}
2403 
2404 	for (i = 0;i < LIST_NUM(e->CryptosList);i++)
2405 	{
2406 		IKE_CRYPTO *c = LIST_DATA(e->CryptosList, i);
2407 
2408 		FreeIkeCrypto(c);
2409 	}
2410 
2411 	ReleaseList(e->CryptosList);
2412 
2413 	for (i = 0;i < LIST_NUM(e->HashesList);i++)
2414 	{
2415 		IKE_HASH *h = LIST_DATA(e->HashesList, i);
2416 
2417 		FreeIkeHash(h);
2418 	}
2419 	ReleaseList(e->HashesList);
2420 
2421 	for (i = 0;i < LIST_NUM(e->DhsList);i++)
2422 	{
2423 		IKE_DH *d = LIST_DATA(e->DhsList, i);
2424 
2425 		FreeIkeDh(d);
2426 	}
2427 	ReleaseList(e->DhsList);
2428 
2429 	Free(e);
2430 }
2431 
2432 // Definition of a new DH algorithm for IKE
NewIkeDh(IKE_ENGINE * e,UINT dh_id,char * name,UINT key_size)2433 IKE_DH *NewIkeDh(IKE_ENGINE *e, UINT dh_id, char *name, UINT key_size)
2434 {
2435 	IKE_DH *d;
2436 	// Validate arguments
2437 	if (e == NULL || name == NULL || key_size == 0)
2438 	{
2439 		return NULL;
2440 	}
2441 
2442 	d = ZeroMalloc(sizeof(IKE_DH));
2443 
2444 	d->DhId = dh_id;
2445 	d->Name = name;
2446 	d->KeySize = key_size;
2447 
2448 	Add(e->DhsList, d);
2449 
2450 	return d;
2451 }
2452 
2453 // Definition of a new encryption algorithm for IKE
NewIkeCrypto(IKE_ENGINE * e,UINT crypto_id,char * name,UINT * key_sizes,UINT num_key_sizes,UINT block_size)2454 IKE_CRYPTO *NewIkeCrypto(IKE_ENGINE *e, UINT crypto_id, char *name, UINT *key_sizes, UINT num_key_sizes, UINT block_size)
2455 {
2456 	IKE_CRYPTO *c;
2457 	UINT i;
2458 	// Validate arguments
2459 	if (e == NULL || name == NULL || key_sizes == NULL)
2460 	{
2461 		return NULL;
2462 	}
2463 
2464 	c = ZeroMalloc(sizeof(IKE_CRYPTO));
2465 
2466 	c->CryptoId = crypto_id;
2467 	c->Name = name;
2468 
2469 	for (i = 0;i < MIN(num_key_sizes, 16);i++)
2470 	{
2471 		c->KeySizes[i] = key_sizes[i];
2472 	}
2473 
2474 	if (num_key_sizes >= 2)
2475 	{
2476 		c->VariableKeySize = true;
2477 	}
2478 
2479 	c->BlockSize = block_size;
2480 
2481 	Add(e->CryptosList, c);
2482 
2483 	return c;
2484 }
2485 
2486 // Release the definition of Encryption algorithm for IKE
FreeIkeCrypto(IKE_CRYPTO * c)2487 void FreeIkeCrypto(IKE_CRYPTO *c)
2488 {
2489 	// Validate arguments
2490 	if (c == NULL)
2491 	{
2492 		return;
2493 	}
2494 
2495 	Free(c);
2496 }
2497 
2498 // Release the definition of IKE hash algorithm
FreeIkeHash(IKE_HASH * h)2499 void FreeIkeHash(IKE_HASH *h)
2500 {
2501 	// Validate arguments
2502 	if (h == NULL)
2503 	{
2504 		return;
2505 	}
2506 
2507 	Free(h);
2508 }
2509 
2510 // Release the definition of the DH algorithm for IKE
FreeIkeDh(IKE_DH * d)2511 void FreeIkeDh(IKE_DH *d)
2512 {
2513 	// Validate arguments
2514 	if (d == NULL)
2515 	{
2516 		return;
2517 	}
2518 
2519 	Free(d);
2520 }
2521 
2522 // Definition of a new hash algorithm for IKE
NewIkeHash(IKE_ENGINE * e,UINT hash_id,char * name,UINT size)2523 IKE_HASH *NewIkeHash(IKE_ENGINE *e, UINT hash_id, char *name, UINT size)
2524 {
2525 	IKE_HASH *h;
2526 	// Validate arguments
2527 	if (e == NULL || name == NULL || size == 0)
2528 	{
2529 		return NULL;
2530 	}
2531 
2532 	h = ZeroMalloc(sizeof(IKE_HASH));
2533 
2534 	h->HashId = hash_id;
2535 	h->Name = name;
2536 	h->HashSize = size;
2537 
2538 	Add(e->HashesList, h);
2539 
2540 	return h;
2541 }
2542 
2543 // Get the encryption algorithm that is used in IKE
GetIkeCrypto(IKE_ENGINE * e,bool for_esp,UINT i)2544 IKE_CRYPTO *GetIkeCrypto(IKE_ENGINE *e, bool for_esp, UINT i)
2545 {
2546 	// Validate arguments
2547 	if (e == NULL || i == 0 || i >= MAX_IKE_ENGINE_ELEMENTS)
2548 	{
2549 		return NULL;
2550 	}
2551 
2552 	if (for_esp)
2553 	{
2554 		return e->EspCryptos[i];
2555 	}
2556 	else
2557 	{
2558 		return e->IkeCryptos[i];
2559 	}
2560 }
2561 
2562 // Get the hash algorithm used in the IKE
GetIkeHash(IKE_ENGINE * e,bool for_esp,UINT i)2563 IKE_HASH *GetIkeHash(IKE_ENGINE *e, bool for_esp, UINT i)
2564 {
2565 	// Validate arguments
2566 	if (e == NULL || i == 0 || i >= MAX_IKE_ENGINE_ELEMENTS)
2567 	{
2568 		return NULL;
2569 	}
2570 
2571 	if (for_esp)
2572 	{
2573 		return e->EspHashes[i];
2574 	}
2575 	else
2576 	{
2577 		return e->IkeHashes[i];
2578 	}
2579 }
2580 
2581 // Get the DH algorithm used in the IKE
GetIkeDh(IKE_ENGINE * e,bool for_esp,UINT i)2582 IKE_DH *GetIkeDh(IKE_ENGINE *e, bool for_esp, UINT i)
2583 {
2584 	// Validate arguments
2585 	if (e == NULL || i == 0 || i >= MAX_IKE_ENGINE_ELEMENTS)
2586 	{
2587 		return NULL;
2588 	}
2589 
2590 	if (for_esp)
2591 	{
2592 		return e->EspDhs[i];
2593 	}
2594 	else
2595 	{
2596 		return e->IkeDhs[i];
2597 	}
2598 }
2599 
2600 // Perform encryption
IkeCryptoEncrypt(IKE_CRYPTO_KEY * k,void * dst,void * src,UINT size,void * ivec)2601 void IkeCryptoEncrypt(IKE_CRYPTO_KEY *k, void *dst, void *src, UINT size, void *ivec)
2602 {
2603 	// Validate arguments
2604 	if (k == NULL || dst == NULL || src == NULL || size == 0 || ivec == NULL)
2605 	{
2606 		Zero(dst, size);
2607 		return;
2608 	}
2609 
2610 	if ((size % k->Crypto->BlockSize) != 0)
2611 	{
2612 		Zero(dst, size);
2613 		return;
2614 	}
2615 
2616 	switch (k->Crypto->CryptoId)
2617 	{
2618 	case IKE_CRYPTO_DES_ID:		// DES
2619 		DesEncrypt(dst, src, size, k->DesKey1, ivec);
2620 		break;
2621 
2622 	case IKE_CRYPTO_3DES_ID:	// 3DES
2623 		Des3Encrypt2(dst, src, size, k->DesKey1, k->DesKey2, k->DesKey3, ivec);
2624 		break;
2625 
2626 	case IKE_CRYPTO_AES_ID:		// AES
2627 		AesEncrypt(dst, src, size, k->AesKey, ivec);
2628 		break;
2629 
2630 	default:
2631 		// Unknown
2632 		Zero(dst, size);
2633 		break;
2634 	}
2635 }
2636 
2637 // Perform decryption
IkeCryptoDecrypt(IKE_CRYPTO_KEY * k,void * dst,void * src,UINT size,void * ivec)2638 void IkeCryptoDecrypt(IKE_CRYPTO_KEY *k, void *dst, void *src, UINT size, void *ivec)
2639 {
2640 	// Validate arguments
2641 	if (k == NULL || dst == NULL || src == NULL || size == 0 || ivec == NULL)
2642 	{
2643 		Zero(dst, size);
2644 		return;
2645 	}
2646 
2647 	if ((size % k->Crypto->BlockSize) != 0)
2648 	{
2649 		Zero(dst, size);
2650 		return;
2651 	}
2652 
2653 	switch (k->Crypto->CryptoId)
2654 	{
2655 	case IKE_CRYPTO_DES_ID:		// DES
2656 		DesDecrypt(dst, src, size, k->DesKey1, ivec);
2657 		break;
2658 
2659 	case IKE_CRYPTO_3DES_ID:	// 3DES
2660 		Des3Decrypt2(dst, src, size, k->DesKey1, k->DesKey2, k->DesKey3, ivec);
2661 		break;
2662 
2663 	case IKE_CRYPTO_AES_ID:		// AES
2664 		AesDecrypt(dst, src, size, k->AesKey, ivec);
2665 		break;
2666 
2667 	default:
2668 		// Unknown
2669 		Zero(dst, size);
2670 		break;
2671 	}
2672 }
2673 
2674 // Calculate a hash
IkeHash(IKE_HASH * h,void * dst,void * src,UINT size)2675 void IkeHash(IKE_HASH *h, void *dst, void *src, UINT size)
2676 {
2677 	// Validate arguments
2678 	if (h == NULL || dst == NULL || (size != 0 && src == NULL))
2679 	{
2680 		Zero(dst, size);
2681 		return;
2682 	}
2683 
2684 	switch (h->HashId)
2685 	{
2686 	case IKE_HASH_MD5_ID:
2687 		// MD5
2688 		Md5(dst, src, size);
2689 		break;
2690 
2691 	case IKE_HASH_SHA1_ID:
2692 		// SHA-1
2693 		Sha1(dst, src, size);
2694 		break;
2695 	case IKE_HASH_SHA2_256_ID:
2696 		Sha2_256(dst, src, size);
2697 		break;
2698 	case IKE_HASH_SHA2_384_ID:
2699 		Sha2_384(dst, src, size);
2700 		break;
2701 	case IKE_HASH_SHA2_512_ID:
2702 		Sha2_512(dst, src, size);
2703 		break;
2704 
2705 	default:
2706 		// Unknown
2707 		Zero(dst, size);
2708 		break;
2709 	}
2710 }
2711 
2712 // Calculation of HMAC
IkeHMac(IKE_HASH * h,void * dst,void * key,UINT key_size,void * data,UINT data_size)2713 void IkeHMac(IKE_HASH *h, void *dst, void *key, UINT key_size, void *data, UINT data_size)
2714 {
2715 	MD *md = NULL;
2716 
2717 	switch (h->HashId)
2718 	{
2719 	case IKE_HASH_MD5_ID:
2720 		md = NewMd("MD5");
2721 		break;
2722 	case IKE_HASH_SHA1_ID:
2723 		md = NewMd("SHA1");
2724 		break;
2725 	case IKE_HASH_SHA2_256_ID:
2726 		md = NewMd("SHA256");
2727 		break;
2728 	case IKE_HASH_SHA2_384_ID:
2729 		md = NewMd("SHA384");
2730 		break;
2731 	case IKE_HASH_SHA2_512_ID:
2732 		md = NewMd("SHA512");
2733 		break;
2734 	}
2735 
2736 	if (md == NULL)
2737 	{
2738 		Debug("IkeHMac(): The MD object is NULL! Either NewMd() failed or the current algorithm is not handled by the switch-case block.\n");
2739 		return;
2740 	}
2741 
2742 	if (SetMdKey(md, key, key_size) == false)
2743 	{
2744 		Debug("IkeHMac(): SetMdKey() failed!\n");
2745 		goto cleanup;
2746 	}
2747 
2748 	if (MdProcess(md, dst, data, data_size) == 0)
2749 	{
2750 		Debug("IkeHMac(): MdProcess() returned 0!\n");
2751 	}
2752 
2753 cleanup:
2754 	FreeMd(md);
2755 }
2756 
IkeHMacBuf(IKE_HASH * h,void * dst,BUF * key,BUF * data)2757 void IkeHMacBuf(IKE_HASH *h, void *dst, BUF *key, BUF *data)
2758 {
2759 	// Validate arguments
2760 	if (h == NULL || dst == NULL || key == NULL || data == NULL)
2761 	{
2762 		return;
2763 	}
2764 
2765 	IkeHMac(h, dst, key->Buf, key->Size, data->Buf, data->Size);
2766 }
2767 
2768 // Check whether the key size is valid
IkeCheckKeySize(IKE_CRYPTO * c,UINT size)2769 bool IkeCheckKeySize(IKE_CRYPTO *c, UINT size)
2770 {
2771 	bool ok = false;
2772 	UINT i;
2773 	// Validate arguments
2774 	if (c == NULL || size == 0)
2775 	{
2776 		return false;
2777 	}
2778 
2779 	for (i = 0;i < sizeof(c->KeySizes) / sizeof(UINT);i++)
2780 	{
2781 		if (c->KeySizes[i] == size)
2782 		{
2783 			ok = true;
2784 			break;
2785 		}
2786 	}
2787 
2788 	return ok;
2789 }
2790 
2791 // Create a key
IkeNewKey(IKE_CRYPTO * c,void * data,UINT size)2792 IKE_CRYPTO_KEY *IkeNewKey(IKE_CRYPTO *c, void *data, UINT size)
2793 {
2794 	IKE_CRYPTO_KEY *k;
2795 	// Validate arguments
2796 	if (c == NULL || data == NULL || size == 0)
2797 	{
2798 		return NULL;
2799 	}
2800 
2801 	if (IkeCheckKeySize(c, size) == false)
2802 	{
2803 		return NULL;
2804 	}
2805 
2806 	k = ZeroMalloc(sizeof(IKE_CRYPTO_KEY));
2807 	k->Crypto = c;
2808 	k->Data = Clone(data, size);
2809 	k->Size = size;
2810 
2811 	switch (k->Crypto->CryptoId)
2812 	{
2813 	case IKE_CRYPTO_DES_ID:
2814 		// DES 64bit key
2815 		k->DesKey1 = DesNewKeyValue(data);
2816 		break;
2817 
2818 	case IKE_CRYPTO_3DES_ID:
2819 		// 3DES 192bit key
2820 		k->DesKey1 = DesNewKeyValue(((UCHAR *)data) + DES_KEY_SIZE * 0);
2821 		k->DesKey2 = DesNewKeyValue(((UCHAR *)data) + DES_KEY_SIZE * 1);
2822 		k->DesKey3 = DesNewKeyValue(((UCHAR *)data) + DES_KEY_SIZE * 2);
2823 		break;
2824 
2825 	case IKE_CRYPTO_AES_ID:
2826 		// AES variable length key
2827 		k->AesKey = AesNewKey(data, size);
2828 		break;
2829 	}
2830 
2831 	return k;
2832 }
2833 
2834 // Release the key
IkeFreeKey(IKE_CRYPTO_KEY * k)2835 void IkeFreeKey(IKE_CRYPTO_KEY *k)
2836 {
2837 	// Validate arguments
2838 	if (k == NULL)
2839 	{
2840 		return;
2841 	}
2842 
2843 	DesFreeKeyValue(k->DesKey1);
2844 	DesFreeKeyValue(k->DesKey2);
2845 	DesFreeKeyValue(k->DesKey3);
2846 
2847 	AesFreeKey(k->AesKey);
2848 
2849 	Free(k->Data);
2850 
2851 	Free(k);
2852 }
2853 
2854 // Create a DH object
IkeDhNewCtx(IKE_DH * d)2855 DH_CTX *IkeDhNewCtx(IKE_DH *d)
2856 {
2857 	// Validate arguments
2858 	if (d == NULL)
2859 	{
2860 		return NULL;
2861 	}
2862 
2863 	switch (d->DhId)
2864 	{
2865 	case IKE_DH_1_ID:
2866 		return DhNewGroup1();
2867 
2868 	case IKE_DH_2_ID:
2869 		return DhNewGroup2();
2870 
2871 	case IKE_DH_5_ID:
2872 		return DhNewGroup5();
2873 
2874 	case IKE_DH_2048_ID:
2875 		return DhNew2048();
2876 
2877 	case IKE_DH_3072_ID:
2878 		return DhNew3072();
2879 
2880 	case IKE_DH_4096_ID:
2881 		return DhNew4096();
2882 	}
2883 
2884 	return NULL;
2885 }
2886 
2887 // Release the DH object
IkeDhFreeCtx(DH_CTX * dh)2888 void IkeDhFreeCtx(DH_CTX *dh)
2889 {
2890 	// Validate arguments
2891 	if (dh == NULL)
2892 	{
2893 		return;
2894 	}
2895 
2896 	DhFree(dh);
2897 }
2898 
2899 
2900 
2901 
2902 
2903