2 Interpret and execute the S3 data in S3 boot script.
4 Copyright (c) 2006 - 2016, Intel Corporation. All rights reserved.<BR>
6 SPDX-License-Identifier: BSD-2-Clause-Patent
9 #include "InternalBootScriptLib.h"
12 Executes an SMBus operation to an SMBus controller. Returns when either the command has been
13 executed or an error is encountered in doing the operation.
15 The SmbusExecute() function provides a standard way to execute an operation as defined in the System
16 Management Bus (SMBus) Specification. The resulting transaction will be either that the SMBus
17 slave devices accept this transaction or that this function returns with error.
19 @param SmbusAddress Address that encodes the SMBUS Slave Address, SMBUS Command, SMBUS Data Length,
21 @param Operation Signifies which particular SMBus hardware protocol instance that
22 it will use to execute the SMBus transactions. This SMBus
23 hardware protocol is defined by the SMBus Specification and is
25 @param Length Signifies the number of bytes that this operation will do. The
26 maximum number of bytes can be revision specific and operation
27 specific. This field will contain the actual number of bytes that
28 are executed for this operation. Not all operations require this
30 @param Buffer Contains the value of data to execute to the SMBus slave device.
31 Not all operations require this argument. The length of this
32 buffer is identified by Length.
34 @retval EFI_SUCCESS The last data that was returned from the access matched the poll
36 @retval EFI_CRC_ERROR Checksum is not correct (PEC is incorrect).
37 @retval EFI_TIMEOUT Timeout expired before the operation was completed. Timeout is
38 determined by the SMBus host controller device.
39 @retval EFI_OUT_OF_RESOURCES The request could not be completed due to a lack of resources.
40 @retval EFI_DEVICE_ERROR The request was not completed because a failure that was
41 reflected in the Host Status Register bit. Device errors are a
42 result of a transaction collision, illegal command field,
43 unclaimed cycle (host initiated), or bus errors (collisions).
44 @retval EFI_INVALID_PARAMETER Operation is not defined in EFI_SMBUS_OPERATION.
45 @retval EFI_INVALID_PARAMETER Length/Buffer is NULL for operations except for EfiSmbusQuickRead
46 and EfiSmbusQuickWrite. Length is outside the range of valid
48 @retval EFI_UNSUPPORTED The SMBus operation or PEC is not supported.
49 @retval EFI_BUFFER_TOO_SMALL Buffer is not sufficient for this operation.
53 InternalSmbusExecute (
54 IN UINTN SmbusAddress
,
55 IN EFI_SMBUS_OPERATION Operation
,
61 UINT8 WorkBuffer
[MAX_SMBUS_BLOCK_LEN
];
64 case EfiSmbusQuickRead
:
65 DEBUG ((EFI_D_INFO
, "EfiSmbusQuickRead - 0x%08x\n", SmbusAddress
));
66 SmBusQuickRead (SmbusAddress
, &Status
);
68 case EfiSmbusQuickWrite
:
69 DEBUG ((EFI_D_INFO
, "EfiSmbusQuickWrite - 0x%08x\n", SmbusAddress
));
70 SmBusQuickWrite (SmbusAddress
, &Status
);
72 case EfiSmbusReceiveByte
:
73 DEBUG ((EFI_D_INFO
, "EfiSmbusReceiveByte - 0x%08x\n", SmbusAddress
));
74 SmBusReceiveByte (SmbusAddress
, &Status
);
76 case EfiSmbusSendByte
:
77 DEBUG ((EFI_D_INFO
, "EfiSmbusSendByte - 0x%08x (0x%02x)\n", SmbusAddress
, (UINTN
)*(UINT8
*) Buffer
));
78 SmBusSendByte (SmbusAddress
, *(UINT8
*) Buffer
, &Status
);
80 case EfiSmbusReadByte
:
81 DEBUG ((EFI_D_INFO
, "EfiSmbusReadByte - 0x%08x\n", SmbusAddress
));
82 SmBusReadDataByte (SmbusAddress
, &Status
);
84 case EfiSmbusWriteByte
:
85 DEBUG ((EFI_D_INFO
, "EfiSmbusWriteByte - 0x%08x (0x%02x)\n", SmbusAddress
, (UINTN
)*(UINT8
*) Buffer
));
86 SmBusWriteDataByte (SmbusAddress
, *(UINT8
*) Buffer
, &Status
);
88 case EfiSmbusReadWord
:
89 DEBUG ((EFI_D_INFO
, "EfiSmbusReadWord - 0x%08x\n", SmbusAddress
));
90 SmBusReadDataWord (SmbusAddress
, &Status
);
92 case EfiSmbusWriteWord
:
93 DEBUG ((EFI_D_INFO
, "EfiSmbusWriteWord - 0x%08x (0x%04x)\n", SmbusAddress
, (UINTN
)*(UINT16
*) Buffer
));
94 SmBusWriteDataWord (SmbusAddress
, *(UINT16
*) Buffer
, &Status
);
96 case EfiSmbusProcessCall
:
97 DEBUG ((EFI_D_INFO
, "EfiSmbusProcessCall - 0x%08x (0x%04x)\n", SmbusAddress
, (UINTN
)*(UINT16
*) Buffer
));
98 SmBusProcessCall (SmbusAddress
, *(UINT16
*) Buffer
, &Status
);
100 case EfiSmbusReadBlock
:
101 DEBUG ((EFI_D_INFO
, "EfiSmbusReadBlock - 0x%08x\n", SmbusAddress
));
102 SmBusReadBlock (SmbusAddress
, WorkBuffer
, &Status
);
104 case EfiSmbusWriteBlock
:
105 DEBUG ((EFI_D_INFO
, "EfiSmbusWriteBlock - 0x%08x\n", SmbusAddress
));
106 SmBusWriteBlock ((SmbusAddress
+ SMBUS_LIB_ADDRESS (0, 0, (*Length
), FALSE
)), Buffer
, &Status
);
108 case EfiSmbusBWBRProcessCall
:
109 DEBUG ((EFI_D_INFO
, "EfiSmbusBWBRProcessCall - 0x%08x\n", SmbusAddress
));
110 SmBusBlockProcessCall ((SmbusAddress
+ SMBUS_LIB_ADDRESS (0, 0, (*Length
), FALSE
)), Buffer
, WorkBuffer
, &Status
);
113 return EFI_INVALID_PARAMETER
;
120 Translates boot script width and address stride to MDE library interface.
123 @param Width Width of the operation.
124 @param Address Address of the operation.
125 @param AddressStride Instride for stepping input buffer.
126 @param BufferStride Outstride for stepping output buffer.
128 @retval EFI_SUCCESS Successful translation.
129 @retval EFI_INVALID_PARAMETER Width or Address is invalid.
133 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
135 OUT UINTN
*AddressStride
,
136 OUT UINTN
*BufferStride
141 if (Width
>= S3BootScriptWidthMaximum
) {
142 return EFI_INVALID_PARAMETER
;
145 *AddressStride
= (UINT32
)(1 << (Width
& 0x03));
146 *BufferStride
= *AddressStride
;
148 AlignMask
= *AddressStride
- 1;
149 if ((Address
& AlignMask
) != 0) {
150 return EFI_INVALID_PARAMETER
;
153 if (Width
>= S3BootScriptWidthFifoUint8
&& Width
<= S3BootScriptWidthFifoUint64
) {
157 if (Width
>= S3BootScriptWidthFillUint8
&& Width
<= S3BootScriptWidthFillUint64
) {
165 Perform IO read operation
167 @param[in] Width Width of the operation.
168 @param[in] Address Address of the operation.
169 @param[in] Count Count of the number of accesses to perform.
170 @param[out] Buffer Pointer to the buffer to read from I/O space.
172 @retval EFI_SUCCESS The data was written to the EFI System.
173 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
175 The Buffer is not aligned for the given Width.
176 Address is outside the legal range of I/O ports.
181 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
192 Out
.Buf
= (UINT8
*) Buffer
;
194 if (Address
> MAX_IO_ADDRESS
) {
195 return EFI_INVALID_PARAMETER
;
198 Status
= BuildLoopData (Width
, Address
, &AddressStride
, &BufferStride
);
199 if (EFI_ERROR (Status
)) {
203 // Loop for each iteration and move the data
205 for (; Count
> 0; Count
--, Address
+= AddressStride
, Out
.Buf
+= BufferStride
) {
208 case S3BootScriptWidthUint8
:
209 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint8 - 0x%08x\n", (UINTN
) Address
));
210 *Out
.Uint8
= IoRead8 ((UINTN
) Address
);
212 case S3BootScriptWidthFifoUint8
:
213 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint8 - 0x%08x\n", (UINTN
) Address
));
214 *Out
.Uint8
= IoRead8 ((UINTN
) Address
);
216 case S3BootScriptWidthFillUint8
:
217 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint8 - 0x%08x\n", (UINTN
) Address
));
218 *Out
.Uint8
= IoRead8 ((UINTN
) Address
);
221 case S3BootScriptWidthUint16
:
222 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint16 - 0x%08x\n", (UINTN
) Address
));
223 *Out
.Uint16
= IoRead16 ((UINTN
) Address
);
225 case S3BootScriptWidthFifoUint16
:
226 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint16 - 0x%08x\n", (UINTN
) Address
));
227 *Out
.Uint16
= IoRead16 ((UINTN
) Address
);
229 case S3BootScriptWidthFillUint16
:
230 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint16 - 0x%08x\n", (UINTN
) Address
));
231 *Out
.Uint16
= IoRead16 ((UINTN
) Address
);
234 case S3BootScriptWidthUint32
:
235 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint32 - 0x%08x\n", (UINTN
) Address
));
236 *Out
.Uint32
= IoRead32 ((UINTN
) Address
);
238 case S3BootScriptWidthFifoUint32
:
239 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint32 - 0x%08x\n", (UINTN
) Address
));
240 *Out
.Uint32
= IoRead32 ((UINTN
) Address
);
242 case S3BootScriptWidthFillUint32
:
243 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint32 - 0x%08x\n", (UINTN
) Address
));
244 *Out
.Uint32
= IoRead32 ((UINTN
) Address
);
247 case S3BootScriptWidthUint64
:
248 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint64 - 0x%08x\n", (UINTN
) Address
));
249 *Out
.Uint64
= IoRead64 ((UINTN
) Address
);
251 case S3BootScriptWidthFifoUint64
:
252 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint64 - 0x%08x\n", (UINTN
) Address
));
253 *Out
.Uint64
= IoRead64 ((UINTN
) Address
);
255 case S3BootScriptWidthFillUint64
:
256 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint64 - 0x%08x\n", (UINTN
) Address
));
257 *Out
.Uint64
= IoRead64 ((UINTN
) Address
);
261 return EFI_INVALID_PARAMETER
;
269 Perform IO write operation
271 @param[in] Width Width of the operation.
272 @param[in] Address Address of the operation.
273 @param[in] Count Count of the number of accesses to perform.
274 @param[in] Buffer Pointer to the buffer to write to I/O space.
276 @retval EFI_SUCCESS The data was written to the EFI System.
277 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
279 The Buffer is not aligned for the given Width.
280 Address is outside the legal range of I/O ports.
285 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
294 UINT64 OriginalAddress
;
298 In
.Buf
= (UINT8
*) Buffer
;
300 if (Address
> MAX_IO_ADDRESS
) {
301 return EFI_INVALID_PARAMETER
;
304 Status
= BuildLoopData (Width
, Address
, &AddressStride
, &BufferStride
);
305 if (EFI_ERROR (Status
)) {
309 // Loop for each iteration and move the data
311 OriginalAddress
= Address
;
312 OriginalIn
.Buf
= In
.Buf
;
313 for (; Count
> 0; Count
--, Address
+= AddressStride
, In
.Buf
+= BufferStride
) {
315 case S3BootScriptWidthUint8
:
316 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint8 - 0x%08x (0x%02x)\n", (UINTN
)Address
, (UINTN
)*In
.Uint8
));
317 IoWrite8 ((UINTN
) Address
, *In
.Uint8
);
319 case S3BootScriptWidthFifoUint8
:
320 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint8 - 0x%08x (0x%02x)\n", (UINTN
)OriginalAddress
, (UINTN
)*In
.Uint8
));
321 IoWrite8 ((UINTN
) OriginalAddress
, *In
.Uint8
);
323 case S3BootScriptWidthFillUint8
:
324 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint8 - 0x%08x (0x%02x)\n", (UINTN
)Address
, (UINTN
)*OriginalIn
.Uint8
));
325 IoWrite8 ((UINTN
) Address
, *OriginalIn
.Uint8
);
327 case S3BootScriptWidthUint16
:
328 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint16 - 0x%08x (0x%04x)\n", (UINTN
)Address
, (UINTN
)*In
.Uint16
));
329 IoWrite16 ((UINTN
) Address
, *In
.Uint16
);
331 case S3BootScriptWidthFifoUint16
:
332 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint16 - 0x%08x (0x%04x)\n", (UINTN
)OriginalAddress
, (UINTN
)*In
.Uint16
));
333 IoWrite16 ((UINTN
) OriginalAddress
, *In
.Uint16
);
335 case S3BootScriptWidthFillUint16
:
336 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint16 - 0x%08x (0x%04x)\n", (UINTN
)Address
, (UINTN
)*OriginalIn
.Uint16
));
337 IoWrite16 ((UINTN
) Address
, *OriginalIn
.Uint16
);
339 case S3BootScriptWidthUint32
:
340 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint32 - 0x%08x (0x%08x)\n", (UINTN
)Address
, (UINTN
)*In
.Uint32
));
341 IoWrite32 ((UINTN
) Address
, *In
.Uint32
);
343 case S3BootScriptWidthFifoUint32
:
344 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint32 - 0x%08x (0x%08x)\n", (UINTN
)OriginalAddress
, (UINTN
)*In
.Uint32
));
345 IoWrite32 ((UINTN
) OriginalAddress
, *In
.Uint32
);
347 case S3BootScriptWidthFillUint32
:
348 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint32 - 0x%08x (0x%08x)\n", (UINTN
)Address
, (UINTN
)*OriginalIn
.Uint32
));
349 IoWrite32 ((UINTN
) Address
, *OriginalIn
.Uint32
);
351 case S3BootScriptWidthUint64
:
352 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint64 - 0x%08x (0x%016lx)\n", (UINTN
)Address
, *In
.Uint64
));
353 IoWrite64 ((UINTN
) Address
, *In
.Uint64
);
355 case S3BootScriptWidthFifoUint64
:
356 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint64 - 0x%08x (0x%016lx)\n", (UINTN
)OriginalAddress
, *In
.Uint64
));
357 IoWrite64 ((UINTN
) OriginalAddress
, *In
.Uint64
);
359 case S3BootScriptWidthFillUint64
:
360 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint64 - 0x%08x (0x%016lx)\n", (UINTN
)Address
, *OriginalIn
.Uint64
));
361 IoWrite64 ((UINTN
) Address
, *OriginalIn
.Uint64
);
364 return EFI_INVALID_PARAMETER
;
372 Interprete the boot script node with EFI_BOOT_SCRIPT_IO_WRITE OP code.
374 @param Script Pointer to the node which is to be interpreted.
376 @retval EFI_SUCCESS The data was written to the EFI System.
377 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
379 The Buffer is not aligned for the given Width.
380 Address is outside the legal range of I/O ports.
384 BootScriptExecuteIoWrite (
388 S3_BOOT_SCRIPT_LIB_WIDTH Width
;
392 EFI_BOOT_SCRIPT_IO_WRITE IoWrite
;
394 CopyMem ((VOID
*)&IoWrite
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_IO_WRITE
));
395 Width
= (S3_BOOT_SCRIPT_LIB_WIDTH
) IoWrite
.Width
;
396 Address
= IoWrite
.Address
;
397 Count
= IoWrite
.Count
;
398 Buffer
= Script
+ sizeof (EFI_BOOT_SCRIPT_IO_WRITE
);
400 DEBUG ((EFI_D_INFO
, "BootScriptExecuteIoWrite - 0x%08x, 0x%08x, 0x%08x\n", (UINTN
)Address
, Count
, (UINTN
)Width
));
401 return ScriptIoWrite(Width
, Address
, Count
, Buffer
);
404 Perform memory read operation
406 @param Width Width of the operation.
407 @param Address Address of the operation.
408 @param Count Count of the number of accesses to perform.
409 @param Buffer Pointer to the buffer read from memory.
411 @retval EFI_SUCCESS The data was written to the EFI System.
412 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
414 The Buffer is not aligned for the given Width.
415 @retval EFI_UNSUPPORTED The address range specified by Address, Width, and Count
416 is not valid for this EFI System.
421 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
434 Status
= BuildLoopData (Width
, Address
, &AddressStride
, &BufferStride
);
435 if (EFI_ERROR (Status
)) {
439 // Loop for each iteration and move the data
441 for (; Count
> 0; Count
--, Address
+= AddressStride
, Out
.Buf
+= BufferStride
) {
443 case S3BootScriptWidthUint8
:
444 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint8 - 0x%08x\n", (UINTN
)Address
));
445 *Out
.Uint8
= MmioRead8 ((UINTN
) Address
);
447 case S3BootScriptWidthFifoUint8
:
448 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint8 - 0x%08x\n", (UINTN
)Address
));
449 *Out
.Uint8
= MmioRead8 ((UINTN
) Address
);
451 case S3BootScriptWidthFillUint8
:
452 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint8 - 0x%08x\n", (UINTN
)Address
));
453 *Out
.Uint8
= MmioRead8 ((UINTN
) Address
);
456 case S3BootScriptWidthUint16
:
457 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint16 - 0x%08x\n", (UINTN
)Address
));
458 *Out
.Uint16
= MmioRead16 ((UINTN
) Address
);
460 case S3BootScriptWidthFifoUint16
:
461 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint16 - 0x%08x\n", (UINTN
)Address
));
462 *Out
.Uint16
= MmioRead16 ((UINTN
) Address
);
464 case S3BootScriptWidthFillUint16
:
465 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint16 - 0x%08x\n", (UINTN
)Address
));
466 *Out
.Uint16
= MmioRead16 ((UINTN
) Address
);
469 case S3BootScriptWidthUint32
:
470 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint32 - 0x%08x\n", (UINTN
)Address
));
471 *Out
.Uint32
= MmioRead32 ((UINTN
) Address
);
473 case S3BootScriptWidthFifoUint32
:
474 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint32 - 0x%08x\n", (UINTN
)Address
));
475 *Out
.Uint32
= MmioRead32 ((UINTN
) Address
);
477 case S3BootScriptWidthFillUint32
:
478 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint32 - 0x%08x\n", (UINTN
)Address
));
479 *Out
.Uint32
= MmioRead32 ((UINTN
) Address
);
482 case S3BootScriptWidthUint64
:
483 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint64 - 0x%08x\n", (UINTN
)Address
));
484 *Out
.Uint64
= MmioRead64 ((UINTN
) Address
);
486 case S3BootScriptWidthFifoUint64
:
487 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint64 - 0x%08x\n", (UINTN
)Address
));
488 *Out
.Uint64
= MmioRead64 ((UINTN
) Address
);
490 case S3BootScriptWidthFillUint64
:
491 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint64 - 0x%08x\n", (UINTN
)Address
));
492 *Out
.Uint64
= MmioRead64 ((UINTN
) Address
);
496 return EFI_UNSUPPORTED
;
503 Perform memory write operation
505 @param Width Width of the operation.
506 @param Address Address of the operation.
507 @param Count Count of the number of accesses to perform.
508 @param Buffer Pointer to the buffer write to memory.
510 @retval EFI_SUCCESS The data was written to the EFI System.
511 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
513 The Buffer is not aligned for the given Width.
514 @retval EFI_UNSUPPORTED The address range specified by Address, Width, and Count
515 is not valid for this EFI System.
520 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
528 UINT64 OriginalAddress
;
535 Status
= BuildLoopData (Width
, Address
, &AddressStride
, &BufferStride
);
536 if (EFI_ERROR (Status
)) {
540 // Loop for each iteration and move the data
542 OriginalAddress
= Address
;
543 OriginalIn
.Buf
= In
.Buf
;
544 for (; Count
> 0; Count
--, Address
+= AddressStride
, In
.Buf
+= BufferStride
) {
546 case S3BootScriptWidthUint8
:
547 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint8 - 0x%08x (0x%02x)\n", (UINTN
)Address
, (UINTN
)*In
.Uint8
));
548 MmioWrite8 ((UINTN
) Address
, *In
.Uint8
);
550 case S3BootScriptWidthFifoUint8
:
551 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint8 - 0x%08x (0x%02x)\n", (UINTN
)OriginalAddress
, (UINTN
)*In
.Uint8
));
552 MmioWrite8 ((UINTN
) OriginalAddress
, *In
.Uint8
);
554 case S3BootScriptWidthFillUint8
:
555 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint8 - 0x%08x (0x%02x)\n", (UINTN
)Address
, (UINTN
)*OriginalIn
.Uint8
));
556 MmioWrite8 ((UINTN
) Address
, *OriginalIn
.Uint8
);
558 case S3BootScriptWidthUint16
:
559 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint16 - 0x%08x (0x%04x)\n", (UINTN
)Address
, (UINTN
)*In
.Uint16
));
560 MmioWrite16 ((UINTN
) Address
, *In
.Uint16
);
562 case S3BootScriptWidthFifoUint16
:
563 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint16 - 0x%08x (0x%04x)\n", (UINTN
)OriginalAddress
, (UINTN
)*In
.Uint16
));
564 MmioWrite16 ((UINTN
) OriginalAddress
, *In
.Uint16
);
566 case S3BootScriptWidthFillUint16
:
567 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint16 - 0x%08x (0x%04x)\n", (UINTN
)Address
, (UINTN
)*OriginalIn
.Uint16
));
568 MmioWrite16 ((UINTN
) Address
, *OriginalIn
.Uint16
);
570 case S3BootScriptWidthUint32
:
571 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint32 - 0x%08x (0x%08x)\n", (UINTN
)Address
, (UINTN
)*In
.Uint32
));
572 MmioWrite32 ((UINTN
) Address
, *In
.Uint32
);
574 case S3BootScriptWidthFifoUint32
:
575 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint32 - 0x%08x (0x%08x)\n", (UINTN
)OriginalAddress
, (UINTN
)*In
.Uint32
));
576 MmioWrite32 ((UINTN
) OriginalAddress
, *In
.Uint32
);
578 case S3BootScriptWidthFillUint32
:
579 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint32 - 0x%08x (0x%08x)\n", (UINTN
)Address
, (UINTN
)*OriginalIn
.Uint32
));
580 MmioWrite32 ((UINTN
) Address
, *OriginalIn
.Uint32
);
582 case S3BootScriptWidthUint64
:
583 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint64 - 0x%08x (0x%016lx)\n", (UINTN
)Address
, *In
.Uint64
));
584 MmioWrite64 ((UINTN
) Address
, *In
.Uint64
);
586 case S3BootScriptWidthFifoUint64
:
587 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint64 - 0x%08x (0x%016lx)\n", (UINTN
)OriginalAddress
, *In
.Uint64
));
588 MmioWrite64 ((UINTN
) OriginalAddress
, *In
.Uint64
);
590 case S3BootScriptWidthFillUint64
:
591 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint64 - 0x%08x (0x%016lx)\n", (UINTN
)Address
, *OriginalIn
.Uint64
));
592 MmioWrite64 ((UINTN
) Address
, *OriginalIn
.Uint64
);
595 return EFI_UNSUPPORTED
;
601 Interprete the boot script node with EFI_BOOT_SCRIPT_MEM_WRITE OP code.
603 @param[in] Script Pointer to the node which is to be interpreted.
605 @retval EFI_SUCCESS The data was written to the EFI System.
606 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
608 The Buffer is not aligned for the given Width.
609 @retval EFI_UNSUPPORTED The address range specified by Address, Width, and Count
610 is not valid for this EFI System.
614 BootScriptExecuteMemoryWrite (
619 S3_BOOT_SCRIPT_LIB_WIDTH Width
;
622 EFI_BOOT_SCRIPT_MEM_WRITE MemWrite
;
624 CopyMem((VOID
*)&MemWrite
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_MEM_WRITE
));
625 Width
= (S3_BOOT_SCRIPT_LIB_WIDTH
)MemWrite
.Width
;
626 Address
= MemWrite
.Address
;
627 Count
= MemWrite
.Count
;
628 Buffer
= Script
+ sizeof(EFI_BOOT_SCRIPT_MEM_WRITE
);
630 DEBUG ((EFI_D_INFO
, "BootScriptExecuteMemoryWrite - 0x%08x, 0x%08x, 0x%08x\n", (UINTN
)Address
, Count
, (UINTN
)Width
));
631 return ScriptMemoryWrite (Width
,Address
, Count
, Buffer
);
635 Performance PCI configuration 2 read operation
637 @param Width Width of the operation.
638 @param Segment Pci segment number
639 @param Address Address of the operation.
640 @param Count Count of the number of accesses to perform.
641 @param Buffer Pointer to the buffer read from PCI config space
643 @retval EFI_SUCCESS The read succeed.
644 @retval EFI_INVALID_PARAMETER if Width is not defined
645 @note A known Limitations in the implementation which is 64bits operations are not supported.
650 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
663 Out
.Buf
= (UINT8
*) Buffer
;
665 PciAddress
= PCI_ADDRESS_ENCODE (Segment
, Address
);
667 Status
= BuildLoopData (Width
, PciAddress
, &AddressStride
, &BufferStride
);
668 if (EFI_ERROR (Status
)) {
672 // Loop for each iteration and move the data
674 for (; Count
> 0; Count
--, PciAddress
+= AddressStride
, Out
.Buf
+= BufferStride
) {
676 case S3BootScriptWidthUint8
:
677 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint8 - 0x%016lx\n", PciAddress
));
678 *Out
.Uint8
= PciSegmentRead8 (PciAddress
);
680 case S3BootScriptWidthFifoUint8
:
681 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint8 - 0x%016lx\n", PciAddress
));
682 *Out
.Uint8
= PciSegmentRead8 (PciAddress
);
684 case S3BootScriptWidthFillUint8
:
685 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint8 - 0x%016lx\n", PciAddress
));
686 *Out
.Uint8
= PciSegmentRead8 (PciAddress
);
689 case S3BootScriptWidthUint16
:
690 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint16 - 0x%016lx\n", PciAddress
));
691 *Out
.Uint16
= PciSegmentRead16 (PciAddress
);
693 case S3BootScriptWidthFifoUint16
:
694 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint16 - 0x%016lx\n", PciAddress
));
695 *Out
.Uint16
= PciSegmentRead16 (PciAddress
);
697 case S3BootScriptWidthFillUint16
:
698 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint16 - 0x%016lx\n", PciAddress
));
699 *Out
.Uint16
= PciSegmentRead16 (PciAddress
);
702 case S3BootScriptWidthUint32
:
703 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint32 - 0x%016lx\n", PciAddress
));
704 *Out
.Uint32
= PciSegmentRead32 (PciAddress
);
706 case S3BootScriptWidthFifoUint32
:
707 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint32 - 0x%016lx\n", PciAddress
));
708 *Out
.Uint32
= PciSegmentRead32 (PciAddress
);
710 case S3BootScriptWidthFillUint32
:
711 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint32 - 0x%016lx\n", PciAddress
));
712 *Out
.Uint32
= PciSegmentRead32 (PciAddress
);
716 return EFI_INVALID_PARAMETER
;
723 Performance PCI configuration 2 write operation
725 @param Width Width of the operation.
726 @param Segment Pci segment number
727 @param Address Address of the operation.
728 @param Count Count of the number of accesses to perform.
729 @param Buffer Pointer to the buffer write to PCI config space
731 @retval EFI_SUCCESS The write succeed.
732 @retval EFI_INVALID_PARAMETER if Width is not defined
733 @note A known Limitations in the implementation which is 64bits operations are not supported.
738 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
748 UINT64 OriginalPciAddress
;
753 In
.Buf
= (UINT8
*) Buffer
;
755 PciAddress
= PCI_ADDRESS_ENCODE (Segment
, Address
);
757 Status
= BuildLoopData (Width
, PciAddress
, &AddressStride
, &BufferStride
);
758 if (EFI_ERROR (Status
)) {
762 // Loop for each iteration and move the data
764 OriginalPciAddress
= PciAddress
;
765 OriginalIn
.Buf
= In
.Buf
;
766 for (; Count
> 0; Count
--, PciAddress
+= AddressStride
, In
.Buf
+= BufferStride
) {
768 case S3BootScriptWidthUint8
:
769 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint8 - 0x%016lx (0x%02x)\n", PciAddress
, (UINTN
)*In
.Uint8
));
770 PciSegmentWrite8 (PciAddress
, *In
.Uint8
);
772 case S3BootScriptWidthFifoUint8
:
773 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint8 - 0x%016lx (0x%02x)\n", OriginalPciAddress
, (UINTN
)*In
.Uint8
));
774 PciSegmentWrite8 (OriginalPciAddress
, *In
.Uint8
);
776 case S3BootScriptWidthFillUint8
:
777 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint8 - 0x%016lx (0x%02x)\n", PciAddress
, (UINTN
)*OriginalIn
.Uint8
));
778 PciSegmentWrite8 (PciAddress
, *OriginalIn
.Uint8
);
780 case S3BootScriptWidthUint16
:
781 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint16 - 0x%016lx (0x%04x)\n", PciAddress
, (UINTN
)*In
.Uint16
));
782 PciSegmentWrite16 (PciAddress
, *In
.Uint16
);
784 case S3BootScriptWidthFifoUint16
:
785 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint16 - 0x%016lx (0x%04x)\n", OriginalPciAddress
, (UINTN
)*In
.Uint16
));
786 PciSegmentWrite16 (OriginalPciAddress
, *In
.Uint16
);
788 case S3BootScriptWidthFillUint16
:
789 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint16 - 0x%016lx (0x%04x)\n", PciAddress
, (UINTN
)*OriginalIn
.Uint16
));
790 PciSegmentWrite16 (PciAddress
, *OriginalIn
.Uint16
);
792 case S3BootScriptWidthUint32
:
793 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthUint32 - 0x%016lx (0x%08x)\n", PciAddress
, (UINTN
)*In
.Uint32
));
794 PciSegmentWrite32 (PciAddress
, *In
.Uint32
);
796 case S3BootScriptWidthFifoUint32
:
797 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFifoUint32 - 0x%016lx (0x%08x)\n", OriginalPciAddress
, (UINTN
)*In
.Uint32
));
798 PciSegmentWrite32 (OriginalPciAddress
, *In
.Uint32
);
800 case S3BootScriptWidthFillUint32
:
801 DEBUG ((EFI_D_INFO
, "S3BootScriptWidthFillUint32 - 0x%016lx (0x%08x)\n", (UINTN
)PciAddress
, (UINTN
)*OriginalIn
.Uint32
));
802 PciSegmentWrite32 (PciAddress
, *OriginalIn
.Uint32
);
805 return EFI_INVALID_PARAMETER
;
811 Performance PCI configuration read operation
813 @param Width Width of the operation.
814 @param Address Address of the operation.
815 @param Count Count of the number of accesses to perform.
816 @param Buffer Pointer to the buffer to read from PCI config space.
818 @retval EFI_SUCCESS The data was written to the EFI System.
819 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
821 The Buffer is not aligned for the given Width.
822 Address is outside the legal range of I/O ports.
827 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
833 return ScriptPciCfg2Read (Width
, 0, Address
, Count
, Buffer
);
836 Performance PCI configuration write operation
838 @param Width Width of the operation.
839 @param Address Address of the operation.
840 @param Count Count of the number of accesses to perform.
841 @param Buffer Pointer to the buffer to write to PCI config space.
843 @retval EFI_SUCCESS The data was written to the EFI System.
844 @retval EFI_INVALID_PARAMETER Width is invalid for this EFI System.
846 The Buffer is not aligned for the given Width.
847 Address is outside the legal range of I/O ports.
853 IN S3_BOOT_SCRIPT_LIB_WIDTH Width
,
859 return ScriptPciCfg2Write (Width
, 0, Address
, Count
, Buffer
);
862 Interprete the boot script node with EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE OP code.
864 @param Script The pointer of typed node in boot script table
866 @retval EFI_SUCCESS The operation was executed successfully
869 BootScriptExecutePciCfgWrite (
874 S3_BOOT_SCRIPT_LIB_WIDTH Width
;
877 EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE PciCfgWrite
;
879 CopyMem ((VOID
*)&PciCfgWrite
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE
));
881 Width
= (S3_BOOT_SCRIPT_LIB_WIDTH
)PciCfgWrite
.Width
;
882 Address
= PciCfgWrite
.Address
;
883 Count
= PciCfgWrite
.Count
;
884 Buffer
= Script
+ sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE
);
886 DEBUG ((EFI_D_INFO
, "BootScriptExecutePciCfgWrite - 0x%016lx, 0x%08x, 0x%08x\n", PCI_ADDRESS_ENCODE (0, Address
), Count
, (UINTN
)Width
));
887 return ScriptPciCfgWrite (Width
, Address
, Count
, Buffer
);
890 Interprete the boot script node with EFI_BOOT_SCRIPT_IO_READ_WRITE OP code.
892 @param Script The pointer of typed node in boot script table
893 @param AndMask Mask value for 'and' operation
894 @param OrMask Mask value for 'or' operation
896 @retval EFI_SUCCESS The operation was executed successfully
899 BootScriptExecuteIoReadWrite (
908 EFI_BOOT_SCRIPT_IO_READ_WRITE IoReadWrite
;
912 CopyMem((VOID
*)&IoReadWrite
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_IO_READ_WRITE
));
914 DEBUG ((EFI_D_INFO
, "BootScriptExecuteIoReadWrite - 0x%08x, 0x%016lx, 0x%016lx\n", (UINTN
)IoReadWrite
.Address
, AndMask
, OrMask
));
916 Status
= ScriptIoRead (
917 (S3_BOOT_SCRIPT_LIB_WIDTH
) IoReadWrite
.Width
,
922 if (!EFI_ERROR (Status
)) {
923 Data
= (Data
& AndMask
) | OrMask
;
924 Status
= ScriptIoWrite (
925 (S3_BOOT_SCRIPT_LIB_WIDTH
) IoReadWrite
.Width
,
934 Interprete the boot script node with EFI_BOOT_SCRIPT_MEM_READ_WRITE OP code.
936 @param Script The pointer of typed node in boot script table
937 @param AndMask Mask value for 'and' operation
938 @param OrMask Mask value for 'or' operation
940 @retval EFI_SUCCESS The operation was executed successfully
943 BootScriptExecuteMemoryReadWrite (
952 EFI_BOOT_SCRIPT_MEM_READ_WRITE MemReadWrite
;
956 CopyMem((VOID
*)&MemReadWrite
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_MEM_READ_WRITE
));
958 DEBUG ((EFI_D_INFO
, "BootScriptExecuteMemoryReadWrite - 0x%08x, 0x%016lx, 0x%016lx\n", (UINTN
)MemReadWrite
.Address
, AndMask
, OrMask
));
960 Status
= ScriptMemoryRead (
961 (S3_BOOT_SCRIPT_LIB_WIDTH
) MemReadWrite
.Width
,
962 MemReadWrite
.Address
,
966 if (!EFI_ERROR (Status
)) {
967 Data
= (Data
& AndMask
) | OrMask
;
968 Status
= ScriptMemoryWrite (
969 (S3_BOOT_SCRIPT_LIB_WIDTH
) MemReadWrite
.Width
,
970 MemReadWrite
.Address
,
978 Interprete the boot script node with EFI_BOOT_SCRIPT_PCI_CFG_READ_WRITE OP code.
980 @param Script The pointer of typed node in boot script table
981 @param AndMask Mask value for 'and' operation
982 @param OrMask Mask value for 'or' operation
984 @retval EFI_SUCCESS The operation was executed successfully
987 BootScriptExecutePciCfgReadWrite (
996 EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE PciCfgReadWrite
;
1000 CopyMem((VOID
*)&PciCfgReadWrite
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE
));
1002 DEBUG ((EFI_D_INFO
, "BootScriptExecutePciCfgReadWrite - 0x%016lx, 0x%016lx, 0x%016lx\n", PCI_ADDRESS_ENCODE (0, PciCfgReadWrite
.Address
), AndMask
, OrMask
));
1004 Status
= ScriptPciCfgRead (
1005 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfgReadWrite
.Width
,
1006 PciCfgReadWrite
.Address
,
1010 if (EFI_ERROR (Status
)) {
1014 Data
= (Data
& AndMask
) | OrMask
;
1016 Status
= ScriptPciCfgWrite (
1017 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfgReadWrite
.Width
,
1018 PciCfgReadWrite
.Address
,
1026 Interprete the boot script node with EFI_BOOT_SCRIPT_SMBUS_EXECUTE OP code.
1028 @param Script The pointer of typed node in boot script table
1030 @retval EFI_SUCCESS The operation was executed successfully
1031 @retval EFI_UNSUPPORTED Cannot locate smbus ppi or occur error of script execution
1032 @retval Others Result of script execution
1035 BootScriptExecuteSmbusExecute (
1041 EFI_BOOT_SCRIPT_SMBUS_EXECUTE SmbusExecuteEntry
;
1043 CopyMem ((VOID
*)&SmbusExecuteEntry
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_SMBUS_EXECUTE
));
1045 DEBUG ((EFI_D_INFO
, "BootScriptExecuteSmbusExecute - 0x%08x, 0x%08x\n", (UINTN
)SmbusExecuteEntry
.SmBusAddress
, (UINTN
)SmbusExecuteEntry
.Operation
));
1047 SmBusAddress
= (UINTN
)SmbusExecuteEntry
.SmBusAddress
;
1048 DataSize
= (UINTN
) SmbusExecuteEntry
.DataSize
;
1049 return InternalSmbusExecute (
1051 (EFI_SMBUS_OPERATION
) SmbusExecuteEntry
.Operation
,
1053 Script
+ sizeof (EFI_BOOT_SCRIPT_SMBUS_EXECUTE
)
1057 Interprete the boot script node with EFI_BOOT_SCRIPT_STALL OP code.
1059 @param Script The pointer of typed node in boot script table
1061 @retval EFI_SUCCESS The operation was executed successfully
1064 BootScriptExecuteStall (
1068 EFI_BOOT_SCRIPT_STALL Stall
;
1070 CopyMem ((VOID
*)&Stall
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_STALL
));
1072 DEBUG ((EFI_D_INFO
, "BootScriptExecuteStall - 0x%08x\n", (UINTN
)Stall
.Duration
));
1074 MicroSecondDelay ((UINTN
) Stall
.Duration
);
1078 Interprete the boot script node with EFI_BOOT_SCRIPT_DISPATCH OP code.
1080 @param Script The pointer of typed node in boot script table
1081 @retval EFI_SUCCESS The operation was executed successfully
1084 BootScriptExecuteDispatch (
1089 DISPATCH_ENTRYPOINT_FUNC EntryFunc
;
1090 EFI_BOOT_SCRIPT_DISPATCH ScriptDispatch
;
1092 CopyMem ((VOID
*)&ScriptDispatch
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_DISPATCH
));
1093 EntryFunc
= (DISPATCH_ENTRYPOINT_FUNC
) (UINTN
) (ScriptDispatch
.EntryPoint
);
1095 DEBUG ((EFI_D_INFO
, "BootScriptExecuteDispatch - 0x%08x\n", (UINTN
)ScriptDispatch
.EntryPoint
));
1097 Status
= EntryFunc (NULL
, NULL
);
1102 Interprete the boot script node with EFI_BOOT_SCRIPT_DISPATCH_2 OP code.
1104 @param Script The pointer of typed node in boot script table
1105 @retval EFI_SUCCESS The operation was executed successfully
1108 BootScriptExecuteDispatch2 (
1113 DISPATCH_ENTRYPOINT_FUNC EntryFunc
;
1114 EFI_BOOT_SCRIPT_DISPATCH_2 ScriptDispatch2
;
1116 CopyMem ((VOID
*)&ScriptDispatch2
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_DISPATCH_2
));
1118 DEBUG ((EFI_D_INFO
, "BootScriptExecuteDispatch2 - 0x%08x(0x%08x)\n", (UINTN
)ScriptDispatch2
.EntryPoint
, (UINTN
)ScriptDispatch2
.Context
));
1120 EntryFunc
= (DISPATCH_ENTRYPOINT_FUNC
) (UINTN
) (ScriptDispatch2
.EntryPoint
);
1122 Status
= EntryFunc (NULL
, (VOID
*) (UINTN
) ScriptDispatch2
.Context
);
1127 Interprete the boot script node with EFI_BOOT_SCRIPT_MEM_POLL OP code.
1129 @param Script The pointer of typed node in boot script table
1130 @param AndMask Mask value for 'and' operation
1131 @param OrMask Mask value for 'or' operation
1133 @retval EFI_DEVICE_ERROR Data polled from memory does not equal to
1134 the epecting data within the Loop Times.
1135 @retval EFI_SUCCESS The operation was executed successfully
1138 BootScriptExecuteMemPoll (
1148 EFI_BOOT_SCRIPT_MEM_POLL MemPoll
;
1150 CopyMem ((VOID
*)&MemPoll
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_MEM_POLL
));
1152 DEBUG ((EFI_D_INFO
, "BootScriptExecuteMemPoll - 0x%08x, 0x%016lx, 0x%016lx\n", (UINTN
)MemPoll
.Address
, AndMask
, OrMask
));
1155 Status
= ScriptMemoryRead (
1156 (S3_BOOT_SCRIPT_LIB_WIDTH
) MemPoll
.Width
,
1161 if ((!EFI_ERROR (Status
)) && (Data
& AndMask
) == OrMask
) {
1165 for (LoopTimes
= 0; LoopTimes
< MemPoll
.LoopTimes
; LoopTimes
++) {
1166 MicroSecondDelay ((UINTN
)MemPoll
.Duration
);
1169 Status
= ScriptMemoryRead (
1170 (S3_BOOT_SCRIPT_LIB_WIDTH
) MemPoll
.Width
,
1175 if ((!EFI_ERROR (Status
)) && (Data
& AndMask
) == OrMask
) {
1180 if (LoopTimes
< MemPoll
.LoopTimes
) {
1183 return EFI_DEVICE_ERROR
;
1187 Execute the boot script to interpret the Store arbitrary information.
1188 This opcode is a no-op on dispatch and is only used for debugging script issues.
1190 @param Script The pointer of node in boot script table
1194 BootScriptExecuteInformation (
1200 EFI_BOOT_SCRIPT_INFORMATION Information
;
1201 UINT8
*InformationData
;
1203 CopyMem ((VOID
*)&Information
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_INFORMATION
));
1205 InformationData
= Script
+ sizeof (EFI_BOOT_SCRIPT_INFORMATION
);
1206 DEBUG ((EFI_D_INFO
, "BootScriptExecuteInformation - 0x%08x\n", (UINTN
) InformationData
));
1208 DEBUG ((EFI_D_INFO
, "BootScriptInformation: "));
1209 for (Index
= 0; Index
< Information
.InformationLength
; Index
++) {
1210 DEBUG ((EFI_D_INFO
, "%02x ", InformationData
[Index
]));
1212 DEBUG ((EFI_D_INFO
, "\n"));
1216 Execute the boot script to interpret the Label information.
1218 @param Script The pointer of node in boot script table
1222 BootScriptExecuteLabel (
1228 EFI_BOOT_SCRIPT_INFORMATION Information
;
1229 UINT8
*InformationData
;
1231 CopyMem ((VOID
*)&Information
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_INFORMATION
));
1233 InformationData
= Script
+ sizeof (EFI_BOOT_SCRIPT_INFORMATION
);
1234 DEBUG ((EFI_D_INFO
, "BootScriptExecuteLabel - 0x%08x\n", (UINTN
) InformationData
));
1236 DEBUG ((EFI_D_INFO
, "BootScriptLabel: "));
1237 for (Index
= 0; Index
< Information
.InformationLength
; Index
++) {
1238 DEBUG ((EFI_D_INFO
, "%02x ", InformationData
[Index
]));
1240 DEBUG ((EFI_D_INFO
, "\n"));
1244 calculate the mask value for 'and' and 'or' operation
1245 @param ScriptHeader The pointer of header of node in boot script table
1246 @param AndMask The Mask value for 'and' operation
1247 @param OrMask The Mask value for 'or' operation
1248 @param Script Pointer to the entry.
1253 IN EFI_BOOT_SCRIPT_COMMON_HEADER
*ScriptHeader
,
1254 OUT UINT64
*AndMask
,
1262 switch (ScriptHeader
->OpCode
) {
1263 case EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE
:
1264 Size
= sizeof (EFI_BOOT_SCRIPT_IO_READ_WRITE
);
1267 case EFI_BOOT_SCRIPT_MEM_READ_WRITE_OPCODE
:
1268 Size
= sizeof (EFI_BOOT_SCRIPT_MEM_READ_WRITE
);
1271 case EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE
:
1272 Size
= sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE
);
1274 case EFI_BOOT_SCRIPT_MEM_POLL_OPCODE
:
1275 Size
= sizeof (EFI_BOOT_SCRIPT_MEM_POLL
);
1278 case EFI_BOOT_SCRIPT_IO_POLL_OPCODE
:
1279 Size
= sizeof (EFI_BOOT_SCRIPT_IO_POLL
);
1282 case EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE_OPCODE
:
1283 Size
= sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE
);
1286 case EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL_OPCODE
:
1287 Size
= sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL
);
1290 case EFI_BOOT_SCRIPT_PCI_CONFIG_POLL_OPCODE
:
1291 Size
= sizeof (EFI_BOOT_SCRIPT_PCI_CONFIG_POLL
);
1298 DataPtr
= Script
+ Size
;
1300 switch (ScriptHeader
->Width
) {
1301 case S3BootScriptWidthUint8
:
1302 *AndMask
= (UINT64
) (*(UINT8
*) (DataPtr
+ 1));
1303 *OrMask
= (UINT64
) (*DataPtr
);
1306 case S3BootScriptWidthUint16
:
1307 *AndMask
= (UINT64
) (*(UINT16
*) (DataPtr
+ 2));
1308 *OrMask
= (UINT64
) (*(UINT16
*) DataPtr
);
1311 case S3BootScriptWidthUint32
:
1312 *AndMask
= (UINT64
) (*(UINT32
*) (DataPtr
+ 4));
1313 *OrMask
= (UINT64
) (*(UINT32
*) DataPtr
);
1316 case S3BootScriptWidthUint64
:
1317 *AndMask
= (UINT64
) (*(UINT64
*) (DataPtr
+ 8));
1318 *OrMask
= (UINT64
) (*(UINT64
*) DataPtr
);
1328 Interprete the boot script node with EFI_BOOT_SCRIPT_IO_POLL OP code.
1330 @param Script The pointer of typed node in boot script table
1331 @param AndMask Mask value for 'and' operation
1332 @param OrMask Mask value for 'or' operation
1334 @retval EFI_DEVICE_ERROR Data polled from memory does not equal to
1335 the epecting data within the Loop Times.
1336 @retval EFI_SUCCESS The operation was executed successfully
1339 BootScriptExecuteIoPoll (
1348 EFI_BOOT_SCRIPT_IO_POLL IoPoll
;
1350 CopyMem ((VOID
*)&IoPoll
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_IO_POLL
));
1352 DEBUG ((EFI_D_INFO
, "BootScriptExecuteIoPoll - 0x%08x, 0x%016lx, 0x%016lx\n", (UINTN
)IoPoll
.Address
, AndMask
, OrMask
));
1355 Status
= ScriptIoRead (
1356 (S3_BOOT_SCRIPT_LIB_WIDTH
) IoPoll
.Width
,
1361 if ((!EFI_ERROR (Status
)) && (Data
& AndMask
) == OrMask
) {
1364 for (LoopTimes
= 0; LoopTimes
< IoPoll
.Delay
; LoopTimes
++) {
1365 NanoSecondDelay (100);
1367 Status
= ScriptIoRead (
1368 (S3_BOOT_SCRIPT_LIB_WIDTH
) IoPoll
.Width
,
1373 if ((!EFI_ERROR (Status
)) &&(Data
& AndMask
) == OrMask
) {
1378 if (LoopTimes
< IoPoll
.Delay
) {
1381 return EFI_DEVICE_ERROR
;
1385 Interprete the boot script node with EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE OP code.
1387 @param Script The pointer of S3 boot script
1389 @retval EFI_SUCCESS The operation was executed successfully
1393 BootScriptExecutePciCfg2Write (
1398 S3_BOOT_SCRIPT_LIB_WIDTH Width
;
1402 EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE PciCfg2Write
;
1404 CopyMem ((VOID
*)&PciCfg2Write
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE
));
1406 Width
= (S3_BOOT_SCRIPT_LIB_WIDTH
)PciCfg2Write
.Width
;
1407 Segment
= PciCfg2Write
.Segment
;
1408 Address
= PciCfg2Write
.Address
;
1409 Count
= PciCfg2Write
.Count
;
1410 Buffer
= Script
+ sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE
);
1412 DEBUG ((EFI_D_INFO
, "BootScriptExecutePciCfg2Write - 0x%016lx, 0x%08x, 0x%08x\n", PCI_ADDRESS_ENCODE (Segment
, Address
), Count
, (UINTN
)Width
));
1413 return ScriptPciCfg2Write (Width
, Segment
, Address
, Count
, Buffer
);
1418 Interprete the boot script node with EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE OP code.
1420 @param Script The pointer of S3 boot script
1421 @param AndMask Mask value for 'and' operation
1422 @param OrMask Mask value for 'or' operation
1424 @retval EFI_SUCCESS The operation was executed successfully
1428 BootScriptExecutePciCfg2ReadWrite (
1436 EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE PciCfg2ReadWrite
;
1440 CopyMem ((VOID
*)&PciCfg2ReadWrite
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE
));
1442 DEBUG ((EFI_D_INFO
, "BootScriptExecutePciCfg2ReadWrite - 0x%016lx, 0x%016lx, 0x%016lx\n", PCI_ADDRESS_ENCODE (PciCfg2ReadWrite
.Segment
, PciCfg2ReadWrite
.Address
), AndMask
, OrMask
));
1444 Status
= ScriptPciCfg2Read (
1445 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfg2ReadWrite
.Width
,
1446 PciCfg2ReadWrite
.Segment
,
1447 PciCfg2ReadWrite
.Address
,
1451 if (EFI_ERROR (Status
)) {
1455 Data
= (Data
& AndMask
) | OrMask
;
1456 Status
= ScriptPciCfg2Write (
1457 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfg2ReadWrite
.Width
,
1458 PciCfg2ReadWrite
.Segment
,
1459 PciCfg2ReadWrite
.Address
,
1466 Interprete the boot script node with EFI_BOOT_SCRIPT_PCI_CONFIG_POLL OP code.
1468 @param Script The pointer of S3 boot script
1469 @param AndMask Mask value for 'and' operation
1470 @param OrMask Mask value for 'or' operation
1472 @retval EFI_SUCCESS The operation was executed successfully
1473 @retval EFI_DEVICE_ERROR Data polled from Pci configuration space does not equal to
1474 epecting data within the Loop Times.
1477 BootScriptPciCfgPoll (
1486 EFI_BOOT_SCRIPT_PCI_CONFIG_POLL PciCfgPoll
;
1487 CopyMem ((VOID
*)&PciCfgPoll
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG_POLL
));
1489 DEBUG ((EFI_D_INFO
, "BootScriptPciCfgPoll - 0x%016lx, 0x%016lx, 0x%016lx\n", PCI_ADDRESS_ENCODE (0, PciCfgPoll
.Address
), AndMask
, OrMask
));
1492 Status
= ScriptPciCfgRead (
1493 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfgPoll
.Width
,
1498 if ((!EFI_ERROR (Status
)) &&(Data
& AndMask
) == OrMask
) {
1502 for (LoopTimes
= 0; LoopTimes
< PciCfgPoll
.Delay
; LoopTimes
++) {
1503 NanoSecondDelay (100);
1505 Status
= ScriptPciCfgRead (
1506 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfgPoll
.Width
,
1511 if ((!EFI_ERROR (Status
)) &&
1512 (Data
& AndMask
) == OrMask
) {
1517 if (LoopTimes
< PciCfgPoll
.Delay
) {
1520 return EFI_DEVICE_ERROR
;
1525 Interprete the boot script node with EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL OP code.
1527 @param Script The pointer of S3 Boot Script
1528 @param AndMask Mask value for 'and' operation
1529 @param OrMask Mask value for 'or' operation
1531 @retval EFI_SUCCESS The operation was executed successfully
1532 @retval EFI_DEVICE_ERROR Data polled from Pci configuration space does not equal to
1533 epecting data within the Loop Times.
1537 BootScriptPciCfg2Poll (
1546 EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL PciCfg2Poll
;
1549 CopyMem ((VOID
*)&PciCfg2Poll
, (VOID
*)Script
, sizeof(EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL
));
1551 DEBUG ((EFI_D_INFO
, "BootScriptPciCfg2Poll - 0x%016lx, 0x%016lx, 0x%016lx\n", PCI_ADDRESS_ENCODE (PciCfg2Poll
.Segment
, PciCfg2Poll
.Address
), AndMask
, OrMask
));
1553 Status
= ScriptPciCfg2Read (
1554 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfg2Poll
.Width
,
1555 PciCfg2Poll
.Segment
,
1556 PciCfg2Poll
.Address
,
1560 if ((!EFI_ERROR (Status
)) && (Data
& AndMask
) == OrMask
) {
1564 for (LoopTimes
= 0; LoopTimes
< PciCfg2Poll
.Delay
; LoopTimes
++) {
1565 NanoSecondDelay (100);
1568 Status
= ScriptPciCfg2Read (
1569 (S3_BOOT_SCRIPT_LIB_WIDTH
) PciCfg2Poll
.Width
,
1570 PciCfg2Poll
.Segment
,
1571 PciCfg2Poll
.Address
,
1575 if ((!EFI_ERROR (Status
)) && (Data
& AndMask
) == OrMask
) {
1580 if (LoopTimes
< PciCfg2Poll
.Delay
) {
1583 return EFI_DEVICE_ERROR
;
1589 Executes the S3 boot script table.
1591 @retval RETURN_SUCCESS The boot script table was executed successfully.
1592 @retval RETURN_UNSUPPORTED Invalid script table or opcode.
1597 S3BootScriptExecute (
1607 EFI_BOOT_SCRIPT_COMMON_HEADER ScriptHeader
;
1608 EFI_BOOT_SCRIPT_TABLE_HEADER TableHeader
;
1609 Script
= mS3BootScriptTablePtr
->TableBase
;
1611 CopyMem ((VOID
*)&TableHeader
, Script
, sizeof(EFI_BOOT_SCRIPT_TABLE_HEADER
));
1613 return EFI_INVALID_PARAMETER
;
1616 DEBUG ((EFI_D_INFO
, "S3BootScriptExecute:\n"));
1617 if (TableHeader
.OpCode
!= S3_BOOT_SCRIPT_LIB_TABLE_OPCODE
) {
1618 return EFI_UNSUPPORTED
;
1621 DEBUG ((EFI_D_INFO
, "TableHeader - 0x%08x\n", Script
));
1623 StartAddress
= (UINTN
) Script
;
1624 TableLength
= TableHeader
.TableLength
;
1625 Script
= Script
+ TableHeader
.Length
;
1626 Status
= EFI_SUCCESS
;
1630 DEBUG ((EFI_D_INFO
, "TableHeader.Version - 0x%04x\n", (UINTN
)TableHeader
.Version
));
1631 DEBUG ((EFI_D_INFO
, "TableHeader.TableLength - 0x%08x\n", (UINTN
)TableLength
));
1633 while ((UINTN
) Script
< (UINTN
) (StartAddress
+ TableLength
)) {
1634 DEBUG ((EFI_D_INFO
, "ExecuteBootScript - %08x\n", (UINTN
)Script
));
1636 CopyMem ((VOID
*)&ScriptHeader
, Script
, sizeof(EFI_BOOT_SCRIPT_COMMON_HEADER
));
1637 switch (ScriptHeader
.OpCode
) {
1639 case EFI_BOOT_SCRIPT_MEM_WRITE_OPCODE
:
1640 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_MEM_WRITE_OPCODE\n"));
1641 Status
= BootScriptExecuteMemoryWrite (Script
);
1644 case EFI_BOOT_SCRIPT_MEM_READ_WRITE_OPCODE
:
1645 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_MEM_READ_WRITE_OPCODE\n"));
1646 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1647 Status
= BootScriptExecuteMemoryReadWrite (
1654 case EFI_BOOT_SCRIPT_IO_WRITE_OPCODE
:
1655 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_IO_WRITE_OPCODE\n"));
1656 Status
= BootScriptExecuteIoWrite (Script
);
1659 case EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE_OPCODE
:
1660 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_PCI_CONFIG_WRITE_OPCODE\n"));
1661 Status
= BootScriptExecutePciCfgWrite (Script
);
1664 case EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE
:
1665 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_PCI_CONFIG_READ_WRITE_OPCODE\n"));
1666 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1667 Status
= BootScriptExecutePciCfgReadWrite (
1673 case EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE_OPCODE
:
1674 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_PCI_CONFIG2_WRITE_OPCODE\n"));
1675 Status
= BootScriptExecutePciCfg2Write (Script
);
1678 case EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE_OPCODE
:
1679 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_PCI_CONFIG2_READ_WRITE_OPCODE\n"));
1680 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1681 Status
= BootScriptExecutePciCfg2ReadWrite (
1687 case EFI_BOOT_SCRIPT_DISPATCH_OPCODE
:
1688 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_DISPATCH_OPCODE\n"));
1689 Status
= BootScriptExecuteDispatch (Script
);
1692 case EFI_BOOT_SCRIPT_DISPATCH_2_OPCODE
:
1693 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_DISPATCH_2_OPCODE\n"));
1694 Status
= BootScriptExecuteDispatch2 (Script
);
1697 case EFI_BOOT_SCRIPT_INFORMATION_OPCODE
:
1698 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_INFORMATION_OPCODE\n"));
1699 BootScriptExecuteInformation (Script
);
1702 case S3_BOOT_SCRIPT_LIB_TERMINATE_OPCODE
:
1703 DEBUG ((EFI_D_INFO
, "S3_BOOT_SCRIPT_LIB_TERMINATE_OPCODE\n"));
1704 DEBUG ((EFI_D_INFO
, "S3BootScriptDone - %r\n", EFI_SUCCESS
));
1707 case EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE
:
1708 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_IO_READ_WRITE_OPCODE\n"));
1709 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1710 Status
= BootScriptExecuteIoReadWrite (
1717 case EFI_BOOT_SCRIPT_SMBUS_EXECUTE_OPCODE
:
1718 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_SMBUS_EXECUTE_OPCODE\n"));
1719 Status
= BootScriptExecuteSmbusExecute (Script
);
1722 case EFI_BOOT_SCRIPT_STALL_OPCODE
:
1723 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_STALL_OPCODE\n"));
1724 Status
= BootScriptExecuteStall (Script
);
1727 case EFI_BOOT_SCRIPT_MEM_POLL_OPCODE
:
1728 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_MEM_POLL_OPCODE\n"));
1729 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1730 Status
= BootScriptExecuteMemPoll (Script
, AndMask
, OrMask
);
1734 case EFI_BOOT_SCRIPT_IO_POLL_OPCODE
:
1735 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_IO_POLL_OPCODE\n"));
1736 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1737 Status
= BootScriptExecuteIoPoll (Script
, AndMask
, OrMask
);
1740 case EFI_BOOT_SCRIPT_PCI_CONFIG_POLL_OPCODE
:
1741 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_PCI_CONFIG_POLL_OPCODE\n"));
1742 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1743 Status
= BootScriptPciCfgPoll (Script
, AndMask
, OrMask
);
1746 case EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL_OPCODE
:
1747 DEBUG ((EFI_D_INFO
, "EFI_BOOT_SCRIPT_PCI_CONFIG2_POLL_OPCODE\n"));
1748 CheckAndOrMask (&ScriptHeader
, &AndMask
, &OrMask
, Script
);
1749 Status
= BootScriptPciCfg2Poll (Script
, AndMask
, OrMask
);
1752 case S3_BOOT_SCRIPT_LIB_LABEL_OPCODE
:
1756 DEBUG ((EFI_D_INFO
, "S3_BOOT_SCRIPT_LIB_LABEL_OPCODE\n"));
1757 BootScriptExecuteLabel (Script
);
1760 DEBUG ((EFI_D_INFO
, "S3BootScriptDone - %r\n", EFI_UNSUPPORTED
));
1761 return EFI_UNSUPPORTED
;
1764 if (EFI_ERROR (Status
)) {
1765 DEBUG ((EFI_D_INFO
, "S3BootScriptDone - %r\n", Status
));
1769 Script
= Script
+ ScriptHeader
.Length
;
1772 DEBUG ((EFI_D_INFO
, "S3BootScriptDone - %r\n", Status
));