diff options
author | Michael Brown | 2016-05-29 14:04:26 +0200 |
---|---|---|
committer | Michael Brown | 2016-05-29 14:10:14 +0200 |
commit | aa4b038c70ca3e23c3126fda4318e9bbe77f3ea2 (patch) | |
tree | b36ef7fe452af987a423785c729cf25c9ca42ce7 /src/interface/efi | |
parent | [dhcp] Fix definitions for x86_64 and EFI BC client architectures (diff) | |
download | ipxe-aa4b038c70ca3e23c3126fda4318e9bbe77f3ea2.tar.gz ipxe-aa4b038c70ca3e23c3126fda4318e9bbe77f3ea2.tar.xz ipxe-aa4b038c70ca3e23c3126fda4318e9bbe77f3ea2.zip |
[efi] Expose DHCP packets via the Apple NetBoot protocol
Mac OS X uses non-standard EFI protocols to obtain the DHCP packets
from the UEFI firmware.
Originally-implemented-by: Michael Kuron <m.kuron@gmx.de>
Signed-off-by: Michael Brown <mcb30@ipxe.org>
Diffstat (limited to 'src/interface/efi')
-rw-r--r-- | src/interface/efi/efi_debug.c | 2 | ||||
-rw-r--r-- | src/interface/efi/efi_guid.c | 5 | ||||
-rw-r--r-- | src/interface/efi/efi_pxe.c | 94 |
3 files changed, 98 insertions, 3 deletions
diff --git a/src/interface/efi/efi_debug.c b/src/interface/efi/efi_debug.c index 84160d64..19531fdc 100644 --- a/src/interface/efi/efi_debug.c +++ b/src/interface/efi/efi_debug.c @@ -71,6 +71,8 @@ struct efi_well_known_guid { static struct efi_well_known_guid efi_well_known_guids[] = { { &efi_absolute_pointer_protocol_guid, "AbsolutePointer" }, + { &efi_apple_net_boot_protocol_guid, + "AppleNetBoot" }, { &efi_arp_protocol_guid, "Arp" }, { &efi_arp_service_binding_protocol_guid, diff --git a/src/interface/efi/efi_guid.c b/src/interface/efi/efi_guid.c index 39da5efe..62ee5a51 100644 --- a/src/interface/efi/efi_guid.c +++ b/src/interface/efi/efi_guid.c @@ -25,6 +25,7 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL ); #include <ipxe/efi/efi.h> #include <ipxe/efi/Protocol/AbsolutePointer.h> +#include <ipxe/efi/Protocol/AppleNetBoot.h> #include <ipxe/efi/Protocol/Arp.h> #include <ipxe/efi/Protocol/BlockIo.h> #include <ipxe/efi/Protocol/BusSpecificDriverOverride.h> @@ -84,6 +85,10 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL ); EFI_GUID efi_absolute_pointer_protocol_guid = EFI_ABSOLUTE_POINTER_PROTOCOL_GUID; +/** Apple NetBoot protocol GUID */ +EFI_GUID efi_apple_net_boot_protocol_guid + = EFI_APPLE_NET_BOOT_PROTOCOL_GUID; + /** ARP protocol GUID */ EFI_GUID efi_arp_protocol_guid = EFI_ARP_PROTOCOL_GUID; diff --git a/src/interface/efi/efi_pxe.c b/src/interface/efi/efi_pxe.c index 1847e3fd..a1f81df5 100644 --- a/src/interface/efi/efi_pxe.c +++ b/src/interface/efi/efi_pxe.c @@ -42,6 +42,7 @@ FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL ); #include <ipxe/efi/efi_snp.h> #include <ipxe/efi/efi_pxe.h> #include <ipxe/efi/Protocol/PxeBaseCode.h> +#include <ipxe/efi/Protocol/AppleNetBoot.h> #include <usr/ifmgmt.h> #include <config/general.h> @@ -80,6 +81,8 @@ struct efi_pxe { EFI_PXE_BASE_CODE_PROTOCOL base; /** PXE base code mode */ EFI_PXE_BASE_CODE_MODE mode; + /** Apple NetBoot protocol */ + EFI_APPLE_NET_BOOT_PROTOCOL apple; /** TCP/IP network-layer protocol */ struct tcpip_net_protocol *tcpip; @@ -1498,6 +1501,83 @@ static EFI_PXE_BASE_CODE_PROTOCOL efi_pxe_base_code_protocol = { .SetPackets = efi_pxe_set_packets, }; +/****************************************************************************** + * + * Apple NetBoot protocol + * + ****************************************************************************** + */ + +/** + * Get DHCP/BSDP response + * + * @v packet Packet + * @v len Length of data buffer + * @v data Data buffer + * @ret efirc EFI status code + */ +static EFI_STATUS EFIAPI +efi_apple_get_response ( EFI_PXE_BASE_CODE_PACKET *packet, UINTN *len, + VOID *data ) { + + /* Check length */ + if ( *len < sizeof ( *packet ) ) { + *len = sizeof ( *packet ); + return EFI_BUFFER_TOO_SMALL; + } + + /* Copy packet */ + memcpy ( data, packet, sizeof ( *packet ) ); + *len = sizeof ( *packet ); + + return EFI_SUCCESS; +} + +/** + * Get DHCP response + * + * @v apple Apple NetBoot protocol + * @v len Length of data buffer + * @v data Data buffer + * @ret efirc EFI status code + */ +static EFI_STATUS EFIAPI +efi_apple_get_dhcp_response ( EFI_APPLE_NET_BOOT_PROTOCOL *apple, + UINTN *len, VOID *data ) { + struct efi_pxe *pxe = container_of ( apple, struct efi_pxe, apple ); + + return efi_apple_get_response ( &pxe->mode.DhcpAck, len, data ); +} + +/** + * Get BSDP response + * + * @v apple Apple NetBoot protocol + * @v len Length of data buffer + * @v data Data buffer + * @ret efirc EFI status code + */ +static EFI_STATUS EFIAPI +efi_apple_get_bsdp_response ( EFI_APPLE_NET_BOOT_PROTOCOL *apple, + UINTN *len, VOID *data ) { + struct efi_pxe *pxe = container_of ( apple, struct efi_pxe, apple ); + + return efi_apple_get_response ( &pxe->mode.PxeReply, len, data ); +} + +/** Apple NetBoot protocol */ +static EFI_APPLE_NET_BOOT_PROTOCOL efi_apple_net_boot_protocol = { + .GetDhcpResponse = efi_apple_get_dhcp_response, + .GetBsdpResponse = efi_apple_get_bsdp_response, +}; + +/****************************************************************************** + * + * Installer + * + ****************************************************************************** + */ + /** * Install PXE base code protocol * @@ -1526,6 +1606,8 @@ int efi_pxe_install ( EFI_HANDLE handle, struct net_device *netdev ) { pxe->handle = handle; memcpy ( &pxe->base, &efi_pxe_base_code_protocol, sizeof ( pxe->base )); pxe->base.Mode = &pxe->mode; + memcpy ( &pxe->apple, &efi_apple_net_boot_protocol, + sizeof ( pxe->apple ) ); pxe->buf.op = &efi_pxe_buf_operations; intf_init ( &pxe->tftp, &efi_pxe_tftp_desc, &pxe->refcnt ); intf_init ( &pxe->udp, &efi_pxe_udp_desc, &pxe->refcnt ); @@ -1545,7 +1627,9 @@ int efi_pxe_install ( EFI_HANDLE handle, struct net_device *netdev ) { /* Install PXE base code protocol */ if ( ( efirc = bs->InstallMultipleProtocolInterfaces ( - &handle, &efi_pxe_base_code_protocol_guid, &pxe->base, + &handle, + &efi_pxe_base_code_protocol_guid, &pxe->base, + &efi_apple_net_boot_protocol_guid, &pxe->apple, NULL ) ) != 0 ) { rc = -EEFI ( efirc ); DBGC ( pxe, "PXE %s could not install base code protocol: %s\n", @@ -1560,7 +1644,9 @@ int efi_pxe_install ( EFI_HANDLE handle, struct net_device *netdev ) { return 0; bs->UninstallMultipleProtocolInterfaces ( - handle, &efi_pxe_base_code_protocol_guid, &pxe->base, + handle, + &efi_pxe_base_code_protocol_guid, &pxe->base, + &efi_apple_net_boot_protocol_guid, &pxe->apple, NULL ); err_install_protocol: ref_put ( &pxe->refcnt ); @@ -1590,7 +1676,9 @@ void efi_pxe_uninstall ( EFI_HANDLE handle ) { /* Uninstall PXE base code protocol */ bs->UninstallMultipleProtocolInterfaces ( - handle, &efi_pxe_base_code_protocol_guid, &pxe->base, + handle, + &efi_pxe_base_code_protocol_guid, &pxe->base, + &efi_apple_net_boot_protocol_guid, &pxe->apple, NULL ); /* Remove from list and drop list's reference */ |