1 /** @file 2 Module produce UC2 on top of UC. 3 4 UEFI 2.1 specification supersedes Inte's EFI Specification 1.10. 5 EFI_UNICODE_COLLATION_PROTOCOL defined in Inte's EFI Specification 1.10 is replaced by 6 EFI_UNICODE_COLLATION_PROTOCOL in UEFI 2.1. 7 This module produces UC2 on top of UC. This module is used on platform when both of 8 these two conditions are true: 9 1) EFI 1.10 module producing UC present 10 2) And the rest of modules on the platform consume UC2 11 12 Copyright (c) 2006 - 2011, Intel Corporation. All rights reserved.<BR> 13 This program and the accompanying materials 14 are licensed and made available under the terms and conditions of the BSD License 15 which accompanies this distribution. The full text of the license may be found at 16 http://opensource.org/licenses/bsd-license.php 17 18 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 19 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 20 Module Name: 21 22 **/ 23 24 #include <PiDxe.h> 25 #include <Protocol/UnicodeCollation.h> 26 #include <Library/BaseLib.h> 27 #include <Library/DebugLib.h> 28 #include <Library/UefiBootServicesTableLib.h> 29 #include <Library/UefiDriverEntryPoint.h> 30 #include <Library/UefiLib.h> 31 #include <Library/MemoryAllocationLib.h> 32 #include <Library/HiiLib.h> 33 #include <Library/BaseMemoryLib.h> 34 #include <Library/LanguageLib.h> 35 36 /** 37 Performs a case-insensitive comparison of two Null-terminated strings. 38 39 @param This Protocol instance pointer. 40 @param Str1 A pointer to a Null-terminated string. 41 @param Str2 A pointer to a Null-terminated string. 42 43 @retval 0 Str1 is equivalent to Str2 44 @retval > 0 Str1 is lexically greater than Str2 45 @retval < 0 Str1 is lexically less than Str2 46 47 **/ 48 INTN 49 EFIAPI 50 StriColl ( 51 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 52 IN CHAR16 *Str1, 53 IN CHAR16 *Str2 54 ); 55 56 /** 57 Converts all the characters in a Null-terminated string to 58 lower case characters. 59 60 @param This Protocol instance pointer. 61 @param Str A pointer to a Null-terminated string. 62 63 **/ 64 VOID 65 EFIAPI 66 StrLwr ( 67 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 68 IN OUT CHAR16 *Str 69 ); 70 71 /** 72 Converts all the characters in a Null-terminated string to upper 73 case characters. 74 75 @param This Protocol instance pointer. 76 @param Str A pointer to a Null-terminated string. 77 78 **/ 79 VOID 80 EFIAPI 81 StrUpr ( 82 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 83 IN OUT CHAR16 *Str 84 ); 85 86 /** 87 Performs a case-insensitive comparison of a Null-terminated 88 pattern string and a Null-terminated string. 89 90 @param This Protocol instance pointer. 91 @param String A pointer to a Null-terminated string. 92 @param Pattern A pointer to a Null-terminated pattern string. 93 94 @retval TRUE Pattern was found in String. 95 @retval FALSE Pattern was not found in String. 96 97 **/ 98 BOOLEAN 99 EFIAPI 100 MetaiMatch ( 101 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 102 IN CHAR16 *String, 103 IN CHAR16 *Pattern 104 ); 105 106 /** 107 Converts an 8.3 FAT file name in an OEM character set to a Null-terminated string. 108 109 @param This Protocol instance pointer. 110 @param FatSize The size of the string Fat in bytes. 111 @param Fat A pointer to a Null-terminated string that contains an 8.3 file 112 name using an OEM character set. 113 @param String A pointer to a Null-terminated string. The string must 114 be preallocated to hold FatSize characters. 115 116 **/ 117 VOID 118 EFIAPI 119 FatToStr ( 120 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 121 IN UINTN FatSize, 122 IN CHAR8 *Fat, 123 OUT CHAR16 *String 124 ); 125 126 /** 127 Converts a Null-terminated string to legal characters in a FAT 128 filename using an OEM character set. 129 130 @param This Protocol instance pointer. 131 @param String A pointer to a Null-terminated string. The string must 132 be preallocated to hold FatSize characters. 133 @param FatSize The size of the string Fat in bytes. 134 @param Fat A pointer to a Null-terminated string that contains an 8.3 file 135 name using an OEM character set. 136 137 @retval TRUE Fat is a Long File Name 138 @retval FALSE Fat is an 8.3 file name 139 140 **/ 141 BOOLEAN 142 EFIAPI 143 StrToFat ( 144 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 145 IN CHAR16 *String, 146 IN UINTN FatSize, 147 OUT CHAR8 *Fat 148 ); 149 150 #define UC2_PRIVATE_DATA_SIGNATURE SIGNATURE_32 ('_', 'U', 'C', '2') 151 152 typedef struct { 153 UINT32 Signature; 154 EFI_UNICODE_COLLATION_PROTOCOL Uc2; 155 EFI_UNICODE_COLLATION_PROTOCOL *Uc; 156 } UC2_PRIVATE_DATA; 157 158 #define UC2_PRIVATE_DATA_FROM_THIS(a) CR (a, UC2_PRIVATE_DATA, Uc2, UC2_PRIVATE_DATA_SIGNATURE) 159 160 // 161 // Firmware Volume Protocol template 162 // 163 EFI_EVENT mUc2Registration; 164 165 UC2_PRIVATE_DATA gUC2PrivateDataTemplate = { 166 UC2_PRIVATE_DATA_SIGNATURE, 167 { 168 StriColl, 169 MetaiMatch, 170 StrLwr, 171 StrUpr, 172 FatToStr, 173 StrToFat, 174 NULL 175 }, 176 NULL 177 }; 178 179 // 180 // Module globals 181 // 182 /** 183 This notification function is invoked when an instance of the 184 EFI_UNICODE_COLLATION_PROTOCOL is produced. It installs another instance of the 185 EFI_UNICODE_COLLATION_PROTOCOL2 on the same handle. 186 187 @param Event The event that occured 188 @param Context Context of event. Not used in this nofication function. 189 190 **/ 191 VOID 192 EFIAPI 193 UcNotificationEvent ( 194 IN EFI_EVENT Event, 195 IN VOID *Context 196 ) 197 { 198 EFI_STATUS Status; 199 UINTN BufferSize; 200 EFI_HANDLE Handle; 201 UC2_PRIVATE_DATA *Private; 202 EFI_UNICODE_COLLATION_PROTOCOL *Uc2; 203 204 while (TRUE) { 205 BufferSize = sizeof (Handle); 206 Status = gBS->LocateHandle ( 207 ByRegisterNotify, 208 &gEfiUnicodeCollationProtocolGuid, 209 mUc2Registration, 210 &BufferSize, 211 &Handle 212 ); 213 if (EFI_ERROR (Status)) { 214 // 215 // Exit Path of While Loop.... 216 // 217 break; 218 } 219 220 // 221 // Skip this handle if the Firmware Volume Protocol is already installed 222 // 223 Status = gBS->HandleProtocol ( 224 Handle, 225 &gEfiUnicodeCollation2ProtocolGuid, 226 (VOID **)&Uc2 227 ); 228 if (!EFI_ERROR (Status)) { 229 continue; 230 } 231 232 // 233 // Allocate private data structure 234 // 235 Private = AllocateCopyPool (sizeof (UC2_PRIVATE_DATA), &gUC2PrivateDataTemplate); 236 if (Private == NULL) { 237 continue; 238 } 239 240 // 241 // Retrieve the UC Protocol 242 // 243 Status = gBS->HandleProtocol ( 244 Handle, 245 &gEfiUnicodeCollationProtocolGuid, 246 (VOID **)&Private->Uc 247 ); 248 ASSERT_EFI_ERROR (Status); 249 250 // 251 // Fill in rest of private data structure 252 // 253 Private->Uc2.SupportedLanguages = ConvertLanguagesIso639ToRfc4646 (Private->Uc->SupportedLanguages); 254 if (Private->Uc2.SupportedLanguages != NULL) { 255 256 // 257 // Install UC2 Protocol onto same handle 258 // 259 Status = gBS->InstallMultipleProtocolInterfaces ( 260 &Handle, 261 &gEfiUnicodeCollation2ProtocolGuid, 262 &Private->Uc2, 263 NULL 264 ); 265 ASSERT_EFI_ERROR (Status); 266 } 267 } 268 } 269 270 271 /** 272 The user Entry Point for DXE driver. The user code starts with this function 273 as the real entry point for the image goes into a library that calls this 274 function. 275 276 @param[in] ImageHandle The firmware allocated handle for the EFI image. 277 @param[in] SystemTable A pointer to the EFI System Table. 278 279 @retval EFI_SUCCESS The entry point is executed successfully. 280 @retval other Some error occurs when executing this entry point. 281 282 **/ 283 EFI_STATUS 284 EFIAPI 285 InitializeUC2 ( 286 IN EFI_HANDLE ImageHandle, 287 IN EFI_SYSTEM_TABLE *SystemTable 288 ) 289 { 290 EfiCreateProtocolNotifyEvent ( 291 &gEfiUnicodeCollationProtocolGuid, 292 TPL_CALLBACK, 293 UcNotificationEvent, 294 NULL, 295 &mUc2Registration 296 ); 297 return EFI_SUCCESS; 298 } 299 300 301 /** 302 Performs a case-insensitive comparison of two Null-terminated strings. 303 304 @param This Protocol instance pointer. 305 @param Str1 A pointer to a Null-terminated string. 306 @param Str2 A pointer to a Null-terminated string. 307 308 @retval 0 Str1 is equivalent to Str2 309 @retval > 0 Str1 is lexically greater than Str2 310 @retval < 0 Str1 is lexically less than Str2 311 312 **/ 313 INTN 314 EFIAPI 315 StriColl ( 316 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 317 IN CHAR16 *Str1, 318 IN CHAR16 *Str2 319 ) 320 { 321 UC2_PRIVATE_DATA *Private; 322 323 Private = UC2_PRIVATE_DATA_FROM_THIS (This); 324 325 return Private->Uc->StriColl (Private->Uc, Str1, Str2); 326 } 327 328 329 /** 330 Converts all the characters in a Null-terminated string to 331 lower case characters. 332 333 @param This Protocol instance pointer. 334 @param Str A pointer to a Null-terminated string. 335 336 **/ 337 VOID 338 EFIAPI 339 StrLwr ( 340 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 341 IN OUT CHAR16 *Str 342 ) 343 { 344 UC2_PRIVATE_DATA *Private; 345 346 Private = UC2_PRIVATE_DATA_FROM_THIS (This); 347 348 Private->Uc->StrLwr (Private->Uc, Str); 349 } 350 351 352 /** 353 Converts all the characters in a Null-terminated string to upper 354 case characters. 355 356 @param This Protocol instance pointer. 357 @param Str A pointer to a Null-terminated string. 358 359 **/ 360 VOID 361 EFIAPI 362 StrUpr ( 363 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 364 IN OUT CHAR16 *Str 365 ) 366 { 367 UC2_PRIVATE_DATA *Private; 368 369 Private = UC2_PRIVATE_DATA_FROM_THIS (This); 370 371 Private->Uc->StrUpr (Private->Uc, Str); 372 } 373 374 /** 375 Performs a case-insensitive comparison of a Null-terminated 376 pattern string and a Null-terminated string. 377 378 @param This Protocol instance pointer. 379 @param String A pointer to a Null-terminated string. 380 @param Pattern A pointer to a Null-terminated pattern string. 381 382 @retval TRUE Pattern was found in String. 383 @retval FALSE Pattern was not found in String. 384 385 **/ 386 BOOLEAN 387 EFIAPI 388 MetaiMatch ( 389 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 390 IN CHAR16 *String, 391 IN CHAR16 *Pattern 392 ) 393 { 394 UC2_PRIVATE_DATA *Private; 395 396 Private = UC2_PRIVATE_DATA_FROM_THIS (This); 397 398 return Private->Uc->MetaiMatch (Private->Uc, String, Pattern); 399 } 400 401 402 /** 403 Converts an 8.3 FAT file name in an OEM character set to a Null-terminated string. 404 405 @param This Protocol instance pointer. 406 @param FatSize The size of the string Fat in bytes. 407 @param Fat A pointer to a Null-terminated string that contains an 8.3 file 408 name using an 8-bit OEM character set. 409 @param String A pointer to a Null-terminated string. The string must 410 be preallocated to hold FatSize characters. 411 412 **/ 413 VOID 414 EFIAPI 415 FatToStr ( 416 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 417 IN UINTN FatSize, 418 IN CHAR8 *Fat, 419 OUT CHAR16 *String 420 ) 421 { 422 UC2_PRIVATE_DATA *Private; 423 424 Private = UC2_PRIVATE_DATA_FROM_THIS (This); 425 426 Private->Uc->FatToStr (Private->Uc, FatSize, Fat, String); 427 } 428 429 430 /** 431 Converts a Null-terminated string to legal characters in a FAT 432 filename using an OEM character set. 433 434 @param This Protocol instance pointer. 435 @param String A pointer to a Null-terminated string. The string must 436 be preallocated to hold FatSize characters. 437 @param FatSize The size of the string Fat in bytes. 438 @param Fat A pointer to a Null-terminated string that contains an 8.3 file 439 name using an OEM character set. 440 441 @retval TRUE Fat is a Long File Name 442 @retval FALSE Fat is an 8.3 file name 443 444 **/ 445 BOOLEAN 446 EFIAPI 447 StrToFat ( 448 IN EFI_UNICODE_COLLATION_PROTOCOL *This, 449 IN CHAR16 *String, 450 IN UINTN FatSize, 451 OUT CHAR8 *Fat 452 ) 453 { 454 UC2_PRIVATE_DATA *Private; 455 456 Private = UC2_PRIVATE_DATA_FROM_THIS (This); 457 458 return Private->Uc->StrToFat (Private->Uc, String, FatSize, Fat); 459 } 460 461