1 /*- 2 * Copyright (c) 2017 Netflix, Inc. 3 * 4 * Redistribution and use in source and binary forms, with or without 5 * modification, are permitted provided that the following conditions 6 * are met: 7 * 1. Redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer. 9 * 2. Redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution. 12 * 13 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 14 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 15 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 16 * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 17 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 18 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 19 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 20 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 21 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 22 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 23 * SUCH DAMAGE. 24 */ 25 26 /* 27 * Routines to format EFI_DEVICE_PATHs from the UEFI standard. Much of 28 * this file is taken from EDK2 and rototilled. 29 */ 30 31 #include <sys/cdefs.h> 32 #include <ctype.h> 33 #include <efivar.h> 34 #include <stdio.h> 35 #include <string.h> 36 #include <wchar.h> 37 38 #include "efichar.h" 39 40 #include "efi-osdep.h" 41 #include "efivar-dp.h" 42 43 #include "uefi-dplib.h" 44 45 /* XXX STUBS -- this stuff doesn't work yet */ 46 #define StrToIpv4Address(str, unk, ipv4ptr, unk2) (void)(str) 47 #define StrToIpv6Address(str, unk, ipv6ptr, unk2) (void)(str) 48 49 /* 50 * OK. Now this is evil. Can't typedef it again. Sure beats changing them all. 51 * Since we're doing it all as narrow characters since wchar_t can't be used on 52 * FreeBSD and CHAR16 strings generally aren't a good fit. Since this parsing 53 * doesn't need Unicode for anything, this works out well. 54 */ 55 #define CHAR16 char 56 57 /* 58 * Taken from MdePkg/Library/UefiDevicePathLib/DevicePathFromText.c 59 */ 60 61 /** @file 62 DevicePathFromText protocol as defined in the UEFI 2.0 specification. 63 64 Copyright (c) 2013 - 2018, Intel Corporation. All rights reserved.<BR> 65 SPDX-License-Identifier: BSD-2-Clause-Patent 66 67 **/ 68 69 // #include "UefiDevicePathLib.h" 70 71 /** 72 73 Duplicates a string. 74 75 @param Src Source string. 76 77 @return The duplicated string. 78 79 **/ 80 static 81 CHAR16 * 82 UefiDevicePathLibStrDuplicate ( 83 IN CONST CHAR16 *Src 84 ) 85 { 86 return AllocateCopyPool (StrSize (Src), Src); 87 } 88 89 /** 90 91 Get parameter in a pair of parentheses follow the given node name. 92 For example, given the "Pci(0,1)" and NodeName "Pci", it returns "0,1". 93 94 @param Str Device Path Text. 95 @param NodeName Name of the node. 96 97 @return Parameter text for the node. 98 99 **/ 100 static 101 CHAR16 * 102 GetParamByNodeName ( 103 IN CHAR16 *Str, 104 IN const CHAR16 *NodeName 105 ) 106 { 107 CHAR16 *ParamStr; 108 CHAR16 *StrPointer; 109 UINTN NodeNameLength; 110 UINTN ParameterLength; 111 112 // 113 // Check whether the node name matchs 114 // 115 NodeNameLength = StrLen (NodeName); 116 if (StrnCmp (Str, NodeName, NodeNameLength) != 0) { 117 return NULL; 118 } 119 120 ParamStr = Str + NodeNameLength; 121 if (!IS_LEFT_PARENTH (*ParamStr)) { 122 return NULL; 123 } 124 125 // 126 // Skip the found '(' and find first occurrence of ')' 127 // 128 ParamStr++; 129 ParameterLength = 0; 130 StrPointer = ParamStr; 131 while (!IS_NULL (*StrPointer)) { 132 if (IS_RIGHT_PARENTH (*StrPointer)) { 133 break; 134 } 135 136 StrPointer++; 137 ParameterLength++; 138 } 139 140 if (IS_NULL (*StrPointer)) { 141 // 142 // ')' not found 143 // 144 return NULL; 145 } 146 147 ParamStr = AllocateCopyPool ((ParameterLength + 1) * sizeof (CHAR16), ParamStr); 148 if (ParamStr == NULL) { 149 return NULL; 150 } 151 152 // 153 // Terminate the parameter string 154 // 155 ParamStr[ParameterLength] = '\0'; 156 157 return ParamStr; 158 } 159 160 /** 161 Gets current sub-string from a string list, before return 162 the list header is moved to next sub-string. The sub-string is separated 163 by the specified character. For example, the separator is ',', the string 164 list is "2,0,3", it returns "2", the remain list move to "0,3" 165 166 @param List A string list separated by the specified separator 167 @param Separator The separator character 168 169 @return A pointer to the current sub-string 170 171 **/ 172 static 173 CHAR16 * 174 SplitStr ( 175 IN OUT CHAR16 **List, 176 IN CHAR16 Separator 177 ) 178 { 179 CHAR16 *Str; 180 CHAR16 *ReturnStr; 181 182 Str = *List; 183 ReturnStr = Str; 184 185 if (IS_NULL (*Str)) { 186 return ReturnStr; 187 } 188 189 // 190 // Find first occurrence of the separator 191 // 192 while (!IS_NULL (*Str)) { 193 if (*Str == Separator) { 194 break; 195 } 196 197 Str++; 198 } 199 200 if (*Str == Separator) { 201 // 202 // Find a sub-string, terminate it 203 // 204 *Str = '\0'; 205 Str++; 206 } 207 208 // 209 // Move to next sub-string 210 // 211 *List = Str; 212 213 return ReturnStr; 214 } 215 216 /** 217 Gets the next parameter string from the list. 218 219 @param List A string list separated by the specified separator 220 221 @return A pointer to the current sub-string 222 223 **/ 224 static 225 CHAR16 * 226 GetNextParamStr ( 227 IN OUT CHAR16 **List 228 ) 229 { 230 // 231 // The separator is comma 232 // 233 return SplitStr (List, ','); 234 } 235 236 /** 237 Get one device node from entire device path text. 238 239 @param DevicePath On input, the current Device Path node; on output, the next device path node 240 @param IsInstanceEnd This node is the end of a device path instance 241 242 @return A device node text or NULL if no more device node available 243 244 **/ 245 static 246 CHAR16 * 247 GetNextDeviceNodeStr ( 248 IN OUT CHAR16 **DevicePath, 249 OUT BOOLEAN *IsInstanceEnd 250 ) 251 { 252 CHAR16 *Str; 253 CHAR16 *ReturnStr; 254 UINTN ParenthesesStack; 255 256 Str = *DevicePath; 257 if (IS_NULL (*Str)) { 258 return NULL; 259 } 260 261 // 262 // Skip the leading '/', '(', ')' and ',' 263 // 264 while (!IS_NULL (*Str)) { 265 if (!IS_SLASH (*Str) && 266 !IS_COMMA (*Str) && 267 !IS_LEFT_PARENTH (*Str) && 268 !IS_RIGHT_PARENTH (*Str)) 269 { 270 break; 271 } 272 273 Str++; 274 } 275 276 ReturnStr = Str; 277 278 // 279 // Scan for the separator of this device node, '/' or ',' 280 // 281 ParenthesesStack = 0; 282 while (!IS_NULL (*Str)) { 283 if ((IS_COMMA (*Str) || IS_SLASH (*Str)) && (ParenthesesStack == 0)) { 284 break; 285 } 286 287 if (IS_LEFT_PARENTH (*Str)) { 288 ParenthesesStack++; 289 } else if (IS_RIGHT_PARENTH (*Str)) { 290 ParenthesesStack--; 291 } 292 293 Str++; 294 } 295 296 if (ParenthesesStack != 0) { 297 // 298 // The '(' doesn't pair with ')', invalid device path text 299 // 300 return NULL; 301 } 302 303 if (IS_COMMA (*Str)) { 304 *IsInstanceEnd = TRUE; 305 *Str = '\0'; 306 Str++; 307 } else { 308 *IsInstanceEnd = FALSE; 309 if (!IS_NULL (*Str)) { 310 *Str = '\0'; 311 Str++; 312 } 313 } 314 315 *DevicePath = Str; 316 317 return ReturnStr; 318 } 319 320 321 #ifndef __FreeBSD__ 322 /** 323 Return whether the integer string is a hex string. 324 325 @param Str The integer string 326 327 @retval TRUE Hex string 328 @retval FALSE Decimal string 329 330 **/ 331 static 332 BOOLEAN 333 IsHexStr ( 334 IN CHAR16 *Str 335 ) 336 { 337 // 338 // skip preceeding white space 339 // 340 while (*Str == ' ') { 341 Str++; 342 } 343 344 // 345 // skip preceeding zeros 346 // 347 while (*Str == '0') { 348 Str++; 349 } 350 351 return (BOOLEAN)(*Str == 'x' || *Str == 'X'); 352 } 353 354 /** 355 356 Convert integer string to uint. 357 358 @param Str The integer string. If leading with "0x" or "0X", it's hexadecimal. 359 360 @return A UINTN value represented by Str 361 362 **/ 363 static 364 UINTN 365 Strtoi ( 366 IN CHAR16 *Str 367 ) 368 { 369 if (IsHexStr (Str)) { 370 return StrHexToUintn (Str); 371 } else { 372 return StrDecimalToUintn (Str); 373 } 374 } 375 376 /** 377 378 Convert integer string to 64 bit data. 379 380 @param Str The integer string. If leading with "0x" or "0X", it's hexadecimal. 381 @param Data A pointer to the UINT64 value represented by Str 382 383 **/ 384 static 385 VOID 386 Strtoi64 ( 387 IN CHAR16 *Str, 388 OUT UINT64 *Data 389 ) 390 { 391 if (IsHexStr (Str)) { 392 *Data = StrHexToUint64 (Str); 393 } else { 394 *Data = StrDecimalToUint64 (Str); 395 } 396 } 397 #endif 398 399 /** 400 Converts a Unicode string to ASCII string. 401 402 @param Str The equivalent Unicode string 403 @param AsciiStr On input, it points to destination ASCII string buffer; on output, it points 404 to the next ASCII string next to it 405 406 **/ 407 static 408 VOID 409 StrToAscii ( 410 IN CHAR16 *Str, 411 IN OUT CHAR8 **AsciiStr 412 ) 413 { 414 CHAR8 *Dest; 415 416 Dest = *AsciiStr; 417 while (!IS_NULL (*Str)) { 418 *(Dest++) = (CHAR8)*(Str++); 419 } 420 421 *Dest = 0; 422 423 // 424 // Return the string next to it 425 // 426 *AsciiStr = Dest + 1; 427 } 428 429 /** 430 Converts a generic text device path node to device path structure. 431 432 @param Type The type of the device path node. 433 @param TextDeviceNode The input text device path node. 434 435 @return A pointer to device path structure. 436 **/ 437 static 438 EFI_DEVICE_PATH_PROTOCOL * 439 DevPathFromTextGenericPath ( 440 IN UINT8 Type, 441 IN CHAR16 *TextDeviceNode 442 ) 443 { 444 EFI_DEVICE_PATH_PROTOCOL *Node; 445 CHAR16 *SubtypeStr; 446 CHAR16 *DataStr; 447 UINTN DataLength; 448 449 SubtypeStr = GetNextParamStr (&TextDeviceNode); 450 DataStr = GetNextParamStr (&TextDeviceNode); 451 452 if (DataStr == NULL) { 453 DataLength = 0; 454 } else { 455 DataLength = StrLen (DataStr) / 2; 456 } 457 458 Node = CreateDeviceNode ( 459 Type, 460 (UINT8)Strtoi (SubtypeStr), 461 (UINT16)(sizeof (EFI_DEVICE_PATH_PROTOCOL) + DataLength) 462 ); 463 464 if (Node != NULL) { 465 StrHexToBytes (DataStr, DataLength * 2, (UINT8 *)(Node + 1), DataLength); 466 } 467 468 return Node; 469 } 470 471 /** 472 Converts a generic text device path node to device path structure. 473 474 @param TextDeviceNode The input Text device path node. 475 476 @return A pointer to device path structure. 477 478 **/ 479 static 480 EFI_DEVICE_PATH_PROTOCOL * 481 DevPathFromTextPath ( 482 IN CHAR16 *TextDeviceNode 483 ) 484 { 485 CHAR16 *TypeStr; 486 487 TypeStr = GetNextParamStr (&TextDeviceNode); 488 489 return DevPathFromTextGenericPath ((UINT8)Strtoi (TypeStr), TextDeviceNode); 490 } 491 492 /** 493 Converts a generic hardware text device path node to Hardware device path structure. 494 495 @param TextDeviceNode The input Text device path node. 496 497 @return A pointer to Hardware device path structure. 498 499 **/ 500 static 501 EFI_DEVICE_PATH_PROTOCOL * 502 DevPathFromTextHardwarePath ( 503 IN CHAR16 *TextDeviceNode 504 ) 505 { 506 return DevPathFromTextGenericPath (HARDWARE_DEVICE_PATH, TextDeviceNode); 507 } 508 509 /** 510 Converts a text device path node to Hardware PCI device path structure. 511 512 @param TextDeviceNode The input Text device path node. 513 514 @return A pointer to Hardware PCI device path structure. 515 516 **/ 517 static 518 EFI_DEVICE_PATH_PROTOCOL * 519 DevPathFromTextPci ( 520 IN CHAR16 *TextDeviceNode 521 ) 522 { 523 CHAR16 *FunctionStr; 524 CHAR16 *DeviceStr; 525 PCI_DEVICE_PATH *Pci; 526 527 DeviceStr = GetNextParamStr (&TextDeviceNode); 528 FunctionStr = GetNextParamStr (&TextDeviceNode); 529 Pci = (PCI_DEVICE_PATH *)CreateDeviceNode ( 530 HARDWARE_DEVICE_PATH, 531 HW_PCI_DP, 532 (UINT16)sizeof (PCI_DEVICE_PATH) 533 ); 534 535 if (Pci != NULL) { 536 Pci->Function = (UINT8)Strtoi (FunctionStr); 537 Pci->Device = (UINT8)Strtoi (DeviceStr); 538 } 539 540 return (EFI_DEVICE_PATH_PROTOCOL *)Pci; 541 } 542 543 /** 544 Converts a text device path node to Hardware PC card device path structure. 545 546 @param TextDeviceNode The input Text device path node. 547 548 @return A pointer to Hardware PC card device path structure. 549 550 **/ 551 static 552 EFI_DEVICE_PATH_PROTOCOL * 553 DevPathFromTextPcCard ( 554 IN CHAR16 *TextDeviceNode 555 ) 556 { 557 CHAR16 *FunctionNumberStr; 558 PCCARD_DEVICE_PATH *Pccard; 559 560 FunctionNumberStr = GetNextParamStr (&TextDeviceNode); 561 Pccard = (PCCARD_DEVICE_PATH *)CreateDeviceNode ( 562 HARDWARE_DEVICE_PATH, 563 HW_PCCARD_DP, 564 (UINT16)sizeof (PCCARD_DEVICE_PATH) 565 ); 566 567 if (Pccard != NULL) { 568 Pccard->FunctionNumber = (UINT8)Strtoi (FunctionNumberStr); 569 } 570 571 return (EFI_DEVICE_PATH_PROTOCOL *)Pccard; 572 } 573 574 /** 575 Converts a text device path node to Hardware memory map device path structure. 576 577 @param TextDeviceNode The input Text device path node. 578 579 @return A pointer to Hardware memory map device path structure. 580 581 **/ 582 static 583 EFI_DEVICE_PATH_PROTOCOL * 584 DevPathFromTextMemoryMapped ( 585 IN CHAR16 *TextDeviceNode 586 ) 587 { 588 CHAR16 *MemoryTypeStr; 589 CHAR16 *StartingAddressStr; 590 CHAR16 *EndingAddressStr; 591 MEMMAP_DEVICE_PATH *MemMap; 592 593 MemoryTypeStr = GetNextParamStr (&TextDeviceNode); 594 StartingAddressStr = GetNextParamStr (&TextDeviceNode); 595 EndingAddressStr = GetNextParamStr (&TextDeviceNode); 596 MemMap = (MEMMAP_DEVICE_PATH *)CreateDeviceNode ( 597 HARDWARE_DEVICE_PATH, 598 HW_MEMMAP_DP, 599 (UINT16)sizeof (MEMMAP_DEVICE_PATH) 600 ); 601 602 if (MemMap != NULL) { 603 MemMap->MemoryType = (UINT32)Strtoi (MemoryTypeStr); 604 Strtoi64 (StartingAddressStr, &MemMap->StartingAddress); 605 Strtoi64 (EndingAddressStr, &MemMap->EndingAddress); 606 } 607 608 return (EFI_DEVICE_PATH_PROTOCOL *)MemMap; 609 } 610 611 /** 612 Converts a text device path node to Vendor device path structure based on the input Type 613 and SubType. 614 615 @param TextDeviceNode The input Text device path node. 616 @param Type The type of device path node. 617 @param SubType The subtype of device path node. 618 619 @return A pointer to the newly-created Vendor device path structure. 620 621 **/ 622 static 623 EFI_DEVICE_PATH_PROTOCOL * 624 ConvertFromTextVendor ( 625 IN CHAR16 *TextDeviceNode, 626 IN UINT8 Type, 627 IN UINT8 SubType 628 ) 629 { 630 CHAR16 *GuidStr; 631 CHAR16 *DataStr; 632 UINTN Length; 633 VENDOR_DEVICE_PATH *Vendor; 634 635 GuidStr = GetNextParamStr (&TextDeviceNode); 636 637 DataStr = GetNextParamStr (&TextDeviceNode); 638 Length = StrLen (DataStr); 639 // 640 // Two hex characters make up 1 buffer byte 641 // 642 Length = (Length + 1) / 2; 643 644 Vendor = (VENDOR_DEVICE_PATH *)CreateDeviceNode ( 645 Type, 646 SubType, 647 (UINT16)(sizeof (VENDOR_DEVICE_PATH) + Length) 648 ); 649 650 if (Vendor != NULL) { 651 StrToGuid (GuidStr, &Vendor->Guid); 652 StrHexToBytes (DataStr, Length * 2, (UINT8 *)(Vendor + 1), Length); 653 } 654 655 return (EFI_DEVICE_PATH_PROTOCOL *)Vendor; 656 } 657 658 /** 659 Converts a text device path node to Vendor Hardware device path structure. 660 661 @param TextDeviceNode The input Text device path node. 662 663 @return A pointer to the newly-created Vendor Hardware device path structure. 664 665 **/ 666 static 667 EFI_DEVICE_PATH_PROTOCOL * 668 DevPathFromTextVenHw ( 669 IN CHAR16 *TextDeviceNode 670 ) 671 { 672 return ConvertFromTextVendor ( 673 TextDeviceNode, 674 HARDWARE_DEVICE_PATH, 675 HW_VENDOR_DP 676 ); 677 } 678 679 /** 680 Converts a text device path node to Hardware Controller device path structure. 681 682 @param TextDeviceNode The input Text device path node. 683 684 @return A pointer to the newly-created Hardware Controller device path structure. 685 686 **/ 687 static 688 EFI_DEVICE_PATH_PROTOCOL * 689 DevPathFromTextCtrl ( 690 IN CHAR16 *TextDeviceNode 691 ) 692 { 693 CHAR16 *ControllerStr; 694 CONTROLLER_DEVICE_PATH *Controller; 695 696 ControllerStr = GetNextParamStr (&TextDeviceNode); 697 Controller = (CONTROLLER_DEVICE_PATH *)CreateDeviceNode ( 698 HARDWARE_DEVICE_PATH, 699 HW_CONTROLLER_DP, 700 (UINT16)sizeof (CONTROLLER_DEVICE_PATH) 701 ); 702 703 if (Controller != NULL) { 704 Controller->ControllerNumber = (UINT32)Strtoi (ControllerStr); 705 } 706 707 return (EFI_DEVICE_PATH_PROTOCOL *)Controller; 708 } 709 710 /** 711 Converts a text device path node to BMC device path structure. 712 713 @param TextDeviceNode The input Text device path node. 714 715 @return A pointer to the newly-created BMC device path structure. 716 717 **/ 718 static 719 EFI_DEVICE_PATH_PROTOCOL * 720 DevPathFromTextBmc ( 721 IN CHAR16 *TextDeviceNode 722 ) 723 { 724 CHAR16 *InterfaceTypeStr; 725 CHAR16 *BaseAddressStr; 726 BMC_DEVICE_PATH *BmcDp; 727 728 InterfaceTypeStr = GetNextParamStr (&TextDeviceNode); 729 BaseAddressStr = GetNextParamStr (&TextDeviceNode); 730 BmcDp = (BMC_DEVICE_PATH *)CreateDeviceNode ( 731 HARDWARE_DEVICE_PATH, 732 HW_BMC_DP, 733 (UINT16)sizeof (BMC_DEVICE_PATH) 734 ); 735 736 if (BmcDp != NULL) { 737 BmcDp->InterfaceType = (UINT8)Strtoi (InterfaceTypeStr); 738 WriteUnaligned64 ( 739 (UINT64 *)(&BmcDp->BaseAddress), 740 StrHexToUint64 (BaseAddressStr) 741 ); 742 } 743 744 return (EFI_DEVICE_PATH_PROTOCOL *)BmcDp; 745 } 746 747 /** 748 Converts a generic ACPI text device path node to ACPI device path structure. 749 750 @param TextDeviceNode The input Text device path node. 751 752 @return A pointer to ACPI device path structure. 753 754 **/ 755 static 756 EFI_DEVICE_PATH_PROTOCOL * 757 DevPathFromTextAcpiPath ( 758 IN CHAR16 *TextDeviceNode 759 ) 760 { 761 return DevPathFromTextGenericPath (ACPI_DEVICE_PATH, TextDeviceNode); 762 } 763 764 /** 765 Converts a string to EisaId. 766 767 @param Text The input string. 768 769 @return UINT32 EISA ID. 770 **/ 771 static 772 UINT32 773 EisaIdFromText ( 774 IN CHAR16 *Text 775 ) 776 { 777 return (((Text[0] - 'A' + 1) & 0x1f) << 10) 778 + (((Text[1] - 'A' + 1) & 0x1f) << 5) 779 + (((Text[2] - 'A' + 1) & 0x1f) << 0) 780 + (UINT32)(StrHexToUintn (&Text[3]) << 16) 781 ; 782 } 783 784 /** 785 Converts a text device path node to ACPI HID device path structure. 786 787 @param TextDeviceNode The input Text device path node. 788 789 @return A pointer to the newly-created ACPI HID device path structure. 790 791 **/ 792 static 793 EFI_DEVICE_PATH_PROTOCOL * 794 DevPathFromTextAcpi ( 795 IN CHAR16 *TextDeviceNode 796 ) 797 { 798 CHAR16 *HIDStr; 799 CHAR16 *UIDStr; 800 ACPI_HID_DEVICE_PATH *Acpi; 801 802 HIDStr = GetNextParamStr (&TextDeviceNode); 803 UIDStr = GetNextParamStr (&TextDeviceNode); 804 Acpi = (ACPI_HID_DEVICE_PATH *)CreateDeviceNode ( 805 ACPI_DEVICE_PATH, 806 ACPI_DP, 807 (UINT16)sizeof (ACPI_HID_DEVICE_PATH) 808 ); 809 810 if (Acpi != NULL) { 811 Acpi->HID = EisaIdFromText (HIDStr); 812 Acpi->UID = (UINT32)Strtoi (UIDStr); 813 } 814 815 return (EFI_DEVICE_PATH_PROTOCOL *)Acpi; 816 } 817 818 /** 819 Converts a text device path node to ACPI HID device path structure. 820 821 @param TextDeviceNode The input Text device path node. 822 @param PnPId The input plug and play identification. 823 824 @return A pointer to the newly-created ACPI HID device path structure. 825 826 **/ 827 static 828 EFI_DEVICE_PATH_PROTOCOL * 829 ConvertFromTextAcpi ( 830 IN CHAR16 *TextDeviceNode, 831 IN UINT32 PnPId 832 ) 833 { 834 CHAR16 *UIDStr; 835 ACPI_HID_DEVICE_PATH *Acpi; 836 837 UIDStr = GetNextParamStr (&TextDeviceNode); 838 Acpi = (ACPI_HID_DEVICE_PATH *)CreateDeviceNode ( 839 ACPI_DEVICE_PATH, 840 ACPI_DP, 841 (UINT16)sizeof (ACPI_HID_DEVICE_PATH) 842 ); 843 844 if (Acpi != NULL) { 845 Acpi->HID = EFI_PNP_ID (PnPId); 846 Acpi->UID = (UINT32)Strtoi (UIDStr); 847 } 848 849 return (EFI_DEVICE_PATH_PROTOCOL *)Acpi; 850 } 851 852 /** 853 Converts a text device path node to PCI root device path structure. 854 855 @param TextDeviceNode The input Text device path node. 856 857 @return A pointer to the newly-created PCI root device path structure. 858 859 **/ 860 static 861 EFI_DEVICE_PATH_PROTOCOL * 862 DevPathFromTextPciRoot ( 863 IN CHAR16 *TextDeviceNode 864 ) 865 { 866 return ConvertFromTextAcpi (TextDeviceNode, 0x0a03); 867 } 868 869 /** 870 Converts a text device path node to PCIE root device path structure. 871 872 @param TextDeviceNode The input Text device path node. 873 874 @return A pointer to the newly-created PCIE root device path structure. 875 876 **/ 877 static 878 EFI_DEVICE_PATH_PROTOCOL * 879 DevPathFromTextPcieRoot ( 880 IN CHAR16 *TextDeviceNode 881 ) 882 { 883 return ConvertFromTextAcpi (TextDeviceNode, 0x0a08); 884 } 885 886 /** 887 Converts a text device path node to Floppy device path structure. 888 889 @param TextDeviceNode The input Text device path node. 890 891 @return A pointer to the newly-created Floppy device path structure. 892 893 **/ 894 static 895 EFI_DEVICE_PATH_PROTOCOL * 896 DevPathFromTextFloppy ( 897 IN CHAR16 *TextDeviceNode 898 ) 899 { 900 return ConvertFromTextAcpi (TextDeviceNode, 0x0604); 901 } 902 903 /** 904 Converts a text device path node to Keyboard device path structure. 905 906 @param TextDeviceNode The input Text device path node. 907 908 @return A pointer to the newly-created Keyboard device path structure. 909 910 **/ 911 static 912 EFI_DEVICE_PATH_PROTOCOL * 913 DevPathFromTextKeyboard ( 914 IN CHAR16 *TextDeviceNode 915 ) 916 { 917 return ConvertFromTextAcpi (TextDeviceNode, 0x0301); 918 } 919 920 /** 921 Converts a text device path node to Serial device path structure. 922 923 @param TextDeviceNode The input Text device path node. 924 925 @return A pointer to the newly-created Serial device path structure. 926 927 **/ 928 static 929 EFI_DEVICE_PATH_PROTOCOL * 930 DevPathFromTextSerial ( 931 IN CHAR16 *TextDeviceNode 932 ) 933 { 934 return ConvertFromTextAcpi (TextDeviceNode, 0x0501); 935 } 936 937 /** 938 Converts a text device path node to Parallel Port device path structure. 939 940 @param TextDeviceNode The input Text device path node. 941 942 @return A pointer to the newly-created Parallel Port device path structure. 943 944 **/ 945 static 946 EFI_DEVICE_PATH_PROTOCOL * 947 DevPathFromTextParallelPort ( 948 IN CHAR16 *TextDeviceNode 949 ) 950 { 951 return ConvertFromTextAcpi (TextDeviceNode, 0x0401); 952 } 953 954 /** 955 Converts a text device path node to ACPI extension device path structure. 956 957 @param TextDeviceNode The input Text device path node. 958 959 @return A pointer to the newly-created ACPI extension device path structure. 960 961 **/ 962 static 963 EFI_DEVICE_PATH_PROTOCOL * 964 DevPathFromTextAcpiEx ( 965 IN CHAR16 *TextDeviceNode 966 ) 967 { 968 CHAR16 *HIDStr; 969 CHAR16 *CIDStr; 970 CHAR16 *UIDStr; 971 CHAR16 *HIDSTRStr; 972 CHAR16 *CIDSTRStr; 973 CHAR16 *UIDSTRStr; 974 CHAR8 *AsciiStr; 975 UINT16 Length; 976 ACPI_EXTENDED_HID_DEVICE_PATH *AcpiEx; 977 978 HIDStr = GetNextParamStr (&TextDeviceNode); 979 CIDStr = GetNextParamStr (&TextDeviceNode); 980 UIDStr = GetNextParamStr (&TextDeviceNode); 981 HIDSTRStr = GetNextParamStr (&TextDeviceNode); 982 CIDSTRStr = GetNextParamStr (&TextDeviceNode); 983 UIDSTRStr = GetNextParamStr (&TextDeviceNode); 984 985 Length = (UINT16)(sizeof (ACPI_EXTENDED_HID_DEVICE_PATH) + StrLen (HIDSTRStr) + 1); 986 Length = (UINT16)(Length + StrLen (UIDSTRStr) + 1); 987 Length = (UINT16)(Length + StrLen (CIDSTRStr) + 1); 988 AcpiEx = (ACPI_EXTENDED_HID_DEVICE_PATH *)CreateDeviceNode ( 989 ACPI_DEVICE_PATH, 990 ACPI_EXTENDED_DP, 991 Length 992 ); 993 994 if (AcpiEx != NULL) { 995 AcpiEx->HID = EisaIdFromText (HIDStr); 996 AcpiEx->CID = EisaIdFromText (CIDStr); 997 AcpiEx->UID = (UINT32)Strtoi (UIDStr); 998 999 AsciiStr = (CHAR8 *)((UINT8 *)AcpiEx + sizeof (ACPI_EXTENDED_HID_DEVICE_PATH)); 1000 StrToAscii (HIDSTRStr, &AsciiStr); 1001 StrToAscii (UIDSTRStr, &AsciiStr); 1002 StrToAscii (CIDSTRStr, &AsciiStr); 1003 } 1004 1005 return (EFI_DEVICE_PATH_PROTOCOL *)AcpiEx; 1006 } 1007 1008 /** 1009 Converts a text device path node to ACPI extension device path structure. 1010 1011 @param TextDeviceNode The input Text device path node. 1012 1013 @return A pointer to the newly-created ACPI extension device path structure. 1014 1015 **/ 1016 static 1017 EFI_DEVICE_PATH_PROTOCOL * 1018 DevPathFromTextAcpiExp ( 1019 IN CHAR16 *TextDeviceNode 1020 ) 1021 { 1022 CHAR16 *HIDStr; 1023 CHAR16 *CIDStr; 1024 CHAR16 *UIDSTRStr; 1025 CHAR8 *AsciiStr; 1026 UINT16 Length; 1027 ACPI_EXTENDED_HID_DEVICE_PATH *AcpiEx; 1028 1029 HIDStr = GetNextParamStr (&TextDeviceNode); 1030 CIDStr = GetNextParamStr (&TextDeviceNode); 1031 UIDSTRStr = GetNextParamStr (&TextDeviceNode); 1032 Length = (UINT16)(sizeof (ACPI_EXTENDED_HID_DEVICE_PATH) + StrLen (UIDSTRStr) + 3); 1033 AcpiEx = (ACPI_EXTENDED_HID_DEVICE_PATH *)CreateDeviceNode ( 1034 ACPI_DEVICE_PATH, 1035 ACPI_EXTENDED_DP, 1036 Length 1037 ); 1038 1039 if (AcpiEx == NULL) { 1040 return (EFI_DEVICE_PATH_PROTOCOL *)AcpiEx; 1041 } 1042 1043 AcpiEx->HID = EisaIdFromText (HIDStr); 1044 // 1045 // According to UEFI spec, the CID parameter is optional and has a default value of 0. 1046 // So when the CID parameter is not specified or specified as 0 in the text device node. 1047 // Set the CID to 0 in the ACPI extension device path structure. 1048 // 1049 if ((*CIDStr == '\0') || (*CIDStr == '0')) { 1050 AcpiEx->CID = 0; 1051 } else { 1052 AcpiEx->CID = EisaIdFromText (CIDStr); 1053 } 1054 1055 AcpiEx->UID = 0; 1056 1057 AsciiStr = (CHAR8 *)((UINT8 *)AcpiEx + sizeof (ACPI_EXTENDED_HID_DEVICE_PATH)); 1058 // 1059 // HID string is NULL 1060 // 1061 *AsciiStr = '\0'; 1062 // 1063 // Convert UID string 1064 // 1065 AsciiStr++; 1066 StrToAscii (UIDSTRStr, &AsciiStr); 1067 // 1068 // CID string is NULL 1069 // 1070 *AsciiStr = '\0'; 1071 1072 return (EFI_DEVICE_PATH_PROTOCOL *)AcpiEx; 1073 } 1074 1075 /** 1076 Converts a text device path node to ACPI _ADR device path structure. 1077 1078 @param TextDeviceNode The input Text device path node. 1079 1080 @return A pointer to the newly-created ACPI _ADR device path structure. 1081 1082 **/ 1083 static 1084 EFI_DEVICE_PATH_PROTOCOL * 1085 DevPathFromTextAcpiAdr ( 1086 IN CHAR16 *TextDeviceNode 1087 ) 1088 { 1089 CHAR16 *DisplayDeviceStr; 1090 ACPI_ADR_DEVICE_PATH *AcpiAdr; 1091 UINTN Index; 1092 UINTN Length; 1093 1094 AcpiAdr = (ACPI_ADR_DEVICE_PATH *)CreateDeviceNode ( 1095 ACPI_DEVICE_PATH, 1096 ACPI_ADR_DP, 1097 (UINT16)sizeof (ACPI_ADR_DEVICE_PATH) 1098 ); 1099 if (AcpiAdr == NULL) { 1100 ASSERT (AcpiAdr != NULL); 1101 return (EFI_DEVICE_PATH_PROTOCOL *)AcpiAdr; 1102 } 1103 1104 for (Index = 0; ; Index++) { 1105 DisplayDeviceStr = GetNextParamStr (&TextDeviceNode); 1106 if (IS_NULL (*DisplayDeviceStr)) { 1107 break; 1108 } 1109 1110 if (Index > 0) { 1111 Length = DevicePathNodeLength (AcpiAdr); 1112 AcpiAdr = ReallocatePool ( 1113 Length, 1114 Length + sizeof (UINT32), 1115 AcpiAdr 1116 ); 1117 1118 if (AcpiAdr == NULL) { 1119 ASSERT (AcpiAdr != NULL); 1120 return (EFI_DEVICE_PATH_PROTOCOL *)AcpiAdr; 1121 } 1122 1123 SetDevicePathNodeLength (AcpiAdr, Length + sizeof (UINT32)); 1124 } 1125 1126 (&AcpiAdr->ADR)[Index] = (UINT32)Strtoi (DisplayDeviceStr); 1127 } 1128 1129 return (EFI_DEVICE_PATH_PROTOCOL *)AcpiAdr; 1130 } 1131 1132 /** 1133 Converts a generic messaging text device path node to messaging device path structure. 1134 1135 @param TextDeviceNode The input Text device path node. 1136 1137 @return A pointer to messaging device path structure. 1138 1139 **/ 1140 static 1141 EFI_DEVICE_PATH_PROTOCOL * 1142 DevPathFromTextMsg ( 1143 IN CHAR16 *TextDeviceNode 1144 ) 1145 { 1146 return DevPathFromTextGenericPath (MESSAGING_DEVICE_PATH, TextDeviceNode); 1147 } 1148 1149 /** 1150 Converts a text device path node to Parallel Port device path structure. 1151 1152 @param TextDeviceNode The input Text device path node. 1153 1154 @return A pointer to the newly-created Parallel Port device path structure. 1155 1156 **/ 1157 static 1158 EFI_DEVICE_PATH_PROTOCOL * 1159 DevPathFromTextAta ( 1160 IN CHAR16 *TextDeviceNode 1161 ) 1162 { 1163 CHAR16 *PrimarySecondaryStr; 1164 CHAR16 *SlaveMasterStr; 1165 CHAR16 *LunStr; 1166 ATAPI_DEVICE_PATH *Atapi; 1167 1168 Atapi = (ATAPI_DEVICE_PATH *)CreateDeviceNode ( 1169 MESSAGING_DEVICE_PATH, 1170 MSG_ATAPI_DP, 1171 (UINT16)sizeof (ATAPI_DEVICE_PATH) 1172 ); 1173 1174 if (Atapi == NULL) { 1175 return (EFI_DEVICE_PATH_PROTOCOL *)Atapi; 1176 } 1177 1178 PrimarySecondaryStr = GetNextParamStr (&TextDeviceNode); 1179 SlaveMasterStr = GetNextParamStr (&TextDeviceNode); 1180 LunStr = GetNextParamStr (&TextDeviceNode); 1181 1182 if (StrCmp (PrimarySecondaryStr, "Primary") == 0) { 1183 Atapi->PrimarySecondary = 0; 1184 } else if (StrCmp (PrimarySecondaryStr, "Secondary") == 0) { 1185 Atapi->PrimarySecondary = 1; 1186 } else { 1187 Atapi->PrimarySecondary = (UINT8)Strtoi (PrimarySecondaryStr); 1188 } 1189 1190 if (StrCmp (SlaveMasterStr, "Master") == 0) { 1191 Atapi->SlaveMaster = 0; 1192 } else if (StrCmp (SlaveMasterStr, "Slave") == 0) { 1193 Atapi->SlaveMaster = 1; 1194 } else { 1195 Atapi->SlaveMaster = (UINT8)Strtoi (SlaveMasterStr); 1196 } 1197 1198 Atapi->Lun = (UINT16)Strtoi (LunStr); 1199 1200 return (EFI_DEVICE_PATH_PROTOCOL *)Atapi; 1201 } 1202 1203 /** 1204 Converts a text device path node to SCSI device path structure. 1205 1206 @param TextDeviceNode The input Text device path node. 1207 1208 @return A pointer to the newly-created SCSI device path structure. 1209 1210 **/ 1211 static 1212 EFI_DEVICE_PATH_PROTOCOL * 1213 DevPathFromTextScsi ( 1214 IN CHAR16 *TextDeviceNode 1215 ) 1216 { 1217 CHAR16 *PunStr; 1218 CHAR16 *LunStr; 1219 SCSI_DEVICE_PATH *Scsi; 1220 1221 PunStr = GetNextParamStr (&TextDeviceNode); 1222 LunStr = GetNextParamStr (&TextDeviceNode); 1223 Scsi = (SCSI_DEVICE_PATH *)CreateDeviceNode ( 1224 MESSAGING_DEVICE_PATH, 1225 MSG_SCSI_DP, 1226 (UINT16)sizeof (SCSI_DEVICE_PATH) 1227 ); 1228 1229 if (Scsi != NULL) { 1230 Scsi->Pun = (UINT16)Strtoi (PunStr); 1231 Scsi->Lun = (UINT16)Strtoi (LunStr); 1232 } 1233 1234 return (EFI_DEVICE_PATH_PROTOCOL *)Scsi; 1235 } 1236 1237 /** 1238 Converts a text device path node to Fibre device path structure. 1239 1240 @param TextDeviceNode The input Text device path node. 1241 1242 @return A pointer to the newly-created Fibre device path structure. 1243 1244 **/ 1245 static 1246 EFI_DEVICE_PATH_PROTOCOL * 1247 DevPathFromTextFibre ( 1248 IN CHAR16 *TextDeviceNode 1249 ) 1250 { 1251 CHAR16 *WWNStr; 1252 CHAR16 *LunStr; 1253 FIBRECHANNEL_DEVICE_PATH *Fibre; 1254 1255 WWNStr = GetNextParamStr (&TextDeviceNode); 1256 LunStr = GetNextParamStr (&TextDeviceNode); 1257 Fibre = (FIBRECHANNEL_DEVICE_PATH *)CreateDeviceNode ( 1258 MESSAGING_DEVICE_PATH, 1259 MSG_FIBRECHANNEL_DP, 1260 (UINT16)sizeof (FIBRECHANNEL_DEVICE_PATH) 1261 ); 1262 1263 if (Fibre != NULL) { 1264 Fibre->Reserved = 0; 1265 Strtoi64 (WWNStr, &Fibre->WWN); 1266 Strtoi64 (LunStr, &Fibre->Lun); 1267 } 1268 1269 return (EFI_DEVICE_PATH_PROTOCOL *)Fibre; 1270 } 1271 1272 /** 1273 Converts a text device path node to FibreEx device path structure. 1274 1275 @param TextDeviceNode The input Text device path node. 1276 1277 @return A pointer to the newly-created FibreEx device path structure. 1278 1279 **/ 1280 static 1281 EFI_DEVICE_PATH_PROTOCOL * 1282 DevPathFromTextFibreEx ( 1283 IN CHAR16 *TextDeviceNode 1284 ) 1285 { 1286 CHAR16 *WWNStr; 1287 CHAR16 *LunStr; 1288 FIBRECHANNELEX_DEVICE_PATH *FibreEx; 1289 1290 WWNStr = GetNextParamStr (&TextDeviceNode); 1291 LunStr = GetNextParamStr (&TextDeviceNode); 1292 FibreEx = (FIBRECHANNELEX_DEVICE_PATH *)CreateDeviceNode ( 1293 MESSAGING_DEVICE_PATH, 1294 MSG_FIBRECHANNELEX_DP, 1295 (UINT16)sizeof (FIBRECHANNELEX_DEVICE_PATH) 1296 ); 1297 1298 if (FibreEx != NULL) { 1299 FibreEx->Reserved = 0; 1300 Strtoi64 (WWNStr, (UINT64 *)(&FibreEx->WWN)); 1301 Strtoi64 (LunStr, (UINT64 *)(&FibreEx->Lun)); 1302 1303 *(UINT64 *)(&FibreEx->WWN) = SwapBytes64 (*(UINT64 *)(&FibreEx->WWN)); 1304 *(UINT64 *)(&FibreEx->Lun) = SwapBytes64 (*(UINT64 *)(&FibreEx->Lun)); 1305 } 1306 1307 return (EFI_DEVICE_PATH_PROTOCOL *)FibreEx; 1308 } 1309 1310 /** 1311 Converts a text device path node to 1394 device path structure. 1312 1313 @param TextDeviceNode The input Text device path node. 1314 1315 @return A pointer to the newly-created 1394 device path structure. 1316 1317 **/ 1318 static 1319 EFI_DEVICE_PATH_PROTOCOL * 1320 DevPathFromText1394 ( 1321 IN CHAR16 *TextDeviceNode 1322 ) 1323 { 1324 CHAR16 *GuidStr; 1325 F1394_DEVICE_PATH *F1394DevPath; 1326 1327 GuidStr = GetNextParamStr (&TextDeviceNode); 1328 F1394DevPath = (F1394_DEVICE_PATH *)CreateDeviceNode ( 1329 MESSAGING_DEVICE_PATH, 1330 MSG_1394_DP, 1331 (UINT16)sizeof (F1394_DEVICE_PATH) 1332 ); 1333 1334 if (F1394DevPath != NULL) { 1335 F1394DevPath->Reserved = 0; 1336 F1394DevPath->Guid = StrHexToUint64 (GuidStr); 1337 } 1338 1339 return (EFI_DEVICE_PATH_PROTOCOL *)F1394DevPath; 1340 } 1341 1342 /** 1343 Converts a text device path node to USB device path structure. 1344 1345 @param TextDeviceNode The input Text device path node. 1346 1347 @return A pointer to the newly-created USB device path structure. 1348 1349 **/ 1350 static 1351 EFI_DEVICE_PATH_PROTOCOL * 1352 DevPathFromTextUsb ( 1353 IN CHAR16 *TextDeviceNode 1354 ) 1355 { 1356 CHAR16 *PortStr; 1357 CHAR16 *InterfaceStr; 1358 USB_DEVICE_PATH *Usb; 1359 1360 PortStr = GetNextParamStr (&TextDeviceNode); 1361 InterfaceStr = GetNextParamStr (&TextDeviceNode); 1362 Usb = (USB_DEVICE_PATH *)CreateDeviceNode ( 1363 MESSAGING_DEVICE_PATH, 1364 MSG_USB_DP, 1365 (UINT16)sizeof (USB_DEVICE_PATH) 1366 ); 1367 1368 if (Usb != NULL) { 1369 Usb->ParentPortNumber = (UINT8)Strtoi (PortStr); 1370 Usb->InterfaceNumber = (UINT8)Strtoi (InterfaceStr); 1371 } 1372 1373 return (EFI_DEVICE_PATH_PROTOCOL *)Usb; 1374 } 1375 1376 /** 1377 Converts a text device path node to I20 device path structure. 1378 1379 @param TextDeviceNode The input Text device path node. 1380 1381 @return A pointer to the newly-created I20 device path structure. 1382 1383 **/ 1384 static 1385 EFI_DEVICE_PATH_PROTOCOL * 1386 DevPathFromTextI2O ( 1387 IN CHAR16 *TextDeviceNode 1388 ) 1389 { 1390 CHAR16 *TIDStr; 1391 I2O_DEVICE_PATH *I2ODevPath; 1392 1393 TIDStr = GetNextParamStr (&TextDeviceNode); 1394 I2ODevPath = (I2O_DEVICE_PATH *)CreateDeviceNode ( 1395 MESSAGING_DEVICE_PATH, 1396 MSG_I2O_DP, 1397 (UINT16)sizeof (I2O_DEVICE_PATH) 1398 ); 1399 1400 if (I2ODevPath != NULL) { 1401 I2ODevPath->Tid = (UINT32)Strtoi (TIDStr); 1402 } 1403 1404 return (EFI_DEVICE_PATH_PROTOCOL *)I2ODevPath; 1405 } 1406 1407 /** 1408 Converts a text device path node to Infini Band device path structure. 1409 1410 @param TextDeviceNode The input Text device path node. 1411 1412 @return A pointer to the newly-created Infini Band device path structure. 1413 1414 **/ 1415 static 1416 EFI_DEVICE_PATH_PROTOCOL * 1417 DevPathFromTextInfiniband ( 1418 IN CHAR16 *TextDeviceNode 1419 ) 1420 { 1421 CHAR16 *FlagsStr; 1422 CHAR16 *GuidStr; 1423 CHAR16 *SidStr; 1424 CHAR16 *TidStr; 1425 CHAR16 *DidStr; 1426 INFINIBAND_DEVICE_PATH *InfiniBand; 1427 1428 FlagsStr = GetNextParamStr (&TextDeviceNode); 1429 GuidStr = GetNextParamStr (&TextDeviceNode); 1430 SidStr = GetNextParamStr (&TextDeviceNode); 1431 TidStr = GetNextParamStr (&TextDeviceNode); 1432 DidStr = GetNextParamStr (&TextDeviceNode); 1433 InfiniBand = (INFINIBAND_DEVICE_PATH *)CreateDeviceNode ( 1434 MESSAGING_DEVICE_PATH, 1435 MSG_INFINIBAND_DP, 1436 (UINT16)sizeof (INFINIBAND_DEVICE_PATH) 1437 ); 1438 1439 if (InfiniBand != NULL) { 1440 InfiniBand->ResourceFlags = (UINT32)Strtoi (FlagsStr); 1441 StrToGuid (GuidStr, (EFI_GUID *)InfiniBand->PortGid); 1442 Strtoi64 (SidStr, &InfiniBand->ServiceId); 1443 Strtoi64 (TidStr, &InfiniBand->TargetPortId); 1444 Strtoi64 (DidStr, &InfiniBand->DeviceId); 1445 } 1446 1447 return (EFI_DEVICE_PATH_PROTOCOL *)InfiniBand; 1448 } 1449 1450 /** 1451 Converts a text device path node to Vendor-Defined Messaging device path structure. 1452 1453 @param TextDeviceNode The input Text device path node. 1454 1455 @return A pointer to the newly-created Vendor-Defined Messaging device path structure. 1456 1457 **/ 1458 static 1459 EFI_DEVICE_PATH_PROTOCOL * 1460 DevPathFromTextVenMsg ( 1461 IN CHAR16 *TextDeviceNode 1462 ) 1463 { 1464 return ConvertFromTextVendor ( 1465 TextDeviceNode, 1466 MESSAGING_DEVICE_PATH, 1467 MSG_VENDOR_DP 1468 ); 1469 } 1470 1471 /** 1472 Converts a text device path node to Vendor defined PC-ANSI device path structure. 1473 1474 @param TextDeviceNode The input Text device path node. 1475 1476 @return A pointer to the newly-created Vendor defined PC-ANSI device path structure. 1477 1478 **/ 1479 static 1480 EFI_DEVICE_PATH_PROTOCOL * 1481 DevPathFromTextVenPcAnsi ( 1482 IN CHAR16 *TextDeviceNode 1483 ) 1484 { 1485 VENDOR_DEVICE_PATH *Vendor; 1486 1487 Vendor = (VENDOR_DEVICE_PATH *)CreateDeviceNode ( 1488 MESSAGING_DEVICE_PATH, 1489 MSG_VENDOR_DP, 1490 (UINT16)sizeof (VENDOR_DEVICE_PATH) 1491 ); 1492 1493 if (Vendor != NULL) { 1494 CopyGuid (&Vendor->Guid, &gEfiPcAnsiGuid); 1495 } 1496 1497 return (EFI_DEVICE_PATH_PROTOCOL *)Vendor; 1498 } 1499 1500 /** 1501 Converts a text device path node to Vendor defined VT100 device path structure. 1502 1503 @param TextDeviceNode The input Text device path node. 1504 1505 @return A pointer to the newly-created Vendor defined VT100 device path structure. 1506 1507 **/ 1508 static 1509 EFI_DEVICE_PATH_PROTOCOL * 1510 DevPathFromTextVenVt100 ( 1511 IN CHAR16 *TextDeviceNode 1512 ) 1513 { 1514 VENDOR_DEVICE_PATH *Vendor; 1515 1516 Vendor = (VENDOR_DEVICE_PATH *)CreateDeviceNode ( 1517 MESSAGING_DEVICE_PATH, 1518 MSG_VENDOR_DP, 1519 (UINT16)sizeof (VENDOR_DEVICE_PATH) 1520 ); 1521 1522 if (Vendor != NULL) { 1523 CopyGuid (&Vendor->Guid, &gEfiVT100Guid); 1524 } 1525 1526 return (EFI_DEVICE_PATH_PROTOCOL *)Vendor; 1527 } 1528 1529 /** 1530 Converts a text device path node to Vendor defined VT100 Plus device path structure. 1531 1532 @param TextDeviceNode The input Text device path node. 1533 1534 @return A pointer to the newly-created Vendor defined VT100 Plus device path structure. 1535 1536 **/ 1537 static 1538 EFI_DEVICE_PATH_PROTOCOL * 1539 DevPathFromTextVenVt100Plus ( 1540 IN CHAR16 *TextDeviceNode 1541 ) 1542 { 1543 VENDOR_DEVICE_PATH *Vendor; 1544 1545 Vendor = (VENDOR_DEVICE_PATH *)CreateDeviceNode ( 1546 MESSAGING_DEVICE_PATH, 1547 MSG_VENDOR_DP, 1548 (UINT16)sizeof (VENDOR_DEVICE_PATH) 1549 ); 1550 1551 if (Vendor != NULL) { 1552 CopyGuid (&Vendor->Guid, &gEfiVT100PlusGuid); 1553 } 1554 1555 return (EFI_DEVICE_PATH_PROTOCOL *)Vendor; 1556 } 1557 1558 /** 1559 Converts a text device path node to Vendor defined UTF8 device path structure. 1560 1561 @param TextDeviceNode The input Text device path node. 1562 1563 @return A pointer to the newly-created Vendor defined UTF8 device path structure. 1564 1565 **/ 1566 static 1567 EFI_DEVICE_PATH_PROTOCOL * 1568 DevPathFromTextVenUtf8 ( 1569 IN CHAR16 *TextDeviceNode 1570 ) 1571 { 1572 VENDOR_DEVICE_PATH *Vendor; 1573 1574 Vendor = (VENDOR_DEVICE_PATH *)CreateDeviceNode ( 1575 MESSAGING_DEVICE_PATH, 1576 MSG_VENDOR_DP, 1577 (UINT16)sizeof (VENDOR_DEVICE_PATH) 1578 ); 1579 1580 if (Vendor != NULL) { 1581 CopyGuid (&Vendor->Guid, &gEfiVTUTF8Guid); 1582 } 1583 1584 return (EFI_DEVICE_PATH_PROTOCOL *)Vendor; 1585 } 1586 1587 /** 1588 Converts a text device path node to UART Flow Control device path structure. 1589 1590 @param TextDeviceNode The input Text device path node. 1591 1592 @return A pointer to the newly-created UART Flow Control device path structure. 1593 1594 **/ 1595 static 1596 EFI_DEVICE_PATH_PROTOCOL * 1597 DevPathFromTextUartFlowCtrl ( 1598 IN CHAR16 *TextDeviceNode 1599 ) 1600 { 1601 CHAR16 *ValueStr; 1602 UART_FLOW_CONTROL_DEVICE_PATH *UartFlowControl; 1603 1604 ValueStr = GetNextParamStr (&TextDeviceNode); 1605 UartFlowControl = (UART_FLOW_CONTROL_DEVICE_PATH *)CreateDeviceNode ( 1606 MESSAGING_DEVICE_PATH, 1607 MSG_VENDOR_DP, 1608 (UINT16)sizeof (UART_FLOW_CONTROL_DEVICE_PATH) 1609 ); 1610 1611 if (UartFlowControl != NULL) { 1612 CopyGuid (&UartFlowControl->Guid, &gEfiUartDevicePathGuid); 1613 if (StrCmp (ValueStr, "XonXoff") == 0) { 1614 UartFlowControl->FlowControlMap = 2; 1615 } else if (StrCmp (ValueStr, "Hardware") == 0) { 1616 UartFlowControl->FlowControlMap = 1; 1617 } else { 1618 UartFlowControl->FlowControlMap = 0; 1619 } 1620 } 1621 1622 return (EFI_DEVICE_PATH_PROTOCOL *)UartFlowControl; 1623 } 1624 1625 /** 1626 Converts a text device path node to Serial Attached SCSI device path structure. 1627 1628 @param TextDeviceNode The input Text device path node. 1629 1630 @return A pointer to the newly-created Serial Attached SCSI device path structure. 1631 1632 **/ 1633 static 1634 EFI_DEVICE_PATH_PROTOCOL * 1635 DevPathFromTextSAS ( 1636 IN CHAR16 *TextDeviceNode 1637 ) 1638 { 1639 CHAR16 *AddressStr; 1640 CHAR16 *LunStr; 1641 CHAR16 *RTPStr; 1642 CHAR16 *SASSATAStr; 1643 CHAR16 *LocationStr; 1644 CHAR16 *ConnectStr; 1645 CHAR16 *DriveBayStr; 1646 CHAR16 *ReservedStr; 1647 UINT16 Info; 1648 UINT16 Uint16; 1649 SAS_DEVICE_PATH *Sas; 1650 1651 AddressStr = GetNextParamStr (&TextDeviceNode); 1652 LunStr = GetNextParamStr (&TextDeviceNode); 1653 RTPStr = GetNextParamStr (&TextDeviceNode); 1654 SASSATAStr = GetNextParamStr (&TextDeviceNode); 1655 LocationStr = GetNextParamStr (&TextDeviceNode); 1656 ConnectStr = GetNextParamStr (&TextDeviceNode); 1657 DriveBayStr = GetNextParamStr (&TextDeviceNode); 1658 ReservedStr = GetNextParamStr (&TextDeviceNode); 1659 Sas = (SAS_DEVICE_PATH *)CreateDeviceNode ( 1660 MESSAGING_DEVICE_PATH, 1661 MSG_VENDOR_DP, 1662 (UINT16)sizeof (SAS_DEVICE_PATH) 1663 ); 1664 1665 if (Sas == NULL) { 1666 return (EFI_DEVICE_PATH_PROTOCOL *)Sas; 1667 } 1668 1669 CopyGuid (&Sas->Guid, &gEfiSasDevicePathGuid); 1670 Strtoi64 (AddressStr, &Sas->SasAddress); 1671 Strtoi64 (LunStr, &Sas->Lun); 1672 Sas->RelativeTargetPort = (UINT16)Strtoi (RTPStr); 1673 1674 if (StrCmp (SASSATAStr, "NoTopology") == 0) { 1675 Info = 0x0; 1676 } else if ((StrCmp (SASSATAStr, "SATA") == 0) || (StrCmp (SASSATAStr, "SAS") == 0)) { 1677 Uint16 = (UINT16)Strtoi (DriveBayStr); 1678 if (Uint16 == 0) { 1679 Info = 0x1; 1680 } else { 1681 Info = (UINT16)(0x2 | ((Uint16 - 1) << 8)); 1682 } 1683 1684 if (StrCmp (SASSATAStr, "SATA") == 0) { 1685 Info |= BIT4; 1686 } 1687 1688 // 1689 // Location is an integer between 0 and 1 or else 1690 // the keyword Internal (0) or External (1). 1691 // 1692 if (StrCmp (LocationStr, "External") == 0) { 1693 Uint16 = 1; 1694 } else if (StrCmp (LocationStr, "Internal") == 0) { 1695 Uint16 = 0; 1696 } else { 1697 Uint16 = ((UINT16)Strtoi (LocationStr) & BIT0); 1698 } 1699 1700 Info |= (Uint16 << 5); 1701 1702 // 1703 // Connect is an integer between 0 and 3 or else 1704 // the keyword Direct (0) or Expanded (1). 1705 // 1706 if (StrCmp (ConnectStr, "Expanded") == 0) { 1707 Uint16 = 1; 1708 } else if (StrCmp (ConnectStr, "Direct") == 0) { 1709 Uint16 = 0; 1710 } else { 1711 Uint16 = ((UINT16)Strtoi (ConnectStr) & (BIT0 | BIT1)); 1712 } 1713 1714 Info |= (Uint16 << 6); 1715 } else { 1716 Info = (UINT16)Strtoi (SASSATAStr); 1717 } 1718 1719 Sas->DeviceTopology = Info; 1720 Sas->Reserved = (UINT32)Strtoi (ReservedStr); 1721 1722 return (EFI_DEVICE_PATH_PROTOCOL *)Sas; 1723 } 1724 1725 /** 1726 Converts a text device path node to Serial Attached SCSI Ex device path structure. 1727 1728 @param TextDeviceNode The input Text device path node. 1729 1730 @return A pointer to the newly-created Serial Attached SCSI Ex device path structure. 1731 1732 **/ 1733 static 1734 EFI_DEVICE_PATH_PROTOCOL * 1735 DevPathFromTextSasEx ( 1736 IN CHAR16 *TextDeviceNode 1737 ) 1738 { 1739 CHAR16 *AddressStr; 1740 CHAR16 *LunStr; 1741 CHAR16 *RTPStr; 1742 CHAR16 *SASSATAStr; 1743 CHAR16 *LocationStr; 1744 CHAR16 *ConnectStr; 1745 CHAR16 *DriveBayStr; 1746 UINT16 Info; 1747 UINT16 Uint16; 1748 UINT64 SasAddress; 1749 UINT64 Lun; 1750 SASEX_DEVICE_PATH *SasEx; 1751 1752 AddressStr = GetNextParamStr (&TextDeviceNode); 1753 LunStr = GetNextParamStr (&TextDeviceNode); 1754 RTPStr = GetNextParamStr (&TextDeviceNode); 1755 SASSATAStr = GetNextParamStr (&TextDeviceNode); 1756 LocationStr = GetNextParamStr (&TextDeviceNode); 1757 ConnectStr = GetNextParamStr (&TextDeviceNode); 1758 DriveBayStr = GetNextParamStr (&TextDeviceNode); 1759 SasEx = (SASEX_DEVICE_PATH *)CreateDeviceNode ( 1760 MESSAGING_DEVICE_PATH, 1761 MSG_SASEX_DP, 1762 (UINT16)sizeof (SASEX_DEVICE_PATH) 1763 ); 1764 1765 if (SasEx == NULL) { 1766 return (EFI_DEVICE_PATH_PROTOCOL *)SasEx; 1767 } 1768 1769 Strtoi64 (AddressStr, &SasAddress); 1770 Strtoi64 (LunStr, &Lun); 1771 WriteUnaligned64 ((UINT64 *)&SasEx->SasAddress, SwapBytes64 (SasAddress)); 1772 WriteUnaligned64 ((UINT64 *)&SasEx->Lun, SwapBytes64 (Lun)); 1773 SasEx->RelativeTargetPort = (UINT16)Strtoi (RTPStr); 1774 1775 if (StrCmp (SASSATAStr, "NoTopology") == 0) { 1776 Info = 0x0; 1777 } else if ((StrCmp (SASSATAStr, "SATA") == 0) || (StrCmp (SASSATAStr, "SAS") == 0)) { 1778 Uint16 = (UINT16)Strtoi (DriveBayStr); 1779 if (Uint16 == 0) { 1780 Info = 0x1; 1781 } else { 1782 Info = (UINT16)(0x2 | ((Uint16 - 1) << 8)); 1783 } 1784 1785 if (StrCmp (SASSATAStr, "SATA") == 0) { 1786 Info |= BIT4; 1787 } 1788 1789 // 1790 // Location is an integer between 0 and 1 or else 1791 // the keyword Internal (0) or External (1). 1792 // 1793 if (StrCmp (LocationStr, "External") == 0) { 1794 Uint16 = 1; 1795 } else if (StrCmp (LocationStr, "Internal") == 0) { 1796 Uint16 = 0; 1797 } else { 1798 Uint16 = ((UINT16)Strtoi (LocationStr) & BIT0); 1799 } 1800 1801 Info |= (Uint16 << 5); 1802 1803 // 1804 // Connect is an integer between 0 and 3 or else 1805 // the keyword Direct (0) or Expanded (1). 1806 // 1807 if (StrCmp (ConnectStr, "Expanded") == 0) { 1808 Uint16 = 1; 1809 } else if (StrCmp (ConnectStr, "Direct") == 0) { 1810 Uint16 = 0; 1811 } else { 1812 Uint16 = ((UINT16)Strtoi (ConnectStr) & (BIT0 | BIT1)); 1813 } 1814 1815 Info |= (Uint16 << 6); 1816 } else { 1817 Info = (UINT16)Strtoi (SASSATAStr); 1818 } 1819 1820 SasEx->DeviceTopology = Info; 1821 1822 return (EFI_DEVICE_PATH_PROTOCOL *)SasEx; 1823 } 1824 1825 /** 1826 Converts a text device path node to NVM Express Namespace device path structure. 1827 1828 @param TextDeviceNode The input Text device path node. 1829 1830 @return A pointer to the newly-created NVM Express Namespace device path structure. 1831 1832 **/ 1833 static 1834 EFI_DEVICE_PATH_PROTOCOL * 1835 DevPathFromTextNVMe ( 1836 IN CHAR16 *TextDeviceNode 1837 ) 1838 { 1839 CHAR16 *NamespaceIdStr; 1840 CHAR16 *NamespaceUuidStr; 1841 NVME_NAMESPACE_DEVICE_PATH *Nvme; 1842 UINT8 *Uuid; 1843 UINTN Index; 1844 1845 NamespaceIdStr = GetNextParamStr (&TextDeviceNode); 1846 NamespaceUuidStr = GetNextParamStr (&TextDeviceNode); 1847 Nvme = (NVME_NAMESPACE_DEVICE_PATH *)CreateDeviceNode ( 1848 MESSAGING_DEVICE_PATH, 1849 MSG_NVME_NAMESPACE_DP, 1850 (UINT16)sizeof (NVME_NAMESPACE_DEVICE_PATH) 1851 ); 1852 1853 if (Nvme != NULL) { 1854 Nvme->NamespaceId = (UINT32)Strtoi (NamespaceIdStr); 1855 Uuid = (UINT8 *)&Nvme->NamespaceUuid; 1856 1857 Index = sizeof (Nvme->NamespaceUuid) / sizeof (UINT8); 1858 while (Index-- != 0) { 1859 Uuid[Index] = (UINT8)StrHexToUintn (SplitStr (&NamespaceUuidStr, '-')); 1860 } 1861 } 1862 1863 return (EFI_DEVICE_PATH_PROTOCOL *)Nvme; 1864 } 1865 1866 /** 1867 Converts a text device path node to UFS device path structure. 1868 1869 @param TextDeviceNode The input Text device path node. 1870 1871 @return A pointer to the newly-created UFS device path structure. 1872 1873 **/ 1874 static 1875 EFI_DEVICE_PATH_PROTOCOL * 1876 DevPathFromTextUfs ( 1877 IN CHAR16 *TextDeviceNode 1878 ) 1879 { 1880 CHAR16 *PunStr; 1881 CHAR16 *LunStr; 1882 UFS_DEVICE_PATH *Ufs; 1883 1884 PunStr = GetNextParamStr (&TextDeviceNode); 1885 LunStr = GetNextParamStr (&TextDeviceNode); 1886 Ufs = (UFS_DEVICE_PATH *)CreateDeviceNode ( 1887 MESSAGING_DEVICE_PATH, 1888 MSG_UFS_DP, 1889 (UINT16)sizeof (UFS_DEVICE_PATH) 1890 ); 1891 1892 if (Ufs != NULL) { 1893 Ufs->Pun = (UINT8)Strtoi (PunStr); 1894 Ufs->Lun = (UINT8)Strtoi (LunStr); 1895 } 1896 1897 return (EFI_DEVICE_PATH_PROTOCOL *)Ufs; 1898 } 1899 1900 /** 1901 Converts a text device path node to SD (Secure Digital) device path structure. 1902 1903 @param TextDeviceNode The input Text device path node. 1904 1905 @return A pointer to the newly-created SD device path structure. 1906 1907 **/ 1908 static 1909 EFI_DEVICE_PATH_PROTOCOL * 1910 DevPathFromTextSd ( 1911 IN CHAR16 *TextDeviceNode 1912 ) 1913 { 1914 CHAR16 *SlotNumberStr; 1915 SD_DEVICE_PATH *Sd; 1916 1917 SlotNumberStr = GetNextParamStr (&TextDeviceNode); 1918 Sd = (SD_DEVICE_PATH *)CreateDeviceNode ( 1919 MESSAGING_DEVICE_PATH, 1920 MSG_SD_DP, 1921 (UINT16)sizeof (SD_DEVICE_PATH) 1922 ); 1923 1924 if (Sd != NULL) { 1925 Sd->SlotNumber = (UINT8)Strtoi (SlotNumberStr); 1926 } 1927 1928 return (EFI_DEVICE_PATH_PROTOCOL *)Sd; 1929 } 1930 1931 /** 1932 Converts a text device path node to EMMC (Embedded MMC) device path structure. 1933 1934 @param TextDeviceNode The input Text device path node. 1935 1936 @return A pointer to the newly-created EMMC device path structure. 1937 1938 **/ 1939 static 1940 EFI_DEVICE_PATH_PROTOCOL * 1941 DevPathFromTextEmmc ( 1942 IN CHAR16 *TextDeviceNode 1943 ) 1944 { 1945 CHAR16 *SlotNumberStr; 1946 EMMC_DEVICE_PATH *Emmc; 1947 1948 SlotNumberStr = GetNextParamStr (&TextDeviceNode); 1949 Emmc = (EMMC_DEVICE_PATH *)CreateDeviceNode ( 1950 MESSAGING_DEVICE_PATH, 1951 MSG_EMMC_DP, 1952 (UINT16)sizeof (EMMC_DEVICE_PATH) 1953 ); 1954 1955 if (Emmc != NULL) { 1956 Emmc->SlotNumber = (UINT8)Strtoi (SlotNumberStr); 1957 } 1958 1959 return (EFI_DEVICE_PATH_PROTOCOL *)Emmc; 1960 } 1961 1962 /** 1963 Converts a text device path node to Debug Port device path structure. 1964 1965 @param TextDeviceNode The input Text device path node. 1966 1967 @return A pointer to the newly-created Debug Port device path structure. 1968 1969 **/ 1970 static 1971 EFI_DEVICE_PATH_PROTOCOL * 1972 DevPathFromTextDebugPort ( 1973 IN CHAR16 *TextDeviceNode 1974 ) 1975 { 1976 VENDOR_DEVICE_PATH *Vend; 1977 1978 Vend = (VENDOR_DEVICE_PATH *)CreateDeviceNode ( 1979 MESSAGING_DEVICE_PATH, 1980 MSG_VENDOR_DP, 1981 (UINT16)sizeof (VENDOR_DEVICE_PATH) 1982 ); 1983 1984 if (Vend != NULL) { 1985 CopyGuid (&Vend->Guid, &gEfiDebugPortProtocolGuid); 1986 } 1987 1988 return (EFI_DEVICE_PATH_PROTOCOL *)Vend; 1989 } 1990 1991 /** 1992 Converts a text device path node to MAC device path structure. 1993 1994 @param TextDeviceNode The input Text device path node. 1995 1996 @return A pointer to the newly-created MAC device path structure. 1997 1998 **/ 1999 static 2000 EFI_DEVICE_PATH_PROTOCOL * 2001 DevPathFromTextMAC ( 2002 IN CHAR16 *TextDeviceNode 2003 ) 2004 { 2005 CHAR16 *AddressStr; 2006 CHAR16 *IfTypeStr; 2007 UINTN Length; 2008 MAC_ADDR_DEVICE_PATH *MACDevPath; 2009 2010 AddressStr = GetNextParamStr (&TextDeviceNode); 2011 IfTypeStr = GetNextParamStr (&TextDeviceNode); 2012 MACDevPath = (MAC_ADDR_DEVICE_PATH *)CreateDeviceNode ( 2013 MESSAGING_DEVICE_PATH, 2014 MSG_MAC_ADDR_DP, 2015 (UINT16)sizeof (MAC_ADDR_DEVICE_PATH) 2016 ); 2017 2018 if (MACDevPath != NULL) { 2019 MACDevPath->IfType = (UINT8)Strtoi (IfTypeStr); 2020 2021 Length = sizeof (EFI_MAC_ADDRESS); 2022 if ((MACDevPath->IfType == 0x01) || (MACDevPath->IfType == 0x00)) { 2023 Length = 6; 2024 } 2025 2026 StrHexToBytes (AddressStr, Length * 2, MACDevPath->MacAddress.Addr, Length); 2027 } 2028 2029 return (EFI_DEVICE_PATH_PROTOCOL *)MACDevPath; 2030 } 2031 2032 /** 2033 Converts a text format to the network protocol ID. 2034 2035 @param Text String of protocol field. 2036 2037 @return Network protocol ID . 2038 2039 **/ 2040 static 2041 UINTN 2042 NetworkProtocolFromText ( 2043 IN CHAR16 *Text 2044 ) 2045 { 2046 if (StrCmp (Text, "UDP") == 0) { 2047 return RFC_1700_UDP_PROTOCOL; 2048 } 2049 2050 if (StrCmp (Text, "TCP") == 0) { 2051 return RFC_1700_TCP_PROTOCOL; 2052 } 2053 2054 return Strtoi (Text); 2055 } 2056 2057 /** 2058 Converts a text device path node to IPV4 device path structure. 2059 2060 @param TextDeviceNode The input Text device path node. 2061 2062 @return A pointer to the newly-created IPV4 device path structure. 2063 2064 **/ 2065 static 2066 EFI_DEVICE_PATH_PROTOCOL * 2067 DevPathFromTextIPv4 ( 2068 IN CHAR16 *TextDeviceNode 2069 ) 2070 { 2071 CHAR16 *RemoteIPStr; 2072 CHAR16 *ProtocolStr; 2073 CHAR16 *TypeStr; 2074 CHAR16 *LocalIPStr; 2075 CHAR16 *GatewayIPStr; 2076 CHAR16 *SubnetMaskStr; 2077 IPv4_DEVICE_PATH *IPv4; 2078 2079 RemoteIPStr = GetNextParamStr (&TextDeviceNode); 2080 ProtocolStr = GetNextParamStr (&TextDeviceNode); 2081 TypeStr = GetNextParamStr (&TextDeviceNode); 2082 LocalIPStr = GetNextParamStr (&TextDeviceNode); 2083 GatewayIPStr = GetNextParamStr (&TextDeviceNode); 2084 SubnetMaskStr = GetNextParamStr (&TextDeviceNode); 2085 IPv4 = (IPv4_DEVICE_PATH *)CreateDeviceNode ( 2086 MESSAGING_DEVICE_PATH, 2087 MSG_IPv4_DP, 2088 (UINT16)sizeof (IPv4_DEVICE_PATH) 2089 ); 2090 2091 if (IPv4 == NULL) { 2092 return (EFI_DEVICE_PATH_PROTOCOL *)IPv4; 2093 } 2094 2095 StrToIpv4Address (RemoteIPStr, NULL, &IPv4->RemoteIpAddress, NULL); 2096 IPv4->Protocol = (UINT16)NetworkProtocolFromText (ProtocolStr); 2097 if (StrCmp (TypeStr, "Static") == 0) { 2098 IPv4->StaticIpAddress = TRUE; 2099 } else { 2100 IPv4->StaticIpAddress = FALSE; 2101 } 2102 2103 StrToIpv4Address (LocalIPStr, NULL, &IPv4->LocalIpAddress, NULL); 2104 if (!IS_NULL (*GatewayIPStr) && !IS_NULL (*SubnetMaskStr)) { 2105 StrToIpv4Address (GatewayIPStr, NULL, &IPv4->GatewayIpAddress, NULL); 2106 StrToIpv4Address (SubnetMaskStr, NULL, &IPv4->SubnetMask, NULL); 2107 } else { 2108 ZeroMem (&IPv4->GatewayIpAddress, sizeof (IPv4->GatewayIpAddress)); 2109 ZeroMem (&IPv4->SubnetMask, sizeof (IPv4->SubnetMask)); 2110 } 2111 2112 IPv4->LocalPort = 0; 2113 IPv4->RemotePort = 0; 2114 2115 return (EFI_DEVICE_PATH_PROTOCOL *)IPv4; 2116 } 2117 2118 /** 2119 Converts a text device path node to IPV6 device path structure. 2120 2121 @param TextDeviceNode The input Text device path node. 2122 2123 @return A pointer to the newly-created IPV6 device path structure. 2124 2125 **/ 2126 static 2127 EFI_DEVICE_PATH_PROTOCOL * 2128 DevPathFromTextIPv6 ( 2129 IN CHAR16 *TextDeviceNode 2130 ) 2131 { 2132 CHAR16 *RemoteIPStr; 2133 CHAR16 *ProtocolStr; 2134 CHAR16 *TypeStr; 2135 CHAR16 *LocalIPStr; 2136 CHAR16 *GatewayIPStr; 2137 CHAR16 *PrefixLengthStr; 2138 IPv6_DEVICE_PATH *IPv6; 2139 2140 RemoteIPStr = GetNextParamStr (&TextDeviceNode); 2141 ProtocolStr = GetNextParamStr (&TextDeviceNode); 2142 TypeStr = GetNextParamStr (&TextDeviceNode); 2143 LocalIPStr = GetNextParamStr (&TextDeviceNode); 2144 PrefixLengthStr = GetNextParamStr (&TextDeviceNode); 2145 GatewayIPStr = GetNextParamStr (&TextDeviceNode); 2146 IPv6 = (IPv6_DEVICE_PATH *)CreateDeviceNode ( 2147 MESSAGING_DEVICE_PATH, 2148 MSG_IPv6_DP, 2149 (UINT16)sizeof (IPv6_DEVICE_PATH) 2150 ); 2151 2152 if (IPv6 == NULL) { 2153 return (EFI_DEVICE_PATH_PROTOCOL *)IPv6; 2154 } 2155 2156 StrToIpv6Address (RemoteIPStr, NULL, &IPv6->RemoteIpAddress, NULL); 2157 IPv6->Protocol = (UINT16)NetworkProtocolFromText (ProtocolStr); 2158 if (StrCmp (TypeStr, "Static") == 0) { 2159 IPv6->IpAddressOrigin = 0; 2160 } else if (StrCmp (TypeStr, "StatelessAutoConfigure") == 0) { 2161 IPv6->IpAddressOrigin = 1; 2162 } else { 2163 IPv6->IpAddressOrigin = 2; 2164 } 2165 2166 StrToIpv6Address (LocalIPStr, NULL, &IPv6->LocalIpAddress, NULL); 2167 if (!IS_NULL (*GatewayIPStr) && !IS_NULL (*PrefixLengthStr)) { 2168 StrToIpv6Address (GatewayIPStr, NULL, &IPv6->GatewayIpAddress, NULL); 2169 IPv6->PrefixLength = (UINT8)Strtoi (PrefixLengthStr); 2170 } else { 2171 ZeroMem (&IPv6->GatewayIpAddress, sizeof (IPv6->GatewayIpAddress)); 2172 IPv6->PrefixLength = 0; 2173 } 2174 2175 IPv6->LocalPort = 0; 2176 IPv6->RemotePort = 0; 2177 2178 return (EFI_DEVICE_PATH_PROTOCOL *)IPv6; 2179 } 2180 2181 /** 2182 Converts a text device path node to UART device path structure. 2183 2184 @param TextDeviceNode The input Text device path node. 2185 2186 @return A pointer to the newly-created UART device path structure. 2187 2188 **/ 2189 static 2190 EFI_DEVICE_PATH_PROTOCOL * 2191 DevPathFromTextUart ( 2192 IN CHAR16 *TextDeviceNode 2193 ) 2194 { 2195 CHAR16 *BaudStr; 2196 CHAR16 *DataBitsStr; 2197 CHAR16 *ParityStr; 2198 CHAR16 *StopBitsStr; 2199 UART_DEVICE_PATH *Uart; 2200 2201 BaudStr = GetNextParamStr (&TextDeviceNode); 2202 DataBitsStr = GetNextParamStr (&TextDeviceNode); 2203 ParityStr = GetNextParamStr (&TextDeviceNode); 2204 StopBitsStr = GetNextParamStr (&TextDeviceNode); 2205 Uart = (UART_DEVICE_PATH *)CreateDeviceNode ( 2206 MESSAGING_DEVICE_PATH, 2207 MSG_UART_DP, 2208 (UINT16)sizeof (UART_DEVICE_PATH) 2209 ); 2210 2211 if (Uart == NULL) { 2212 return (EFI_DEVICE_PATH_PROTOCOL *)Uart; 2213 } 2214 2215 if (StrCmp (BaudStr, "DEFAULT") == 0) { 2216 Uart->BaudRate = 115200; 2217 } else { 2218 Strtoi64 (BaudStr, &Uart->BaudRate); 2219 } 2220 2221 Uart->DataBits = (UINT8)((StrCmp (DataBitsStr, "DEFAULT") == 0) ? 8 : Strtoi (DataBitsStr)); 2222 switch (*ParityStr) { 2223 case 'D': 2224 Uart->Parity = 0; 2225 break; 2226 2227 case 'N': 2228 Uart->Parity = 1; 2229 break; 2230 2231 case 'E': 2232 Uart->Parity = 2; 2233 break; 2234 2235 case 'O': 2236 Uart->Parity = 3; 2237 break; 2238 2239 case 'M': 2240 Uart->Parity = 4; 2241 break; 2242 2243 case 'S': 2244 Uart->Parity = 5; 2245 break; 2246 2247 default: 2248 Uart->Parity = (UINT8)Strtoi (ParityStr); 2249 break; 2250 } 2251 2252 if (StrCmp (StopBitsStr, "D") == 0) { 2253 Uart->StopBits = (UINT8)0; 2254 } else if (StrCmp (StopBitsStr, "1") == 0) { 2255 Uart->StopBits = (UINT8)1; 2256 } else if (StrCmp (StopBitsStr, "1.5") == 0) { 2257 Uart->StopBits = (UINT8)2; 2258 } else if (StrCmp (StopBitsStr, "2") == 0) { 2259 Uart->StopBits = (UINT8)3; 2260 } else { 2261 Uart->StopBits = (UINT8)Strtoi (StopBitsStr); 2262 } 2263 2264 return (EFI_DEVICE_PATH_PROTOCOL *)Uart; 2265 } 2266 2267 /** 2268 Converts a text device path node to USB class device path structure. 2269 2270 @param TextDeviceNode The input Text device path node. 2271 @param UsbClassText A pointer to USB_CLASS_TEXT structure to be integrated to USB Class Text. 2272 2273 @return A pointer to the newly-created USB class device path structure. 2274 2275 **/ 2276 static 2277 EFI_DEVICE_PATH_PROTOCOL * 2278 ConvertFromTextUsbClass ( 2279 IN CHAR16 *TextDeviceNode, 2280 IN USB_CLASS_TEXT *UsbClassText 2281 ) 2282 { 2283 CHAR16 *VIDStr; 2284 CHAR16 *PIDStr; 2285 CHAR16 *ClassStr; 2286 CHAR16 *SubClassStr; 2287 CHAR16 *ProtocolStr; 2288 USB_CLASS_DEVICE_PATH *UsbClass; 2289 2290 UsbClass = (USB_CLASS_DEVICE_PATH *)CreateDeviceNode ( 2291 MESSAGING_DEVICE_PATH, 2292 MSG_USB_CLASS_DP, 2293 (UINT16)sizeof (USB_CLASS_DEVICE_PATH) 2294 ); 2295 2296 if (UsbClass == NULL) { 2297 return (EFI_DEVICE_PATH_PROTOCOL *)UsbClass; 2298 } 2299 2300 VIDStr = GetNextParamStr (&TextDeviceNode); 2301 PIDStr = GetNextParamStr (&TextDeviceNode); 2302 if (UsbClassText->ClassExist) { 2303 ClassStr = GetNextParamStr (&TextDeviceNode); 2304 if (*ClassStr == '\0') { 2305 UsbClass->DeviceClass = 0xFF; 2306 } else { 2307 UsbClass->DeviceClass = (UINT8)Strtoi (ClassStr); 2308 } 2309 } else { 2310 UsbClass->DeviceClass = UsbClassText->Class; 2311 } 2312 2313 if (UsbClassText->SubClassExist) { 2314 SubClassStr = GetNextParamStr (&TextDeviceNode); 2315 if (*SubClassStr == '\0') { 2316 UsbClass->DeviceSubClass = 0xFF; 2317 } else { 2318 UsbClass->DeviceSubClass = (UINT8)Strtoi (SubClassStr); 2319 } 2320 } else { 2321 UsbClass->DeviceSubClass = UsbClassText->SubClass; 2322 } 2323 2324 ProtocolStr = GetNextParamStr (&TextDeviceNode); 2325 2326 if (*VIDStr == '\0') { 2327 UsbClass->VendorId = 0xFFFF; 2328 } else { 2329 UsbClass->VendorId = (UINT16)Strtoi (VIDStr); 2330 } 2331 2332 if (*PIDStr == '\0') { 2333 UsbClass->ProductId = 0xFFFF; 2334 } else { 2335 UsbClass->ProductId = (UINT16)Strtoi (PIDStr); 2336 } 2337 2338 if (*ProtocolStr == '\0') { 2339 UsbClass->DeviceProtocol = 0xFF; 2340 } else { 2341 UsbClass->DeviceProtocol = (UINT8)Strtoi (ProtocolStr); 2342 } 2343 2344 return (EFI_DEVICE_PATH_PROTOCOL *)UsbClass; 2345 } 2346 2347 /** 2348 Converts a text device path node to USB class device path structure. 2349 2350 @param TextDeviceNode The input Text device path node. 2351 2352 @return A pointer to the newly-created USB class device path structure. 2353 2354 **/ 2355 static 2356 EFI_DEVICE_PATH_PROTOCOL * 2357 DevPathFromTextUsbClass ( 2358 IN CHAR16 *TextDeviceNode 2359 ) 2360 { 2361 USB_CLASS_TEXT UsbClassText; 2362 2363 UsbClassText.ClassExist = TRUE; 2364 UsbClassText.SubClassExist = TRUE; 2365 2366 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2367 } 2368 2369 /** 2370 Converts a text device path node to USB audio device path structure. 2371 2372 @param TextDeviceNode The input Text device path node. 2373 2374 @return A pointer to the newly-created USB audio device path structure. 2375 2376 **/ 2377 static 2378 EFI_DEVICE_PATH_PROTOCOL * 2379 DevPathFromTextUsbAudio ( 2380 IN CHAR16 *TextDeviceNode 2381 ) 2382 { 2383 USB_CLASS_TEXT UsbClassText; 2384 2385 UsbClassText.ClassExist = FALSE; 2386 UsbClassText.Class = USB_CLASS_AUDIO; 2387 UsbClassText.SubClassExist = TRUE; 2388 2389 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2390 } 2391 2392 /** 2393 Converts a text device path node to USB CDC Control device path structure. 2394 2395 @param TextDeviceNode The input Text device path node. 2396 2397 @return A pointer to the newly-created USB CDC Control device path structure. 2398 2399 **/ 2400 static 2401 EFI_DEVICE_PATH_PROTOCOL * 2402 DevPathFromTextUsbCDCControl ( 2403 IN CHAR16 *TextDeviceNode 2404 ) 2405 { 2406 USB_CLASS_TEXT UsbClassText; 2407 2408 UsbClassText.ClassExist = FALSE; 2409 UsbClassText.Class = USB_CLASS_CDCCONTROL; 2410 UsbClassText.SubClassExist = TRUE; 2411 2412 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2413 } 2414 2415 /** 2416 Converts a text device path node to USB HID device path structure. 2417 2418 @param TextDeviceNode The input Text device path node. 2419 2420 @return A pointer to the newly-created USB HID device path structure. 2421 2422 **/ 2423 static 2424 EFI_DEVICE_PATH_PROTOCOL * 2425 DevPathFromTextUsbHID ( 2426 IN CHAR16 *TextDeviceNode 2427 ) 2428 { 2429 USB_CLASS_TEXT UsbClassText; 2430 2431 UsbClassText.ClassExist = FALSE; 2432 UsbClassText.Class = USB_CLASS_HID; 2433 UsbClassText.SubClassExist = TRUE; 2434 2435 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2436 } 2437 2438 /** 2439 Converts a text device path node to USB Image device path structure. 2440 2441 @param TextDeviceNode The input Text device path node. 2442 2443 @return A pointer to the newly-created USB Image device path structure. 2444 2445 **/ 2446 static 2447 EFI_DEVICE_PATH_PROTOCOL * 2448 DevPathFromTextUsbImage ( 2449 IN CHAR16 *TextDeviceNode 2450 ) 2451 { 2452 USB_CLASS_TEXT UsbClassText; 2453 2454 UsbClassText.ClassExist = FALSE; 2455 UsbClassText.Class = USB_CLASS_IMAGE; 2456 UsbClassText.SubClassExist = TRUE; 2457 2458 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2459 } 2460 2461 /** 2462 Converts a text device path node to USB Print device path structure. 2463 2464 @param TextDeviceNode The input Text device path node. 2465 2466 @return A pointer to the newly-created USB Print device path structure. 2467 2468 **/ 2469 static 2470 EFI_DEVICE_PATH_PROTOCOL * 2471 DevPathFromTextUsbPrinter ( 2472 IN CHAR16 *TextDeviceNode 2473 ) 2474 { 2475 USB_CLASS_TEXT UsbClassText; 2476 2477 UsbClassText.ClassExist = FALSE; 2478 UsbClassText.Class = USB_CLASS_PRINTER; 2479 UsbClassText.SubClassExist = TRUE; 2480 2481 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2482 } 2483 2484 /** 2485 Converts a text device path node to USB mass storage device path structure. 2486 2487 @param TextDeviceNode The input Text device path node. 2488 2489 @return A pointer to the newly-created USB mass storage device path structure. 2490 2491 **/ 2492 static 2493 EFI_DEVICE_PATH_PROTOCOL * 2494 DevPathFromTextUsbMassStorage ( 2495 IN CHAR16 *TextDeviceNode 2496 ) 2497 { 2498 USB_CLASS_TEXT UsbClassText; 2499 2500 UsbClassText.ClassExist = FALSE; 2501 UsbClassText.Class = USB_CLASS_MASS_STORAGE; 2502 UsbClassText.SubClassExist = TRUE; 2503 2504 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2505 } 2506 2507 /** 2508 Converts a text device path node to USB HUB device path structure. 2509 2510 @param TextDeviceNode The input Text device path node. 2511 2512 @return A pointer to the newly-created USB HUB device path structure. 2513 2514 **/ 2515 static 2516 EFI_DEVICE_PATH_PROTOCOL * 2517 DevPathFromTextUsbHub ( 2518 IN CHAR16 *TextDeviceNode 2519 ) 2520 { 2521 USB_CLASS_TEXT UsbClassText; 2522 2523 UsbClassText.ClassExist = FALSE; 2524 UsbClassText.Class = USB_CLASS_HUB; 2525 UsbClassText.SubClassExist = TRUE; 2526 2527 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2528 } 2529 2530 /** 2531 Converts a text device path node to USB CDC data device path structure. 2532 2533 @param TextDeviceNode The input Text device path node. 2534 2535 @return A pointer to the newly-created USB CDC data device path structure. 2536 2537 **/ 2538 static 2539 EFI_DEVICE_PATH_PROTOCOL * 2540 DevPathFromTextUsbCDCData ( 2541 IN CHAR16 *TextDeviceNode 2542 ) 2543 { 2544 USB_CLASS_TEXT UsbClassText; 2545 2546 UsbClassText.ClassExist = FALSE; 2547 UsbClassText.Class = USB_CLASS_CDCDATA; 2548 UsbClassText.SubClassExist = TRUE; 2549 2550 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2551 } 2552 2553 /** 2554 Converts a text device path node to USB smart card device path structure. 2555 2556 @param TextDeviceNode The input Text device path node. 2557 2558 @return A pointer to the newly-created USB smart card device path structure. 2559 2560 **/ 2561 static 2562 EFI_DEVICE_PATH_PROTOCOL * 2563 DevPathFromTextUsbSmartCard ( 2564 IN CHAR16 *TextDeviceNode 2565 ) 2566 { 2567 USB_CLASS_TEXT UsbClassText; 2568 2569 UsbClassText.ClassExist = FALSE; 2570 UsbClassText.Class = USB_CLASS_SMART_CARD; 2571 UsbClassText.SubClassExist = TRUE; 2572 2573 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2574 } 2575 2576 /** 2577 Converts a text device path node to USB video device path structure. 2578 2579 @param TextDeviceNode The input Text device path node. 2580 2581 @return A pointer to the newly-created USB video device path structure. 2582 2583 **/ 2584 static 2585 EFI_DEVICE_PATH_PROTOCOL * 2586 DevPathFromTextUsbVideo ( 2587 IN CHAR16 *TextDeviceNode 2588 ) 2589 { 2590 USB_CLASS_TEXT UsbClassText; 2591 2592 UsbClassText.ClassExist = FALSE; 2593 UsbClassText.Class = USB_CLASS_VIDEO; 2594 UsbClassText.SubClassExist = TRUE; 2595 2596 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2597 } 2598 2599 /** 2600 Converts a text device path node to USB diagnostic device path structure. 2601 2602 @param TextDeviceNode The input Text device path node. 2603 2604 @return A pointer to the newly-created USB diagnostic device path structure. 2605 2606 **/ 2607 static 2608 EFI_DEVICE_PATH_PROTOCOL * 2609 DevPathFromTextUsbDiagnostic ( 2610 IN CHAR16 *TextDeviceNode 2611 ) 2612 { 2613 USB_CLASS_TEXT UsbClassText; 2614 2615 UsbClassText.ClassExist = FALSE; 2616 UsbClassText.Class = USB_CLASS_DIAGNOSTIC; 2617 UsbClassText.SubClassExist = TRUE; 2618 2619 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2620 } 2621 2622 /** 2623 Converts a text device path node to USB wireless device path structure. 2624 2625 @param TextDeviceNode The input Text device path node. 2626 2627 @return A pointer to the newly-created USB wireless device path structure. 2628 2629 **/ 2630 static 2631 EFI_DEVICE_PATH_PROTOCOL * 2632 DevPathFromTextUsbWireless ( 2633 IN CHAR16 *TextDeviceNode 2634 ) 2635 { 2636 USB_CLASS_TEXT UsbClassText; 2637 2638 UsbClassText.ClassExist = FALSE; 2639 UsbClassText.Class = USB_CLASS_WIRELESS; 2640 UsbClassText.SubClassExist = TRUE; 2641 2642 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2643 } 2644 2645 /** 2646 Converts a text device path node to USB device firmware update device path structure. 2647 2648 @param TextDeviceNode The input Text device path node. 2649 2650 @return A pointer to the newly-created USB device firmware update device path structure. 2651 2652 **/ 2653 static 2654 EFI_DEVICE_PATH_PROTOCOL * 2655 DevPathFromTextUsbDeviceFirmwareUpdate ( 2656 IN CHAR16 *TextDeviceNode 2657 ) 2658 { 2659 USB_CLASS_TEXT UsbClassText; 2660 2661 UsbClassText.ClassExist = FALSE; 2662 UsbClassText.Class = USB_CLASS_RESERVE; 2663 UsbClassText.SubClassExist = FALSE; 2664 UsbClassText.SubClass = USB_SUBCLASS_FW_UPDATE; 2665 2666 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2667 } 2668 2669 /** 2670 Converts a text device path node to USB IRDA bridge device path structure. 2671 2672 @param TextDeviceNode The input Text device path node. 2673 2674 @return A pointer to the newly-created USB IRDA bridge device path structure. 2675 2676 **/ 2677 static 2678 EFI_DEVICE_PATH_PROTOCOL * 2679 DevPathFromTextUsbIrdaBridge ( 2680 IN CHAR16 *TextDeviceNode 2681 ) 2682 { 2683 USB_CLASS_TEXT UsbClassText; 2684 2685 UsbClassText.ClassExist = FALSE; 2686 UsbClassText.Class = USB_CLASS_RESERVE; 2687 UsbClassText.SubClassExist = FALSE; 2688 UsbClassText.SubClass = USB_SUBCLASS_IRDA_BRIDGE; 2689 2690 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2691 } 2692 2693 /** 2694 Converts a text device path node to USB text and measurement device path structure. 2695 2696 @param TextDeviceNode The input Text device path node. 2697 2698 @return A pointer to the newly-created USB text and measurement device path structure. 2699 2700 **/ 2701 static 2702 EFI_DEVICE_PATH_PROTOCOL * 2703 DevPathFromTextUsbTestAndMeasurement ( 2704 IN CHAR16 *TextDeviceNode 2705 ) 2706 { 2707 USB_CLASS_TEXT UsbClassText; 2708 2709 UsbClassText.ClassExist = FALSE; 2710 UsbClassText.Class = USB_CLASS_RESERVE; 2711 UsbClassText.SubClassExist = FALSE; 2712 UsbClassText.SubClass = USB_SUBCLASS_TEST; 2713 2714 return ConvertFromTextUsbClass (TextDeviceNode, &UsbClassText); 2715 } 2716 2717 /** 2718 Converts a text device path node to USB WWID device path structure. 2719 2720 @param TextDeviceNode The input Text device path node. 2721 2722 @return A pointer to the newly-created USB WWID device path structure. 2723 2724 **/ 2725 static 2726 EFI_DEVICE_PATH_PROTOCOL * 2727 DevPathFromTextUsbWwid ( 2728 IN CHAR16 *TextDeviceNode 2729 ) 2730 { 2731 CHAR16 *VIDStr; 2732 CHAR16 *PIDStr; 2733 CHAR16 *InterfaceNumStr; 2734 CHAR16 *SerialNumberStr; 2735 USB_WWID_DEVICE_PATH *UsbWwid; 2736 UINTN SerialNumberStrLen; 2737 2738 VIDStr = GetNextParamStr (&TextDeviceNode); 2739 PIDStr = GetNextParamStr (&TextDeviceNode); 2740 InterfaceNumStr = GetNextParamStr (&TextDeviceNode); 2741 SerialNumberStr = GetNextParamStr (&TextDeviceNode); 2742 SerialNumberStrLen = StrLen (SerialNumberStr); 2743 if ((SerialNumberStrLen >= 2) && 2744 (SerialNumberStr[0] == '\"') && 2745 (SerialNumberStr[SerialNumberStrLen - 1] == '\"') 2746 ) 2747 { 2748 SerialNumberStr[SerialNumberStrLen - 1] = '\0'; 2749 SerialNumberStr++; 2750 SerialNumberStrLen -= 2; 2751 } 2752 2753 UsbWwid = (USB_WWID_DEVICE_PATH *)CreateDeviceNode ( 2754 MESSAGING_DEVICE_PATH, 2755 MSG_USB_WWID_DP, 2756 (UINT16)(sizeof (USB_WWID_DEVICE_PATH) + SerialNumberStrLen * sizeof (CHAR16)) 2757 ); 2758 2759 if (UsbWwid != NULL) { 2760 UsbWwid->VendorId = (UINT16)Strtoi (VIDStr); 2761 UsbWwid->ProductId = (UINT16)Strtoi (PIDStr); 2762 UsbWwid->InterfaceNumber = (UINT16)Strtoi (InterfaceNumStr); 2763 2764 // 2765 // There is no memory allocated in UsbWwid for the '\0' in SerialNumberStr. 2766 // Therefore, the '\0' will not be copied. 2767 // 2768 CopyMem ( 2769 (UINT8 *)UsbWwid + sizeof (USB_WWID_DEVICE_PATH), 2770 SerialNumberStr, 2771 SerialNumberStrLen * sizeof (CHAR16) 2772 ); 2773 } 2774 2775 return (EFI_DEVICE_PATH_PROTOCOL *)UsbWwid; 2776 } 2777 2778 /** 2779 Converts a text device path node to Logic Unit device path structure. 2780 2781 @param TextDeviceNode The input Text device path node. 2782 2783 @return A pointer to the newly-created Logic Unit device path structure. 2784 2785 **/ 2786 static 2787 EFI_DEVICE_PATH_PROTOCOL * 2788 DevPathFromTextUnit ( 2789 IN CHAR16 *TextDeviceNode 2790 ) 2791 { 2792 CHAR16 *LunStr; 2793 DEVICE_LOGICAL_UNIT_DEVICE_PATH *LogicalUnit; 2794 2795 LunStr = GetNextParamStr (&TextDeviceNode); 2796 LogicalUnit = (DEVICE_LOGICAL_UNIT_DEVICE_PATH *)CreateDeviceNode ( 2797 MESSAGING_DEVICE_PATH, 2798 MSG_DEVICE_LOGICAL_UNIT_DP, 2799 (UINT16)sizeof (DEVICE_LOGICAL_UNIT_DEVICE_PATH) 2800 ); 2801 2802 if (LogicalUnit != NULL) { 2803 LogicalUnit->Lun = (UINT8)Strtoi (LunStr); 2804 } 2805 2806 return (EFI_DEVICE_PATH_PROTOCOL *)LogicalUnit; 2807 } 2808 2809 /** 2810 Converts a text device path node to iSCSI device path structure. 2811 2812 @param TextDeviceNode The input Text device path node. 2813 2814 @return A pointer to the newly-created iSCSI device path structure. 2815 2816 **/ 2817 static 2818 EFI_DEVICE_PATH_PROTOCOL * 2819 DevPathFromTextiSCSI ( 2820 IN CHAR16 *TextDeviceNode 2821 ) 2822 { 2823 UINT16 Options; 2824 CHAR16 *NameStr; 2825 CHAR16 *PortalGroupStr; 2826 CHAR16 *LunStr; 2827 CHAR16 *HeaderDigestStr; 2828 CHAR16 *DataDigestStr; 2829 CHAR16 *AuthenticationStr; 2830 CHAR16 *ProtocolStr; 2831 CHAR8 *AsciiStr; 2832 ISCSI_DEVICE_PATH_WITH_NAME *ISCSIDevPath; 2833 UINT64 Lun; 2834 2835 NameStr = GetNextParamStr (&TextDeviceNode); 2836 PortalGroupStr = GetNextParamStr (&TextDeviceNode); 2837 LunStr = GetNextParamStr (&TextDeviceNode); 2838 HeaderDigestStr = GetNextParamStr (&TextDeviceNode); 2839 DataDigestStr = GetNextParamStr (&TextDeviceNode); 2840 AuthenticationStr = GetNextParamStr (&TextDeviceNode); 2841 ProtocolStr = GetNextParamStr (&TextDeviceNode); 2842 ISCSIDevPath = (ISCSI_DEVICE_PATH_WITH_NAME *)CreateDeviceNode ( 2843 MESSAGING_DEVICE_PATH, 2844 MSG_ISCSI_DP, 2845 (UINT16)(sizeof (ISCSI_DEVICE_PATH_WITH_NAME) + StrLen (NameStr)) 2846 ); 2847 2848 if (ISCSIDevPath == NULL) { 2849 return (EFI_DEVICE_PATH_PROTOCOL *)ISCSIDevPath; 2850 } 2851 2852 AsciiStr = ISCSIDevPath->TargetName; 2853 StrToAscii (NameStr, &AsciiStr); 2854 2855 ISCSIDevPath->TargetPortalGroupTag = (UINT16)Strtoi (PortalGroupStr); 2856 Strtoi64 (LunStr, &Lun); 2857 WriteUnaligned64 ((UINT64 *)&ISCSIDevPath->Lun, SwapBytes64 (Lun)); 2858 2859 Options = 0x0000; 2860 if (StrCmp (HeaderDigestStr, "CRC32C") == 0) { 2861 Options |= 0x0002; 2862 } 2863 2864 if (StrCmp (DataDigestStr, "CRC32C") == 0) { 2865 Options |= 0x0008; 2866 } 2867 2868 if (StrCmp (AuthenticationStr, "None") == 0) { 2869 Options |= 0x0800; 2870 } 2871 2872 if (StrCmp (AuthenticationStr, "CHAP_UNI") == 0) { 2873 Options |= 0x1000; 2874 } 2875 2876 ISCSIDevPath->LoginOption = (UINT16)Options; 2877 2878 if (IS_NULL (*ProtocolStr) || (StrCmp (ProtocolStr, "TCP") == 0)) { 2879 ISCSIDevPath->NetworkProtocol = 0; 2880 } else { 2881 // 2882 // Undefined and reserved. 2883 // 2884 ISCSIDevPath->NetworkProtocol = 1; 2885 } 2886 2887 return (EFI_DEVICE_PATH_PROTOCOL *)ISCSIDevPath; 2888 } 2889 2890 /** 2891 Converts a text device path node to VLAN device path structure. 2892 2893 @param TextDeviceNode The input Text device path node. 2894 2895 @return A pointer to the newly-created VLAN device path structure. 2896 2897 **/ 2898 static 2899 EFI_DEVICE_PATH_PROTOCOL * 2900 DevPathFromTextVlan ( 2901 IN CHAR16 *TextDeviceNode 2902 ) 2903 { 2904 CHAR16 *VlanStr; 2905 VLAN_DEVICE_PATH *Vlan; 2906 2907 VlanStr = GetNextParamStr (&TextDeviceNode); 2908 Vlan = (VLAN_DEVICE_PATH *)CreateDeviceNode ( 2909 MESSAGING_DEVICE_PATH, 2910 MSG_VLAN_DP, 2911 (UINT16)sizeof (VLAN_DEVICE_PATH) 2912 ); 2913 2914 if (Vlan != NULL) { 2915 Vlan->VlanId = (UINT16)Strtoi (VlanStr); 2916 } 2917 2918 return (EFI_DEVICE_PATH_PROTOCOL *)Vlan; 2919 } 2920 2921 /** 2922 Converts a text device path node to Bluetooth device path structure. 2923 2924 @param TextDeviceNode The input Text device path node. 2925 2926 @return A pointer to the newly-created Bluetooth device path structure. 2927 2928 **/ 2929 static 2930 EFI_DEVICE_PATH_PROTOCOL * 2931 DevPathFromTextBluetooth ( 2932 IN CHAR16 *TextDeviceNode 2933 ) 2934 { 2935 CHAR16 *BluetoothStr; 2936 BLUETOOTH_DEVICE_PATH *BluetoothDp; 2937 2938 BluetoothStr = GetNextParamStr (&TextDeviceNode); 2939 BluetoothDp = (BLUETOOTH_DEVICE_PATH *)CreateDeviceNode ( 2940 MESSAGING_DEVICE_PATH, 2941 MSG_BLUETOOTH_DP, 2942 (UINT16)sizeof (BLUETOOTH_DEVICE_PATH) 2943 ); 2944 2945 if (BluetoothDp != NULL) { 2946 StrHexToBytes ( 2947 BluetoothStr, 2948 sizeof (BLUETOOTH_ADDRESS) * 2, 2949 BluetoothDp->BD_ADDR.Address, 2950 sizeof (BLUETOOTH_ADDRESS) 2951 ); 2952 } 2953 2954 return (EFI_DEVICE_PATH_PROTOCOL *)BluetoothDp; 2955 } 2956 2957 /** 2958 Converts a text device path node to Wi-Fi device path structure. 2959 2960 @param TextDeviceNode The input Text device path node. 2961 2962 @return A pointer to the newly-created Wi-Fi device path structure. 2963 2964 **/ 2965 static 2966 EFI_DEVICE_PATH_PROTOCOL * 2967 DevPathFromTextWiFi ( 2968 IN CHAR16 *TextDeviceNode 2969 ) 2970 { 2971 CHAR16 *SSIdStr; 2972 CHAR8 AsciiStr[33]; 2973 UINTN DataLen; 2974 WIFI_DEVICE_PATH *WiFiDp; 2975 2976 SSIdStr = GetNextParamStr (&TextDeviceNode); 2977 WiFiDp = (WIFI_DEVICE_PATH *)CreateDeviceNode ( 2978 MESSAGING_DEVICE_PATH, 2979 MSG_WIFI_DP, 2980 (UINT16)sizeof (WIFI_DEVICE_PATH) 2981 ); 2982 2983 if ((NULL != SSIdStr) && (NULL != WiFiDp)) { 2984 DataLen = StrLen (SSIdStr); 2985 if (StrLen (SSIdStr) > 32) { 2986 SSIdStr[32] = '\0'; 2987 DataLen = 32; 2988 } 2989 2990 UnicodeStrToAsciiStrS (SSIdStr, AsciiStr, sizeof (AsciiStr)); 2991 CopyMem (WiFiDp->SSId, AsciiStr, DataLen); 2992 } 2993 2994 return (EFI_DEVICE_PATH_PROTOCOL *)WiFiDp; 2995 } 2996 2997 /** 2998 Converts a text device path node to Bluetooth LE device path structure. 2999 3000 @param TextDeviceNode The input Text device path node. 3001 3002 @return A pointer to the newly-created Bluetooth LE device path structure. 3003 3004 **/ 3005 static 3006 EFI_DEVICE_PATH_PROTOCOL * 3007 DevPathFromTextBluetoothLE ( 3008 IN CHAR16 *TextDeviceNode 3009 ) 3010 { 3011 CHAR16 *BluetoothLeAddrStr; 3012 CHAR16 *BluetoothLeAddrTypeStr; 3013 BLUETOOTH_LE_DEVICE_PATH *BluetoothLeDp; 3014 3015 BluetoothLeAddrStr = GetNextParamStr (&TextDeviceNode); 3016 BluetoothLeAddrTypeStr = GetNextParamStr (&TextDeviceNode); 3017 BluetoothLeDp = (BLUETOOTH_LE_DEVICE_PATH *)CreateDeviceNode ( 3018 MESSAGING_DEVICE_PATH, 3019 MSG_BLUETOOTH_LE_DP, 3020 (UINT16)sizeof (BLUETOOTH_LE_DEVICE_PATH) 3021 ); 3022 3023 if (BluetoothLeDp != NULL) { 3024 BluetoothLeDp->Address.Type = (UINT8)Strtoi (BluetoothLeAddrTypeStr); 3025 StrHexToBytes ( 3026 BluetoothLeAddrStr, 3027 sizeof (BluetoothLeDp->Address.Address) * 2, 3028 BluetoothLeDp->Address.Address, 3029 sizeof (BluetoothLeDp->Address.Address) 3030 ); 3031 } 3032 3033 return (EFI_DEVICE_PATH_PROTOCOL *)BluetoothLeDp; 3034 } 3035 3036 /** 3037 Converts a text device path node to DNS device path structure. 3038 3039 @param TextDeviceNode The input Text device path node. 3040 3041 @return A pointer to the newly-created DNS device path structure. 3042 3043 **/ 3044 static 3045 EFI_DEVICE_PATH_PROTOCOL * 3046 DevPathFromTextDns ( 3047 IN CHAR16 *TextDeviceNode 3048 ) 3049 { 3050 CHAR16 *DeviceNodeStr; 3051 CHAR16 *DeviceNodeStrPtr; 3052 UINT32 DnsServerIpCount; 3053 UINT16 DnsDeviceNodeLength; 3054 DNS_DEVICE_PATH *DnsDeviceNode; 3055 UINT32 DnsServerIpIndex; 3056 CHAR16 *DnsServerIp; 3057 3058 // 3059 // Count the DNS server address number. 3060 // 3061 DeviceNodeStr = UefiDevicePathLibStrDuplicate (TextDeviceNode); 3062 if (DeviceNodeStr == NULL) { 3063 return NULL; 3064 } 3065 3066 DeviceNodeStrPtr = DeviceNodeStr; 3067 3068 DnsServerIpCount = 0; 3069 while (DeviceNodeStrPtr != NULL && *DeviceNodeStrPtr != '\0') { 3070 GetNextParamStr (&DeviceNodeStrPtr); 3071 DnsServerIpCount++; 3072 } 3073 3074 FreePool (DeviceNodeStr); 3075 DeviceNodeStr = NULL; 3076 3077 // 3078 // One or more instances of the DNS server address in EFI_IP_ADDRESS, 3079 // otherwise, NULL will be returned. 3080 // 3081 if (DnsServerIpCount == 0) { 3082 return NULL; 3083 } 3084 3085 // 3086 // Create the DNS DeviceNode. 3087 // 3088 DnsDeviceNodeLength = (UINT16)(sizeof (EFI_DEVICE_PATH_PROTOCOL) + sizeof (UINT8) + DnsServerIpCount * sizeof (EFI_IP_ADDRESS)); 3089 DnsDeviceNode = (DNS_DEVICE_PATH *)CreateDeviceNode ( 3090 MESSAGING_DEVICE_PATH, 3091 MSG_DNS_DP, 3092 DnsDeviceNodeLength 3093 ); 3094 if (DnsDeviceNode == NULL) { 3095 return NULL; 3096 } 3097 3098 // 3099 // Confirm the DNS server address is IPv4 or IPv6 type. 3100 // 3101 DeviceNodeStrPtr = TextDeviceNode; 3102 while (!IS_NULL (*DeviceNodeStrPtr)) { 3103 if (*DeviceNodeStrPtr == '.') { 3104 DnsDeviceNode->IsIPv6 = 0x00; 3105 break; 3106 } 3107 3108 if (*DeviceNodeStrPtr == ':') { 3109 DnsDeviceNode->IsIPv6 = 0x01; 3110 break; 3111 } 3112 3113 DeviceNodeStrPtr++; 3114 } 3115 3116 for (DnsServerIpIndex = 0; DnsServerIpIndex < DnsServerIpCount; DnsServerIpIndex++) { 3117 DnsServerIp = GetNextParamStr (&TextDeviceNode); 3118 if (DnsDeviceNode->IsIPv6 == 0x00) { 3119 StrToIpv4Address (DnsServerIp, NULL, &(DnsDeviceNode->DnsServerIp[DnsServerIpIndex].v4), NULL); 3120 } else { 3121 StrToIpv6Address (DnsServerIp, NULL, &(DnsDeviceNode->DnsServerIp[DnsServerIpIndex].v6), NULL); 3122 } 3123 } 3124 3125 return (EFI_DEVICE_PATH_PROTOCOL *)DnsDeviceNode; 3126 } 3127 3128 /** 3129 Converts a text device path node to URI device path structure. 3130 3131 @param TextDeviceNode The input Text device path node. 3132 3133 @return A pointer to the newly-created URI device path structure. 3134 3135 **/ 3136 static 3137 EFI_DEVICE_PATH_PROTOCOL * 3138 DevPathFromTextUri ( 3139 IN CHAR16 *TextDeviceNode 3140 ) 3141 { 3142 CHAR16 *UriStr; 3143 UINTN UriLength; 3144 URI_DEVICE_PATH *Uri; 3145 3146 UriStr = GetNextParamStr (&TextDeviceNode); 3147 UriLength = StrnLenS (UriStr, MAX_UINT16 - sizeof (URI_DEVICE_PATH)); 3148 Uri = (URI_DEVICE_PATH *)CreateDeviceNode ( 3149 MESSAGING_DEVICE_PATH, 3150 MSG_URI_DP, 3151 (UINT16)(sizeof (URI_DEVICE_PATH) + UriLength) 3152 ); 3153 3154 while (Uri != NULL && UriLength-- != 0) { 3155 Uri->Uri[UriLength] = (CHAR8)UriStr[UriLength]; 3156 } 3157 3158 return (EFI_DEVICE_PATH_PROTOCOL *)Uri; 3159 } 3160 3161 /** 3162 Converts a media text device path node to media device path structure. 3163 3164 @param TextDeviceNode The input Text device path node. 3165 3166 @return A pointer to media device path structure. 3167 3168 **/ 3169 static 3170 EFI_DEVICE_PATH_PROTOCOL * 3171 DevPathFromTextMediaPath ( 3172 IN CHAR16 *TextDeviceNode 3173 ) 3174 { 3175 return DevPathFromTextGenericPath (MEDIA_DEVICE_PATH, TextDeviceNode); 3176 } 3177 3178 /** 3179 Converts a text device path node to HD device path structure. 3180 3181 @param TextDeviceNode The input Text device path node. 3182 3183 @return A pointer to the newly-created HD device path structure. 3184 3185 **/ 3186 static 3187 EFI_DEVICE_PATH_PROTOCOL * 3188 DevPathFromTextHD ( 3189 IN CHAR16 *TextDeviceNode 3190 ) 3191 { 3192 CHAR16 *PartitionStr; 3193 CHAR16 *TypeStr; 3194 CHAR16 *SignatureStr; 3195 CHAR16 *StartStr; 3196 CHAR16 *SizeStr; 3197 UINT32 Signature32; 3198 HARDDRIVE_DEVICE_PATH *Hd; 3199 3200 PartitionStr = GetNextParamStr (&TextDeviceNode); 3201 TypeStr = GetNextParamStr (&TextDeviceNode); 3202 SignatureStr = GetNextParamStr (&TextDeviceNode); 3203 StartStr = GetNextParamStr (&TextDeviceNode); 3204 SizeStr = GetNextParamStr (&TextDeviceNode); 3205 Hd = (HARDDRIVE_DEVICE_PATH *)CreateDeviceNode ( 3206 MEDIA_DEVICE_PATH, 3207 MEDIA_HARDDRIVE_DP, 3208 (UINT16)sizeof (HARDDRIVE_DEVICE_PATH) 3209 ); 3210 3211 if (Hd == NULL) { 3212 return (EFI_DEVICE_PATH_PROTOCOL *)Hd; 3213 } 3214 3215 Hd->PartitionNumber = (UINT32)Strtoi (PartitionStr); 3216 3217 ZeroMem (Hd->Signature, 16); 3218 Hd->MBRType = (UINT8)0; 3219 3220 if (StrCmp (TypeStr, "MBR") == 0) { 3221 Hd->SignatureType = SIGNATURE_TYPE_MBR; 3222 Hd->MBRType = 0x01; 3223 3224 Signature32 = (UINT32)Strtoi (SignatureStr); 3225 CopyMem (Hd->Signature, &Signature32, sizeof (UINT32)); 3226 } else if (StrCmp (TypeStr, "GPT") == 0) { 3227 Hd->SignatureType = SIGNATURE_TYPE_GUID; 3228 Hd->MBRType = 0x02; 3229 3230 StrToGuid (SignatureStr, (EFI_GUID *)Hd->Signature); 3231 } else { 3232 Hd->SignatureType = (UINT8)Strtoi (TypeStr); 3233 } 3234 3235 Strtoi64 (StartStr, &Hd->PartitionStart); 3236 Strtoi64 (SizeStr, &Hd->PartitionSize); 3237 3238 return (EFI_DEVICE_PATH_PROTOCOL *)Hd; 3239 } 3240 3241 /** 3242 Converts a text device path node to CDROM device path structure. 3243 3244 @param TextDeviceNode The input Text device path node. 3245 3246 @return A pointer to the newly-created CDROM device path structure. 3247 3248 **/ 3249 static 3250 EFI_DEVICE_PATH_PROTOCOL * 3251 DevPathFromTextCDROM ( 3252 IN CHAR16 *TextDeviceNode 3253 ) 3254 { 3255 CHAR16 *EntryStr; 3256 CHAR16 *StartStr; 3257 CHAR16 *SizeStr; 3258 CDROM_DEVICE_PATH *CDROMDevPath; 3259 3260 EntryStr = GetNextParamStr (&TextDeviceNode); 3261 StartStr = GetNextParamStr (&TextDeviceNode); 3262 SizeStr = GetNextParamStr (&TextDeviceNode); 3263 CDROMDevPath = (CDROM_DEVICE_PATH *)CreateDeviceNode ( 3264 MEDIA_DEVICE_PATH, 3265 MEDIA_CDROM_DP, 3266 (UINT16)sizeof (CDROM_DEVICE_PATH) 3267 ); 3268 3269 if (CDROMDevPath != NULL) { 3270 CDROMDevPath->BootEntry = (UINT32)Strtoi (EntryStr); 3271 Strtoi64 (StartStr, &CDROMDevPath->PartitionStart); 3272 Strtoi64 (SizeStr, &CDROMDevPath->PartitionSize); 3273 } 3274 3275 return (EFI_DEVICE_PATH_PROTOCOL *)CDROMDevPath; 3276 } 3277 3278 /** 3279 Converts a text device path node to Vendor-defined media device path structure. 3280 3281 @param TextDeviceNode The input Text device path node. 3282 3283 @return A pointer to the newly-created Vendor-defined media device path structure. 3284 3285 **/ 3286 static 3287 EFI_DEVICE_PATH_PROTOCOL * 3288 DevPathFromTextVenMedia ( 3289 IN CHAR16 *TextDeviceNode 3290 ) 3291 { 3292 return ConvertFromTextVendor ( 3293 TextDeviceNode, 3294 MEDIA_DEVICE_PATH, 3295 MEDIA_VENDOR_DP 3296 ); 3297 } 3298 3299 /** 3300 Converts a text device path node to File device path structure. 3301 3302 @param TextDeviceNode The input Text device path node. 3303 3304 @return A pointer to the newly-created File device path structure. 3305 3306 **/ 3307 static 3308 EFI_DEVICE_PATH_PROTOCOL * 3309 DevPathFromTextFilePath ( 3310 IN CHAR16 *TextDeviceNode 3311 ) 3312 { 3313 FILEPATH_DEVICE_PATH *File; 3314 3315 #ifndef __FreeBSD__ 3316 File = (FILEPATH_DEVICE_PATH *)CreateDeviceNode ( 3317 MEDIA_DEVICE_PATH, 3318 MEDIA_FILEPATH_DP, 3319 (UINT16)(sizeof (FILEPATH_DEVICE_PATH) + StrLen (TextDeviceNode) * 2) 3320 ); 3321 3322 if (File != NULL) { 3323 StrCpyS (File->PathName, StrLen (TextDeviceNode) + 1, TextDeviceNode); 3324 } 3325 #else 3326 size_t len = (sizeof (FILEPATH_DEVICE_PATH) + StrLen (TextDeviceNode) * 2); 3327 efi_char *v; 3328 File = (FILEPATH_DEVICE_PATH *)CreateDeviceNode ( 3329 MEDIA_DEVICE_PATH, 3330 MEDIA_FILEPATH_DP, 3331 (UINT16)len 3332 ); 3333 if (File != NULL) { 3334 v = File->PathName; 3335 utf8_to_ucs2(TextDeviceNode, &v, &len); 3336 } 3337 #endif 3338 3339 return (EFI_DEVICE_PATH_PROTOCOL *)File; 3340 } 3341 3342 /** 3343 Converts a text device path node to Media protocol device path structure. 3344 3345 @param TextDeviceNode The input Text device path node. 3346 3347 @return A pointer to the newly-created Media protocol device path structure. 3348 3349 **/ 3350 static 3351 EFI_DEVICE_PATH_PROTOCOL * 3352 DevPathFromTextMedia ( 3353 IN CHAR16 *TextDeviceNode 3354 ) 3355 { 3356 CHAR16 *GuidStr; 3357 MEDIA_PROTOCOL_DEVICE_PATH *Media; 3358 3359 GuidStr = GetNextParamStr (&TextDeviceNode); 3360 Media = (MEDIA_PROTOCOL_DEVICE_PATH *)CreateDeviceNode ( 3361 MEDIA_DEVICE_PATH, 3362 MEDIA_PROTOCOL_DP, 3363 (UINT16)sizeof (MEDIA_PROTOCOL_DEVICE_PATH) 3364 ); 3365 3366 if (Media != NULL) { 3367 StrToGuid (GuidStr, &Media->Protocol); 3368 } 3369 3370 return (EFI_DEVICE_PATH_PROTOCOL *)Media; 3371 } 3372 3373 /** 3374 Converts a text device path node to firmware volume device path structure. 3375 3376 @param TextDeviceNode The input Text device path node. 3377 3378 @return A pointer to the newly-created firmware volume device path structure. 3379 3380 **/ 3381 static 3382 EFI_DEVICE_PATH_PROTOCOL * 3383 DevPathFromTextFv ( 3384 IN CHAR16 *TextDeviceNode 3385 ) 3386 { 3387 CHAR16 *GuidStr; 3388 MEDIA_FW_VOL_DEVICE_PATH *Fv; 3389 3390 GuidStr = GetNextParamStr (&TextDeviceNode); 3391 Fv = (MEDIA_FW_VOL_DEVICE_PATH *)CreateDeviceNode ( 3392 MEDIA_DEVICE_PATH, 3393 MEDIA_PIWG_FW_VOL_DP, 3394 (UINT16)sizeof (MEDIA_FW_VOL_DEVICE_PATH) 3395 ); 3396 3397 if (Fv != NULL) { 3398 StrToGuid (GuidStr, &Fv->FvName); 3399 } 3400 3401 return (EFI_DEVICE_PATH_PROTOCOL *)Fv; 3402 } 3403 3404 /** 3405 Converts a text device path node to firmware file device path structure. 3406 3407 @param TextDeviceNode The input Text device path node. 3408 3409 @return A pointer to the newly-created firmware file device path structure. 3410 3411 **/ 3412 static 3413 EFI_DEVICE_PATH_PROTOCOL * 3414 DevPathFromTextFvFile ( 3415 IN CHAR16 *TextDeviceNode 3416 ) 3417 { 3418 CHAR16 *GuidStr; 3419 MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *FvFile; 3420 3421 GuidStr = GetNextParamStr (&TextDeviceNode); 3422 FvFile = (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH *)CreateDeviceNode ( 3423 MEDIA_DEVICE_PATH, 3424 MEDIA_PIWG_FW_FILE_DP, 3425 (UINT16)sizeof (MEDIA_FW_VOL_FILEPATH_DEVICE_PATH) 3426 ); 3427 3428 if (FvFile != NULL) { 3429 StrToGuid (GuidStr, &FvFile->FvFileName); 3430 } 3431 3432 return (EFI_DEVICE_PATH_PROTOCOL *)FvFile; 3433 } 3434 3435 /** 3436 Converts a text device path node to text relative offset device path structure. 3437 3438 @param TextDeviceNode The input Text device path node. 3439 3440 @return A pointer to the newly-created Text device path structure. 3441 3442 **/ 3443 static 3444 EFI_DEVICE_PATH_PROTOCOL * 3445 DevPathFromTextRelativeOffsetRange ( 3446 IN CHAR16 *TextDeviceNode 3447 ) 3448 { 3449 CHAR16 *StartingOffsetStr; 3450 CHAR16 *EndingOffsetStr; 3451 MEDIA_RELATIVE_OFFSET_RANGE_DEVICE_PATH *Offset; 3452 3453 StartingOffsetStr = GetNextParamStr (&TextDeviceNode); 3454 EndingOffsetStr = GetNextParamStr (&TextDeviceNode); 3455 Offset = (MEDIA_RELATIVE_OFFSET_RANGE_DEVICE_PATH *)CreateDeviceNode ( 3456 MEDIA_DEVICE_PATH, 3457 MEDIA_RELATIVE_OFFSET_RANGE_DP, 3458 (UINT16)sizeof (MEDIA_RELATIVE_OFFSET_RANGE_DEVICE_PATH) 3459 ); 3460 3461 if (Offset != NULL) { 3462 Strtoi64 (StartingOffsetStr, &Offset->StartingOffset); 3463 Strtoi64 (EndingOffsetStr, &Offset->EndingOffset); 3464 } 3465 3466 return (EFI_DEVICE_PATH_PROTOCOL *)Offset; 3467 } 3468 3469 /** 3470 Converts a text device path node to text ram disk device path structure. 3471 3472 @param TextDeviceNode The input Text device path node. 3473 3474 @return A pointer to the newly-created Text device path structure. 3475 3476 **/ 3477 static 3478 EFI_DEVICE_PATH_PROTOCOL * 3479 DevPathFromTextRamDisk ( 3480 IN CHAR16 *TextDeviceNode 3481 ) 3482 { 3483 CHAR16 *StartingAddrStr; 3484 CHAR16 *EndingAddrStr; 3485 CHAR16 *TypeGuidStr; 3486 CHAR16 *InstanceStr; 3487 MEDIA_RAM_DISK_DEVICE_PATH *RamDisk; 3488 UINT64 StartingAddr; 3489 UINT64 EndingAddr; 3490 3491 StartingAddrStr = GetNextParamStr (&TextDeviceNode); 3492 EndingAddrStr = GetNextParamStr (&TextDeviceNode); 3493 InstanceStr = GetNextParamStr (&TextDeviceNode); 3494 TypeGuidStr = GetNextParamStr (&TextDeviceNode); 3495 RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *)CreateDeviceNode ( 3496 MEDIA_DEVICE_PATH, 3497 MEDIA_RAM_DISK_DP, 3498 (UINT16)sizeof (MEDIA_RAM_DISK_DEVICE_PATH) 3499 ); 3500 3501 if (RamDisk != NULL) { 3502 Strtoi64 (StartingAddrStr, &StartingAddr); 3503 WriteUnaligned64 ((UINT64 *)&(RamDisk->StartingAddr[0]), StartingAddr); 3504 Strtoi64 (EndingAddrStr, &EndingAddr); 3505 WriteUnaligned64 ((UINT64 *)&(RamDisk->EndingAddr[0]), EndingAddr); 3506 RamDisk->Instance = (UINT16)Strtoi (InstanceStr); 3507 StrToGuid (TypeGuidStr, &RamDisk->TypeGuid); 3508 } 3509 3510 return (EFI_DEVICE_PATH_PROTOCOL *)RamDisk; 3511 } 3512 3513 /** 3514 Converts a text device path node to text virtual disk device path structure. 3515 3516 @param TextDeviceNode The input Text device path node. 3517 3518 @return A pointer to the newly-created Text device path structure. 3519 3520 **/ 3521 static 3522 EFI_DEVICE_PATH_PROTOCOL * 3523 DevPathFromTextVirtualDisk ( 3524 IN CHAR16 *TextDeviceNode 3525 ) 3526 { 3527 CHAR16 *StartingAddrStr; 3528 CHAR16 *EndingAddrStr; 3529 CHAR16 *InstanceStr; 3530 MEDIA_RAM_DISK_DEVICE_PATH *RamDisk; 3531 UINT64 StartingAddr; 3532 UINT64 EndingAddr; 3533 3534 StartingAddrStr = GetNextParamStr (&TextDeviceNode); 3535 EndingAddrStr = GetNextParamStr (&TextDeviceNode); 3536 InstanceStr = GetNextParamStr (&TextDeviceNode); 3537 3538 RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *)CreateDeviceNode ( 3539 MEDIA_DEVICE_PATH, 3540 MEDIA_RAM_DISK_DP, 3541 (UINT16)sizeof (MEDIA_RAM_DISK_DEVICE_PATH) 3542 ); 3543 3544 if (RamDisk != NULL) { 3545 Strtoi64 (StartingAddrStr, &StartingAddr); 3546 WriteUnaligned64 ((UINT64 *)&(RamDisk->StartingAddr[0]), StartingAddr); 3547 Strtoi64 (EndingAddrStr, &EndingAddr); 3548 WriteUnaligned64 ((UINT64 *)&(RamDisk->EndingAddr[0]), EndingAddr); 3549 RamDisk->Instance = (UINT16)Strtoi (InstanceStr); 3550 CopyGuid (&RamDisk->TypeGuid, &gEfiVirtualDiskGuid); 3551 } 3552 3553 return (EFI_DEVICE_PATH_PROTOCOL *)RamDisk; 3554 } 3555 3556 /** 3557 Converts a text device path node to text virtual cd device path structure. 3558 3559 @param TextDeviceNode The input Text device path node. 3560 3561 @return A pointer to the newly-created Text device path structure. 3562 3563 **/ 3564 static 3565 EFI_DEVICE_PATH_PROTOCOL * 3566 DevPathFromTextVirtualCd ( 3567 IN CHAR16 *TextDeviceNode 3568 ) 3569 { 3570 CHAR16 *StartingAddrStr; 3571 CHAR16 *EndingAddrStr; 3572 CHAR16 *InstanceStr; 3573 MEDIA_RAM_DISK_DEVICE_PATH *RamDisk; 3574 UINT64 StartingAddr; 3575 UINT64 EndingAddr; 3576 3577 StartingAddrStr = GetNextParamStr (&TextDeviceNode); 3578 EndingAddrStr = GetNextParamStr (&TextDeviceNode); 3579 InstanceStr = GetNextParamStr (&TextDeviceNode); 3580 3581 RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *)CreateDeviceNode ( 3582 MEDIA_DEVICE_PATH, 3583 MEDIA_RAM_DISK_DP, 3584 (UINT16)sizeof (MEDIA_RAM_DISK_DEVICE_PATH) 3585 ); 3586 3587 if (RamDisk != NULL) { 3588 Strtoi64 (StartingAddrStr, &StartingAddr); 3589 WriteUnaligned64 ((UINT64 *)&(RamDisk->StartingAddr[0]), StartingAddr); 3590 Strtoi64 (EndingAddrStr, &EndingAddr); 3591 WriteUnaligned64 ((UINT64 *)&(RamDisk->EndingAddr[0]), EndingAddr); 3592 RamDisk->Instance = (UINT16)Strtoi (InstanceStr); 3593 CopyGuid (&RamDisk->TypeGuid, &gEfiVirtualCdGuid); 3594 } 3595 3596 return (EFI_DEVICE_PATH_PROTOCOL *)RamDisk; 3597 } 3598 3599 /** 3600 Converts a text device path node to text persistent virtual disk device path structure. 3601 3602 @param TextDeviceNode The input Text device path node. 3603 3604 @return A pointer to the newly-created Text device path structure. 3605 3606 **/ 3607 static 3608 EFI_DEVICE_PATH_PROTOCOL * 3609 DevPathFromTextPersistentVirtualDisk ( 3610 IN CHAR16 *TextDeviceNode 3611 ) 3612 { 3613 CHAR16 *StartingAddrStr; 3614 CHAR16 *EndingAddrStr; 3615 CHAR16 *InstanceStr; 3616 MEDIA_RAM_DISK_DEVICE_PATH *RamDisk; 3617 UINT64 StartingAddr; 3618 UINT64 EndingAddr; 3619 3620 StartingAddrStr = GetNextParamStr (&TextDeviceNode); 3621 EndingAddrStr = GetNextParamStr (&TextDeviceNode); 3622 InstanceStr = GetNextParamStr (&TextDeviceNode); 3623 3624 RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *)CreateDeviceNode ( 3625 MEDIA_DEVICE_PATH, 3626 MEDIA_RAM_DISK_DP, 3627 (UINT16)sizeof (MEDIA_RAM_DISK_DEVICE_PATH) 3628 ); 3629 3630 if (RamDisk != NULL) { 3631 Strtoi64 (StartingAddrStr, &StartingAddr); 3632 WriteUnaligned64 ((UINT64 *)&(RamDisk->StartingAddr[0]), StartingAddr); 3633 Strtoi64 (EndingAddrStr, &EndingAddr); 3634 WriteUnaligned64 ((UINT64 *)&(RamDisk->EndingAddr[0]), EndingAddr); 3635 RamDisk->Instance = (UINT16)Strtoi (InstanceStr); 3636 CopyGuid (&RamDisk->TypeGuid, &gEfiPersistentVirtualDiskGuid); 3637 } 3638 3639 return (EFI_DEVICE_PATH_PROTOCOL *)RamDisk; 3640 } 3641 3642 /** 3643 Converts a text device path node to text persistent virtual cd device path structure. 3644 3645 @param TextDeviceNode The input Text device path node. 3646 3647 @return A pointer to the newly-created Text device path structure. 3648 3649 **/ 3650 static 3651 EFI_DEVICE_PATH_PROTOCOL * 3652 DevPathFromTextPersistentVirtualCd ( 3653 IN CHAR16 *TextDeviceNode 3654 ) 3655 { 3656 CHAR16 *StartingAddrStr; 3657 CHAR16 *EndingAddrStr; 3658 CHAR16 *InstanceStr; 3659 MEDIA_RAM_DISK_DEVICE_PATH *RamDisk; 3660 UINT64 StartingAddr; 3661 UINT64 EndingAddr; 3662 3663 StartingAddrStr = GetNextParamStr (&TextDeviceNode); 3664 EndingAddrStr = GetNextParamStr (&TextDeviceNode); 3665 InstanceStr = GetNextParamStr (&TextDeviceNode); 3666 3667 RamDisk = (MEDIA_RAM_DISK_DEVICE_PATH *)CreateDeviceNode ( 3668 MEDIA_DEVICE_PATH, 3669 MEDIA_RAM_DISK_DP, 3670 (UINT16)sizeof (MEDIA_RAM_DISK_DEVICE_PATH) 3671 ); 3672 3673 if (RamDisk != NULL) { 3674 Strtoi64 (StartingAddrStr, &StartingAddr); 3675 WriteUnaligned64 ((UINT64 *)&(RamDisk->StartingAddr[0]), StartingAddr); 3676 Strtoi64 (EndingAddrStr, &EndingAddr); 3677 WriteUnaligned64 ((UINT64 *)&(RamDisk->EndingAddr[0]), EndingAddr); 3678 RamDisk->Instance = (UINT16)Strtoi (InstanceStr); 3679 CopyGuid (&RamDisk->TypeGuid, &gEfiPersistentVirtualCdGuid); 3680 } 3681 3682 return (EFI_DEVICE_PATH_PROTOCOL *)RamDisk; 3683 } 3684 3685 /** 3686 Converts a BBS text device path node to BBS device path structure. 3687 3688 @param TextDeviceNode The input Text device path node. 3689 3690 @return A pointer to BBS device path structure. 3691 3692 **/ 3693 static 3694 EFI_DEVICE_PATH_PROTOCOL * 3695 DevPathFromTextBbsPath ( 3696 IN CHAR16 *TextDeviceNode 3697 ) 3698 { 3699 return DevPathFromTextGenericPath (BBS_DEVICE_PATH, TextDeviceNode); 3700 } 3701 3702 /** 3703 Converts a text device path node to BIOS Boot Specification device path structure. 3704 3705 @param TextDeviceNode The input Text device path node. 3706 3707 @return A pointer to the newly-created BIOS Boot Specification device path structure. 3708 3709 **/ 3710 static 3711 EFI_DEVICE_PATH_PROTOCOL * 3712 DevPathFromTextBBS ( 3713 IN CHAR16 *TextDeviceNode 3714 ) 3715 { 3716 CHAR16 *TypeStr; 3717 CHAR16 *IdStr; 3718 CHAR16 *FlagsStr; 3719 CHAR8 *AsciiStr; 3720 BBS_BBS_DEVICE_PATH *Bbs; 3721 3722 TypeStr = GetNextParamStr (&TextDeviceNode); 3723 IdStr = GetNextParamStr (&TextDeviceNode); 3724 FlagsStr = GetNextParamStr (&TextDeviceNode); 3725 Bbs = (BBS_BBS_DEVICE_PATH *)CreateDeviceNode ( 3726 BBS_DEVICE_PATH, 3727 BBS_BBS_DP, 3728 (UINT16)(sizeof (BBS_BBS_DEVICE_PATH) + StrLen (IdStr)) 3729 ); 3730 3731 if (Bbs == NULL) { 3732 return (EFI_DEVICE_PATH_PROTOCOL *)Bbs; 3733 } 3734 3735 if (StrCmp (TypeStr, "Floppy") == 0) { 3736 Bbs->DeviceType = BBS_TYPE_FLOPPY; 3737 } else if (StrCmp (TypeStr, "HD") == 0) { 3738 Bbs->DeviceType = BBS_TYPE_HARDDRIVE; 3739 } else if (StrCmp (TypeStr, "CDROM") == 0) { 3740 Bbs->DeviceType = BBS_TYPE_CDROM; 3741 } else if (StrCmp (TypeStr, "PCMCIA") == 0) { 3742 Bbs->DeviceType = BBS_TYPE_PCMCIA; 3743 } else if (StrCmp (TypeStr, "USB") == 0) { 3744 Bbs->DeviceType = BBS_TYPE_USB; 3745 } else if (StrCmp (TypeStr, "Network") == 0) { 3746 Bbs->DeviceType = BBS_TYPE_EMBEDDED_NETWORK; 3747 } else { 3748 Bbs->DeviceType = (UINT16)Strtoi (TypeStr); 3749 } 3750 3751 AsciiStr = Bbs->String; 3752 StrToAscii (IdStr, &AsciiStr); 3753 3754 Bbs->StatusFlag = (UINT16)Strtoi (FlagsStr); 3755 3756 return (EFI_DEVICE_PATH_PROTOCOL *)Bbs; 3757 } 3758 3759 /** 3760 Converts a text device path node to SATA device path structure. 3761 3762 @param TextDeviceNode The input Text device path node. 3763 3764 @return A pointer to the newly-created SATA device path structure. 3765 3766 **/ 3767 static 3768 EFI_DEVICE_PATH_PROTOCOL * 3769 DevPathFromTextSata ( 3770 IN CHAR16 *TextDeviceNode 3771 ) 3772 { 3773 SATA_DEVICE_PATH *Sata; 3774 CHAR16 *Param1; 3775 CHAR16 *Param2; 3776 CHAR16 *Param3; 3777 3778 Param1 = GetNextParamStr (&TextDeviceNode); 3779 Param2 = GetNextParamStr (&TextDeviceNode); 3780 Param3 = GetNextParamStr (&TextDeviceNode); 3781 3782 Sata = (SATA_DEVICE_PATH *)CreateDeviceNode ( 3783 MESSAGING_DEVICE_PATH, 3784 MSG_SATA_DP, 3785 (UINT16)sizeof (SATA_DEVICE_PATH) 3786 ); 3787 3788 if (Sata == NULL) { 3789 return (EFI_DEVICE_PATH_PROTOCOL *)Sata; 3790 } 3791 3792 Sata->HBAPortNumber = (UINT16)Strtoi (Param1); 3793 3794 // 3795 // According to UEFI spec, if PMPN is not provided, the default is 0xFFFF 3796 // 3797 if (*Param2 == '\0' ) { 3798 Sata->PortMultiplierPortNumber = 0xFFFF; 3799 } else { 3800 Sata->PortMultiplierPortNumber = (UINT16)Strtoi (Param2); 3801 } 3802 3803 Sata->Lun = (UINT16)Strtoi (Param3); 3804 3805 return (EFI_DEVICE_PATH_PROTOCOL *)Sata; 3806 } 3807 3808 GLOBAL_REMOVE_IF_UNREFERENCED DEVICE_PATH_FROM_TEXT_TABLE mUefiDevicePathLibDevPathFromTextTable[] = { 3809 { "Path", DevPathFromTextPath }, 3810 3811 { "HardwarePath", DevPathFromTextHardwarePath }, 3812 { "Pci", DevPathFromTextPci }, 3813 { "PcCard", DevPathFromTextPcCard }, 3814 { "MemoryMapped", DevPathFromTextMemoryMapped }, 3815 { "VenHw", DevPathFromTextVenHw }, 3816 { "Ctrl", DevPathFromTextCtrl }, 3817 { "BMC", DevPathFromTextBmc }, 3818 3819 { "AcpiPath", DevPathFromTextAcpiPath }, 3820 { "Acpi", DevPathFromTextAcpi }, 3821 { "PciRoot", DevPathFromTextPciRoot }, 3822 { "PcieRoot", DevPathFromTextPcieRoot }, 3823 { "Floppy", DevPathFromTextFloppy }, 3824 { "Keyboard", DevPathFromTextKeyboard }, 3825 { "Serial", DevPathFromTextSerial }, 3826 { "ParallelPort", DevPathFromTextParallelPort }, 3827 { "AcpiEx", DevPathFromTextAcpiEx }, 3828 { "AcpiExp", DevPathFromTextAcpiExp }, 3829 { "AcpiAdr", DevPathFromTextAcpiAdr }, 3830 3831 { "Msg", DevPathFromTextMsg }, 3832 { "Ata", DevPathFromTextAta }, 3833 { "Scsi", DevPathFromTextScsi }, 3834 { "Fibre", DevPathFromTextFibre }, 3835 { "FibreEx", DevPathFromTextFibreEx }, 3836 { "I1394", DevPathFromText1394 }, 3837 { "USB", DevPathFromTextUsb }, 3838 { "I2O", DevPathFromTextI2O }, 3839 { "Infiniband", DevPathFromTextInfiniband }, 3840 { "VenMsg", DevPathFromTextVenMsg }, 3841 { "VenPcAnsi", DevPathFromTextVenPcAnsi }, 3842 { "VenVt100", DevPathFromTextVenVt100 }, 3843 { "VenVt100Plus", DevPathFromTextVenVt100Plus }, 3844 { "VenUtf8", DevPathFromTextVenUtf8 }, 3845 { "UartFlowCtrl", DevPathFromTextUartFlowCtrl }, 3846 { "SAS", DevPathFromTextSAS }, 3847 { "SasEx", DevPathFromTextSasEx }, 3848 { "NVMe", DevPathFromTextNVMe }, 3849 { "UFS", DevPathFromTextUfs }, 3850 { "SD", DevPathFromTextSd }, 3851 { "eMMC", DevPathFromTextEmmc }, 3852 { "DebugPort", DevPathFromTextDebugPort }, 3853 { "MAC", DevPathFromTextMAC }, 3854 { "IPv4", DevPathFromTextIPv4 }, 3855 { "IPv6", DevPathFromTextIPv6 }, 3856 { "Uart", DevPathFromTextUart }, 3857 { "UsbClass", DevPathFromTextUsbClass }, 3858 { "UsbAudio", DevPathFromTextUsbAudio }, 3859 { "UsbCDCControl", DevPathFromTextUsbCDCControl }, 3860 { "UsbHID", DevPathFromTextUsbHID }, 3861 { "UsbImage", DevPathFromTextUsbImage }, 3862 { "UsbPrinter", DevPathFromTextUsbPrinter }, 3863 { "UsbMassStorage", DevPathFromTextUsbMassStorage }, 3864 { "UsbHub", DevPathFromTextUsbHub }, 3865 { "UsbCDCData", DevPathFromTextUsbCDCData }, 3866 { "UsbSmartCard", DevPathFromTextUsbSmartCard }, 3867 { "UsbVideo", DevPathFromTextUsbVideo }, 3868 { "UsbDiagnostic", DevPathFromTextUsbDiagnostic }, 3869 { "UsbWireless", DevPathFromTextUsbWireless }, 3870 { "UsbDeviceFirmwareUpdate", DevPathFromTextUsbDeviceFirmwareUpdate }, 3871 { "UsbIrdaBridge", DevPathFromTextUsbIrdaBridge }, 3872 { "UsbTestAndMeasurement", DevPathFromTextUsbTestAndMeasurement }, 3873 { "UsbWwid", DevPathFromTextUsbWwid }, 3874 { "Unit", DevPathFromTextUnit }, 3875 { "iSCSI", DevPathFromTextiSCSI }, 3876 { "Vlan", DevPathFromTextVlan }, 3877 { "Dns", DevPathFromTextDns }, 3878 { "Uri", DevPathFromTextUri }, 3879 { "Bluetooth", DevPathFromTextBluetooth }, 3880 { "Wi-Fi", DevPathFromTextWiFi }, 3881 { "BluetoothLE", DevPathFromTextBluetoothLE }, 3882 { "MediaPath", DevPathFromTextMediaPath }, 3883 { "HD", DevPathFromTextHD }, 3884 { "CDROM", DevPathFromTextCDROM }, 3885 { "VenMedia", DevPathFromTextVenMedia }, 3886 { "Media", DevPathFromTextMedia }, 3887 { "Fv", DevPathFromTextFv }, 3888 { "FvFile", DevPathFromTextFvFile }, 3889 { "File", DevPathFromTextFilePath }, 3890 { "Offset", DevPathFromTextRelativeOffsetRange }, 3891 { "RamDisk", DevPathFromTextRamDisk }, 3892 { "VirtualDisk", DevPathFromTextVirtualDisk }, 3893 { "VirtualCD", DevPathFromTextVirtualCd }, 3894 { "PersistentVirtualDisk", DevPathFromTextPersistentVirtualDisk }, 3895 { "PersistentVirtualCD", DevPathFromTextPersistentVirtualCd }, 3896 3897 { "BbsPath", DevPathFromTextBbsPath }, 3898 { "BBS", DevPathFromTextBBS }, 3899 { "Sata", DevPathFromTextSata }, 3900 { NULL, NULL } 3901 }; 3902 3903 /** 3904 Convert text to the binary representation of a device node. 3905 3906 @param TextDeviceNode TextDeviceNode points to the text representation of a device 3907 node. Conversion starts with the first character and continues 3908 until the first non-device node character. 3909 3910 @return A pointer to the EFI device node or NULL if TextDeviceNode is NULL or there was 3911 insufficient memory or text unsupported. 3912 3913 **/ 3914 static 3915 EFI_DEVICE_PATH_PROTOCOL * 3916 EFIAPI 3917 UefiDevicePathLibConvertTextToDeviceNode ( 3918 IN CONST CHAR16 *TextDeviceNode 3919 ) 3920 { 3921 DEVICE_PATH_FROM_TEXT FromText; 3922 CHAR16 *ParamStr; 3923 EFI_DEVICE_PATH_PROTOCOL *DeviceNode; 3924 CHAR16 *DeviceNodeStr; 3925 UINTN Index; 3926 3927 if ((TextDeviceNode == NULL) || (IS_NULL (*TextDeviceNode))) { 3928 return NULL; 3929 } 3930 3931 ParamStr = NULL; 3932 FromText = NULL; 3933 DeviceNodeStr = UefiDevicePathLibStrDuplicate (TextDeviceNode); 3934 ASSERT (DeviceNodeStr != NULL); 3935 3936 for (Index = 0; mUefiDevicePathLibDevPathFromTextTable[Index].Function != NULL; Index++) { 3937 ParamStr = GetParamByNodeName (DeviceNodeStr, mUefiDevicePathLibDevPathFromTextTable[Index].DevicePathNodeText); 3938 if (ParamStr != NULL) { 3939 FromText = mUefiDevicePathLibDevPathFromTextTable[Index].Function; 3940 break; 3941 } 3942 } 3943 3944 if (FromText == NULL) { 3945 // 3946 // A file path 3947 // 3948 FromText = DevPathFromTextFilePath; 3949 DeviceNode = FromText (DeviceNodeStr); 3950 } else { 3951 DeviceNode = FromText (ParamStr); 3952 FreePool (ParamStr); 3953 } 3954 3955 FreePool (DeviceNodeStr); 3956 3957 return DeviceNode; 3958 } 3959 3960 /** 3961 Convert text to the binary representation of a device path. 3962 3963 3964 @param TextDevicePath TextDevicePath points to the text representation of a device 3965 path. Conversion starts with the first character and continues 3966 until the first non-device node character. 3967 3968 @return A pointer to the allocated device path or NULL if TextDeviceNode is NULL or 3969 there was insufficient memory. 3970 3971 **/ 3972 static 3973 EFI_DEVICE_PATH_PROTOCOL * 3974 EFIAPI 3975 UefiDevicePathLibConvertTextToDevicePath ( 3976 IN CONST CHAR16 *TextDevicePath 3977 ) 3978 { 3979 EFI_DEVICE_PATH_PROTOCOL *DeviceNode; 3980 EFI_DEVICE_PATH_PROTOCOL *NewDevicePath; 3981 CHAR16 *DevicePathStr; 3982 CHAR16 *Str; 3983 CHAR16 *DeviceNodeStr; 3984 BOOLEAN IsInstanceEnd; 3985 EFI_DEVICE_PATH_PROTOCOL *DevicePath; 3986 3987 if ((TextDevicePath == NULL) || (IS_NULL (*TextDevicePath))) { 3988 return NULL; 3989 } 3990 3991 DevicePath = (EFI_DEVICE_PATH_PROTOCOL *)AllocatePool (END_DEVICE_PATH_LENGTH); 3992 3993 if (DevicePath == NULL) { 3994 ASSERT (DevicePath != NULL); 3995 return NULL; 3996 } 3997 3998 SetDevicePathEndNode (DevicePath); 3999 4000 DevicePathStr = UefiDevicePathLibStrDuplicate (TextDevicePath); 4001 4002 if (DevicePathStr == NULL) { 4003 return NULL; 4004 } 4005 4006 Str = DevicePathStr; 4007 while ((DeviceNodeStr = GetNextDeviceNodeStr (&Str, &IsInstanceEnd)) != NULL) { 4008 DeviceNode = UefiDevicePathLibConvertTextToDeviceNode (DeviceNodeStr); 4009 4010 NewDevicePath = AppendDevicePathNode (DevicePath, DeviceNode); 4011 if (DevicePath != NULL) { 4012 FreePool (DevicePath); 4013 } 4014 4015 if (DeviceNode != NULL) { 4016 FreePool (DeviceNode); 4017 } 4018 4019 DevicePath = NewDevicePath; 4020 4021 if (IsInstanceEnd) { 4022 DeviceNode = (EFI_DEVICE_PATH_PROTOCOL *)AllocatePool (END_DEVICE_PATH_LENGTH); 4023 if (DeviceNode == NULL) { 4024 ASSERT (DeviceNode != NULL); 4025 return NULL; 4026 } 4027 4028 SetDevicePathEndNode (DeviceNode); 4029 DeviceNode->SubType = END_INSTANCE_DEVICE_PATH_SUBTYPE; 4030 4031 NewDevicePath = AppendDevicePathNode (DevicePath, DeviceNode); 4032 if (DevicePath != NULL) { 4033 FreePool (DevicePath); 4034 } 4035 4036 if (DeviceNode != NULL) { 4037 FreePool (DeviceNode); 4038 } 4039 4040 DevicePath = NewDevicePath; 4041 } 4042 } 4043 4044 FreePool (DevicePathStr); 4045 return DevicePath; 4046 } 4047 4048 ssize_t 4049 efidp_parse_device_path(char *path, efidp out, size_t max) 4050 { 4051 EFI_DEVICE_PATH_PROTOCOL *dp; 4052 UINTN len; 4053 4054 dp = UefiDevicePathLibConvertTextToDevicePath (path); 4055 if (dp == NULL) 4056 return -1; 4057 len = GetDevicePathSize(dp); 4058 if (len > max) { 4059 free(dp); 4060 return -1; 4061 } 4062 memcpy(out, dp, len); 4063 free(dp); 4064 4065 return len; 4066 } 4067