1 /** @file
2   Shared code for the Base Null and PEI fw_cfg instances of the QemuFwCfgS3Lib
3   class.
4 
5   Copyright (C) 2017, Red Hat, Inc.
6 
7   SPDX-License-Identifier: BSD-2-Clause-Patent
8 **/
9 
10 #include <Library/DebugLib.h>
11 #include <Library/QemuFwCfgS3Lib.h>
12 
13 /**
14   Produce ACPI S3 Boot Script opcodes that (optionally) select an fw_cfg item,
15   and transfer data to it.
16 
17   The opcodes produced by QemuFwCfgS3ScriptWriteBytes() will first restore
18   NumberOfBytes bytes in ScratchBuffer in-place, in reserved memory, then write
19   them to fw_cfg using DMA.
20 
21   If the operation fails during S3 resume, the boot script will hang.
22 
23   This function may only be called from the client module's
24   FW_CFG_BOOT_SCRIPT_CALLBACK_FUNCTION, which was passed to
25   QemuFwCfgS3CallWhenBootScriptReady() as Callback.
26 
27   @param[in] FirmwareConfigItem  The UINT16 selector key of the firmware config
28                                  item to write, expressed as INT32. If
29                                  FirmwareConfigItem is -1, no selection is
30                                  made, the write will occur to the currently
31                                  selected item, at its currently selected
32                                  offset. Otherwise, the specified item will be
33                                  selected, and the write will occur at offset
34                                  0.
35 
36   @param[in] NumberOfBytes       Size of the data to restore in ScratchBuffer,
37                                  and to write from ScratchBuffer, during S3
38                                  resume. NumberOfBytes must not exceed
39                                  ScratchBufferSize, which was passed to
40                                  QemuFwCfgS3CallWhenBootScriptReady().
41 
42   @retval RETURN_SUCCESS            The opcodes were appended to the ACPI S3
43                                     Boot Script successfully. There is no way
44                                     to undo this action.
45 
46   @retval RETURN_INVALID_PARAMETER  FirmwareConfigItem is invalid.
47 
48   @retval RETURN_BAD_BUFFER_SIZE    NumberOfBytes is larger than
49                                     ScratchBufferSize.
50 
51   @return                           Error codes from underlying functions.
52 **/
53 RETURN_STATUS
54 EFIAPI
QemuFwCfgS3ScriptWriteBytes(IN INT32 FirmwareConfigItem,IN UINTN NumberOfBytes)55 QemuFwCfgS3ScriptWriteBytes (
56   IN INT32 FirmwareConfigItem,
57   IN UINTN NumberOfBytes
58   )
59 {
60   ASSERT (FALSE);
61   return RETURN_UNSUPPORTED;
62 }
63 
64 
65 /**
66   Produce ACPI S3 Boot Script opcodes that (optionally) select an fw_cfg item,
67   and transfer data from it.
68 
69   The opcodes produced by QemuFwCfgS3ScriptReadBytes() will read NumberOfBytes
70   bytes from fw_cfg using DMA, storing the result in ScratchBuffer, in reserved
71   memory.
72 
73   If the operation fails during S3 resume, the boot script will hang.
74 
75   This function may only be called from the client module's
76   FW_CFG_BOOT_SCRIPT_CALLBACK_FUNCTION, which was passed to
77   QemuFwCfgS3CallWhenBootScriptReady() as Callback.
78 
79   @param[in] FirmwareConfigItem  The UINT16 selector key of the firmware config
80                                  item to read, expressed as INT32. If
81                                  FirmwareConfigItem is -1, no selection is
82                                  made, the read will occur from the currently
83                                  selected item, from its currently selected
84                                  offset. Otherwise, the specified item will be
85                                  selected, and the read will occur from offset
86                                  0.
87 
88   @param[in] NumberOfBytes       Size of the data to read during S3 resume.
89                                  NumberOfBytes must not exceed
90                                  ScratchBufferSize, which was passed to
91                                  QemuFwCfgS3CallWhenBootScriptReady().
92 
93   @retval RETURN_SUCCESS            The opcodes were appended to the ACPI S3
94                                     Boot Script successfully. There is no way
95                                     to undo this action.
96 
97   @retval RETURN_INVALID_PARAMETER  FirmwareConfigItem is invalid.
98 
99   @retval RETURN_BAD_BUFFER_SIZE    NumberOfBytes is larger than
100                                     ScratchBufferSize.
101 
102   @return                           Error codes from underlying functions.
103 **/
104 RETURN_STATUS
105 EFIAPI
QemuFwCfgS3ScriptReadBytes(IN INT32 FirmwareConfigItem,IN UINTN NumberOfBytes)106 QemuFwCfgS3ScriptReadBytes (
107   IN INT32 FirmwareConfigItem,
108   IN UINTN NumberOfBytes
109   )
110 {
111   ASSERT (FALSE);
112   return RETURN_UNSUPPORTED;
113 }
114 
115 
116 /**
117   Produce ACPI S3 Boot Script opcodes that (optionally) select an fw_cfg item,
118   and increase its offset.
119 
120   If the operation fails during S3 resume, the boot script will hang.
121 
122   This function may only be called from the client module's
123   FW_CFG_BOOT_SCRIPT_CALLBACK_FUNCTION, which was passed to
124   QemuFwCfgS3CallWhenBootScriptReady() as Callback.
125 
126   @param[in] FirmwareConfigItem  The UINT16 selector key of the firmware config
127                                  item to advance the offset of, expressed as
128                                  INT32. If FirmwareConfigItem is -1, no
129                                  selection is made, and the offset for the
130                                  currently selected item is increased.
131                                  Otherwise, the specified item will be
132                                  selected, and the offset increment will occur
133                                  from offset 0.
134 
135   @param[in] NumberOfBytes       The number of bytes to skip in the subject
136                                  fw_cfg item.
137 
138   @retval RETURN_SUCCESS            The opcodes were appended to the ACPI S3
139                                     Boot Script successfully. There is no way
140                                     to undo this action.
141 
142   @retval RETURN_INVALID_PARAMETER  FirmwareConfigItem is invalid.
143 
144   @retval RETURN_BAD_BUFFER_SIZE    NumberOfBytes is too large.
145 
146   @return                           Error codes from underlying functions.
147 **/
148 RETURN_STATUS
149 EFIAPI
QemuFwCfgS3ScriptSkipBytes(IN INT32 FirmwareConfigItem,IN UINTN NumberOfBytes)150 QemuFwCfgS3ScriptSkipBytes (
151   IN INT32 FirmwareConfigItem,
152   IN UINTN NumberOfBytes
153   )
154 {
155   ASSERT (FALSE);
156   return RETURN_UNSUPPORTED;
157 }
158 
159 
160 /**
161   Produce ACPI S3 Boot Script opcodes that check a value in ScratchBuffer.
162 
163   If the check fails during S3 resume, the boot script will hang.
164 
165   This function may only be called from the client module's
166   FW_CFG_BOOT_SCRIPT_CALLBACK_FUNCTION, which was passed to
167   QemuFwCfgS3CallWhenBootScriptReady() as Callback.
168 
169   @param[in] ScratchData  Pointer to the UINT8, UINT16, UINT32 or UINT64 field
170                           in ScratchBuffer that should be checked. The caller
171                           is responsible for populating the field during S3
172                           resume, by calling QemuFwCfgS3ScriptReadBytes() ahead
173                           of QemuFwCfgS3ScriptCheckValue().
174 
175                           ScratchData must point into ScratchBuffer, which was
176                           allocated, and passed to Callback(), by
177                           QemuFwCfgS3CallWhenBootScriptReady().
178 
179                           ScratchData must be aligned at ValueSize bytes.
180 
181   @param[in] ValueSize    One of 1, 2, 4 or 8, specifying the size of the field
182                           to check.
183 
184   @param[in] ValueMask    The value read from ScratchData is binarily AND-ed
185                           with ValueMask, and the result is compared against
186                           Value. If the masked data equals Value, the check
187                           passes, and the boot script can proceed. Otherwise,
188                           the check fails, and the boot script hangs.
189 
190   @param[in] Value        Refer to ValueMask.
191 
192   @retval RETURN_SUCCESS            The opcodes were appended to the ACPI S3
193                                     Boot Script successfully. There is no way
194                                     to undo this action.
195 
196   @retval RETURN_INVALID_PARAMETER  ValueSize is invalid.
197 
198   @retval RETURN_INVALID_PARAMETER  ValueMask or Value cannot be represented in
199                                     ValueSize bytes.
200 
201   @retval RETURN_INVALID_PARAMETER  ScratchData is not aligned at ValueSize
202                                     bytes.
203 
204   @retval RETURN_BAD_BUFFER_SIZE    The ValueSize bytes at ScratchData aren't
205                                     wholly contained in the ScratchBufferSize
206                                     bytes at ScratchBuffer.
207 
208   @return                           Error codes from underlying functions.
209 **/
210 RETURN_STATUS
211 EFIAPI
QemuFwCfgS3ScriptCheckValue(IN VOID * ScratchData,IN UINT8 ValueSize,IN UINT64 ValueMask,IN UINT64 Value)212 QemuFwCfgS3ScriptCheckValue (
213   IN VOID   *ScratchData,
214   IN UINT8  ValueSize,
215   IN UINT64 ValueMask,
216   IN UINT64 Value
217   )
218 {
219   ASSERT (FALSE);
220   return RETURN_UNSUPPORTED;
221 }
222