Skip site navigation (1)Skip section navigation (2)
Date:      Sat, 14 Apr 2018 12:07:58 +0000 (UTC)
From:      Eugene Grosbein <eugen@FreeBSD.org>
To:        ports-committers@freebsd.org, svn-ports-all@freebsd.org, svn-ports-head@freebsd.org
Subject:   svn commit: r467313 - in head/security/ipsec-tools: . files
Message-ID:  <201804141207.w3EC7w33023814@repo.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: eugen
Date: Sat Apr 14 12:07:58 2018
New Revision: 467313
URL: https://svnweb.freebsd.org/changeset/ports/467313

Log:
  security/ipsec-tools: fix CVE-2016-10396
  
  The racoon daemon in IPsec-Tools 0.8.2 contains a remotely exploitable
  computational-complexity attack when parsing and storing ISAKMP fragments.
  The implementation permits a remote attacker to exhaust computational
  resources on the remote endpoint by repeatedly sending ISAKMP fragment
  packets in a particular order such that the worst-case computational
  complexity is realized in the algorithm utilized to determine
  if reassembly of the fragments can take place.
  
  The fix obtained from NetBSD CVS head with a command:
  
  cvs diff -D 2017-01-24 -D 2017-09-01 \
  	src/racoon/handler.h \
  	src/racoon/isakmp.c \
  	src/racoon/isakmp_frag.c \
  	src/racoon/isakmp_inf.c
  
  While here, add LICENSE.
  
  PR:		225066
  Approved by:	VANHULLEBUS Yvan (maintainer timeout, 3 months)
  Obtained from:	NetBSD
  MFH:		2018Q1
  Security:	CVE-2016-10396

Added:
  head/security/ipsec-tools/files/patch-handler.c   (contents, props changed)
  head/security/ipsec-tools/files/patch-isakmp.c   (contents, props changed)
  head/security/ipsec-tools/files/patch-isakmp_frag.c   (contents, props changed)
  head/security/ipsec-tools/files/patch-isakmp_inf.c   (contents, props changed)
Modified:
  head/security/ipsec-tools/Makefile

Modified: head/security/ipsec-tools/Makefile
==============================================================================
--- head/security/ipsec-tools/Makefile	Sat Apr 14 12:06:35 2018	(r467312)
+++ head/security/ipsec-tools/Makefile	Sat Apr 14 12:07:58 2018	(r467313)
@@ -8,12 +8,14 @@
 
 PORTNAME=	ipsec-tools
 PORTVERSION=	0.8.2
-PORTREVISION=	2
+PORTREVISION=	3
 CATEGORIES=	security
 MASTER_SITES=	SF
 
 MAINTAINER=	vanhu@FreeBSD.org
 COMMENT=	KAME racoon IKE daemon, ipsec-tools version
+
+LICENSE=	BSD3CLAUSE
 
 CONFLICTS=	racoon-[0-9]*
 

