]> git.proxmox.com Git - mirror_edk2.git/blob - MdeModulePkg/Core/Dxe/FwVol/Ffs.c
CalculateSum8() and CalculateSum16() defined in BaseLib are used to calculate checksum.
[mirror_edk2.git] / MdeModulePkg / Core / Dxe / FwVol / Ffs.c
1 /** @file
2 FFS file access utilities.
3
4 Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.<BR>
5 This program and the accompanying materials
6 are licensed and made available under the terms and conditions of the BSD License
7 which accompanies this distribution. The full text of the license may be found at
8 http://opensource.org/licenses/bsd-license.php
9
10 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
12
13 **/
14
15
16 #include "DxeMain.h"
17 #include "FwVolDriver.h"
18
19
20 /**
21 Get the FFS file state by checking the highest bit set in the header's state field.
22
23 @param ErasePolarity Erase polarity attribute of the firmware volume
24 @param FfsHeader Points to the FFS file header
25
26 @return FFS File state
27
28 **/
29 EFI_FFS_FILE_STATE
30 GetFileState (
31 IN UINT8 ErasePolarity,
32 IN EFI_FFS_FILE_HEADER *FfsHeader
33 )
34 {
35 EFI_FFS_FILE_STATE FileState;
36 UINT8 HighestBit;
37
38 FileState = FfsHeader->State;
39
40 if (ErasePolarity != 0) {
41 FileState = (EFI_FFS_FILE_STATE)~FileState;
42 }
43
44 HighestBit = 0x80;
45 while (HighestBit != 0 && ((HighestBit & FileState) == 0)) {
46 HighestBit >>= 1;
47 }
48
49 return (EFI_FFS_FILE_STATE) HighestBit;
50 }
51
52
53
54 /**
55 Check if a block of buffer is erased.
56
57 @param ErasePolarity Erase polarity attribute of the firmware volume
58 @param InBuffer The buffer to be checked
59 @param BufferSize Size of the buffer in bytes
60
61 @retval TRUE The block of buffer is erased
62 @retval FALSE The block of buffer is not erased
63
64 **/
65 BOOLEAN
66 IsBufferErased (
67 IN UINT8 ErasePolarity,
68 IN VOID *InBuffer,
69 IN UINTN BufferSize
70 )
71 {
72 UINTN Count;
73 UINT8 EraseByte;
74 UINT8 *Buffer;
75
76 if(ErasePolarity == 1) {
77 EraseByte = 0xFF;
78 } else {
79 EraseByte = 0;
80 }
81
82 Buffer = InBuffer;
83 for (Count = 0; Count < BufferSize; Count++) {
84 if (Buffer[Count] != EraseByte) {
85 return FALSE;
86 }
87 }
88
89 return TRUE;
90 }
91
92
93
94 /**
95 Verify checksum of the firmware volume header.
96
97 @param FvHeader Points to the firmware volume header to be checked
98
99 @retval TRUE Checksum verification passed
100 @retval FALSE Checksum verification failed
101
102 **/
103 BOOLEAN
104 VerifyFvHeaderChecksum (
105 IN EFI_FIRMWARE_VOLUME_HEADER *FvHeader
106 )
107 {
108 UINT16 Checksum;
109
110 Checksum = CalculateSum16 ((UINT16 *) FvHeader, FvHeader->HeaderLength);
111
112 if (Checksum == 0) {
113 return TRUE;
114 } else {
115 return FALSE;
116 }
117 }
118
119
120 /**
121 Verify checksum of the FFS file header.
122
123 @param FfsHeader Points to the FFS file header to be checked
124
125 @retval TRUE Checksum verification passed
126 @retval FALSE Checksum verification failed
127
128 **/
129 BOOLEAN
130 VerifyHeaderChecksum (
131 IN EFI_FFS_FILE_HEADER *FfsHeader
132 )
133 {
134 UINT8 HeaderChecksum;
135
136 HeaderChecksum = CalculateSum8 ((UINT8 *) FfsHeader, sizeof (EFI_FFS_FILE_HEADER));
137 HeaderChecksum = (UINT8) (HeaderChecksum - FfsHeader->State - FfsHeader->IntegrityCheck.Checksum.File);
138
139 if (HeaderChecksum == 0) {
140 return TRUE;
141 } else {
142 return FALSE;
143 }
144 }
145
146
147
148 /**
149 Check if it's a valid FFS file header.
150
151 @param ErasePolarity Erase polarity attribute of the firmware volume
152 @param FfsHeader Points to the FFS file header to be checked
153 @param FileState FFS file state to be returned
154
155 @retval TRUE Valid FFS file header
156 @retval FALSE Invalid FFS file header
157
158 **/
159 BOOLEAN
160 IsValidFfsHeader (
161 IN UINT8 ErasePolarity,
162 IN EFI_FFS_FILE_HEADER *FfsHeader,
163 OUT EFI_FFS_FILE_STATE *FileState
164 )
165 {
166 *FileState = GetFileState (ErasePolarity, FfsHeader);
167
168 switch (*FileState) {
169 case EFI_FILE_HEADER_VALID:
170 case EFI_FILE_DATA_VALID:
171 case EFI_FILE_MARKED_FOR_UPDATE:
172 case EFI_FILE_DELETED:
173 //
174 // Here we need to verify header checksum
175 //
176 return VerifyHeaderChecksum (FfsHeader);
177
178 case EFI_FILE_HEADER_CONSTRUCTION:
179 case EFI_FILE_HEADER_INVALID:
180 default:
181 return FALSE;
182 }
183 }
184
185
186 /**
187 Check if it's a valid FFS file.
188 Here we are sure that it has a valid FFS file header since we must call IsValidFfsHeader() first.
189
190 @param ErasePolarity Erase polarity attribute of the firmware volume
191 @param FfsHeader Points to the FFS file to be checked
192
193 @retval TRUE Valid FFS file
194 @retval FALSE Invalid FFS file
195
196 **/
197 BOOLEAN
198 IsValidFfsFile (
199 IN UINT8 ErasePolarity,
200 IN EFI_FFS_FILE_HEADER *FfsHeader
201 )
202 {
203 EFI_FFS_FILE_STATE FileState;
204 UINT8 DataCheckSum;
205 UINT32 FileLength;
206
207 FileState = GetFileState (ErasePolarity, FfsHeader);
208 switch (FileState) {
209
210 case EFI_FILE_DELETED:
211 case EFI_FILE_DATA_VALID:
212 case EFI_FILE_MARKED_FOR_UPDATE:
213 DataCheckSum = FFS_FIXED_CHECKSUM;
214 FileLength = *(UINT32 *)(FfsHeader->Size) & 0x00FFFFFF;
215 if ((FfsHeader->Attributes & FFS_ATTRIB_CHECKSUM) == FFS_ATTRIB_CHECKSUM) {
216 DataCheckSum = CalculateCheckSum8 ((CONST UINT8 *)FfsHeader + sizeof(EFI_FFS_FILE_HEADER), FileLength - sizeof(EFI_FFS_FILE_HEADER));
217 }
218 if (FfsHeader->IntegrityCheck.Checksum.File == DataCheckSum) {
219 return TRUE;
220 }
221
222 default:
223 return FALSE;
224 }
225 }
226
227