summaryrefslogtreecommitdiffstats
path: root/NetworkPkg/IpSecDxe/IkePacket.c
diff options
context:
space:
mode:
authorqianouyang <qianouyang@6f19259b-4bc3-4df7-8a09-765794883524>2010-12-31 10:43:54 +0000
committerqianouyang <qianouyang@6f19259b-4bc3-4df7-8a09-765794883524>2010-12-31 10:43:54 +0000
commit9166f840d2a70b924b0ff66528f056515443e4e8 (patch)
treeba1f372f4e1165be3c06dd19758d151714ad77ca /NetworkPkg/IpSecDxe/IkePacket.c
parent4a8266f570ef411c21d7991f129e29aac817aa96 (diff)
downloadedk2-9166f840d2a70b924b0ff66528f056515443e4e8.tar.gz
edk2-9166f840d2a70b924b0ff66528f056515443e4e8.tar.bz2
edk2-9166f840d2a70b924b0ff66528f056515443e4e8.zip
Add IPsec/Ikev2 support.
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@11219 6f19259b-4bc3-4df7-8a09-765794883524
Diffstat (limited to 'NetworkPkg/IpSecDxe/IkePacket.c')
-rw-r--r--NetworkPkg/IpSecDxe/IkePacket.c257
1 files changed, 257 insertions, 0 deletions
diff --git a/NetworkPkg/IpSecDxe/IkePacket.c b/NetworkPkg/IpSecDxe/IkePacket.c
new file mode 100644
index 0000000000..fa29d54876
--- /dev/null
+++ b/NetworkPkg/IpSecDxe/IkePacket.c
@@ -0,0 +1,257 @@
+/** @file
+ IKE Packet related operation.
+
+ Copyright (c) 2010, Intel Corporation. All rights reserved.<BR>
+
+ This program and the accompanying materials
+ are licensed and made available under the terms and conditions of the BSD License
+ which accompanies this distribution. The full text of the license may be found at
+ http://opensource.org/licenses/bsd-license.php.
+
+ THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
+ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
+
+**/
+
+#include "IpSecDebug.h"
+#include "Ikev2/Utility.h"
+
+/**
+ Allocate a buffer for the IKE_PACKET and intitalize its Header and payloadlist.
+
+ @return The pointer of the IKE_PACKET.
+
+**/
+IKE_PACKET *
+IkePacketAlloc (
+ VOID
+ )
+{
+ IKE_PACKET *IkePacket;
+
+ IkePacket = (IKE_PACKET *) AllocateZeroPool (sizeof (IKE_PACKET));
+ if (IkePacket == NULL) {
+ return NULL;
+ }
+
+ IkePacket->RefCount = 1;
+ InitializeListHead (&IkePacket->PayloadList);
+
+ IkePacket->Header = (IKE_HEADER *) AllocateZeroPool (sizeof (IKE_HEADER));
+ if (IkePacket->Header == NULL) {
+ FreePool (IkePacket);
+ return NULL;
+ }
+ return IkePacket;
+}
+
+/**
+ Free the IkePacket by the specified IKE_PACKET pointer.
+
+ @param[in] IkePacket The pointer of the IKE_PACKET to be freed.
+
+**/
+VOID
+IkePacketFree (
+ IN IKE_PACKET *IkePacket
+ )
+{
+ LIST_ENTRY *Entry;
+ IKE_PAYLOAD *IkePayload;
+
+ if (IkePacket == NULL) {
+ return;
+ }
+ //
+ // Check if the Packet is referred by others.
+ //
+ if (--IkePacket->RefCount == 0) {
+ //
+ // Free IkePacket header
+ //
+ if (!IkePacket->IsHdrExt && IkePacket->Header != NULL) {
+ FreePool (IkePacket->Header);
+ }
+ //
+ // Free the PayloadsBuff
+ //
+ if (!IkePacket->IsPayloadsBufExt && IkePacket->PayloadsBuf != NULL) {
+ FreePool (IkePacket->PayloadsBuf);
+ }
+ //
+ // Iterate payloadlist and free all payloads
+ //
+ for (Entry = (IkePacket)->PayloadList.ForwardLink; Entry != &(IkePacket)->PayloadList;) {
+ IkePayload = IKE_PAYLOAD_BY_PACKET (Entry);
+ Entry = Entry->ForwardLink;
+
+ IkePayloadFree (IkePayload);
+ }
+
+ FreePool (IkePacket);
+ }
+}
+
+/**
+ Callback funtion of NetbufFromExt()
+
+ @param[in] Arg The data passed from the NetBufFromExe().
+
+**/
+VOID
+IkePacketNetbufFree (
+ IN VOID *Arg
+ )
+{
+ //
+ // TODO: add something if need.
+ //
+}
+
+/**
+ Copy the NetBuf into a IKE_PACKET sturcture.
+
+ Create a IKE_PACKET and fill the received IKE header into the header of IKE_PACKET
+ and copy the recieved packet without IKE HEADER to the PayloadBuf of IKE_PACKET.
+
+ @param[in] Netbuf The pointer of the Netbuf which contains the whole received
+ IKE packet.
+
+ @return The pointer of the IKE_PACKET which contains the received packet.
+
+**/
+IKE_PACKET *
+IkePacketFromNetbuf (
+ IN NET_BUF *Netbuf
+ )
+{
+ IKE_PACKET *IkePacket;
+
+ IkePacket = NULL;
+ if (Netbuf->TotalSize < sizeof (IKE_HEADER)) {
+ goto Error;
+ }
+
+ IkePacket = IkePacketAlloc ();
+ if (IkePacket == NULL) {
+ return NULL;
+ }
+ //
+ // Copy the IKE header from Netbuf to IkePacket->Hdr
+ //
+ NetbufCopy (Netbuf, 0, sizeof (IKE_HEADER), (UINT8 *) IkePacket->Header);
+ //
+ // Net order to host order
+ //
+ IkeHdrNetToHost (IkePacket->Header);
+ if (IkePacket->Header->Length < Netbuf->TotalSize) {
+ goto Error;
+ }
+
+ IkePacket->PayloadTotalSize = IkePacket->Header->Length - sizeof (IKE_HEADER);
+ IkePacket->PayloadsBuf = (UINT8 *) AllocateZeroPool (IkePacket->PayloadTotalSize);
+
+ if (IkePacket->PayloadsBuf == NULL) {
+ goto Error;
+ }
+ //
+ // Copy the IKE packet without the header into the IkePacket->PayloadsBuf.
+ //
+ NetbufCopy (Netbuf, sizeof (IKE_HEADER), (UINT32) IkePacket->PayloadTotalSize, IkePacket->PayloadsBuf);
+ return IkePacket;
+
+Error:
+ if (IkePacket != NULL) {
+ IkePacketFree (IkePacket);
+ }
+
+ return NULL;
+}
+
+/**
+ Convert the format from IKE_PACKET to NetBuf.
+
+ @param[in] SessionCommon Pointer of related IKE_COMMON_SESSION
+ @param[in] IkePacket Pointer of IKE_PACKET to be copy to NetBuf
+ @param[in] IkeType The IKE type to pointer the packet is for which IKE
+ phase. Now it supports IKE_SA_TYPE, IKE_CHILDSA_TYPE,
+ IKE_INFO_TYPE.
+
+ @return a pointer of Netbuff which contains the IKE_PACKE in network order.
+
+**/
+NET_BUF *
+IkeNetbufFromPacket (
+ IN UINT8 *SessionCommon,
+ IN IKE_PACKET *IkePacket,
+ IN UINTN IkeType
+ )
+{
+ NET_BUF *Netbuf;
+ NET_FRAGMENT *Fragments;
+ UINTN Index;
+ UINTN NumPayloads;
+ LIST_ENTRY *PacketEntry;
+ LIST_ENTRY *Entry;
+ IKE_PAYLOAD *IkePayload;
+
+ if (!IkePacket->IsEncoded) {
+ IkePacket->IsEncoded = TRUE;
+ //
+ // Convert Host order to Network order for IKE_PACKET header and payloads
+ // Encryption payloads if needed
+ //
+ if (((IKEV2_SESSION_COMMON *) SessionCommon)->IkeVer == 2) {
+ Ikev2EncodePacket ((IKEV2_SESSION_COMMON *) SessionCommon, IkePacket, IkeType);
+ } else {
+ //
+ //If IKEv1 support, check it here.
+ //
+ return NULL;
+ }
+ }
+
+ NumPayloads = 0;
+ //
+ // Get the number of the payloads
+ //
+ NET_LIST_FOR_EACH (PacketEntry, &(IkePacket)->PayloadList) {
+
+ NumPayloads++;
+ }
+ //
+ // Allocate the Framgents according to the numbers of the IkePayload
+ //
+ Fragments = (NET_FRAGMENT *) AllocateZeroPool ((1 + NumPayloads) * sizeof (NET_FRAGMENT));
+ if (Fragments == NULL) {
+ return NULL;
+ }
+
+ Fragments[0].Bulk = (UINT8 *) IkePacket->Header;
+ Fragments[0].Len = sizeof (IKE_HEADER);
+ Index = 0;
+
+ //
+ // Set payloads to the Framgments.
+ //
+ NET_LIST_FOR_EACH (Entry, &(IkePacket)->PayloadList) {
+ IkePayload = IKE_PAYLOAD_BY_PACKET (Entry);
+
+ Fragments[Index + 1].Bulk = IkePayload->PayloadBuf;
+ Fragments[Index + 1].Len = (UINT32) IkePayload->PayloadSize;
+ Index++;
+ }
+
+ Netbuf = NetbufFromExt (
+ Fragments,
+ (UINT32) (NumPayloads + 1),
+ 0,
+ 0,
+ IkePacketNetbufFree,
+ NULL
+ );
+
+ FreePool (Fragments);
+ return Netbuf;
+}
+