Added: head/security/ipsec-tools/files/patch-handler.c
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/security/ipsec-tools/files/patch-handler.c	Sat Apr 14 12:07:58 2018	(r467313)
@@ -0,0 +1,22 @@
+Index: src/racoon/handler.h
+===================================================================
+RCS file: /cvsroot/src/crypto/dist/ipsec-tools/src/racoon/handler.h,v
+retrieving revision 1.25
+retrieving revision 1.26
+diff -p -u -r1.25 -r1.26
+--- src/racoon/handler.h	17 Nov 2010 10:40:41 -0000	1.25
++++ src/racoon/handler.h	24 Jan 2017 19:23:56 -0000	1.26
+@@ -1,4 +1,4 @@
+-/*	$NetBSD: handler.h,v 1.25 2010/11/17 10:40:41 tteras Exp $	*/
++/*	$NetBSD: handler.h,v 1.26 2017/01/24 19:23:56 christos Exp $	*/
+ 
+ /* Id: handler.h,v 1.19 2006/02/25 08:25:12 manubsd Exp */
+ 
+@@ -141,6 +141,7 @@ struct ph1handle {
+ #endif
+ #ifdef ENABLE_FRAG
+ 	int frag;			/* IKE phase 1 fragmentation */
++	int frag_last_index;
+ 	struct isakmp_frag_item *frag_chain;	/* Received fragments */
+ #endif
+ 

Added: head/security/ipsec-tools/files/patch-isakmp.c
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/security/ipsec-tools/files/patch-isakmp.c	Sat Apr 14 12:07:58 2018	(r467313)
@@ -0,0 +1,30 @@
+Index: src/racoon/isakmp.c
+===================================================================
+RCS file: /cvsroot/src/crypto/dist/ipsec-tools/src/racoon/isakmp.c,v
+retrieving revision 1.75
+retrieving revision 1.76
+diff -p -u -r1.75 -r1.76
+--- src/racoon/isakmp.c	9 Mar 2016 22:27:17 -0000	1.75
++++ src/racoon/isakmp.c	24 Jan 2017 19:23:56 -0000	1.76
+@@ -1,4 +1,4 @@
+-/*	$NetBSD: isakmp.c,v 1.75 2016/03/09 22:27:17 christos Exp $	*/
++/*	$NetBSD: isakmp.c,v 1.76 2017/01/24 19:23:56 christos Exp $	*/
+ 
+ /* Id: isakmp.c,v 1.74 2006/05/07 21:32:59 manubsd Exp */
+ 
+@@ -1077,6 +1077,7 @@ isakmp_ph1begin_i(rmconf, remote, local)
+ 		iph1->frag = 1;
+ 	else
+ 		iph1->frag = 0;
++	iph1->frag_last_index = 0;
+ 	iph1->frag_chain = NULL;
+ #endif
+ 	iph1->approval = NULL;
+@@ -1181,6 +1182,7 @@ isakmp_ph1begin_r(msg, remote, local, et
+ #endif
+ #ifdef ENABLE_FRAG
+ 	iph1->frag = 0;
++	iph1->frag_last_index = 0;
+ 	iph1->frag_chain = NULL;
+ #endif
+ 	iph1->approval = NULL;

Added: head/security/ipsec-tools/files/patch-isakmp_frag.c
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/security/ipsec-tools/files/patch-isakmp_frag.c	Sat Apr 14 12:07:58 2018	(r467313)
@@ -0,0 +1,151 @@
+Index: src/racoon/isakmp_frag.c
+===================================================================
+RCS file: /cvsroot/src/crypto/dist/ipsec-tools/src/racoon/isakmp_frag.c,v
+retrieving revision 1.5
+retrieving revision 1.7
+diff -p -u -r1.5 -r1.7
+--- src/racoon/isakmp_frag.c	22 Apr 2009 11:24:20 -0000	1.5
++++ src/racoon/isakmp_frag.c	23 Jul 2017 05:40:27 -0000	1.7
+@@ -1,4 +1,4 @@
+-/*	$NetBSD: isakmp_frag.c,v 1.5 2009/04/22 11:24:20 tteras Exp $	*/
++/*	$NetBSD: isakmp_frag.c,v 1.7 2017/07/23 05:40:27 christos Exp $	*/
+ 
+ /* Id: isakmp_frag.c,v 1.4 2004/11/13 17:31:36 manubsd Exp */
+ 
+@@ -173,6 +173,43 @@ vendorid_frag_cap(gen)
+ 	return ntohl(hp[MD5_DIGEST_LENGTH / sizeof(*hp)]);
+ }
+ 
++static int 
++isakmp_frag_insert(struct ph1handle *iph1, struct isakmp_frag_item *item)
++{
++	struct isakmp_frag_item *pitem = NULL;
++	struct isakmp_frag_item *citem = iph1->frag_chain;
++
++	/* no frag yet, just insert at beginning of list */
++	if (iph1->frag_chain == NULL) {
++		iph1->frag_chain = item;
++		return 0;
++	}
++
++	do {
++		/* duplicate fragment number, abort (CVE-2016-10396) */
++		if (citem->frag_num == item->frag_num)
++			return -1;
++
++		/* need to insert before current item */
++		if (citem->frag_num > item->frag_num) {
++			if (pitem != NULL)
++				pitem->frag_next = item;
++			else
++				/* insert at the beginning of the list  */
++				iph1->frag_chain = item;
++			item->frag_next = citem;
++			return 0;
++		}
++
++		pitem = citem;
++		citem = citem->frag_next;
++	} while (citem != NULL);
++
++	/* we reached the end of the list, insert */
++	pitem->frag_next = item;
++	return 0;
++}
++
+ int 
+ isakmp_frag_extract(iph1, msg)
+ 	struct ph1handle *iph1;
+@@ -224,39 +261,43 @@ isakmp_frag_extract(iph1, msg)
+ 	item->frag_next = NULL;
+ 	item->frag_packet = buf;
+ 
+-	/* Look for the last frag while inserting the new item in the chain */
+-	if (item->frag_last)
+-		last_frag = item->frag_num;
++	/* Check for the last frag before inserting the new item in the chain */
++	if (item->frag_last) {
++		/* if we have the last fragment, indices must match */
++		if (iph1->frag_last_index != 0 &&
++		    item->frag_last != iph1->frag_last_index) {
++			plog(LLV_ERROR, LOCATION, NULL,
++			     "Repeated last fragment index mismatch\n");
++			racoon_free(item);
++			vfree(buf);
++			return -1;
++		}
+ 
+-	if (iph1->frag_chain == NULL) {
+-		iph1->frag_chain = item;
+-	} else {
+-		struct isakmp_frag_item *current;
++		last_frag = iph1->frag_last_index = item->frag_num;
++	}
+ 
+-		current = iph1->frag_chain;
+-		while (current->frag_next) {
+-			if (current->frag_last)
+-				last_frag = item->frag_num;
+-			current = current->frag_next;
+-		}
+-		current->frag_next = item;
++	/* insert fragment into chain */
++	if (isakmp_frag_insert(iph1, item) == -1) {
++		plog(LLV_ERROR, LOCATION, NULL,
++		    "Repeated fragment index mismatch\n");
++		racoon_free(item);
++		vfree(buf);
++		return -1;
+ 	}
+ 
+-	/* If we saw the last frag, check if the chain is complete */
++	/* If we saw the last frag, check if the chain is complete
++	 * we have a sorted list now, so just walk through */
+ 	if (last_frag != 0) {
++		item = iph1->frag_chain;
+ 		for (i = 1; i <= last_frag; i++) {
+-			item = iph1->frag_chain;
+-			do {
+-				if (item->frag_num == i)
+-					break;
+-				item = item->frag_next;
+-			} while (item != NULL);
+-
++			if (item->frag_num != i)
++				break;
++			item = item->frag_next;
+ 			if (item == NULL) /* Not found */
+ 				break;
+ 		}
+ 
+-		if (item != NULL) /* It is complete */
++		if (i > last_frag) /* It is complete */
+ 			return 1;
+ 	}
+ 		
+@@ -291,15 +332,9 @@ isakmp_frag_reassembly(iph1)
+ 	}
+ 	data = buf->v;
+ 
++	item = iph1->frag_chain;
+ 	for (i = 1; i <= frag_count; i++) {
+-		item = iph1->frag_chain;
+-		do {
+-			if (item->frag_num == i)
+-				break;
+-			item = item->frag_next;
+-		} while (item != NULL);
+-
+-		if (item == NULL) {
++		if (item->frag_num != i) {
+ 			plog(LLV_ERROR, LOCATION, NULL, 
+ 			    "Missing fragment #%d\n", i);
+ 			vfree(buf);
+@@ -308,6 +343,7 @@ isakmp_frag_reassembly(iph1)
+ 		}
+ 		memcpy(data, item->frag_packet->v, item->frag_packet->l);
+ 		data += item->frag_packet->l;
++		item = item->frag_next;
+ 	}
+ 
+ out:

Added: head/security/ipsec-tools/files/patch-isakmp_inf.c
==============================================================================
--- /dev/null	00:00:00 1970	(empty, because file is newly added)
+++ head/security/ipsec-tools/files/patch-isakmp_inf.c	Sat Apr 14 12:07:58 2018	(r467313)
@@ -0,0 +1,22 @@
+Index: src/racoon/isakmp_inf.c
+===================================================================
+RCS file: /cvsroot/src/crypto/dist/ipsec-tools/src/racoon/isakmp_inf.c,v
+retrieving revision 1.50
+retrieving revision 1.51
+diff -p -u -r1.50 -r1.51
+--- src/racoon/isakmp_inf.c	12 Apr 2013 09:53:10 -0000	1.50
++++ src/racoon/isakmp_inf.c	24 Jan 2017 19:23:56 -0000	1.51
+@@ -1,4 +1,4 @@
+-/*	$NetBSD: isakmp_inf.c,v 1.50 2013/04/12 09:53:10 tteras Exp $	*/
++/*	$NetBSD: isakmp_inf.c,v 1.51 2017/01/24 19:23:56 christos Exp $	*/
+ 
+ /* Id: isakmp_inf.c,v 1.44 2006/05/06 20:45:52 manubsd Exp */
+ 
+@@ -720,6 +720,7 @@ isakmp_info_send_nx(isakmp, remote, loca
+ #endif
+ #ifdef ENABLE_FRAG
+ 	iph1->frag = 0;
++	iph1->frag_last_index = 0;
+ 	iph1->frag_chain = NULL;
+ #endif
+ 



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201804141207.w3EC7w33023814>