summaryrefslogtreecommitdiffstats
path: root/NetworkPkg/HttpBootDxe
diff options
context:
space:
mode:
authorFu Siyuan <siyuan.fu@intel.com>2016-03-22 13:30:58 +0800
committerFu Siyuan <siyuan.fu@intel.com>2016-04-11 09:49:05 +0800
commit587d204ccda4b507be4f9f42e8c9d226fd755be0 (patch)
tree56f5d7668645348a3f4ec16055df3e84db72452f /NetworkPkg/HttpBootDxe
parent64ee6ed72ad5c1e4b7c9a96f419c3592e93314ad (diff)
downloadedk2-587d204ccda4b507be4f9f42e8c9d226fd755be0.tar.gz
edk2-587d204ccda4b507be4f9f42e8c9d226fd755be0.tar.bz2
edk2-587d204ccda4b507be4f9f42e8c9d226fd755be0.zip
NetworkPkg: Add RAM disk boot support to HTTP Boot driver.
This patch updates the HTTP Boot driver to support the download and boot a RAM disk image from HTTP server. The HTTP RAM disk boot is described in section 23.7 "HTTP Boot" in UEFI 2.6. HTTP server could provide either an UEFI image or a RAM disk image for the HTTP boot client to use. The RAM disk image must contain a UEFI compliant file system in it. HTTP boot driver will identify the image type either by the "Content-Type" entity header filed or by the file name extension as below: "application/efi" or *.efi -> EFI Image *.iso -> CD/DVD Image *.img -> Virtual Disk Image Contributed-under: TianoCore Contribution Agreement 1.0 Signed-off-by: Fu Siyuan <siyuan.fu@intel.com> Reviewed-by: Ye Ting <ting.ye@intel.com> Reviewed-by: El-Haj-Mahmoud Samer <samer.el-haj-mahmoud@hpe.com>
Diffstat (limited to 'NetworkPkg/HttpBootDxe')
-rw-r--r--NetworkPkg/HttpBootDxe/HttpBootClient.c37
-rw-r--r--NetworkPkg/HttpBootDxe/HttpBootClient.h5
-rw-r--r--NetworkPkg/HttpBootDxe/HttpBootDxe.h19
-rw-r--r--NetworkPkg/HttpBootDxe/HttpBootDxe.inf3
-rw-r--r--NetworkPkg/HttpBootDxe/HttpBootImpl.c136
-rw-r--r--NetworkPkg/HttpBootDxe/HttpBootSupport.c142
-rw-r--r--NetworkPkg/HttpBootDxe/HttpBootSupport.h47
7 files changed, 334 insertions, 55 deletions
diff --git a/NetworkPkg/HttpBootDxe/HttpBootClient.c b/NetworkPkg/HttpBootDxe/HttpBootClient.c
index 0c472938a0..9d445e3c8e 100644
--- a/NetworkPkg/HttpBootDxe/HttpBootClient.c
+++ b/NetworkPkg/HttpBootDxe/HttpBootClient.c
@@ -570,6 +570,7 @@ HttpBootFreeCacheList (
@param[out] Buffer The memory buffer to transfer the file to. IF Buffer is NULL,
then the size of the requested file is returned in
BufferSize.
+ @param[out] ImageType The image type of the downloaded file.
@retval EFI_SUCCESS Successfully created.
@retval Others Failed to create HttpIo.
@@ -580,7 +581,8 @@ HttpBootGetFileFromCache (
IN HTTP_BOOT_PRIVATE_DATA *Private,
IN CHAR16 *Uri,
IN OUT UINTN *BufferSize,
- OUT UINT8 *Buffer
+ OUT UINT8 *Buffer,
+ OUT HTTP_BOOT_IMAGE_TYPE *ImageType
)
{
LIST_ENTRY *Entry;
@@ -589,7 +591,7 @@ HttpBootGetFileFromCache (
HTTP_BOOT_ENTITY_DATA *EntityData;
UINTN CopyedSize;
- if (Uri == NULL || BufferSize == 0 || Buffer == NULL) {
+ if (Uri == NULL || BufferSize == 0 || Buffer == NULL || ImageType == NULL) {
return EFI_INVALID_PARAMETER;
}
@@ -603,7 +605,12 @@ HttpBootGetFileFromCache (
(StrCmp (Uri, Cache->RequestData->Url) == 0))
{
//
- // Hit cache, check buffer size.
+ // Hit in cache, record image type.
+ //
+ *ImageType = Cache->ImageType;
+
+ //
+ // Check buffer size.
//
if (*BufferSize < Cache->EntityLength) {
*BufferSize = Cache->EntityLength;
@@ -712,6 +719,7 @@ HttpBootGetBootFileCallback (
@param[out] Buffer The memory buffer to transfer the file to. IF Buffer is NULL,
then the size of the requested file is returned in
BufferSize.
+ @param[out] ImageType The image type of the downloaded file.
@retval EFI_SUCCESS The file was loaded.
@retval EFI_INVALID_PARAMETER BufferSize is NULL or Buffer Size is not NULL but Buffer is NULL.
@@ -727,7 +735,8 @@ HttpBootGetBootFile (
IN HTTP_BOOT_PRIVATE_DATA *Private,
IN BOOLEAN HeaderOnly,
IN OUT UINTN *BufferSize,
- OUT UINT8 *Buffer
+ OUT UINT8 *Buffer,
+ OUT HTTP_BOOT_IMAGE_TYPE *ImageType
)
{
EFI_STATUS Status;
@@ -750,7 +759,7 @@ HttpBootGetBootFile (
ASSERT (Private != NULL);
ASSERT (Private->HttpCreated);
- if (BufferSize == NULL) {
+ if (BufferSize == NULL || ImageType == NULL) {
return EFI_INVALID_PARAMETER;
}
@@ -767,7 +776,7 @@ HttpBootGetBootFile (
}
AsciiStrToUnicodeStr (Private->BootFileUri, Url);
if (!HeaderOnly) {
- Status = HttpBootGetFileFromCache (Private, Url, BufferSize, Buffer);
+ Status = HttpBootGetFileFromCache (Private, Url, BufferSize, Buffer, ImageType);
if (Status != EFI_NOT_FOUND) {
FreePool (Url);
return Status;
@@ -788,6 +797,7 @@ HttpBootGetBootFile (
Status = EFI_OUT_OF_RESOURCES;
goto ERROR_1;
}
+ Cache->ImageType = ImageTypeMax;
InitializeListHead (&Cache->EntityDataList);
}
@@ -919,10 +929,25 @@ HttpBootGetBootFile (
}
//
+ // Check the image type according to server's response.
+ //
+ Status = HttpBootCheckImageType (
+ Private->BootFileUri,
+ Private->BootFileUriParser,
+ ResponseData->HeaderCount,
+ ResponseData->Headers,
+ ImageType
+ );
+ if (EFI_ERROR (Status)) {
+ goto ERROR_5;
+ }
+
+ //
// 3.2 Cache the response header.
//
if (Cache != NULL) {
Cache->ResponseData = ResponseData;
+ Cache->ImageType = *ImageType;
}
//
diff --git a/NetworkPkg/HttpBootDxe/HttpBootClient.h b/NetworkPkg/HttpBootDxe/HttpBootClient.h
index b929fa7dc2..2fd7dfc716 100644
--- a/NetworkPkg/HttpBootDxe/HttpBootClient.h
+++ b/NetworkPkg/HttpBootDxe/HttpBootClient.h
@@ -40,6 +40,7 @@ typedef struct {
LIST_ENTRY Link; // Link to the CacheList in driver's private data.
EFI_HTTP_REQUEST_DATA *RequestData;
HTTP_IO_RESPONSE_DATA *ResponseData; // Not include any message-body data.
+ HTTP_BOOT_IMAGE_TYPE ImageType;
UINTN EntityLength;
LIST_ENTRY EntityDataList; // Entity data (message-body)
} HTTP_BOOT_CACHE_CONTENT;
@@ -105,6 +106,7 @@ HttpBootCreateHttpIo (
@param[out] Buffer The memory buffer to transfer the file to. IF Buffer is NULL,
then the size of the requested file is returned in
BufferSize.
+ @param[out] ImageType The image type of the downloaded file.
@retval EFI_SUCCESS The file was loaded.
@retval EFI_INVALID_PARAMETER BufferSize is NULL or Buffer Size is not NULL but Buffer is NULL.
@@ -120,7 +122,8 @@ HttpBootGetBootFile (
IN HTTP_BOOT_PRIVATE_DATA *Private,
IN BOOLEAN HeaderOnly,
IN OUT UINTN *BufferSize,
- OUT UINT8 *Buffer
+ OUT UINT8 *Buffer,
+ OUT HTTP_BOOT_IMAGE_TYPE *ImageType
);
/**
diff --git a/NetworkPkg/HttpBootDxe/HttpBootDxe.h b/NetworkPkg/HttpBootDxe/HttpBootDxe.h
index b3e2576e1e..76b794321e 100644
--- a/NetworkPkg/HttpBootDxe/HttpBootDxe.h
+++ b/NetworkPkg/HttpBootDxe/HttpBootDxe.h
@@ -55,6 +55,7 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#include <Protocol/Http.h>
#include <Protocol/Ip4Config2.h>
#include <Protocol/Ip6Config.h>
+#include <Protocol/RamDisk.h>
//
// Produced Protocols
//
@@ -71,6 +72,12 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
#define HTTP_BOOT_DXE_VERSION 0xa
//
+// Provisional Standard Media Types defined in
+// http://www.iana.org/assignments/provisional-standard-media-types/provisional-standard-media-types.xhtml
+//
+#define HTTP_CONTENT_TYPE_APP_EFI "application/efi"
+
+//
// Protocol instances
//
extern EFI_DRIVER_BINDING_PROTOCOL gHttpBootDxeDriverBinding;
@@ -83,6 +90,13 @@ extern EFI_COMPONENT_NAME_PROTOCOL gHttpBootDxeComponentName;
typedef struct _HTTP_BOOT_PRIVATE_DATA HTTP_BOOT_PRIVATE_DATA;
typedef struct _HTTP_BOOT_VIRTUAL_NIC HTTP_BOOT_VIRTUAL_NIC;
+typedef enum {
+ ImageTypeEfi,
+ ImageTypeVirtualCd,
+ ImageTypeVirtualDisk,
+ ImageTypeMax
+} HTTP_BOOT_IMAGE_TYPE;
+
//
// Include files with internal function prototypes
//
@@ -166,6 +180,11 @@ struct _HTTP_BOOT_PRIVATE_DATA {
EFI_IP_ADDRESS GatewayIp;
EFI_IP_ADDRESS ServerIp;
UINT16 Port;
+
+ //
+ // The URI string attempt to download through HTTP, may point to
+ // the memory in cached DHCP offer, or to the memory in FilePathUri.
+ //
CHAR8 *BootFileUri;
VOID *BootFileUriParser;
UINTN BootFileSize;
diff --git a/NetworkPkg/HttpBootDxe/HttpBootDxe.inf b/NetworkPkg/HttpBootDxe/HttpBootDxe.inf
index 7393ecd367..d3df5f7d6e 100644
--- a/NetworkPkg/HttpBootDxe/HttpBootDxe.inf
+++ b/NetworkPkg/HttpBootDxe/HttpBootDxe.inf
@@ -81,6 +81,7 @@
gEfiIp6ProtocolGuid ## TO_START
gEfiIp6ConfigProtocolGuid ## TO_START
gEfiNetworkInterfaceIdentifierProtocolGuid_31 ## SOMETIMES_CONSUMES
+ gEfiRamDiskProtocolGuid ## SOMETIMES_CONSUMES
gEfiHiiConfigAccessProtocolGuid ## BY_START
[Guids]
@@ -89,6 +90,8 @@
## SOMETIMES_PRODUCES ## GUID # HiiGetBrowserData mHttpBootConfigStorageName
## SOMETIMES_CONSUMES ## HII
gHttpBootConfigGuid
+ gEfiVirtualCdGuid ## SOMETIMES_CONSUMES ## GUID
+ gEfiVirtualDiskGuid ## SOMETIMES_CONSUMES ## GUID
[UserExtensions.TianoCore."ExtraFiles"]
HttpBootDxeExtra.uni
diff --git a/NetworkPkg/HttpBootDxe/HttpBootImpl.c b/NetworkPkg/HttpBootDxe/HttpBootImpl.c
index c4a3e707fb..cf643d86bc 100644
--- a/NetworkPkg/HttpBootDxe/HttpBootImpl.c
+++ b/NetworkPkg/HttpBootDxe/HttpBootImpl.c
@@ -17,6 +17,9 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
/**
Enable the use of UEFI HTTP boot function.
+ If the driver has already been started but not satisfy the requirement (IP stack and
+ specified boot file path), this function will stop the driver and start it again.
+
@param[in] Private The pointer to the driver's private data.
@param[in] UsingIpv6 Specifies the type of IP addresses that are to be
used during the session that is being started.
@@ -24,7 +27,8 @@ WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
@param[in] FilePath The device specific path of the file to load.
@retval EFI_SUCCESS HTTP boot was successfully enabled.
- @retval EFI_INVALID_PARAMETER Private is NULL.
+ @retval EFI_INVALID_PARAMETER Private is NULL or FilePath is NULL.
+ @retval EFI_INVALID_PARAMETER The FilePath doesn't contain a valid URI device path node.
@retval EFI_ALREADY_STARTED The driver is already in started state.
@retval EFI_OUT_OF_RESOURCES There are not enough resources.
@@ -38,13 +42,50 @@ HttpBootStart (
{
UINTN Index;
EFI_STATUS Status;
+ CHAR8 *Uri;
+
if (Private == NULL || FilePath == NULL) {
return EFI_INVALID_PARAMETER;
}
-
+
+ //
+ // Check the URI in the input FilePath, in order to see whether it is
+ // required to boot from a new specified boot file.
+ //
+ Status = HttpBootParseFilePath (FilePath, &Uri);
+ if (EFI_ERROR (Status)) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // Check whether we need to stop and restart the HTTP boot driver.
+ //
if (Private->Started) {
- return EFI_ALREADY_STARTED;
+ //
+ // Restart is needed in 2 cases:
+ // 1. Http boot driver has already been started but not on the required IP stack.
+ // 2. The specified boot file URI in FilePath is different with the one we have
+ // recorded before.
+ //
+ if ((UsingIpv6 != Private->UsingIpv6) ||
+ ((Uri != NULL) && (AsciiStrCmp (Private->BootFileUri, Uri) != 0))) {
+ //
+ // Restart is required, first stop then continue this start function.
+ //
+ Status = HttpBootStop (Private);
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+ } else {
+ //
+ // Restart is not required.
+ //
+ if (Uri != NULL) {
+ FreePool (Uri);
+ }
+ return EFI_ALREADY_STARTED;
+ }
}
//
@@ -55,17 +96,16 @@ HttpBootStart (
} else if (!UsingIpv6 && Private->Ip4Nic != NULL) {
Private->UsingIpv6 = FALSE;
} else {
+ if (Uri != NULL) {
+ FreePool (Uri);
+ }
return EFI_UNSUPPORTED;
}
//
- // Check whether the URI address is specified.
+ // Record the specified URI and prepare the URI parser if needed.
//
- Status = HttpBootParseFilePath (FilePath, &Private->FilePathUri);
- if (EFI_ERROR (Status)) {
- return EFI_INVALID_PARAMETER;
- }
-
+ Private->FilePathUri = Uri;
if (Private->FilePathUri != NULL) {
Status = HttpParseUrl (
Private->FilePathUri,
@@ -74,6 +114,7 @@ HttpBootStart (
&Private->FilePathUriParser
);
if (EFI_ERROR (Status)) {
+ FreePool (Private->FilePathUri);
return Status;
}
}
@@ -101,7 +142,7 @@ HttpBootStart (
return Status;
}
}
- Private->Started = TRUE;
+ Private->Started = TRUE;
return EFI_SUCCESS;
}
@@ -161,9 +202,11 @@ HttpBootDhcp (
@param[in] Buffer The memory buffer to transfer the file to. If Buffer is NULL,
then the size of the requested file is returned in
BufferSize.
+ @param[out] ImageType The image type of the downloaded file.
@retval EFI_SUCCESS Boot file was loaded successfully.
- @retval EFI_INVALID_PARAMETER Private is NULL.
+ @retval EFI_INVALID_PARAMETER Private is NULL, or ImageType is NULL, or BufferSize is NULL.
+ @retval EFI_INVALID_PARAMETER *BufferSize is not zero, and Buffer is NULL.
@retval EFI_NOT_STARTED The driver is in stopped state.
@retval EFI_BUFFER_TOO_SMALL The BufferSize is too small to read the boot file. BufferSize has
been updated with the size needed to complete the request.
@@ -175,12 +218,17 @@ EFI_STATUS
HttpBootLoadFile (
IN HTTP_BOOT_PRIVATE_DATA *Private,
IN OUT UINTN *BufferSize,
- IN VOID *Buffer OPTIONAL
+ IN VOID *Buffer, OPTIONAL
+ OUT HTTP_BOOT_IMAGE_TYPE *ImageType
)
{
EFI_STATUS Status;
- if (Private == NULL) {
+ if (Private == NULL || ImageType == NULL || BufferSize == NULL ) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ if (*BufferSize != 0 && Buffer == NULL) {
return EFI_INVALID_PARAMETER;
}
@@ -222,7 +270,8 @@ HttpBootLoadFile (
Private,
TRUE,
&Private->BootFileSize,
- NULL
+ NULL,
+ ImageType
);
if (EFI_ERROR (Status) && Status != EFI_BUFFER_TOO_SMALL) {
//
@@ -233,7 +282,8 @@ HttpBootLoadFile (
Private,
FALSE,
&Private->BootFileSize,
- NULL
+ NULL,
+ ImageType
);
if (EFI_ERROR (Status) && Status != EFI_BUFFER_TOO_SMALL) {
return Status;
@@ -253,7 +303,8 @@ HttpBootLoadFile (
Private,
FALSE,
BufferSize,
- Buffer
+ Buffer,
+ ImageType
);
}
@@ -388,6 +439,7 @@ HttpBootDxeLoadFile (
BOOLEAN MediaPresent;
BOOLEAN UsingIpv6;
EFI_STATUS Status;
+ HTTP_BOOT_IMAGE_TYPE ImageType;
if (This == NULL || BufferSize == NULL || FilePath == NULL) {
return EFI_INVALID_PARAMETER;
@@ -424,46 +476,34 @@ HttpBootDxeLoadFile (
// Initialize HTTP boot.
//
Status = HttpBootStart (Private, UsingIpv6, FilePath);
- if (Status == EFI_ALREADY_STARTED) {
- //
- // Restart the HTTP boot driver in 2 cases:
- // 1. Http boot Driver has already been started but not on the required IP version.
- // 2. The required boot FilePath is different with the one we produced in the device path
- // protocol.
- //
- if ((UsingIpv6 != Private->UsingIpv6) || ((Private->FilePathUri != NULL) && (AsciiStrCmp (Private->BootFileUri, Private->FilePathUri) != 0))) {
- Status = HttpBootStop (Private);
- if (!EFI_ERROR (Status)) {
- Status = HttpBootStart (Private, UsingIpv6, FilePath);
- }
- }
+ if (Status != EFI_SUCCESS && Status != EFI_ALREADY_STARTED) {
+ return Status;
}
-
+
//
// Load the boot file.
//
- if (Status == EFI_SUCCESS || Status == EFI_ALREADY_STARTED) {
- Status = HttpBootLoadFile (Private, BufferSize, Buffer);
+ ImageType = ImageTypeMax;
+ Status = HttpBootLoadFile (Private, BufferSize, Buffer, &ImageType);
+ if (EFI_ERROR (Status)) {
+ if (Status == EFI_BUFFER_TOO_SMALL && (ImageType == ImageTypeVirtualCd || ImageType == ImageTypeVirtualDisk)) {
+ Status = EFI_WARN_FILE_SYSTEM;
+ } else if (Status != EFI_BUFFER_TOO_SMALL) {
+ HttpBootStop (Private);
+ }
+ return Status;
}
- if (Status != EFI_SUCCESS && Status != EFI_BUFFER_TOO_SMALL) {
- HttpBootStop (Private);
- } else {
- if (!Private->UsingIpv6) {
- //
- // Stop and release the DHCP4 child.
- //
- Private->Dhcp4->Stop (Private->Dhcp4);
- Private->Dhcp4->Configure (Private->Dhcp4, NULL);
- } else {
- //
- // Stop and release the DHCP6 child.
- //
- Private->Dhcp6->Stop (Private->Dhcp6);
- Private->Dhcp6->Configure (Private->Dhcp6, NULL);
+ //
+ // Register the RAM Disk to the system if needed.
+ //
+ if (ImageType == ImageTypeVirtualCd || ImageType == ImageTypeVirtualDisk) {
+ Status = HttpBootRegisterRamDisk (Private, *BufferSize, Buffer, ImageType);
+ if (!EFI_ERROR (Status)) {
+ Status = EFI_WARN_FILE_SYSTEM;
}
}
-
+
return Status;
}
diff --git a/NetworkPkg/HttpBootDxe/HttpBootSupport.c b/NetworkPkg/HttpBootDxe/HttpBootSupport.c
index bd99a913c6..66eca783af 100644
--- a/NetworkPkg/HttpBootDxe/HttpBootSupport.c
+++ b/NetworkPkg/HttpBootDxe/HttpBootSupport.c
@@ -1007,3 +1007,145 @@ HttpBootParseFilePath (
return EFI_SUCCESS;
}
+
+/**
+ This function returns the image type according to server replied HTTP message
+ and also the image's URI info.
+
+ @param[in] Uri The pointer to the image's URI string.
+ @param[in] UriParser URI Parse result returned by NetHttpParseUrl().
+ @param[in] HeaderCount Number of HTTP header structures in Headers list.
+ @param[in] Headers Array containing list of HTTP headers.
+ @param[out] ImageType The image type of the downloaded file.
+
+ @retval EFI_SUCCESS The image type is returned in ImageType.
+ @retval EFI_INVALID_PARAMETER ImageType, Uri or UriParser is NULL.
+ @retval EFI_INVALID_PARAMETER HeaderCount is not zero, and Headers is NULL.
+ @retval EFI_NOT_FOUND Failed to identify the image type.
+ @retval Others Unexpect error happened.
+
+**/
+EFI_STATUS
+HttpBootCheckImageType (
+ IN CHAR8 *Uri,
+ IN VOID *UriParser,
+ IN UINTN HeaderCount,
+ IN EFI_HTTP_HEADER *Headers,
+ OUT HTTP_BOOT_IMAGE_TYPE *ImageType
+ )
+{
+ EFI_STATUS Status;
+ EFI_HTTP_HEADER *Header;
+ CHAR8 *FilePath;
+ CHAR8 *FilePost;
+
+ if (Uri == NULL || UriParser == NULL || ImageType == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ if (HeaderCount != 0 && Headers == NULL) {
+ return EFI_INVALID_PARAMETER;
+ }
+
+ //
+ // Determine the image type by the HTTP Content-Type header field first.
+ // "application/efi" -> EFI Image
+ //
+ Header = HttpFindHeader (HeaderCount, Headers, HTTP_HEADER_CONTENT_TYPE);
+ if (Header != NULL) {
+ if (AsciiStriCmp (Header->FieldValue, HTTP_CONTENT_TYPE_APP_EFI) == 0) {
+ *ImageType = ImageTypeEfi;
+ return EFI_SUCCESS;
+ }
+ }
+
+ //
+ // Determine the image type by file extension:
+ // *.efi -> EFI Image
+ // *.iso -> CD/DVD Image
+ // *.img -> Virtual Disk Image
+ //
+ Status = HttpUrlGetPath (
+ Uri,
+ UriParser,
+ &FilePath
+ );
+ if (EFI_ERROR (Status)) {
+ return Status;
+ }
+
+ FilePost = FilePath + AsciiStrLen (FilePath) - 4;
+ if (AsciiStrCmp (FilePost, ".efi") == 0) {
+ *ImageType = ImageTypeEfi;
+ } else if (AsciiStrCmp (FilePost, ".iso") == 0) {
+ *ImageType = ImageTypeVirtualCd;
+ } else if (AsciiStrCmp (FilePost, ".img") == 0) {
+ *ImageType = ImageTypeVirtualDisk;
+ } else {
+ *ImageType = ImageTypeMax;
+ }
+
+ FreePool (FilePath);
+
+ return (*ImageType < ImageTypeMax) ? EFI_SUCCESS : EFI_NOT_FOUND;
+}
+
+/**
+ This function register the RAM disk info to the system.
+
+ @param[in] Private The pointer to the driver's private data.
+ @param[in] BufferSize The size of Buffer in bytes.
+ @param[in] Buffer The base address of the RAM disk.
+ @param[in] ImageType The image type of the file in Buffer.
+
+ @retval EFI_SUCCESS The RAM disk has been registered.
+ @retval EFI_NOT_FOUND No RAM disk protocol instances were found.
+ @retval EFI_UNSUPPORTED The ImageType is not supported.
+ @retval Others Unexpected error happened.
+
+**/
+EFI_STATUS
+HttpBootRegisterRamDisk (
+ IN HTTP_BOOT_PRIVATE_DATA *Private,
+ IN UINTN BufferSize,
+ IN VOID *Buffer,
+ IN HTTP_BOOT_IMAGE_TYPE ImageType
+ )
+{
+ EFI_RAM_DISK_PROTOCOL *RamDisk;
+ EFI_STATUS Status;
+ EFI_DEVICE_PATH_PROTOCOL *DevicePath;
+ EFI_GUID *RamDiskType;
+
+ ASSERT (Private != NULL);
+ ASSERT (Buffer != NULL);
+ ASSERT (BufferSize != 0);
+
+ Status = gBS->LocateProtocol (&gEfiRamDiskProtocolGuid, NULL, (VOID**) &RamDisk);
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "HTTP Boot: Couldn't find the RAM Disk protocol - %r\n", Status));
+ return Status;
+ }
+
+ if (ImageType == ImageTypeVirtualCd) {
+ RamDiskType = &gEfiVirtualCdGuid;
+ } else if (ImageType == ImageTypeVirtualDisk) {
+ RamDiskType = &gEfiVirtualDiskGuid;
+ } else {
+ return EFI_UNSUPPORTED;
+ }
+
+ Status = RamDisk->Register (
+ (UINTN)Buffer,
+ (UINT64)BufferSize,
+ RamDiskType,
+ Private->UsingIpv6 ? Private->Ip6Nic->DevicePath : Private->Ip4Nic->DevicePath,
+ &DevicePath
+ );
+ if (EFI_ERROR (Status)) {
+ DEBUG ((EFI_D_ERROR, "HTTP Boot: Failed to register RAM Disk - %r\n", Status));
+ }
+
+ return Status;
+}
+
diff --git a/NetworkPkg/HttpBootDxe/HttpBootSupport.h b/NetworkPkg/HttpBootDxe/HttpBootSupport.h
index f382d6309c..28e8005d21 100644
--- a/NetworkPkg/HttpBootDxe/HttpBootSupport.h
+++ b/NetworkPkg/HttpBootDxe/HttpBootSupport.h
@@ -347,4 +347,51 @@ HttpBootParseFilePath (
OUT CHAR8 **UriAddress
);
+/**
+ This function returns the image type according to server replied HTTP message
+ and also the image's URI info.
+
+ @param[in] Uri The pointer to the image's URI string.
+ @param[in] UriParser URI Parse result returned by NetHttpParseUrl().
+ @param[in] HeaderCount Number of HTTP header structures in Headers list.
+ @param[in] Headers Array containing list of HTTP headers.
+ @param[out] ImageType The image type of the downloaded file.
+
+ @retval EFI_SUCCESS The image type is returned in ImageType.
+ @retval EFI_INVALID_PARAMETER ImageType, Uri or UriParser is NULL.
+ @retval EFI_INVALID_PARAMETER HeaderCount is not zero, and Headers is NULL.
+ @retval EFI_NOT_FOUND Failed to identify the image type.
+ @retval Others Unexpect error happened.
+
+**/
+EFI_STATUS
+HttpBootCheckImageType (
+ IN CHAR8 *Uri,
+ IN VOID *UriParser,
+ IN UINTN HeaderCount,
+ IN EFI_HTTP_HEADER *Headers,
+ OUT HTTP_BOOT_IMAGE_TYPE *ImageType
+ );
+
+/**
+ This function register the RAM disk info to the system.
+
+ @param[in] Private The pointer to the driver's private data.
+ @param[in] BufferSize The size of Buffer in bytes.
+ @param[in] Buffer The base address of the RAM disk.
+ @param[in] ImageType The image type of the file in Buffer.
+
+ @retval EFI_SUCCESS The RAM disk has been registered.
+ @retval EFI_NOT_FOUND No RAM disk protocol instances were found.
+ @retval EFI_UNSUPPORTED The ImageType is not supported.
+ @retval Others Unexpected error happened.
+
+**/
+EFI_STATUS
+HttpBootRegisterRamDisk (
+ IN HTTP_BOOT_PRIVATE_DATA *Private,
+ IN UINTN BufferSize,
+ IN VOID *Buffer,
+ IN HTTP_BOOT_IMAGE_TYPE ImageType
+ );
#endif