/** @file
Functions declaration related with DHCPv4 for HTTP boot driver.
Copyright (c) 2015 - 2018, Intel Corporation. All rights reserved.
Copyright (c) 2020, Hewlett Packard Enterprise Development LP. All rights reserved.
SPDX-License-Identifier: BSD-2-Clause-Patent
**/
#ifndef __EFI_UEFI_HTTP_BOOT_DHCP4_H__
#define __EFI_UEFI_HTTP_BOOT_DHCP4_H__
#define HTTP_BOOT_DHCP4_OPTION_MAX_NUM 16
#define HTTP_BOOT_DHCP4_OPTION_MAX_SIZE 312
#define HTTP_BOOT_DHCP4_PACKET_MAX_SIZE 1472
#define HTTP_BOOT_DHCP4_OPCODE_REQUEST 1
#define HTTP_BOOT_DHCP4_OPCODE_REPLY 2
#define HTTP_BOOT_DHCP4_MSG_TYPE_REQUEST 3
#define HTTP_BOOT_DHCP4_MAGIC 0x63538263 // network byte order
#define HTTP_BOOT_DHCP4_OVERLOAD_FILE 1
#define HTTP_BOOT_DHCP4_OVERLOAD_SERVER_NAME 2
///
/// HTTP Tag definition that identifies the processor
/// and programming environment of the client system.
/// These identifiers are defined by IETF:
/// http://www.ietf.org/assignments/dhcpv6-parameters/dhcpv6-parameters.xml
///
#if defined (MDE_CPU_IA32)
#define EFI_HTTP_BOOT_CLIENT_SYSTEM_ARCHITECTURE HTTP_CLIENT_ARCH_IA32
#elif defined (MDE_CPU_X64)
#define EFI_HTTP_BOOT_CLIENT_SYSTEM_ARCHITECTURE HTTP_CLIENT_ARCH_X64
#elif defined (MDE_CPU_ARM)
#define EFI_HTTP_BOOT_CLIENT_SYSTEM_ARCHITECTURE HTTP_CLIENT_ARCH_ARM
#elif defined (MDE_CPU_AARCH64)
#define EFI_HTTP_BOOT_CLIENT_SYSTEM_ARCHITECTURE HTTP_CLIENT_ARCH_AARCH64
#elif defined (MDE_CPU_RISCV64)
#define EFI_HTTP_BOOT_CLIENT_SYSTEM_ARCHITECTURE HTTP_CLIENT_ARCH_RISCV64
#elif defined (MDE_CPU_EBC)
#define EFI_HTTP_BOOT_CLIENT_SYSTEM_ARCHITECTURE HTTP_CLIENT_ARCH_EBC
#endif
/// DHCP offer types among HTTP boot.
/// Dhcp4 and Dhcp6 share this definition, and corresponding
/// relationship is as follows:
/// Dhcp4Discover <> Dhcp6Solicit
/// Dhcp4Offer <> Dhcp6Advertise
/// Dhcp4Request <> Dhcp6Request
/// Dhcp4Ack <> DHcp6Reply
///
typedef enum {
//
//
//
HttpOfferTypeDhcpIpUri,
//
//
//
HttpOfferTypeDhcpIpUriDns,
//
//
//
HttpOfferTypeDhcpNameUriDns,
//
//
//
HttpOfferTypeDhcpDns,
//
//
//
HttpOfferTypeDhcpOnly,
//
// or
//
//
HttpOfferTypeProxyNameUri,
//
// or
//
//
HttpOfferTypeProxyIpUri,
//
//
//
HttpOfferTypeDhcpNameUri,
HttpOfferTypeMax
} HTTP_BOOT_OFFER_TYPE;
#define HTTP_BOOT_DHCP_RETRIES 4
#define HTTP_BOOT_OFFER_MAX_NUM 16
// The array index of the DHCP4 option tag interested
//
#define HTTP_BOOT_DHCP4_TAG_INDEX_BOOTFILE_LEN 0
#define HTTP_BOOT_DHCP4_TAG_INDEX_OVERLOAD 1
#define HTTP_BOOT_DHCP4_TAG_INDEX_MSG_TYPE 2
#define HTTP_BOOT_DHCP4_TAG_INDEX_SERVER_ID 3
#define HTTP_BOOT_DHCP4_TAG_INDEX_CLASS_ID 4
#define HTTP_BOOT_DHCP4_TAG_INDEX_BOOTFILE 5
#define HTTP_BOOT_DHCP4_TAG_INDEX_DNS_SERVER 6
#define HTTP_BOOT_DHCP4_TAG_INDEX_MAX 7
#pragma pack(1)
typedef struct {
UINT8 ParaList[135];
} HTTP_BOOT_DHCP4_OPTION_PARA;
typedef struct {
UINT16 Size;
} HTTP_BOOT_DHCP4_OPTION_MAX_MESG_SIZE;
typedef struct {
UINT8 Type;
UINT8 MajorVer;
UINT8 MinorVer;
} HTTP_BOOT_DHCP4_OPTION_UNDI;
typedef struct {
UINT8 Type;
} HTTP_BOOT_DHCP4_OPTION_MESG;
typedef struct {
UINT16 Type;
} HTTP_BOOT_DHCP4_OPTION_ARCH;
typedef struct {
UINT8 ClassIdentifier[11];
UINT8 ArchitecturePrefix[5];
UINT8 ArchitectureType[5];
UINT8 Lit3[1];
UINT8 InterfaceName[4];
UINT8 Lit4[1];
UINT8 UndiMajor[3];
UINT8 UndiMinor[3];
} HTTP_BOOT_DHCP4_OPTION_CLID;
typedef struct {
UINT8 Type;
UINT8 Guid[16];
} HTTP_BOOT_DHCP4_OPTION_UUID;
typedef struct {
UINT16 Type;
UINT16 Layer;
} HTTP_BOOT_OPTION_BOOT_ITEM;
#pragma pack()
typedef union {
HTTP_BOOT_DHCP4_OPTION_PARA *Para;
HTTP_BOOT_DHCP4_OPTION_UNDI *Undi;
HTTP_BOOT_DHCP4_OPTION_ARCH *Arch;
HTTP_BOOT_DHCP4_OPTION_CLID *Clid;
HTTP_BOOT_DHCP4_OPTION_UUID *Uuid;
HTTP_BOOT_DHCP4_OPTION_MESG *Mesg;
HTTP_BOOT_DHCP4_OPTION_MAX_MESG_SIZE *MaxMesgSize;
} HTTP_BOOT_DHCP4_OPTION_ENTRY;
#define GET_NEXT_DHCP_OPTION(Opt) \
(EFI_DHCP4_PACKET_OPTION *) ((UINT8 *) (Opt) + \
sizeof (EFI_DHCP4_PACKET_OPTION) + (Opt)->Length - 1)
#define GET_OPTION_BUFFER_LEN(Pkt) \
((Pkt)->Length - sizeof (EFI_DHCP4_HEADER) - 4)
#define DEFAULT_CLASS_ID_DATA "HTTPClient:Arch:xxxxx:UNDI:003000"
#define DEFAULT_UNDI_TYPE 1
#define DEFAULT_UNDI_MAJOR 3
#define DEFAULT_UNDI_MINOR 0
typedef struct {
UINT32 Reserved;
} HTTP_BOOT_VENDOR_OPTION;
#define HTTP_CACHED_DHCP4_PACKET_MAX_SIZE (OFFSET_OF (EFI_DHCP4_PACKET, Dhcp4) + HTTP_BOOT_DHCP4_PACKET_MAX_SIZE)
typedef union {
EFI_DHCP4_PACKET Offer;
EFI_DHCP4_PACKET Ack;
UINT8 Buffer[HTTP_CACHED_DHCP4_PACKET_MAX_SIZE];
} HTTP_BOOT_DHCP4_PACKET;
typedef struct {
//
// URI component
//
CHAR8 *Scheme;
CHAR8 *Authority;
CHAR8 *Path;
CHAR8 *Query;
CHAR8 *Fragment; /// TODO: may not required in HTTP URL
CHAR8 *RegName; /// Point to somewhere in Authority
BOOLEAN AddrIsOk;
EFI_IP_ADDRESS Address;
UINT16 Port;
} HTTP_BOOT_URI_CONTENT;
typedef struct {
HTTP_BOOT_DHCP4_PACKET Packet;
HTTP_BOOT_OFFER_TYPE OfferType;
VOID *UriParser;
EFI_DHCP4_PACKET_OPTION *OptList[HTTP_BOOT_DHCP4_TAG_INDEX_MAX];
} HTTP_BOOT_DHCP4_PACKET_CACHE;
/**
Select an DHCPv4 or DHCP6 offer, and record SelectIndex and SelectProxyType.
@param[in] Private Pointer to HTTP boot driver private data.
**/
VOID
HttpBootSelectDhcpOffer (
IN HTTP_BOOT_PRIVATE_DATA *Private
);
/**
Start the D.O.R.A DHCPv4 process to acquire the IPv4 address and other Http boot information.
@param[in] Private Pointer to HTTP_BOOT private data.
@retval EFI_SUCCESS The D.O.R.A process successfully finished.
@retval Others Failed to finish the D.O.R.A process.
**/
EFI_STATUS
HttpBootDhcp4Dora (
IN HTTP_BOOT_PRIVATE_DATA *Private
);
/**
This function will register the default DNS addresses to the network device.
@param[in] Private The pointer to HTTP_BOOT_PRIVATE_DATA.
@param[in] DataLength Size of the buffer pointed to by DnsServerData in bytes.
@param[in] DnsServerData Point a list of DNS server address in an array
of EFI_IPv4_ADDRESS instances.
@retval EFI_SUCCESS The DNS configuration has been configured successfully.
@retval Others Failed to configure the address.
**/
EFI_STATUS
HttpBootRegisterIp4Dns (
IN HTTP_BOOT_PRIVATE_DATA *Private,
IN UINTN DataLength,
IN VOID *DnsServerData
);
#endif