From patchwork Tue Nov 26 02:25:21 2024 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Hongxu Jia X-Patchwork-Id: 53188 Return-Path: X-Spam-Checker-Version: SpamAssassin 3.4.0 (2014-02-07) on aws-us-west-2-korg-lkml-1.web.codeaurora.org Received: from aws-us-west-2-korg-lkml-1.web.codeaurora.org (localhost.localdomain [127.0.0.1]) by smtp.lore.kernel.org (Postfix) with ESMTP id 5C1A4D5A6CC for ; Tue, 26 Nov 2024 02:25:49 +0000 (UTC) Received: from mx0b-0064b401.pphosted.com (mx0b-0064b401.pphosted.com [205.220.178.238]) by mx.groups.io with SMTP id smtpd.web11.36923.1732587947148046803 for ; Mon, 25 Nov 2024 18:25:47 -0800 Authentication-Results: mx.groups.io; dkim=none (message not signed); spf=permerror, err=parse error for token &{10 18 %{ir}.%{v}.%{d}.spf.has.pphosted.com}: invalid domain name (domain: windriver.com, ip: 205.220.178.238, mailfrom: prvs=1060df9989=hongxu.jia@windriver.com) Received: from pps.filterd (m0250812.ppops.net [127.0.0.1]) by mx0a-0064b401.pphosted.com (8.18.1.2/8.18.1.2) with ESMTP id 4AQ1KgEH007184; Tue, 26 Nov 2024 02:25:46 GMT Received: from ala-exchng02.corp.ad.wrs.com (ala-exchng02.wrs.com [147.11.82.254]) by mx0a-0064b401.pphosted.com (PPS) with ESMTPS id 433618aq0g-8 (version=TLSv1.2 cipher=ECDHE-RSA-AES128-GCM-SHA256 bits=128 verify=NOT); Tue, 26 Nov 2024 02:25:45 +0000 (GMT) Received: from ala-exchng01.corp.ad.wrs.com (147.11.82.252) by ALA-EXCHNG02.corp.ad.wrs.com (147.11.82.254) with Microsoft SMTP Server (version=TLS1_2, cipher=TLS_ECDHE_RSA_WITH_AES_128_GCM_SHA256) id 15.1.2507.43; Mon, 25 Nov 2024 18:25:28 -0800 Received: from ala-lpggp7.wrs.com (147.11.136.210) by ala-exchng01.corp.ad.wrs.com (147.11.82.252) with Microsoft SMTP Server id 15.1.2507.43 via Frontend Transport; Mon, 25 Nov 2024 18:25:28 -0800 From: Hongxu Jia To: CC: Subject: [kirkstone][PATCH V2 08/13] ovmf: Fix CVE-2023-45229 Date: Mon, 25 Nov 2024 18:25:21 -0800 Message-ID: <20241126022526.3389121-8-hongxu.jia@windriver.com> X-Mailer: git-send-email 2.25.1 In-Reply-To: <20241126022526.3389121-1-hongxu.jia@windriver.com> References: <20241126022526.3389121-1-hongxu.jia@windriver.com> MIME-Version: 1.0 X-Proofpoint-ORIG-GUID: 9jKz55rwy37SCKVY8TGhPbMkgBo6fEv- X-Proofpoint-GUID: 9jKz55rwy37SCKVY8TGhPbMkgBo6fEv- X-Authority-Analysis: v=2.4 cv=O65rvw9W c=1 sm=1 tr=0 ts=674531aa cx=c_pps a=K4BcnWQioVPsTJd46EJO2w==:117 a=K4BcnWQioVPsTJd46EJO2w==:17 a=VlfZXiiP6vEA:10 a=PYnjg3YJAAAA:8 a=NEAV23lmAAAA:8 a=hqBzw_eTAAAA:8 a=XkRKQH6RAAAA:8 a=QQrwgld0AAAA:8 a=VKio34HhAAAA:8 a=t7CeM3EgAAAA:8 a=yMhMjlubAAAA:8 a=QyXUC8HyAAAA:8 a=pGLkceISAAAA:8 a=COk6AnOGAAAA:8 a=wpvmLeFpByndl7j4LjUA:9 a=3YgzRljvZfCK9fvt:21 a=lBZTsuZDXdQA:10 a=Hv90Ch-Tvl0A:10 a=bkWp_v3HvcftT6DRAIDL:22 a=1gUyE30hU_ULiMxJiLUW:22 a=GixL4z90Y-kx4mQuXZm8:22 a=ALVy6clGPs_Yy9GZ8Zsv:22 a=FdTzh2GWekK77mhwV6Dw:22 a=TjNXssC_j7lpFel5tvFf:22 X-Proofpoint-Virus-Version: vendor=baseguard engine=ICAP:2.0.293,Aquarius:18.0.1057,Hydra:6.0.680,FMLib:17.12.68.34 definitions=2024-11-26_01,2024-11-25_01,2024-11-22_01 X-Proofpoint-Spam-Details: rule=outbound_notspam policy=outbound score=0 phishscore=0 suspectscore=0 clxscore=1015 mlxscore=0 bulkscore=0 mlxlogscore=999 spamscore=0 priorityscore=1501 lowpriorityscore=0 adultscore=0 malwarescore=0 impostorscore=0 classifier=spam authscore=0 adjust=0 reason=mlx scancount=1 engine=8.21.0-2409260000 definitions=main-2411260019 List-Id: X-Webhook-Received: from li982-79.members.linode.com [45.33.32.79] by aws-us-west-2-korg-lkml-1.web.codeaurora.org with HTTPS for ; Tue, 26 Nov 2024 02:25:49 -0000 X-Groupsio-URL: https://lists.openembedded.org/g/openembedded-core/message/207832 From: Soumya Sambu EDK2's Network Package is susceptible to an out-of-bounds read vulnerability when processing the IA_NA or IA_TA option in a DHCPv6 Advertise message. This vulnerability can be exploited by an attacker to gain unauthorized access and potentially lead to a loss of Confidentiality. References: https://nvd.nist.gov/vuln/detail/CVE-2023-45229 Upstream-patches: https://github.com/tianocore/edk2/commit/1dbb10cc52dc8ef49bb700daa1cefc76b26d52e0 https://github.com/tianocore/edk2/commit/07362769ab7a7d74dbea1c7a7a3662c7b5d1f097 https://github.com/tianocore/edk2/commit/1c440a5eceedc64e892877eeac0f1a4938f5abbb https://github.com/tianocore/edk2/commit/1d0b95f6457d225c5108302a9da74b4ed7aa5a38 Signed-off-by: Soumya Sambu --- .../ovmf/ovmf/CVE-2023-45229-0001.patch | 604 ++++++++++++++++++ .../ovmf/ovmf/CVE-2023-45229-0002.patch | 539 ++++++++++++++++ .../ovmf/ovmf/CVE-2023-45229-0003.patch | 244 +++++++ .../ovmf/ovmf/CVE-2023-45229-0004.patch | 157 +++++ meta/recipes-core/ovmf/ovmf_git.bb | 4 + 5 files changed, 1548 insertions(+) create mode 100644 meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0001.patch create mode 100644 meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0002.patch create mode 100644 meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0003.patch create mode 100644 meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0004.patch diff --git a/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0001.patch b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0001.patch new file mode 100644 index 0000000000..9d8549b27d --- /dev/null +++ b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0001.patch @@ -0,0 +1,604 @@ +From 1dbb10cc52dc8ef49bb700daa1cefc76b26d52e0 Mon Sep 17 00:00:00 2001 +From: "Doug Flick via groups.io" +Date: Fri, 26 Jan 2024 05:54:46 +0800 +Subject: [PATCH] NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45229 Patch + +REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4534 + +Bug Details: +PixieFail Bug #1 +CVE-2023-45229 +CVSS 6.5 : CVSS:3.1/AV:A/AC:L/PR:N/UI:N/S:U/C:H/I:N/A:N +CWE-125 Out-of-bounds Read + +Change Overview: + +Introduce Dhcp6SeekInnerOptionSafe which performs checks before seeking +the Inner Option from a DHCP6 Option. + +> +> EFI_STATUS +> Dhcp6SeekInnerOptionSafe ( +> IN UINT16 IaType, +> IN UINT8 *Option, +> IN UINT32 OptionLen, +> OUT UINT8 **IaInnerOpt, +> OUT UINT16 *IaInnerLen +> ); +> + +Lots of code cleanup to improve code readability. + +Cc: Saloni Kasbekar +Cc: Zachary Clark-williams + +Signed-off-by: Doug Flick [MSFT] +Reviewed-by: Saloni Kasbekar + +CVE: CVE-2023-45229 + +Upstream-Status: Backport [https://github.com/tianocore/edk2/commit/1dbb10cc52dc8ef49bb700daa1cefc76b26d52e0] + +Signed-off-by: Soumya Sambu +--- + NetworkPkg/Dhcp6Dxe/Dhcp6Impl.h | 138 +++++++++++++++++++--- + NetworkPkg/Dhcp6Dxe/Dhcp6Io.c | 203 +++++++++++++++++++++----------- + 2 files changed, 256 insertions(+), 85 deletions(-) + +diff --git a/NetworkPkg/Dhcp6Dxe/Dhcp6Impl.h b/NetworkPkg/Dhcp6Dxe/Dhcp6Impl.h +index f2422c2f28..220e7c68f1 100644 +--- a/NetworkPkg/Dhcp6Dxe/Dhcp6Impl.h ++++ b/NetworkPkg/Dhcp6Dxe/Dhcp6Impl.h +@@ -45,6 +45,20 @@ typedef struct _DHCP6_INSTANCE DHCP6_INSTANCE; + #define DHCP6_SERVICE_SIGNATURE SIGNATURE_32 ('D', 'H', '6', 'S') + #define DHCP6_INSTANCE_SIGNATURE SIGNATURE_32 ('D', 'H', '6', 'I') + ++#define DHCP6_PACKET_ALL 0 ++#define DHCP6_PACKET_STATEFUL 1 ++#define DHCP6_PACKET_STATELESS 2 ++ ++#define DHCP6_BASE_PACKET_SIZE 1024 ++ ++#define DHCP6_PORT_CLIENT 546 ++#define DHCP6_PORT_SERVER 547 ++ ++#define DHCP_CHECK_MEDIA_WAITING_TIME EFI_TIMER_PERIOD_SECONDS(20) ++ ++#define DHCP6_INSTANCE_FROM_THIS(Instance) CR ((Instance), DHCP6_INSTANCE, Dhcp6, DHCP6_INSTANCE_SIGNATURE) ++#define DHCP6_SERVICE_FROM_THIS(Service) CR ((Service), DHCP6_SERVICE, ServiceBinding, DHCP6_SERVICE_SIGNATURE) ++ + // + // For more information on DHCP options see RFC 8415, Section 21.1 + // +@@ -59,12 +73,10 @@ typedef struct _DHCP6_INSTANCE DHCP6_INSTANCE; + // | (option-len octets) | + // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ + // +-#define DHCP6_SIZE_OF_OPT_CODE (sizeof(UINT16)) +-#define DHCP6_SIZE_OF_OPT_LEN (sizeof(UINT16)) ++#define DHCP6_SIZE_OF_OPT_CODE (sizeof (((EFI_DHCP6_PACKET_OPTION *)0)->OpCode)) ++#define DHCP6_SIZE_OF_OPT_LEN (sizeof (((EFI_DHCP6_PACKET_OPTION *)0)->OpLen)) + +-// + // Combined size of Code and Length +-// + #define DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN (DHCP6_SIZE_OF_OPT_CODE + \ + DHCP6_SIZE_OF_OPT_LEN) + +@@ -73,34 +85,122 @@ STATIC_ASSERT ( + "Combined size of Code and Length must be 4 per RFC 8415" + ); + +-// + // Offset to the length is just past the code +-// +-#define DHCP6_OPT_LEN_OFFSET(a) (a + DHCP6_SIZE_OF_OPT_CODE) ++#define DHCP6_OFFSET_OF_OPT_LEN(a) (a + DHCP6_SIZE_OF_OPT_CODE) + STATIC_ASSERT ( +- DHCP6_OPT_LEN_OFFSET (0) == 2, ++ DHCP6_OFFSET_OF_OPT_LEN (0) == 2, + "Offset of length is + 2 past start of option" + ); + +-#define DHCP6_OPT_DATA_OFFSET(a) (a + DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN) ++#define DHCP6_OFFSET_OF_OPT_DATA(a) (a + DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN) + STATIC_ASSERT ( +- DHCP6_OPT_DATA_OFFSET (0) == 4, ++ DHCP6_OFFSET_OF_OPT_DATA (0) == 4, + "Offset to option data should be +4 from start of option" + ); ++// ++// Identity Association options (both NA (Non-Temporary) and TA (Temporary Association)) ++// are defined in RFC 8415 and are a deriviation of a TLV stucture ++// For more information on IA_NA see Section 21.4 ++// For more information on IA_TA see Section 21.5 ++// ++// ++// The format of IA_NA and IA_TA option: ++// ++// 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// | OPTION_IA_NA | option-len | ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// | IAID (4 octets) | ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// | T1 (only for IA_NA) | ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// | T2 (only for IA_NA) | ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// | | ++// . IA_NA-options/IA_TA-options . ++// . . ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// ++#define DHCP6_SIZE_OF_IAID (sizeof(UINT32)) ++#define DHCP6_SIZE_OF_TIME_INTERVAL (sizeof(UINT32)) + +-#define DHCP6_PACKET_ALL 0 +-#define DHCP6_PACKET_STATEFUL 1 +-#define DHCP6_PACKET_STATELESS 2 ++// Combined size of IAID, T1, and T2 ++#define DHCP6_SIZE_OF_COMBINED_IAID_T1_T2 (DHCP6_SIZE_OF_IAID + \ ++ DHCP6_SIZE_OF_TIME_INTERVAL + \ ++ DHCP6_SIZE_OF_TIME_INTERVAL) ++STATIC_ASSERT ( ++ DHCP6_SIZE_OF_COMBINED_IAID_T1_T2 == 12, ++ "Combined size of IAID, T1, T2 must be 12 per RFC 8415" ++ ); + +-#define DHCP6_BASE_PACKET_SIZE 1024 ++// This is the size of IA_TA without options ++#define DHCP6_MIN_SIZE_OF_IA_TA (DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN + \ ++ DHCP6_SIZE_OF_IAID) ++STATIC_ASSERT ( ++ DHCP6_MIN_SIZE_OF_IA_TA == 8, ++ "Minimum combined size of IA_TA per RFC 8415" ++ ); + +-#define DHCP6_PORT_CLIENT 546 +-#define DHCP6_PORT_SERVER 547 ++// Offset to a IA_TA inner option ++#define DHCP6_OFFSET_OF_IA_TA_INNER_OPT(a) (a + DHCP6_MIN_SIZE_OF_IA_TA) ++STATIC_ASSERT ( ++ DHCP6_OFFSET_OF_IA_TA_INNER_OPT (0) == 8, ++ "Offset of IA_TA Inner option is + 8 past start of option" ++ ); + +-#define DHCP_CHECK_MEDIA_WAITING_TIME EFI_TIMER_PERIOD_SECONDS(20) ++// This is the size of IA_NA without options (16) ++#define DHCP6_MIN_SIZE_OF_IA_NA DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN + \ ++ DHCP6_SIZE_OF_COMBINED_IAID_T1_T2 ++STATIC_ASSERT ( ++ DHCP6_MIN_SIZE_OF_IA_NA == 16, ++ "Minimum combined size of IA_TA per RFC 8415" ++ ); + +-#define DHCP6_INSTANCE_FROM_THIS(Instance) CR ((Instance), DHCP6_INSTANCE, Dhcp6, DHCP6_INSTANCE_SIGNATURE) +-#define DHCP6_SERVICE_FROM_THIS(Service) CR ((Service), DHCP6_SERVICE, ServiceBinding, DHCP6_SERVICE_SIGNATURE) ++#define DHCP6_OFFSET_OF_IA_NA_INNER_OPT(a) (a + DHCP6_MIN_SIZE_OF_IA_NA) ++STATIC_ASSERT ( ++ DHCP6_OFFSET_OF_IA_NA_INNER_OPT (0) == 16, ++ "Offset of IA_NA Inner option is + 16 past start of option" ++ ); ++ ++#define DHCP6_OFFSET_OF_IA_NA_T1(a) (a + \ ++ DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN + \ ++ DHCP6_SIZE_OF_IAID) ++STATIC_ASSERT ( ++ DHCP6_OFFSET_OF_IA_NA_T1 (0) == 8, ++ "Offset of IA_NA Inner option is + 8 past start of option" ++ ); ++ ++#define DHCP6_OFFSET_OF_IA_NA_T2(a) (a + \ ++ DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN +\ ++ DHCP6_SIZE_OF_IAID + \ ++ DHCP6_SIZE_OF_TIME_INTERVAL) ++STATIC_ASSERT ( ++ DHCP6_OFFSET_OF_IA_NA_T2 (0) == 12, ++ "Offset of IA_NA Inner option is + 12 past start of option" ++ ); ++ ++// ++// For more information see RFC 8415 Section 21.13 ++// ++// The format of the Status Code Option: ++// ++// 0 1 2 3 ++// 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// | OPTION_STATUS_CODE | option-len | ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// | status-code | | ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ | ++// . . ++// . status-message . ++// . . ++// +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++// ++#define DHCP6_OFFSET_OF_STATUS_CODE(a) (a + DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN) ++STATIC_ASSERT ( ++ DHCP6_OFFSET_OF_STATUS_CODE (0) == 4, ++ "Offset of status is + 4 past start of option" ++ ); + + extern EFI_IPv6_ADDRESS mAllDhcpRelayAndServersAddress; + extern EFI_DHCP6_PROTOCOL gDhcp6ProtocolTemplate; +diff --git a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c +index bf5aa7a769..89d16484a5 100644 +--- a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c ++++ b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c +@@ -598,8 +598,8 @@ Dhcp6UpdateIaInfo ( + // The inner options still start with 2 bytes option-code and 2 bytes option-len. + // + if (Instance->Config->IaDescriptor.Type == Dhcp6OptIana) { +- T1 = NTOHL (ReadUnaligned32 ((UINT32 *)(Option + 8))); +- T2 = NTOHL (ReadUnaligned32 ((UINT32 *)(Option + 12))); ++ T1 = NTOHL (ReadUnaligned32 ((UINT32 *)(DHCP6_OFFSET_OF_IA_NA_T1 (Option)))); ++ T2 = NTOHL (ReadUnaligned32 ((UINT32 *)(DHCP6_OFFSET_OF_IA_NA_T2 (Option)))); + // + // Refer to RFC3155 Chapter 22.4. If a client receives an IA_NA with T1 greater than T2, + // and both T1 and T2 are greater than 0, the client discards the IA_NA option and processes +@@ -609,13 +609,14 @@ Dhcp6UpdateIaInfo ( + return EFI_DEVICE_ERROR; + } + +- IaInnerOpt = Option + 16; +- IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(Option + 2))) - 12); ++ IaInnerOpt = DHCP6_OFFSET_OF_IA_NA_INNER_OPT (Option); ++ IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))) - DHCP6_SIZE_OF_COMBINED_IAID_T1_T2); + } else { +- T1 = 0; +- T2 = 0; +- IaInnerOpt = Option + 8; +- IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(Option + 2))) - 4); ++ T1 = 0; ++ T2 = 0; ++ ++ IaInnerOpt = DHCP6_OFFSET_OF_IA_TA_INNER_OPT (Option); ++ IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))) - DHCP6_SIZE_OF_IAID); + } + + // +@@ -641,7 +642,7 @@ Dhcp6UpdateIaInfo ( + Option = Dhcp6SeekOption (IaInnerOpt, IaInnerLen, Dhcp6OptStatusCode); + + if (Option != NULL) { +- StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(Option + 4))); ++ StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))); + if (StsCode != Dhcp6StsSuccess) { + return EFI_DEVICE_ERROR; + } +@@ -661,6 +662,87 @@ Dhcp6UpdateIaInfo ( + return Status; + } + ++/** ++ Seeks the Inner Options from a DHCP6 Option ++ ++ @param[in] IaType The type of the IA option. ++ @param[in] Option The pointer to the DHCP6 Option. ++ @param[in] OptionLen The length of the DHCP6 Option. ++ @param[out] IaInnerOpt The pointer to the IA inner option. ++ @param[out] IaInnerLen The length of the IA inner option. ++ ++ @retval EFI_SUCCESS Seek the inner option successfully. ++ @retval EFI_DEVICE_ERROR The OptionLen is invalid. On Error, ++ the pointers are not modified ++**/ ++EFI_STATUS ++Dhcp6SeekInnerOptionSafe ( ++ IN UINT16 IaType, ++ IN UINT8 *Option, ++ IN UINT32 OptionLen, ++ OUT UINT8 **IaInnerOpt, ++ OUT UINT16 *IaInnerLen ++ ) ++{ ++ UINT16 IaInnerLenTmp; ++ UINT8 *IaInnerOptTmp; ++ ++ if (Option == NULL) { ++ ASSERT (Option != NULL); ++ return EFI_DEVICE_ERROR; ++ } ++ ++ if (IaInnerOpt == NULL) { ++ ASSERT (IaInnerOpt != NULL); ++ return EFI_DEVICE_ERROR; ++ } ++ ++ if (IaInnerLen == NULL) { ++ ASSERT (IaInnerLen != NULL); ++ return EFI_DEVICE_ERROR; ++ } ++ ++ if (IaType == Dhcp6OptIana) { ++ // Verify we have a fully formed IA_NA ++ if (OptionLen < DHCP6_MIN_SIZE_OF_IA_NA) { ++ return EFI_DEVICE_ERROR; ++ } ++ ++ // ++ IaInnerOptTmp = DHCP6_OFFSET_OF_IA_NA_INNER_OPT (Option); ++ ++ // Verify the IaInnerLen is valid. ++ IaInnerLenTmp = (UINT16)NTOHS (ReadUnaligned16 ((UINT16 *)DHCP6_OFFSET_OF_OPT_LEN (Option))); ++ if (IaInnerLenTmp < DHCP6_SIZE_OF_COMBINED_IAID_T1_T2) { ++ return EFI_DEVICE_ERROR; ++ } ++ ++ IaInnerLenTmp -= DHCP6_SIZE_OF_COMBINED_IAID_T1_T2; ++ } else if (IaType == Dhcp6OptIata) { ++ // Verify the OptionLen is valid. ++ if (OptionLen < DHCP6_MIN_SIZE_OF_IA_TA) { ++ return EFI_DEVICE_ERROR; ++ } ++ ++ IaInnerOptTmp = DHCP6_OFFSET_OF_IA_TA_INNER_OPT (Option); ++ ++ // Verify the IaInnerLen is valid. ++ IaInnerLenTmp = (UINT16)NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))); ++ if (IaInnerLenTmp < DHCP6_SIZE_OF_IAID) { ++ return EFI_DEVICE_ERROR; ++ } ++ ++ IaInnerLenTmp -= DHCP6_SIZE_OF_IAID; ++ } else { ++ return EFI_DEVICE_ERROR; ++ } ++ ++ *IaInnerOpt = IaInnerOptTmp; ++ *IaInnerLen = IaInnerLenTmp; ++ ++ return EFI_SUCCESS; ++} ++ + /** + Seek StatusCode Option in package. A Status Code option may appear in the + options field of a DHCP message and/or in the options field of another option. +@@ -684,6 +766,12 @@ Dhcp6SeekStsOption ( + UINT8 *IaInnerOpt; + UINT16 IaInnerLen; + UINT16 StsCode; ++ UINT32 OptionLen; ++ ++ // OptionLen is the length of the Options excluding the DHCP header. ++ // Length of the EFI_DHCP6_PACKET from the first byte of the Header field to the last ++ // byte of the Option[] field. ++ OptionLen = Packet->Length - sizeof (Packet->Dhcp6.Header); + + // + // Seek StatusCode option directly in DHCP message body. That is, search in +@@ -691,12 +779,12 @@ Dhcp6SeekStsOption ( + // + *Option = Dhcp6SeekOption ( + Packet->Dhcp6.Option, +- Packet->Length - 4, ++ OptionLen, + Dhcp6OptStatusCode + ); + + if (*Option != NULL) { +- StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(*Option + 4))); ++ StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_STATUS_CODE (*Option)))); + if (StsCode != Dhcp6StsSuccess) { + return EFI_DEVICE_ERROR; + } +@@ -707,7 +795,7 @@ Dhcp6SeekStsOption ( + // + *Option = Dhcp6SeekIaOption ( + Packet->Dhcp6.Option, +- Packet->Length - sizeof (EFI_DHCP6_HEADER), ++ OptionLen, + &Instance->Config->IaDescriptor + ); + if (*Option == NULL) { +@@ -715,52 +803,35 @@ Dhcp6SeekStsOption ( + } + + // +- // The format of the IA_NA option is: ++ // Calculate the distance from Packet->Dhcp6.Option to the IA option. + // +- // 0 1 2 3 +- // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | OPTION_IA_NA | option-len | +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | IAID (4 octets) | +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | T1 | +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | T2 | +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | | +- // . IA_NA-options . +- // . . +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++ // Packet->Size and Packet->Length are both UINT32 type, and Packet->Size is ++ // the size of the whole packet, including the DHCP header, and Packet->Length ++ // is the length of the DHCP message body, excluding the DHCP header. + // +- // The format of the IA_TA option is: ++ // (*Option - Packet->Dhcp6.Option) is the number of bytes from the start of ++ // DHCP6 option area to the start of the IA option. + // +- // 0 1 2 3 +- // 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | OPTION_IA_TA | option-len | +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | IAID (4 octets) | +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ +- // | | +- // . IA_TA-options . +- // . . +- // +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ ++ // Dhcp6SeekInnerOptionSafe() is searching starting from the start of the ++ // IA option to the end of the DHCP6 option area, thus subtract the space ++ // up until this option + // ++ OptionLen = OptionLen - (*Option - Packet->Dhcp6.Option); + + // +- // sizeof (option-code + option-len + IaId) = 8 +- // sizeof (option-code + option-len + IaId + T1) = 12 +- // sizeof (option-code + option-len + IaId + T1 + T2) = 16 +- // +- // The inner options still start with 2 bytes option-code and 2 bytes option-len. ++ // Seek the inner option + // +- if (Instance->Config->IaDescriptor.Type == Dhcp6OptIana) { +- IaInnerOpt = *Option + 16; +- IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(*Option + 2))) - 12); +- } else { +- IaInnerOpt = *Option + 8; +- IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(*Option + 2))) - 4); ++ if (EFI_ERROR ( ++ Dhcp6SeekInnerOptionSafe ( ++ Instance->Config->IaDescriptor.Type, ++ *Option, ++ OptionLen, ++ &IaInnerOpt, ++ &IaInnerLen ++ ) ++ )) ++ { ++ return EFI_DEVICE_ERROR; + } + + // +@@ -784,7 +855,7 @@ Dhcp6SeekStsOption ( + // + *Option = Dhcp6SeekOption (IaInnerOpt, IaInnerLen, Dhcp6OptStatusCode); + if (*Option != NULL) { +- StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(*Option + 4))); ++ StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)((DHCP6_OFFSET_OF_STATUS_CODE (*Option))))); + if (StsCode != Dhcp6StsSuccess) { + return EFI_DEVICE_ERROR; + } +@@ -1105,7 +1176,7 @@ Dhcp6SendRequestMsg ( + // + Option = Dhcp6SeekOption ( + Instance->AdSelect->Dhcp6.Option, +- Instance->AdSelect->Length - 4, ++ Instance->AdSelect->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptServerId + ); + if (Option == NULL) { +@@ -1289,7 +1360,7 @@ Dhcp6SendDeclineMsg ( + // + Option = Dhcp6SeekOption ( + LastReply->Dhcp6.Option, +- LastReply->Length - 4, ++ LastReply->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptServerId + ); + if (Option == NULL) { +@@ -1448,7 +1519,7 @@ Dhcp6SendReleaseMsg ( + // + Option = Dhcp6SeekOption ( + LastReply->Dhcp6.Option, +- LastReply->Length - 4, ++ LastReply->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptServerId + ); + if (Option == NULL) { +@@ -1673,7 +1744,7 @@ Dhcp6SendRenewRebindMsg ( + + Option = Dhcp6SeekOption ( + LastReply->Dhcp6.Option, +- LastReply->Length - 4, ++ LastReply->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptServerId + ); + if (Option == NULL) { +@@ -2208,7 +2279,7 @@ Dhcp6HandleReplyMsg ( + // + Option = Dhcp6SeekOption ( + Packet->Dhcp6.Option, +- Packet->Length - 4, ++ Packet->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptRapidCommit + ); + +@@ -2354,7 +2425,7 @@ Dhcp6HandleReplyMsg ( + // + // Any error status code option is found. + // +- StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(Option + 4))); ++ StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)((DHCP6_OFFSET_OF_STATUS_CODE (Option))))); + switch (StsCode) { + case Dhcp6StsUnspecFail: + // +@@ -2487,7 +2558,7 @@ Dhcp6SelectAdvertiseMsg ( + // + Option = Dhcp6SeekOption ( + AdSelect->Dhcp6.Option, +- AdSelect->Length - 4, ++ AdSelect->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptServerUnicast + ); + +@@ -2498,7 +2569,7 @@ Dhcp6SelectAdvertiseMsg ( + return EFI_OUT_OF_RESOURCES; + } + +- CopyMem (Instance->Unicast, Option + 4, sizeof (EFI_IPv6_ADDRESS)); ++ CopyMem (Instance->Unicast, DHCP6_OFFSET_OF_OPT_DATA (Option), sizeof (EFI_IPv6_ADDRESS)); + } + + // +@@ -2551,7 +2622,7 @@ Dhcp6HandleAdvertiseMsg ( + // + Option = Dhcp6SeekOption ( + Packet->Dhcp6.Option, +- Packet->Length - 4, ++ Packet->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptRapidCommit + ); + +@@ -2645,7 +2716,7 @@ Dhcp6HandleAdvertiseMsg ( + CopyMem (Instance->AdSelect, Packet, Packet->Size); + + if (Option != NULL) { +- Instance->AdPref = *(Option + 4); ++ Instance->AdPref = *(DHCP6_OFFSET_OF_OPT_DATA (Option)); + } + } else { + // +@@ -2714,11 +2785,11 @@ Dhcp6HandleStateful ( + // + Option = Dhcp6SeekOption ( + Packet->Dhcp6.Option, +- Packet->Length - 4, ++ Packet->Length - DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN, + Dhcp6OptClientId + ); + +- if ((Option == NULL) || (CompareMem (Option + 4, ClientId->Duid, ClientId->Length) != 0)) { ++ if ((Option == NULL) || (CompareMem (DHCP6_OFFSET_OF_OPT_DATA (Option), ClientId->Duid, ClientId->Length) != 0)) { + goto ON_CONTINUE; + } + +@@ -2727,7 +2798,7 @@ Dhcp6HandleStateful ( + // + Option = Dhcp6SeekOption ( + Packet->Dhcp6.Option, +- Packet->Length - 4, ++ Packet->Length - DHCP6_SIZE_OF_COMBINED_CODE_AND_LEN, + Dhcp6OptServerId + ); + +@@ -2832,7 +2903,7 @@ Dhcp6HandleStateless ( + // + Option = Dhcp6SeekOption ( + Packet->Dhcp6.Option, +- Packet->Length - 4, ++ Packet->Length - sizeof (EFI_DHCP6_HEADER), + Dhcp6OptServerId + ); + +-- +2.40.0 + diff --git a/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0002.patch b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0002.patch new file mode 100644 index 0000000000..7ce5c98789 --- /dev/null +++ b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0002.patch @@ -0,0 +1,539 @@ +From 07362769ab7a7d74dbea1c7a7a3662c7b5d1f097 Mon Sep 17 00:00:00 2001 +From: "Doug Flick via groups.io" +Date: Fri, 26 Jan 2024 05:54:47 +0800 +Subject: [PATCH] NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45229 Unit + Tests + +REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4534 + +These tests confirm that the report bug... + +"Out-of-bounds read when processing IA_NA/IA_TA options in a +DHCPv6 Advertise message" + +..has been patched. + +The following functions are tested to confirm an out of bounds read is +patched and that the correct statuses are returned: + +Dhcp6SeekInnerOptionSafe +Dhcp6SeekStsOption + +TCBZ4534 +CVE-2023-45229 +CVSS 6.5 : CVSS:3.1/AV:A/AC:L/PR:N/UI:N/S:U/C:H/I:N/A:N +CWE-125 Out-of-bounds Read + +Cc: Saloni Kasbekar +Cc: Zachary Clark-williams + +Signed-off-by: Doug Flick [MSFT] +Reviewed-by: Saloni Kasbekar + +CVE: CVE-2023-45229 + +Upstream-Status: Backport [https://github.com/tianocore/edk2/commit/07362769ab7a7d74dbea1c7a7a3662c7b5d1f097] + +Signed-off-by: Soumya Sambu +--- + NetworkPkg/Dhcp6Dxe/Dhcp6Io.c | 2 +- + .../GoogleTest/Dhcp6DxeGoogleTest.inf | 1 + + .../Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.cpp | 365 +++++++++++++++++- + .../Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.h | 58 +++ + 4 files changed, 423 insertions(+), 3 deletions(-) + create mode 100644 NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.h + +diff --git a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c +index 89d16484a5..3b8feb4a20 100644 +--- a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c ++++ b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c +@@ -816,7 +816,7 @@ Dhcp6SeekStsOption ( + // IA option to the end of the DHCP6 option area, thus subtract the space + // up until this option + // +- OptionLen = OptionLen - (*Option - Packet->Dhcp6.Option); ++ OptionLen = OptionLen - (UINT32)(*Option - Packet->Dhcp6.Option); + + // + // Seek the inner option +diff --git a/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6DxeGoogleTest.inf b/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6DxeGoogleTest.inf +index 8e9119a371..12532ed30c 100644 +--- a/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6DxeGoogleTest.inf ++++ b/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6DxeGoogleTest.inf +@@ -18,6 +18,7 @@ + [Sources] + Dhcp6DxeGoogleTest.cpp + Dhcp6IoGoogleTest.cpp ++ Dhcp6IoGoogleTest.h + ../Dhcp6Io.c + ../Dhcp6Utility.c + +diff --git a/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.cpp b/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.cpp +index 7ee40e4af4..7db253a7b8 100644 +--- a/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.cpp ++++ b/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.cpp +@@ -13,6 +13,7 @@ extern "C" { + #include + #include "../Dhcp6Impl.h" + #include "../Dhcp6Utility.h" ++ #include "Dhcp6IoGoogleTest.h" + } + + //////////////////////////////////////////////////////////////////////// +@@ -21,7 +22,35 @@ extern "C" { + + #define DHCP6_PACKET_MAX_LEN 1500 + ++// This definition is used by this test but is also required to compile ++// by Dhcp6Io.c ++#define DHCPV6_OPTION_IA_NA 3 ++#define DHCPV6_OPTION_IA_TA 4 ++ ++#define SEARCH_PATTERN 0xDEADC0DE ++#define SEARCH_PATTERN_LEN sizeof(SEARCH_PATTERN) ++ + //////////////////////////////////////////////////////////////////////// ++// Test structures for IA_NA and IA_TA options ++//////////////////////////////////////////////////////////////////////// ++typedef struct { ++ UINT16 Code; ++ UINT16 Len; ++ UINT32 IAID; ++} DHCPv6_OPTION; ++ ++typedef struct { ++ DHCPv6_OPTION Header; ++ UINT32 T1; ++ UINT32 T2; ++ UINT8 InnerOptions[0]; ++} DHCPv6_OPTION_IA_NA; ++ ++typedef struct { ++ DHCPv6_OPTION Header; ++ UINT8 InnerOptions[0]; ++} DHCPv6_OPTION_IA_TA; ++ + //////////////////////////////////////////////////////////////////////// + // Symbol Definitions + // These functions are not directly under test - but required to compile +@@ -210,7 +239,7 @@ TEST_F (Dhcp6AppendETOptionTest, InvalidDataExpectBufferTooSmall) { + Status = Dhcp6AppendETOption ( + Dhcp6AppendETOptionTest::Packet, + &Cursor, +- &Instance, // Instance is not used in this function ++ &Instance, // Instance is not used in this function + &ElapsedTime + ); + +@@ -240,7 +269,7 @@ TEST_F (Dhcp6AppendETOptionTest, ValidDataExpectSuccess) { + Status = Dhcp6AppendETOption ( + Dhcp6AppendETOptionTest::Packet, + &Cursor, +- &Instance, // Instance is not used in this function ++ &Instance, // Instance is not used in this function + &ElapsedTime + ); + +@@ -476,3 +505,335 @@ TEST_F (Dhcp6AppendIaOptionTest, IaTaValidDataExpectSuccess) { + // verify that the status is EFI_SUCCESS + ASSERT_EQ (Status, EFI_SUCCESS); + } ++ ++//////////////////////////////////////////////////////////////////////// ++// Dhcp6SeekInnerOptionSafe Tests ++//////////////////////////////////////////////////////////////////////// ++ ++// Define a fixture for your tests if needed ++class Dhcp6SeekInnerOptionSafeTest : public ::testing::Test { ++protected: ++ // Add any setup code if needed ++ virtual void ++ SetUp ( ++ ) ++ { ++ // Initialize any resources or variables ++ } ++ ++ // Add any cleanup code if needed ++ virtual void ++ TearDown ( ++ ) ++ { ++ // Clean up any resources or variables ++ } ++}; ++ ++// Test Description: ++// This test verifies that Dhcp6SeekInnerOptionSafe returns EFI_SUCCESS when the IANA option is found. ++TEST_F (Dhcp6SeekInnerOptionSafeTest, IANAValidOptionExpectSuccess) { ++ EFI_STATUS Result; ++ UINT8 Option[sizeof (DHCPv6_OPTION_IA_NA) + SEARCH_PATTERN_LEN] = { 0 }; ++ UINT32 OptionLength = sizeof (Option); ++ DHCPv6_OPTION_IA_NA *OptionPtr = (DHCPv6_OPTION_IA_NA *)Option; ++ UINT32 SearchPattern = SEARCH_PATTERN; ++ ++ UINTN SearchPatternLength = SEARCH_PATTERN_LEN; ++ UINT8 *InnerOptionPtr = NULL; ++ UINT16 InnerOptionLength = 0; ++ ++ OptionPtr->Header.Code = Dhcp6OptIana; ++ OptionPtr->Header.Len = HTONS (4 + 12); // Valid length has to be more than 12 ++ OptionPtr->Header.IAID = 0x12345678; ++ OptionPtr->T1 = 0x11111111; ++ OptionPtr->T2 = 0x22222222; ++ CopyMem (OptionPtr->InnerOptions, &SearchPattern, SearchPatternLength); ++ ++ Result = Dhcp6SeekInnerOptionSafe ( ++ Dhcp6OptIana, ++ Option, ++ OptionLength, ++ &InnerOptionPtr, ++ &InnerOptionLength ++ ); ++ ASSERT_EQ (Result, EFI_SUCCESS); ++ ASSERT_EQ (InnerOptionLength, 4); ++ ASSERT_EQ (CompareMem (InnerOptionPtr, &SearchPattern, SearchPatternLength), 0); ++} ++ ++// Test Description: ++// This test verifies that Dhcp6SeekInnerOptionSafe returns EFI_DEIVCE_ERROR when the IANA option size is invalid. ++TEST_F (Dhcp6SeekInnerOptionSafeTest, IANAInvalidSizeExpectFail) { ++ // Lets add an inner option of bytes we expect to find ++ EFI_STATUS Status; ++ UINT8 Option[sizeof (DHCPv6_OPTION_IA_NA) + SEARCH_PATTERN_LEN] = { 0 }; ++ UINT32 OptionLength = sizeof (Option); ++ DHCPv6_OPTION_IA_NA *OptionPtr = (DHCPv6_OPTION_IA_NA *)Option; ++ UINT32 SearchPattern = SEARCH_PATTERN; ++ ++ UINTN SearchPatternLength = SEARCH_PATTERN_LEN; ++ UINT8 *InnerOptionPtr = NULL; ++ UINT16 InnerOptionLength = 0; ++ ++ OptionPtr->Header.Code = Dhcp6OptIana; ++ OptionPtr->Header.Len = HTONS (4); // Set the length to lower than expected (12) ++ OptionPtr->Header.IAID = 0x12345678; ++ OptionPtr->T1 = 0x11111111; ++ OptionPtr->T2 = 0x22222222; ++ CopyMem (OptionPtr->InnerOptions, &SearchPattern, SearchPatternLength); ++ ++ // Set the InnerOptionLength to be less than the size of the option ++ Status = Dhcp6SeekInnerOptionSafe ( ++ Dhcp6OptIana, ++ Option, ++ OptionLength, ++ &InnerOptionPtr, ++ &InnerOptionLength ++ ); ++ ASSERT_EQ (Status, EFI_DEVICE_ERROR); ++ ++ // Now set the OptionLength to be less than the size of the option ++ OptionLength = sizeof (DHCPv6_OPTION_IA_NA) - 1; ++ Status = Dhcp6SeekInnerOptionSafe ( ++ Dhcp6OptIana, ++ Option, ++ OptionLength, ++ &InnerOptionPtr, ++ &InnerOptionLength ++ ); ++ ASSERT_EQ (Status, EFI_DEVICE_ERROR); ++} ++ ++// Test Description: ++// This test verifies that Dhcp6SeekInnerOptionSafe returns EFI_SUCCESS when the IATA option is found ++TEST_F (Dhcp6SeekInnerOptionSafeTest, IATAValidOptionExpectSuccess) { ++ // Lets add an inner option of bytes we expect to find ++ EFI_STATUS Status; ++ UINT8 Option[sizeof (DHCPv6_OPTION_IA_TA) + SEARCH_PATTERN_LEN] = { 0 }; ++ UINT32 OptionLength = sizeof (Option); ++ DHCPv6_OPTION_IA_TA *OptionPtr = (DHCPv6_OPTION_IA_TA *)Option; ++ UINT32 SearchPattern = SEARCH_PATTERN; ++ ++ UINTN SearchPatternLength = SEARCH_PATTERN_LEN; ++ UINT8 *InnerOptionPtr = NULL; ++ UINT16 InnerOptionLength = 0; ++ ++ OptionPtr->Header.Code = Dhcp6OptIata; ++ OptionPtr->Header.Len = HTONS (4 + 4); // Valid length has to be more than 4 ++ OptionPtr->Header.IAID = 0x12345678; ++ CopyMem (OptionPtr->InnerOptions, &SearchPattern, SearchPatternLength); ++ ++ Status = Dhcp6SeekInnerOptionSafe ( ++ Dhcp6OptIata, ++ Option, ++ OptionLength, ++ &InnerOptionPtr, ++ &InnerOptionLength ++ ); ++ ASSERT_EQ (Status, EFI_SUCCESS); ++ ASSERT_EQ (InnerOptionLength, 4); ++ ASSERT_EQ (CompareMem (InnerOptionPtr, &SearchPattern, SearchPatternLength), 0); ++} ++ ++// Test Description: ++// This test verifies that Dhcp6SeekInnerOptionSafe returns EFI_SUCCESS when the IATA option size is invalid. ++TEST_F (Dhcp6SeekInnerOptionSafeTest, IATAInvalidSizeExpectFail) { ++ // Lets add an inner option of bytes we expect to find ++ EFI_STATUS Status; ++ UINT8 Option[sizeof (DHCPv6_OPTION_IA_TA) + SEARCH_PATTERN_LEN] = { 0 }; ++ UINT32 OptionLength = sizeof (Option); ++ DHCPv6_OPTION_IA_TA *OptionPtr = (DHCPv6_OPTION_IA_TA *)Option; ++ UINT32 SearchPattern = SEARCH_PATTERN; ++ ++ UINTN SearchPatternLength = SEARCH_PATTERN_LEN; ++ UINT8 *InnerOptionPtr = NULL; ++ UINT16 InnerOptionLength = 0; ++ ++ OptionPtr->Header.Code = Dhcp6OptIata; ++ OptionPtr->Header.Len = HTONS (2); // Set the length to lower than expected (4) ++ OptionPtr->Header.IAID = 0x12345678; ++ CopyMem (OptionPtr->InnerOptions, &SearchPattern, SearchPatternLength); ++ ++ Status = Dhcp6SeekInnerOptionSafe ( ++ Dhcp6OptIata, ++ Option, ++ OptionLength, ++ &InnerOptionPtr, ++ &InnerOptionLength ++ ); ++ ASSERT_EQ (Status, EFI_DEVICE_ERROR); ++ ++ // Now lets try modifying the OptionLength to be less than the size of the option ++ OptionLength = sizeof (DHCPv6_OPTION_IA_TA) - 1; ++ Status = Dhcp6SeekInnerOptionSafe ( ++ Dhcp6OptIata, ++ Option, ++ OptionLength, ++ &InnerOptionPtr, ++ &InnerOptionLength ++ ); ++ ASSERT_EQ (Status, EFI_DEVICE_ERROR); ++} ++ ++// Test Description: ++// This test verifies that any other Option Type fails ++TEST_F (Dhcp6SeekInnerOptionSafeTest, InvalidOption) { ++ // Lets add an inner option of bytes we expect to find ++ EFI_STATUS Result; ++ UINT8 Option[sizeof (DHCPv6_OPTION_IA_TA) + SEARCH_PATTERN_LEN] = { 0 }; ++ UINT32 OptionLength = sizeof (Option); ++ DHCPv6_OPTION_IA_TA *OptionPtr = (DHCPv6_OPTION_IA_TA *)Option; ++ UINT32 SearchPattern = SEARCH_PATTERN; ++ ++ UINTN SearchPatternLength = SEARCH_PATTERN_LEN; ++ UINT8 *InnerOptionPtr = NULL; ++ UINT16 InnerOptionLength = 0; ++ ++ OptionPtr->Header.Code = 0xC0DE; ++ OptionPtr->Header.Len = HTONS (2); // Set the length to lower than expected (4) ++ OptionPtr->Header.IAID = 0x12345678; ++ CopyMem (OptionPtr->InnerOptions, &SearchPattern, SearchPatternLength); ++ ++ Result = Dhcp6SeekInnerOptionSafe (0xC0DE, Option, OptionLength, &InnerOptionPtr, &InnerOptionLength); ++ ASSERT_EQ (Result, EFI_DEVICE_ERROR); ++} ++ ++//////////////////////////////////////////////////////////////////////// ++// Dhcp6SeekStsOption Tests ++//////////////////////////////////////////////////////////////////////// ++ ++#define PACKET_SIZE (1500) ++ ++class Dhcp6SeekStsOptionTest : public ::testing::Test { ++public: ++ DHCP6_INSTANCE Instance = { 0 }; ++ EFI_DHCP6_PACKET *Packet = NULL; ++ EFI_DHCP6_CONFIG_DATA Config = { 0 }; ++ ++protected: ++ // Add any setup code if needed ++ virtual void ++ SetUp ( ++ ) ++ { ++ // Allocate a packet ++ Packet = (EFI_DHCP6_PACKET *)AllocateZeroPool (PACKET_SIZE); ++ ASSERT_NE (Packet, nullptr); ++ ++ // Initialize the packet ++ Packet->Size = PACKET_SIZE; ++ ++ Instance.Config = &Config; ++ } ++ ++ // Add any cleanup code if needed ++ virtual void ++ TearDown ( ++ ) ++ { ++ // Clean up any resources or variables ++ FreePool (Packet); ++ } ++}; ++ ++// Test Description: ++// This test verifies that Dhcp6SeekStsOption returns EFI_DEVICE_ERROR when the option is invalid ++// This verifies that the calling function is working as expected ++TEST_F (Dhcp6SeekStsOptionTest, SeekIATAOptionExpectFail) { ++ EFI_STATUS Status; ++ UINT8 *Option = NULL; ++ UINT32 SearchPattern = SEARCH_PATTERN; ++ UINT16 SearchPatternLength = SEARCH_PATTERN_LEN; ++ UINT16 *Len = NULL; ++ EFI_DHCP6_IA Ia = { 0 }; ++ ++ Ia.Descriptor.Type = DHCPV6_OPTION_IA_TA; ++ Ia.IaAddressCount = 1; ++ Ia.IaAddress[0].PreferredLifetime = 0xDEADBEEF; ++ Ia.IaAddress[0].ValidLifetime = 0xDEADAAAA; ++ Ia.IaAddress[0].IpAddress = mAllDhcpRelayAndServersAddress; ++ ++ Packet->Length = sizeof (EFI_DHCP6_HEADER); ++ ++ Option = Dhcp6SeekStsOptionTest::Packet->Dhcp6.Option; ++ ++ // Let's append the option to the packet ++ Status = Dhcp6AppendOption ( ++ Dhcp6SeekStsOptionTest::Packet, ++ &Option, ++ Dhcp6OptStatusCode, ++ SearchPatternLength, ++ (UINT8 *)&SearchPattern ++ ); ++ ASSERT_EQ (Status, EFI_SUCCESS); ++ ++ // Inner option length - this will be overwritten later ++ Len = (UINT16 *)(Option + 2); ++ ++ // Fill in the inner IA option ++ Status = Dhcp6AppendIaOption ( ++ Dhcp6SeekStsOptionTest::Packet, ++ &Option, ++ &Ia, ++ 0x12345678, ++ 0x11111111, ++ 0x22222222 ++ ); ++ ASSERT_EQ (Status, EFI_SUCCESS); ++ ++ // overwrite the len of inner Ia option ++ *Len = HTONS (3); ++ ++ Dhcp6SeekStsOptionTest::Instance.Config->IaDescriptor.Type = DHCPV6_OPTION_IA_TA; ++ ++ Option = NULL; ++ Status = Dhcp6SeekStsOption (&(Dhcp6SeekStsOptionTest::Instance), Dhcp6SeekStsOptionTest::Packet, &Option); ++ ++ ASSERT_EQ (Status, EFI_DEVICE_ERROR); ++} ++ ++// Test Description: ++// This test verifies that Dhcp6SeekInnerOptionSafe returns EFI_SUCCESS when the IATA option size is invalid. ++TEST_F (Dhcp6SeekStsOptionTest, SeekIANAOptionExpectSuccess) { ++ EFI_STATUS Status = EFI_NOT_FOUND; ++ UINT8 *Option = NULL; ++ UINT32 SearchPattern = SEARCH_PATTERN; ++ UINT16 SearchPatternLength = SEARCH_PATTERN_LEN; ++ EFI_DHCP6_IA Ia = { 0 }; ++ ++ Ia.Descriptor.Type = DHCPV6_OPTION_IA_NA; ++ Ia.IaAddressCount = 1; ++ Ia.IaAddress[0].PreferredLifetime = 0x11111111; ++ Ia.IaAddress[0].ValidLifetime = 0x22222222; ++ Ia.IaAddress[0].IpAddress = mAllDhcpRelayAndServersAddress; ++ Packet->Length = sizeof (EFI_DHCP6_HEADER); ++ ++ Option = Dhcp6SeekStsOptionTest::Packet->Dhcp6.Option; ++ ++ Status = Dhcp6AppendOption ( ++ Dhcp6SeekStsOptionTest::Packet, ++ &Option, ++ Dhcp6OptStatusCode, ++ SearchPatternLength, ++ (UINT8 *)&SearchPattern ++ ); ++ ASSERT_EQ (Status, EFI_SUCCESS); ++ ++ Status = Dhcp6AppendIaOption ( ++ Dhcp6SeekStsOptionTest::Packet, ++ &Option, ++ &Ia, ++ 0x12345678, ++ 0x11111111, ++ 0x22222222 ++ ); ++ ASSERT_EQ (Status, EFI_SUCCESS); ++ ++ Dhcp6SeekStsOptionTest::Instance.Config->IaDescriptor.Type = DHCPV6_OPTION_IA_NA; ++ ++ Option = NULL; ++ Status = Dhcp6SeekStsOption (&(Dhcp6SeekStsOptionTest::Instance), Dhcp6SeekStsOptionTest::Packet, &Option); ++ ++ ASSERT_EQ (Status, EFI_SUCCESS); ++} +diff --git a/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.h b/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.h +new file mode 100644 +index 0000000000..aed3b89082 +--- /dev/null ++++ b/NetworkPkg/Dhcp6Dxe/GoogleTest/Dhcp6IoGoogleTest.h +@@ -0,0 +1,58 @@ ++/** @file ++ Acts as header for private functions under test in Dhcp6Io.c ++ ++ Copyright (c) Microsoft Corporation ++ SPDX-License-Identifier: BSD-2-Clause-Patent ++**/ ++ ++#ifndef DHCP6_IO_GOOGLE_TEST_H_ ++#define DHCP6_IO_GOOGLE_TEST_H_ ++ ++//////////////////////////////////////////////////////////////////////////////// ++// These are the functions that are being unit tested ++//////////////////////////////////////////////////////////////////////////////// ++ ++#include ++ ++/** ++ Seeks the Inner Options from a DHCP6 Option ++ ++ @param[in] IaType The type of the IA option. ++ @param[in] Option The pointer to the DHCP6 Option. ++ @param[in] OptionLen The length of the DHCP6 Option. ++ @param[out] IaInnerOpt The pointer to the IA inner option. ++ @param[out] IaInnerLen The length of the IA inner option. ++ ++ @retval EFI_SUCCESS Seek the inner option successfully. ++ @retval EFI_DEVICE_ERROR The OptionLen is invalid. ++*/ ++EFI_STATUS ++Dhcp6SeekInnerOptionSafe ( ++ UINT16 IaType, ++ UINT8 *Option, ++ UINT32 OptionLen, ++ UINT8 **IaInnerOpt, ++ UINT16 *IaInnerLen ++ ); ++ ++/** ++ Seek StatusCode Option in package. A Status Code option may appear in the ++ options field of a DHCP message and/or in the options field of another option. ++ See details in section 22.13, RFC3315. ++ ++ @param[in] Instance The pointer to the Dhcp6 instance. ++ @param[in] Packet The pointer to reply messages. ++ @param[out] Option The pointer to status code option. ++ ++ @retval EFI_SUCCESS Seek status code option successfully. ++ @retval EFI_DEVICE_ERROR An unexpected error. ++ ++**/ ++EFI_STATUS ++Dhcp6SeekStsOption ( ++ IN DHCP6_INSTANCE *Instance, ++ IN EFI_DHCP6_PACKET *Packet, ++ OUT UINT8 **Option ++ ); ++ ++#endif // DHCP6_IO_GOOGLE_TEST_H +-- +2.40.0 + diff --git a/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0003.patch b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0003.patch new file mode 100644 index 0000000000..bf4e8eda1f --- /dev/null +++ b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0003.patch @@ -0,0 +1,244 @@ +From 1c440a5eceedc64e892877eeac0f1a4938f5abbb Mon Sep 17 00:00:00 2001 +From: Doug Flick +Date: Tue, 13 Feb 2024 10:46:00 -0800 +Subject: [PATCH] NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45229 Related + Patch + +REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4673 +REF: https://bugzilla.tianocore.org/show_bug.cgi?id=4534 + +This was not part of the Quarkslab bugs however the same pattern +as CVE-2023-45229 exists in Dhcp6UpdateIaInfo. + +This patch replaces the code in question with the safe function +created to patch CVE-2023-45229 + +> +> if (EFI_ERROR ( +> Dhcp6SeekInnerOptionSafe ( +> Instance->Config->IaDescriptor.Type, +> Option, +> OptionLen, +> &IaInnerOpt, +> &IaInnerLen +> ) +> )) +> { +> return EFI_DEVICE_ERROR; +> } +> + +Additionally corrects incorrect usage of macro to read the status + +> - StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)DHCP6_OFFSET_OF_OPT_LEN + (Option))); +> + StsCode = NTOHS (ReadUnaligned16 ((UINT16 *) +DHCP6_OFFSET_OF_STATUS_CODE (Option)); + +Cc: Saloni Kasbekar +Cc: Zachary Clark-williams +Signed-off-by: Doug Flick [MSFT] +Reviewed-by: Saloni Kasbekar +Reviewed-by: Leif Lindholm + +CVE: CVE-2023-45229 + +Upstream-Status: Backport [https://github.com/tianocore/edk2/commit/1c440a5eceedc64e892877eeac0f1a4938f5abbb] + +Signed-off-by: Soumya Sambu +--- + NetworkPkg/Dhcp6Dxe/Dhcp6Io.c | 70 ++++++++++++++++++++++++++--------- + NetworkPkg/Dhcp6Dxe/Dhcp6Io.h | 22 +++++++++++ + 2 files changed, 75 insertions(+), 17 deletions(-) + +diff --git a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c +index 3b8feb4a20..a9bffae353 100644 +--- a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c ++++ b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.c +@@ -528,13 +528,23 @@ Dhcp6UpdateIaInfo ( + { + EFI_STATUS Status; + UINT8 *Option; ++ UINT32 OptionLen; + UINT8 *IaInnerOpt; + UINT16 IaInnerLen; + UINT16 StsCode; + UINT32 T1; + UINT32 T2; + ++ T1 = 0; ++ T2 = 0; ++ + ASSERT (Instance->Config != NULL); ++ ++ // OptionLen is the length of the Options excluding the DHCP header. ++ // Length of the EFI_DHCP6_PACKET from the first byte of the Header field to the last ++ // byte of the Option[] field. ++ OptionLen = Packet->Length - sizeof (Packet->Dhcp6.Header); ++ + // + // If the reply was received in response to a solicit with rapid commit option, + // request, renew or rebind message, the client updates the information it has +@@ -549,13 +559,29 @@ Dhcp6UpdateIaInfo ( + // + Option = Dhcp6SeekIaOption ( + Packet->Dhcp6.Option, +- Packet->Length - sizeof (EFI_DHCP6_HEADER), ++ OptionLen, + &Instance->Config->IaDescriptor + ); + if (Option == NULL) { + return EFI_DEVICE_ERROR; + } + ++ // ++ // Calculate the distance from Packet->Dhcp6.Option to the IA option. ++ // ++ // Packet->Size and Packet->Length are both UINT32 type, and Packet->Size is ++ // the size of the whole packet, including the DHCP header, and Packet->Length ++ // is the length of the DHCP message body, excluding the DHCP header. ++ // ++ // (*Option - Packet->Dhcp6.Option) is the number of bytes from the start of ++ // DHCP6 option area to the start of the IA option. ++ // ++ // Dhcp6SeekInnerOptionSafe() is searching starting from the start of the ++ // IA option to the end of the DHCP6 option area, thus subtract the space ++ // up until this option ++ // ++ OptionLen = OptionLen - (UINT32)(Option - Packet->Dhcp6.Option); ++ + // + // The format of the IA_NA option is: + // +@@ -591,32 +617,32 @@ Dhcp6UpdateIaInfo ( + // + + // +- // sizeof (option-code + option-len + IaId) = 8 +- // sizeof (option-code + option-len + IaId + T1) = 12 +- // sizeof (option-code + option-len + IaId + T1 + T2) = 16 +- // +- // The inner options still start with 2 bytes option-code and 2 bytes option-len. ++ // Seek the inner option + // ++ if (EFI_ERROR ( ++ Dhcp6SeekInnerOptionSafe ( ++ Instance->Config->IaDescriptor.Type, ++ Option, ++ OptionLen, ++ &IaInnerOpt, ++ &IaInnerLen ++ ) ++ )) ++ { ++ return EFI_DEVICE_ERROR; ++ } ++ + if (Instance->Config->IaDescriptor.Type == Dhcp6OptIana) { + T1 = NTOHL (ReadUnaligned32 ((UINT32 *)(DHCP6_OFFSET_OF_IA_NA_T1 (Option)))); + T2 = NTOHL (ReadUnaligned32 ((UINT32 *)(DHCP6_OFFSET_OF_IA_NA_T2 (Option)))); + // + // Refer to RFC3155 Chapter 22.4. If a client receives an IA_NA with T1 greater than T2, + // and both T1 and T2 are greater than 0, the client discards the IA_NA option and processes +- // the remainder of the message as though the server had not included the invalid IA_NA option. ++ // the remainder of the message as though the server had not included the invalid IA_NA option. + // + if ((T1 > T2) && (T2 > 0)) { + return EFI_DEVICE_ERROR; + } +- +- IaInnerOpt = DHCP6_OFFSET_OF_IA_NA_INNER_OPT (Option); +- IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))) - DHCP6_SIZE_OF_COMBINED_IAID_T1_T2); +- } else { +- T1 = 0; +- T2 = 0; +- +- IaInnerOpt = DHCP6_OFFSET_OF_IA_TA_INNER_OPT (Option); +- IaInnerLen = (UINT16)(NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))) - DHCP6_SIZE_OF_IAID); + } + + // +@@ -642,7 +668,7 @@ Dhcp6UpdateIaInfo ( + Option = Dhcp6SeekOption (IaInnerOpt, IaInnerLen, Dhcp6OptStatusCode); + + if (Option != NULL) { +- StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))); ++ StsCode = NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_STATUS_CODE (Option)))); + if (StsCode != Dhcp6StsSuccess) { + return EFI_DEVICE_ERROR; + } +@@ -703,15 +729,21 @@ Dhcp6SeekInnerOptionSafe ( + } + + if (IaType == Dhcp6OptIana) { ++ // + // Verify we have a fully formed IA_NA ++ // + if (OptionLen < DHCP6_MIN_SIZE_OF_IA_NA) { + return EFI_DEVICE_ERROR; + } + ++ // ++ // Get the IA Inner Option and Length + // + IaInnerOptTmp = DHCP6_OFFSET_OF_IA_NA_INNER_OPT (Option); + ++ // + // Verify the IaInnerLen is valid. ++ // + IaInnerLenTmp = (UINT16)NTOHS (ReadUnaligned16 ((UINT16 *)DHCP6_OFFSET_OF_OPT_LEN (Option))); + if (IaInnerLenTmp < DHCP6_SIZE_OF_COMBINED_IAID_T1_T2) { + return EFI_DEVICE_ERROR; +@@ -719,14 +751,18 @@ Dhcp6SeekInnerOptionSafe ( + + IaInnerLenTmp -= DHCP6_SIZE_OF_COMBINED_IAID_T1_T2; + } else if (IaType == Dhcp6OptIata) { ++ // + // Verify the OptionLen is valid. ++ // + if (OptionLen < DHCP6_MIN_SIZE_OF_IA_TA) { + return EFI_DEVICE_ERROR; + } + + IaInnerOptTmp = DHCP6_OFFSET_OF_IA_TA_INNER_OPT (Option); + ++ // + // Verify the IaInnerLen is valid. ++ // + IaInnerLenTmp = (UINT16)NTOHS (ReadUnaligned16 ((UINT16 *)(DHCP6_OFFSET_OF_OPT_LEN (Option)))); + if (IaInnerLenTmp < DHCP6_SIZE_OF_IAID) { + return EFI_DEVICE_ERROR; +diff --git a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.h b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.h +index 051a652f2b..ab0e1ac27f 100644 +--- a/NetworkPkg/Dhcp6Dxe/Dhcp6Io.h ++++ b/NetworkPkg/Dhcp6Dxe/Dhcp6Io.h +@@ -217,4 +217,26 @@ Dhcp6OnTimerTick ( + IN VOID *Context + ); + ++/** ++ Seeks the Inner Options from a DHCP6 Option ++ ++ @param[in] IaType The type of the IA option. ++ @param[in] Option The pointer to the DHCP6 Option. ++ @param[in] OptionLen The length of the DHCP6 Option. ++ @param[out] IaInnerOpt The pointer to the IA inner option. ++ @param[out] IaInnerLen The length of the IA inner option. ++ ++ @retval EFI_SUCCESS Seek the inner option successfully. ++ @retval EFI_DEVICE_ERROR The OptionLen is invalid. On Error, ++ the pointers are not modified ++**/ ++EFI_STATUS ++Dhcp6SeekInnerOptionSafe ( ++ IN UINT16 IaType, ++ IN UINT8 *Option, ++ IN UINT32 OptionLen, ++ OUT UINT8 **IaInnerOpt, ++ OUT UINT16 *IaInnerLen ++ ); ++ + #endif +-- +2.40.0 + diff --git a/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0004.patch b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0004.patch new file mode 100644 index 0000000000..85d204972d --- /dev/null +++ b/meta/recipes-core/ovmf/ovmf/CVE-2023-45229-0004.patch @@ -0,0 +1,157 @@ +From 1d0b95f6457d225c5108302a9da74b4ed7aa5a38 Mon Sep 17 00:00:00 2001 +From: "Doug Flick via groups.io" +Date: Fri, 26 Jan 2024 05:54:57 +0800 +Subject: [PATCH] NetworkPkg: : Adds a SecurityFix.yaml file + +This creates / adds a security file that tracks the security fixes +found in this package and can be used to find the fixes that were +applied. + +Cc: Saloni Kasbekar +Cc: Zachary Clark-williams + +Signed-off-by: Doug Flick [MSFT] +Reviewed-by: Saloni Kasbekar + +CVE: CVE_2023_45229 + +Upstream-Status: Backport [https://github.com/tianocore/edk2/commit/1d0b95f6457d225c5108302a9da74b4ed7aa5a38] + +Signed-off-by: Soumya Sambu +--- + NetworkPkg/SecurityFixes.yaml | 123 ++++++++++++++++++++++++++++++++++ + 1 file changed, 123 insertions(+) + create mode 100644 NetworkPkg/SecurityFixes.yaml + +diff --git a/NetworkPkg/SecurityFixes.yaml b/NetworkPkg/SecurityFixes.yaml +new file mode 100644 +index 0000000000..7e900483fe +--- /dev/null ++++ b/NetworkPkg/SecurityFixes.yaml +@@ -0,0 +1,123 @@ ++## @file ++# Security Fixes for SecurityPkg ++# ++# Copyright (c) Microsoft Corporation ++# SPDX-License-Identifier: BSD-2-Clause-Patent ++## ++CVE_2023_45229: ++ commit_titles: ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45229 Patch" ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45229 Unit Tests" ++ cve: CVE-2023-45229 ++ date_reported: 2023-08-28 13:56 UTC ++ description: "Bug 01 - edk2/NetworkPkg: Out-of-bounds read when processing IA_NA/IA_TA options in a DHCPv6 Advertise message" ++ note: ++ files_impacted: ++ - NetworkPkg\Dhcp6Dxe\Dhcp6Io.c ++ - NetworkPkg\Dhcp6Dxe\Dhcp6Impl.h ++ links: ++ - https://bugzilla.tianocore.org/show_bug.cgi?id=4534 ++ - https://nvd.nist.gov/vuln/detail/CVE-2023-45229 ++ - http://www.openwall.com/lists/oss-security/2024/01/16/2 ++ - http://packetstormsecurity.com/files/176574/PixieFail-Proof-Of-Concepts.html ++ - https://blog.quarkslab.com/pixiefail-nine-vulnerabilities-in-tianocores-edk-ii-ipv6-network-stack.html ++CVE_2023_45230: ++ commit_titles: ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45230 Patch" ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45230 Unit Tests" ++ cve: CVE-2023-45230 ++ date_reported: 2023-08-28 13:56 UTC ++ description: "Bug 02 - edk2/NetworkPkg: Buffer overflow in the DHCPv6 client via a long Server ID option" ++ note: ++ files_impacted: ++ - NetworkPkg\Dhcp6Dxe\Dhcp6Io.c ++ - NetworkPkg\Dhcp6Dxe\Dhcp6Impl.h ++ links: ++ - https://bugzilla.tianocore.org/show_bug.cgi?id=4535 ++ - https://nvd.nist.gov/vuln/detail/CVE-2023-45230 ++ - http://www.openwall.com/lists/oss-security/2024/01/16/2 ++ - http://packetstormsecurity.com/files/176574/PixieFail-Proof-Of-Concepts.html ++ - https://blog.quarkslab.com/pixiefail-nine-vulnerabilities-in-tianocores-edk-ii-ipv6-network-stack.html ++CVE_2023_45231: ++ commit_titles: ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45231 Patch" ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45231 Unit Tests" ++ cve: CVE-2023-45231 ++ date_reported: 2023-08-28 13:56 UTC ++ description: "Bug 03 - edk2/NetworkPkg: Out-of-bounds read when handling a ND Redirect message with truncated options" ++ note: ++ files_impacted: ++ - NetworkPkg/Ip6Dxe/Ip6Option.c ++ links: ++ - https://bugzilla.tianocore.org/show_bug.cgi?id=4536 ++ - https://nvd.nist.gov/vuln/detail/CVE-2023-45231 ++ - http://www.openwall.com/lists/oss-security/2024/01/16/2 ++ - http://packetstormsecurity.com/files/176574/PixieFail-Proof-Of-Concepts.html ++ - https://blog.quarkslab.com/pixiefail-nine-vulnerabilities-in-tianocores-edk-ii-ipv6-network-stack.html ++CVE_2023_45232: ++ commit_titles: ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45232 Patch" ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45232 Unit Tests" ++ cve: CVE-2023-45232 ++ date_reported: 2023-08-28 13:56 UTC ++ description: "Bug 04 - edk2/NetworkPkg: Infinite loop when parsing unknown options in the Destination Options header" ++ note: ++ files_impacted: ++ - NetworkPkg/Ip6Dxe/Ip6Option.c ++ - NetworkPkg/Ip6Dxe/Ip6Option.h ++ links: ++ - https://bugzilla.tianocore.org/show_bug.cgi?id=4537 ++ - https://nvd.nist.gov/vuln/detail/CVE-2023-45232 ++ - http://www.openwall.com/lists/oss-security/2024/01/16/2 ++ - http://packetstormsecurity.com/files/176574/PixieFail-Proof-Of-Concepts.html ++ - https://blog.quarkslab.com/pixiefail-nine-vulnerabilities-in-tianocores-edk-ii-ipv6-network-stack.html ++CVE_2023_45233: ++ commit_titles: ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45232 Patch" ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45232 Unit Tests" ++ cve: CVE-2023-45233 ++ date_reported: 2023-08-28 13:56 UTC ++ description: "Bug 05 - edk2/NetworkPkg: Infinite loop when parsing a PadN option in the Destination Options header " ++ note: This was fixed along with CVE-2023-45233 ++ files_impacted: ++ - NetworkPkg/Ip6Dxe/Ip6Option.c ++ - NetworkPkg/Ip6Dxe/Ip6Option.h ++ links: ++ - https://bugzilla.tianocore.org/show_bug.cgi?id=4538 ++ - https://nvd.nist.gov/vuln/detail/CVE-2023-45233 ++ - http://www.openwall.com/lists/oss-security/2024/01/16/2 ++ - http://packetstormsecurity.com/files/176574/PixieFail-Proof-Of-Concepts.html ++ - https://blog.quarkslab.com/pixiefail-nine-vulnerabilities-in-tianocores-edk-ii-ipv6-network-stack.html ++CVE_2023_45234: ++ commit_titles: ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45234 Patch" ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45234 Unit Tests" ++ cve: CVE-2023-45234 ++ date_reported: 2023-08-28 13:56 UTC ++ description: "Bug 06 - edk2/NetworkPkg: Buffer overflow when processing DNS Servers option in a DHCPv6 Advertise message" ++ note: ++ files_impacted: ++ - NetworkPkg/UefiPxeBcDxe/PxeBcDhcp6.c ++ links: ++ - https://bugzilla.tianocore.org/show_bug.cgi?id=4539 ++ - https://nvd.nist.gov/vuln/detail/CVE-2023-45234 ++ - http://www.openwall.com/lists/oss-security/2024/01/16/2 ++ - http://packetstormsecurity.com/files/176574/PixieFail-Proof-Of-Concepts.html ++ - https://blog.quarkslab.com/pixiefail-nine-vulnerabilities-in-tianocores-edk-ii-ipv6-network-stack.html ++CVE_2023_45235: ++ commit_titles: ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45235 Patch" ++ - "NetworkPkg: Dhcp6Dxe: SECURITY PATCH CVE-2023-45235 Unit Tests" ++ cve: CVE-2023-45235 ++ date_reported: 2023-08-28 13:56 UTC ++ description: "Bug 07 - edk2/NetworkPkg: Buffer overflow when handling Server ID option from a DHCPv6 proxy Advertise message" ++ note: ++ files_impacted: ++ - NetworkPkg/UefiPxeBcDxe/PxeBcDhcp6.c ++ - NetworkPkg/UefiPxeBcDxe/PxeBcDhcp6.h ++ links: ++ - https://bugzilla.tianocore.org/show_bug.cgi?id=4540 ++ - https://nvd.nist.gov/vuln/detail/CVE-2023-45235 ++ - http://www.openwall.com/lists/oss-security/2024/01/16/2 ++ - http://packetstormsecurity.com/files/176574/PixieFail-Proof-Of-Concepts.html ++ - https://blog.quarkslab.com/pixiefail-nine-vulnerabilities-in-tianocores-edk-ii-ipv6-network-stack.html +-- +2.40.0 + diff --git a/meta/recipes-core/ovmf/ovmf_git.bb b/meta/recipes-core/ovmf/ovmf_git.bb index ceebb53438..6ac72772d1 100644 --- a/meta/recipes-core/ovmf/ovmf_git.bb +++ b/meta/recipes-core/ovmf/ovmf_git.bb @@ -43,6 +43,10 @@ SRC_URI = "gitsm://github.com/tianocore/edk2.git;branch=master;protocol=https \ file://CVE-2023-45234-0002.patch \ file://CVE-2023-45235-0001.patch \ file://CVE-2023-45235-0002.patch \ + file://CVE-2023-45229-0001.patch \ + file://CVE-2023-45229-0002.patch \ + file://CVE-2023-45229-0003.patch \ + file://CVE-2023-45229-0004.patch \ " PV = "edk2-stable202202"