iPXE
efi_mp.c
Go to the documentation of this file.
1 /*
2  * Copyright (C) 2024 Michael Brown <mbrown@fensystems.co.uk>.
3  *
4  * This program is free software; you can redistribute it and/or
5  * modify it under the terms of the GNU General Public License as
6  * published by the Free Software Foundation; either version 2 of the
7  * License, or any later version.
8  *
9  * This program is distributed in the hope that it will be useful, but
10  * WITHOUT ANY WARRANTY; without even the implied warranty of
11  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12  * General Public License for more details.
13  *
14  * You should have received a copy of the GNU General Public License
15  * along with this program; if not, write to the Free Software
16  * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
17  * 02110-1301, USA.
18  *
19  * You can also choose to distribute this program under the terms of
20  * the Unmodified Binary Distribution Licence (as given in the file
21  * COPYING.UBDL), provided that you have satisfied its requirements.
22  */
23 
24 FILE_LICENCE ( GPL2_OR_LATER_OR_UBDL );
25 
26 /** @file
27  *
28  * EFI multiprocessor API implementation
29  *
30  */
31 
32 #include <string.h>
33 #include <errno.h>
34 #include <ipxe/mp.h>
35 #include <ipxe/efi/efi.h>
37 
38 /** EFI multiprocessor function call data */
40  /** Multiprocessor function */
42  /** Opaque data pointer */
44 };
45 
46 /** Multiprocessor services protocol */
49 
50 /**
51  * Call multiprocessor function on current CPU
52  *
53  * @v buffer Multiprocessor function call data
54  */
56  struct efi_mp_func_data *data = buffer;
57 
58  /* Call multiprocessor function */
59  mp_call ( data->func, data->opaque );
60 }
61 
62 /**
63  * Execute a multiprocessor function on the boot processor
64  *
65  * @v func Multiprocessor function
66  * @v opaque Opaque data pointer
67  */
68 static void efi_mp_exec_boot ( mp_func_t func, void *opaque ) {
69  struct efi_mp_func_data data;
70 
71  /* Construct call data */
72  data.func = mp_address ( func );
73  data.opaque = mp_address ( opaque );
74 
75  /* Call multiprocesor function */
76  efi_mp_call ( &data );
77 }
78 
79 /**
80  * Start a multiprocessor function on all application processors
81  *
82  * @v func Multiprocessor function
83  * @v opaque Opaque data pointer
84  */
85 static void efi_mp_start_all ( mp_func_t func, void *opaque ) {
86  struct efi_mp_func_data data;
87  EFI_STATUS efirc;
88  int rc;
89 
90  /* Do nothing if MP services is not present */
91  if ( ! efimp ) {
92  DBGC ( func, "EFIMP has no multiprocessor services\n" );
93  return;
94  }
95 
96  /* Construct call data */
97  data.func = mp_address ( func );
98  data.opaque = mp_address ( opaque );
99 
100  /* Start up all application processors */
101  if ( ( efirc = efimp->StartupAllAPs ( efimp, efi_mp_call, FALSE, NULL,
102  0, &data, NULL ) ) != 0 ) {
103  rc = -EEFI ( efirc );
104  DBGC ( func, "EFIMP could not start APs: %s\n",
105  strerror ( rc ) );
106  return;
107  }
108 }
109 
struct arbelprm_rc_send_wqe rc
Definition: arbel.h:14
#define EEFI(efirc)
Convert an EFI status code to an iPXE status code.
Definition: efi.h:171
When installed, the MP Services Protocol produces a collection of services that are needed for MP man...
mp_addr_t opaque
Opaque data pointer.
Definition: efi_mp.c:43
Error codes.
mp_addr_t func
Multiprocessor function.
Definition: efi_mp.c:41
EFI_REQUEST_PROTOCOL(EFI_MP_SERVICES_PROTOCOL, &efimp)
#define DBGC(...)
Definition: compiler.h:505
static mp_address(void *address)
Calculate address as seen by a multiprocessor function.
Definition: efi_mp.h:25
uint32_t buffer
Buffer index (or NETVSC_RNDIS_NO_BUFFER)
Definition: netvsc.h:16
static void efi_mp_start_all(mp_func_t func, void *opaque)
Start a multiprocessor function on all application processors.
Definition: efi_mp.c:85
static EFI_MP_SERVICES_PROTOCOL * efimp
Multiprocessor services protocol.
Definition: efi_mp.c:47
EFI_MP_SERVICES_STARTUP_ALL_APS StartupAllAPs
Definition: MpService.h:667
void mp_start_all(mp_func_t func, void *opaque)
Start a multiprocessor function on all application processors.
void __asmcall mp_call(mp_addr_t func, mp_addr_t opaque)
Call a multiprocessor function from C code on the current CPU.
PROVIDE_MPAPI(efi, mp_exec_boot, efi_mp_exec_boot)
PROVIDE_MPAPI_INLINE(efi, mp_address)
void() mp_func_t(mp_addr_t opaque, unsigned int cpuid)
A multiprocessor function.
Definition: mp.h:51
static void efi_mp_exec_boot(mp_func_t func, void *opaque)
Execute a multiprocessor function on the boot processor.
Definition: efi_mp.c:68
char * strerror(int errno)
Retrieve string representation of error number.
Definition: strerror.c:78
#define EFIAPI
unsigned long mp_addr_t
An address within the address space for a multiprocessor function.
Definition: mp.h:24
FILE_LICENCE(GPL2_OR_LATER_OR_UBDL)
When installed, the MP Services Protocol produces a collection of services that are needed for MP man...
Definition: MpService.h:664
#define VOID
Undeclared type.
Definition: Base.h:271
Multiprocessor functions.
EFI API.
static EFIAPI VOID efi_mp_call(VOID *buffer)
Call multiprocessor function on current CPU.
Definition: efi_mp.c:55
RETURN_STATUS EFI_STATUS
Function return status for EFI API.
Definition: UefiBaseType.h:31
uint8_t data[48]
Additional event data.
Definition: ena.h:22
#define FALSE
Definition: tlan.h:45
void mp_exec_boot(mp_func_t func, void *opaque)
Execute a multiprocessor function on the boot processor.
EFI multiprocessor function call data.
Definition: efi_mp.c:39
#define NULL
NULL pointer (VOID *)
Definition: Base.h:321
String functions.