1 /******************************************************************************
3 * Module Name: osefixf - EFI OSL interfaces
5 *****************************************************************************/
8 * Copyright (C) 2000 - 2014, Intel Corp.
11 * Redistribution and use in source and binary forms, with or without
12 * modification, are permitted provided that the following conditions
14 * 1. Redistributions of source code must retain the above copyright
15 * notice, this list of conditions, and the following disclaimer,
16 * without modification.
17 * 2. Redistributions in binary form must reproduce at minimum a disclaimer
18 * substantially similar to the "NO WARRANTY" disclaimer below
19 * ("Disclaimer") and any redistribution must be conditioned upon
20 * including a substantially similar Disclaimer requirement for further
21 * binary redistribution.
22 * 3. Neither the names of the above-listed copyright holders nor the names
23 * of any contributors may be used to endorse or promote products derived
24 * from this software without specific prior written permission.
26 * Alternatively, this software may be distributed under the terms of the
27 * GNU General Public License ("GPL") version 2 as published by the Free
28 * Software Foundation.
31 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
32 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
33 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTIBILITY AND FITNESS FOR
34 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
35 * HOLDERS OR CONTRIBUTORS BE LIABLE FOR SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
36 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
37 * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
38 * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT,
39 * STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING
40 * IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
41 * POSSIBILITY OF SUCH DAMAGES.
49 /* Local definitions */
51 #define ACPI_EFI_PRINT_LENGTH 256
54 /* Local prototypes */
75 static ACPI_PHYSICAL_ADDRESS
76 AcpiEfiGetRsdpViaGuid (
90 static EFI_FILE_HANDLE AcpiGbl_EfiCurrentVolume = NULL;
93 /******************************************************************************
95 * FUNCTION: AcpiEfiGetRsdpViaGuid
97 * PARAMETERS: Guid1 - GUID to compare
98 * Guid2 - GUID to compare
100 * RETURN: TRUE if Guid1 == Guid2
102 * DESCRIPTION: Compares two GUIDs
104 *****************************************************************************/
116 g1 = (INT32 *) Guid1;
117 g2 = (INT32 *) Guid2;
124 return (r ? FALSE : TRUE);
128 /******************************************************************************
130 * FUNCTION: AcpiEfiGetRsdpViaGuid
134 * RETURN: RSDP address if found
136 * DESCRIPTION: Find RSDP address via EFI using specified GUID.
138 *****************************************************************************/
140 static ACPI_PHYSICAL_ADDRESS
141 AcpiEfiGetRsdpViaGuid (
144 unsigned long Address = 0;
148 for (i = 0; i < ST->NumberOfTableEntries; i++)
150 if (AcpiEfiCompareGuid (&ST->ConfigurationTable[i].VendorGuid, Guid))
152 Address = (ACPI_PHYSICAL_ADDRESS)
153 ST->ConfigurationTable[i].VendorTable;
158 return ((ACPI_PHYSICAL_ADDRESS) (Address));
162 /******************************************************************************
164 * FUNCTION: AcpiOsGetRootPointer
168 * RETURN: RSDP physical address
170 * DESCRIPTION: Gets the ACPI root pointer (RSDP)
172 *****************************************************************************/
174 ACPI_PHYSICAL_ADDRESS
175 AcpiOsGetRootPointer (
178 ACPI_PHYSICAL_ADDRESS Address;
179 EFI_GUID Guid10 = ACPI_TABLE_GUID;
180 EFI_GUID Guid20 = ACPI_20_TABLE_GUID;
183 Address = AcpiEfiGetRsdpViaGuid (&Guid20);
186 Address = AcpiEfiGetRsdpViaGuid (&Guid10);
193 /******************************************************************************
195 * FUNCTION: AcpiOsMapMemory
197 * PARAMETERS: where - Physical address of memory to be mapped
198 * length - How much memory to map
200 * RETURN: Pointer to mapped memory. Null on error.
202 * DESCRIPTION: Map physical memory into caller's address space
204 *****************************************************************************/
208 ACPI_PHYSICAL_ADDRESS where,
212 return (ACPI_TO_POINTER ((ACPI_SIZE) where));
216 /******************************************************************************
218 * FUNCTION: AcpiOsUnmapMemory
220 * PARAMETERS: where - Logical address of memory to be unmapped
221 * length - How much memory to unmap
225 * DESCRIPTION: Delete a previously created mapping. Where and Length must
226 * correspond to a previous mapping exactly.
228 *****************************************************************************/
240 /******************************************************************************
242 * FUNCTION: Spinlock interfaces
244 * DESCRIPTION: No-op on single threaded BIOS
246 *****************************************************************************/
250 ACPI_SPINLOCK *OutHandle)
257 ACPI_SPINLOCK Handle)
263 ACPI_SPINLOCK Handle)
270 ACPI_SPINLOCK Handle,
271 ACPI_CPU_FLAGS Flags)
276 /******************************************************************************
278 * FUNCTION: AcpiOsAllocate
280 * PARAMETERS: Size - Amount to allocate, in bytes
282 * RETURN: Pointer to the new allocation. Null on error.
284 * DESCRIPTION: Allocate memory. Algorithm is dependent on the OS.
286 *****************************************************************************/
292 EFI_STATUS EfiStatus;
296 EfiStatus = uefi_call_wrapper (BS->AllocatePool, 3,
297 EfiLoaderData, Size, &Mem);
298 if (EFI_ERROR (EfiStatus))
300 AcpiLogError ("EFI_BOOT_SERVICES->AllocatePool(EfiLoaderData) failure.\n");
308 #ifdef USE_NATIVE_ALLOCATE_ZEROED
309 /******************************************************************************
311 * FUNCTION: AcpiOsAllocateZeroed
313 * PARAMETERS: Size - Amount to allocate, in bytes
315 * RETURN: Pointer to the new allocation. Null on error.
317 * DESCRIPTION: Allocate and zero memory. Algorithm is dependent on the OS.
319 *****************************************************************************/
322 AcpiOsAllocateZeroed (
328 Mem = AcpiOsAllocate (Size);
331 ACPI_MEMSET (Mem, 0, Size);
339 /******************************************************************************
341 * FUNCTION: AcpiOsFree
343 * PARAMETERS: Mem - Pointer to previously allocated memory
347 * DESCRIPTION: Free memory allocated via AcpiOsAllocate
349 *****************************************************************************/
356 uefi_call_wrapper (BS->FreePool, 1, Mem);
360 /*******************************************************************************
362 * FUNCTION: AcpiOsOpenFile
364 * PARAMETERS: Path - File path
365 * Modes - File operation type
367 * RETURN: File descriptor
369 * DESCRIPTION: Open a file for reading (ACPI_FILE_READING) or/and writing
370 * (ACPI_FILE_WRITING).
372 ******************************************************************************/
379 EFI_STATUS EfiStatus = EFI_SUCCESS;
381 EFI_FILE_HANDLE EfiFile = NULL;
382 CHAR16 *Path16 = NULL;
395 OpenModes = EFI_FILE_MODE_READ;
396 if (Modes & ACPI_FILE_WRITING)
398 OpenModes |= (EFI_FILE_MODE_WRITE | EFI_FILE_MODE_CREATE);
401 /* Allocate path buffer */
403 Count = ACPI_STRLEN (Path);
404 Path16 = ACPI_ALLOCATE_ZEROED ((Count + 1) * sizeof (CHAR16));
407 EfiStatus = EFI_BAD_BUFFER_SIZE;
412 while (*Pos == '/' || *Pos == '\\')
417 for (i = 0; i < Count; i++)
431 EfiStatus = uefi_call_wrapper (AcpiGbl_EfiCurrentVolume->Open, 5,
432 AcpiGbl_EfiCurrentVolume, &EfiFile, Path16, OpenModes, 0);
433 if (EFI_ERROR (EfiStatus))
435 AcpiLogError ("EFI_FILE_HANDLE->Open() failure.\n");
446 return ((ACPI_FILE) EfiFile);
450 /*******************************************************************************
452 * FUNCTION: AcpiOsCloseFile
454 * PARAMETERS: File - File descriptor
458 * DESCRIPTION: Close a file.
460 ******************************************************************************/
466 EFI_FILE_HANDLE EfiFile;
469 if (File == ACPI_FILE_OUT ||
470 File == ACPI_FILE_ERR)
474 EfiFile = (EFI_FILE_HANDLE) File;
475 (void) uefi_call_wrapper (AcpiGbl_EfiCurrentVolume->Close, 1, EfiFile);
481 /*******************************************************************************
483 * FUNCTION: AcpiOsReadFile
485 * PARAMETERS: File - File descriptor
486 * Buffer - Data buffer
487 * Size - Data block size
488 * Count - Number of data blocks
490 * RETURN: Size of successfully read buffer
492 * DESCRIPTION: Read from a file.
494 ******************************************************************************/
504 EFI_FILE_HANDLE EfiFile;
506 EFI_STATUS EfiStatus;
509 if (File == ACPI_FILE_OUT ||
510 File == ACPI_FILE_ERR)
515 EfiFile = (EFI_FILE_HANDLE) File;
520 ReadSize = Size * Count;
522 EfiStatus = uefi_call_wrapper (AcpiGbl_EfiCurrentVolume->Read, 3,
523 EfiFile, &ReadSize, Buffer);
524 if (EFI_ERROR (EfiStatus))
526 AcpiLogError ("EFI_FILE_HANDLE->Read() failure.\n");
538 /*******************************************************************************
540 * FUNCTION: AcpiEfiFlushFile
542 * PARAMETERS: File - File descriptor
543 * Begin - String with boundary
544 * End - Boundary of the string
545 * Pos - Current position
546 * FlushAll - Whether checking boundary before flushing
548 * RETURN: Updated position
550 * DESCRIPTION: Flush cached buffer to the file.
552 ******************************************************************************/
563 if (FlushAll || Pos >= (End - 1))
566 uefi_call_wrapper (File->OutputString, 2, File, Begin);
574 /*******************************************************************************
576 * FUNCTION: AcpiOsWriteFile
578 * PARAMETERS: File - File descriptor
579 * Buffer - Data buffer
580 * Size - Data block size
581 * Count - Number of data blocks
583 * RETURN: Size of successfully written buffer
585 * DESCRIPTION: Write to a file.
587 ******************************************************************************/
597 CHAR16 String[ACPI_EFI_PRINT_LENGTH];
602 EFI_FILE_HANDLE EfiFile;
604 EFI_STATUS EfiStatus;
607 if (File == ACPI_FILE_OUT ||
608 File == ACPI_FILE_ERR)
611 End = String + ACPI_EFI_PRINT_LENGTH - 1;
612 Ascii = ACPI_CAST_PTR (const char, Buffer);
615 for (j = 0; j < Count; j++)
617 for (i = 0; i < Size; i++)
622 Pos = AcpiEfiFlushFile (File, String,
627 Pos = AcpiEfiFlushFile (File, String,
631 Pos = AcpiEfiFlushFile (File, String, End, Pos, TRUE);
635 EfiFile = (EFI_FILE_HANDLE) File;
640 WriteSize = Size * Count;
642 EfiStatus = uefi_call_wrapper (AcpiGbl_EfiCurrentVolume->Write, 3,
643 EfiFile, &WriteSize, Buffer);
644 if (EFI_ERROR (EfiStatus))
646 AcpiLogError ("EFI_FILE_HANDLE->Write() failure.\n");
658 /*******************************************************************************
660 * FUNCTION: AcpiOsGetFileOffset
662 * PARAMETERS: File - File descriptor
664 * RETURN: Size of current position
666 * DESCRIPTION: Get current file offset.
668 ******************************************************************************/
671 AcpiOsGetFileOffset (
681 /*******************************************************************************
683 * FUNCTION: AcpiOsSetFileOffset
685 * PARAMETERS: File - File descriptor
686 * Offset - File offset
687 * From - From begin/end of file
691 * DESCRIPTION: Set current file offset.
693 ******************************************************************************/
696 AcpiOsSetFileOffset (
706 /******************************************************************************
708 * FUNCTION: AcpiOsPrintf
710 * PARAMETERS: Format, ... - Standard printf format
714 * DESCRIPTION: Formatted output.
716 *****************************************************************************/
718 void ACPI_INTERNAL_VAR_XFACE
726 va_start (Args, Format);
727 AcpiOsVprintf (Format, Args);
732 /******************************************************************************
734 * FUNCTION: AcpiOsVprintf
736 * PARAMETERS: Format - Standard printf format
737 * Args - Argument list
741 * DESCRIPTION: Formatted output with arguments list pointer.
743 *****************************************************************************/
751 (void) AcpiUtFileVprintf (ACPI_FILE_OUT, Format, Args);
755 /******************************************************************************
757 * FUNCTION: AcpiOsInitialize
763 * DESCRIPTION: Initialize this module.
765 *****************************************************************************/
776 /******************************************************************************
778 * FUNCTION: AcpiEfiArgify
780 * PARAMETERS: String - Pointer to command line argument strings
781 * which are seperated with spaces
782 * ArgcPtr - Return number of the arguments
783 * ArgvPtr - Return vector of the arguments
787 * DESCRIPTION: Convert EFI arguments into C arguments.
789 *****************************************************************************/
798 int MaxArgc = *ArgcPtr;
800 char **Argv = *ArgvPtr;
802 BOOLEAN IsSingleQuote = FALSE;
803 BOOLEAN IsDoubleQuote = FALSE;
804 BOOLEAN IsEscape = FALSE;
809 return (AE_BAD_PARAMETER);
814 while (*String != '\0')
816 while (ACPI_IS_SPACE (*String))
821 while (*String != '\0')
823 if (ACPI_IS_SPACE (*String) &&
824 !IsSingleQuote && !IsDoubleQuote && !IsEscape)
835 else if (*String == '\\')
839 else if (IsSingleQuote)
843 IsSingleQuote = FALSE;
851 else if (IsDoubleQuote)
855 IsDoubleQuote = FALSE;
867 IsSingleQuote = TRUE;
869 else if (*String == '"')
871 IsDoubleQuote = TRUE;
880 if (Argv && Argc < MaxArgc)
882 Argv[Argc] = CopyBuffer;
887 if (Argv && Argc < MaxArgc)
895 return ((MaxArgc < Argc) ? AE_NO_MEMORY : AE_OK);
899 /******************************************************************************
901 * FUNCTION: AcpiEfiConvertArgcv
903 * PARAMETERS: LoadOptions - Pointer to the EFI options buffer, which
905 * LoadOptionsSize - Size of the EFI options buffer
906 * ArgcPtr - Return number of the arguments
907 * ArgvPtr - Return vector of the arguments
908 * BufferPtr - Buffer to contain the argument strings
912 * DESCRIPTION: Convert EFI arguments into C arguments.
914 *****************************************************************************/
917 AcpiEfiConvertArgcv (
919 UINT32 LoadOptionsSize,
924 ACPI_STATUS Status = AE_OK;
925 UINT32 Count = LoadOptionsSize / sizeof (CHAR16);
934 /* Prepare a buffer to contain the argument strings */
936 Buffer = ACPI_ALLOCATE_ZEROED (Count);
939 Status = AE_NO_MEMORY;
945 /* Extend the argument vector */
954 Argv = ACPI_ALLOCATE_ZEROED (sizeof (char *) * (Argc + 1));
957 Status = AE_NO_MEMORY;
963 * Note: As AcpiEfiArgify() will modify the content of the buffer, so
964 * we need to restore it each time before invoking
968 To = ACPI_CAST_PTR (char, Buffer);
969 for (i = 0; i < Count; i++)
971 *To++ = (char) *From++;
975 * The "Buffer" will contain NULL terminated strings after invoking
976 * AcpiEfiArgify(). The number of the strings are saved in Argc and the
977 * pointers of the strings are saved in Argv.
979 Status = AcpiEfiArgify (Buffer, &Argc, &Argv);
980 if (ACPI_FAILURE (Status))
982 if (Status == AE_NO_MEMORY)
990 if (ACPI_FAILURE (Status))
1005 /******************************************************************************
1007 * FUNCTION: efi_main
1009 * PARAMETERS: Image - EFI image handle
1010 * SystemTab - EFI system table
1012 * RETURN: EFI Status
1014 * DESCRIPTION: Entry point of EFI executable
1016 *****************************************************************************/
1021 EFI_SYSTEM_TABLE *SystemTab)
1023 EFI_LOADED_IMAGE *Info;
1024 EFI_STATUS EfiStatus = EFI_SUCCESS;
1028 char *OptBuffer = NULL;
1029 EFI_FILE_IO_INTERFACE *Volume = NULL;
1032 /* Initialize EFI library */
1034 InitializeLib (Image, SystemTab);
1036 /* Retrieve image information */
1038 EfiStatus = uefi_call_wrapper (BS->HandleProtocol, 3,
1039 Image, &LoadedImageProtocol, ACPI_CAST_PTR (VOID, &Info));
1040 if (EFI_ERROR (EfiStatus))
1042 AcpiLogError ("EFI_BOOT_SERVICES->HandleProtocol(LoadedImageProtocol) failure.\n");
1045 EfiStatus = uefi_call_wrapper (BS->HandleProtocol, 3,
1046 Info->DeviceHandle, &FileSystemProtocol, (void **) &Volume);
1047 if (EFI_ERROR (EfiStatus))
1049 AcpiLogError ("EFI_BOOT_SERVICES->HandleProtocol(FileSystemProtocol) failure.\n");
1052 EfiStatus = uefi_call_wrapper (Volume->OpenVolume, 2,
1053 Volume, &AcpiGbl_EfiCurrentVolume);
1054 if (EFI_ERROR (EfiStatus))
1056 AcpiLogError ("EFI_FILE_IO_INTERFACE->OpenVolume() failure.\n");
1060 Status = AcpiEfiConvertArgcv (Info->LoadOptions,
1061 Info->LoadOptionsSize, &argc, &argv, &OptBuffer);
1062 if (ACPI_FAILURE (Status))
1064 EfiStatus = EFI_DEVICE_ERROR;
1068 acpi_main (argc, argv);
1078 ACPI_FREE (OptBuffer);