summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorLv Zheng <lv.zheng@intel.com>2016-07-12 14:37:54 +0800
committerLv Zheng <lv.zheng@intel.com>2016-12-14 16:33:22 +0800
commitcc6947172dcced4f7909eb351981b3413bb9a27a (patch)
treee7a81e4c295c15336b4664459f69394db8fae725
parent24abc25e62fe6bc7cc375bf3d63132639614bd57 (diff)
downloadacpica-cc6947172dcced4f7909eb351981b3413bb9a27a.tar.gz
Clib/EFI: Add file position seeking/telling support
This patch adds file position seeking/telling support. Lv Zheng. Signed-off-by: Lv Zheng <lv.zheng@intel.com>
-rw-r--r--source/include/platform/acefiex.h31
-rw-r--r--source/os_specific/efi/oseficlib.c142
2 files changed, 171 insertions, 2 deletions
diff --git a/source/include/platform/acefiex.h b/source/include/platform/acefiex.h
index 9f5b9208c..e90b89712 100644
--- a/source/include/platform/acefiex.h
+++ b/source/include/platform/acefiex.h
@@ -167,6 +167,20 @@ typedef struct {
UINT8 Data4[8];
} ACPI_EFI_GUID;
+typedef struct {
+ UINT16 Year; /* 1998 - 20XX */
+ UINT8 Month; /* 1 - 12 */
+ UINT8 Day; /* 1 - 31 */
+ UINT8 Hour; /* 0 - 23 */
+ UINT8 Minute; /* 0 - 59 */
+ UINT8 Second; /* 0 - 59 */
+ UINT8 Pad1;
+ UINT32 Nanosecond; /* 0 - 999,999,999 */
+ INT16 TimeZone; /* -1440 to 1440 or 2047 */
+ UINT8 Daylight;
+ UINT8 Pad2;
+} ACPI_EFI_TIME;
+
typedef struct _ACPI_EFI_DEVICE_PATH {
UINT8 Type;
UINT8 SubType;
@@ -447,6 +461,22 @@ ACPI_EFI_STATUS
struct _ACPI_EFI_FILE_HANDLE *File,
UINT64 *Position);
+#define ACPI_EFI_FILE_INFO_ID \
+ { 0x9576e92, 0x6d3f, 0x11d2, {0x8e, 0x39, 0x0, 0xa0, 0xc9, 0x69, 0x72, 0x3b} }
+
+typedef struct {
+ UINT64 Size;
+ UINT64 FileSize;
+ UINT64 PhysicalSize;
+ ACPI_EFI_TIME CreateTime;
+ ACPI_EFI_TIME LastAccessTime;
+ ACPI_EFI_TIME ModificationTime;
+ UINT64 Attribute;
+ CHAR16 FileName[1];
+} ACPI_EFI_FILE_INFO;
+
+#define SIZE_OF_ACPI_EFI_FILE_INFO ACPI_OFFSET(ACPI_EFI_FILE_INFO, FileName)
+
typedef
ACPI_EFI_STATUS
(ACPI_EFI_API *ACPI_EFI_FILE_GET_INFO) (
@@ -1018,5 +1048,6 @@ extern ACPI_EFI_GUID AcpiGbl_LoadedImageProtocol;
extern ACPI_EFI_GUID AcpiGbl_TextInProtocol;
extern ACPI_EFI_GUID AcpiGbl_TextOutProtocol;
extern ACPI_EFI_GUID AcpiGbl_FileSystemProtocol;
+extern ACPI_EFI_GUID AcpiGbl_GenericFileInfo;
#endif /* __ACEFIEX_H__ */
diff --git a/source/os_specific/efi/oseficlib.c b/source/os_specific/efi/oseficlib.c
index 96b6f9f9c..333031801 100644
--- a/source/os_specific/efi/oseficlib.c
+++ b/source/os_specific/efi/oseficlib.c
@@ -153,6 +153,11 @@ AcpiEfiConvertArgcv (
char ***ArgvPtr,
char **BufferPtr);
+static int
+AcpiEfiGetFileInfo (
+ FILE *File,
+ ACPI_EFI_FILE_INFO **InfoPtr);
+
static CHAR16 *
AcpiEfiFlushFile (
FILE *File,
@@ -172,6 +177,7 @@ ACPI_EFI_GUID AcpiGbl_LoadedImageProtocol = ACPI_EFI_LOADED_IMAGE_
ACPI_EFI_GUID AcpiGbl_TextInProtocol = ACPI_SIMPLE_TEXT_INPUT_PROTOCOL;
ACPI_EFI_GUID AcpiGbl_TextOutProtocol = ACPI_SIMPLE_TEXT_OUTPUT_PROTOCOL;
ACPI_EFI_GUID AcpiGbl_FileSystemProtocol = ACPI_SIMPLE_FILE_SYSTEM_PROTOCOL;
+ACPI_EFI_GUID AcpiGbl_GenericFileInfo = ACPI_EFI_FILE_INFO_ID;
int errno = 0;
@@ -683,11 +689,68 @@ ErrorExit:
/*******************************************************************************
*
+ * FUNCTION: AcpiEfiGetFileInfo
+ *
+ * PARAMETERS: File - File descriptor
+ * InfoPtr - Pointer to contain file information
+ *
+ * RETURN: Clibrary error code
+ *
+ * DESCRIPTION: Get file information.
+ *
+ ******************************************************************************/
+
+static int
+AcpiEfiGetFileInfo (
+ FILE *File,
+ ACPI_EFI_FILE_INFO **InfoPtr)
+{
+ ACPI_EFI_STATUS EfiStatus = ACPI_EFI_BUFFER_TOO_SMALL;
+ ACPI_EFI_FILE_INFO *Buffer = NULL;
+ UINTN BufferSize = SIZE_OF_ACPI_EFI_FILE_INFO + 200;
+ ACPI_EFI_FILE_HANDLE EfiFile;
+
+
+ if (!InfoPtr)
+ {
+ errno = EINVAL;
+ return (-EINVAL);
+ }
+
+ while (EfiStatus == ACPI_EFI_BUFFER_TOO_SMALL)
+ {
+ EfiFile = (ACPI_EFI_FILE_HANDLE) File;
+ Buffer = AcpiOsAllocate (BufferSize);
+ if (!Buffer)
+ {
+ errno = ENOMEM;
+ return (-ENOMEM);
+ }
+ EfiStatus = uefi_call_wrapper (EfiFile->GetInfo, 4, EfiFile,
+ &AcpiGbl_GenericFileInfo, &BufferSize, Buffer);
+ if (ACPI_EFI_ERROR (EfiStatus))
+ {
+ AcpiOsFree (Buffer);
+ if (EfiStatus != ACPI_EFI_BUFFER_TOO_SMALL)
+ {
+ errno = EIO;
+ return (-EIO);
+ }
+ }
+ }
+
+ *InfoPtr = Buffer;
+ return (0);
+}
+
+
+/*******************************************************************************
+ *
* FUNCTION: ftell
*
* PARAMETERS: File - File descriptor
*
- * RETURN: Size of current position
+ * RETURN: current position
*
* DESCRIPTION: Get current file offset.
*
@@ -698,8 +761,32 @@ ftell (
FILE *File)
{
long Offset = -1;
+ UINT64 Current;
+ ACPI_EFI_STATUS EfiStatus;
+ ACPI_EFI_FILE_HANDLE EfiFile;
+
+ if (File == stdin || File == stdout || File == stderr)
+ {
+ Offset = 0;
+ }
+ else
+ {
+ EfiFile = (ACPI_EFI_FILE_HANDLE) File;
+
+ EfiStatus = uefi_call_wrapper (EfiFile->GetPosition, 2,
+ EfiFile, &Current);
+ if (ACPI_EFI_ERROR (EfiStatus))
+ {
+ goto ErrorExit;
+ }
+ else
+ {
+ Offset = (long) Current;
+ }
+ }
+ErrorExit:
return (Offset);
}
@@ -724,8 +811,59 @@ fseek (
long Offset,
int From)
{
+ ACPI_EFI_FILE_INFO *Info;
+ int Error;
+ ACPI_SIZE Size;
+ UINT64 Current;
+ ACPI_EFI_STATUS EfiStatus;
+ ACPI_EFI_FILE_HANDLE EfiFile;
+
+
+ if (File == stdin || File == stdout || File == stderr)
+ {
+ return (0);
+ }
+ else
+ {
+ EfiFile = (ACPI_EFI_FILE_HANDLE) File;
+ Error = AcpiEfiGetFileInfo (File, &Info);
+ if (Error)
+ {
+ return (Error);
+ }
+ Size = Info->FileSize;
+ AcpiOsFree (Info);
+
+ if (From == SEEK_CUR)
+ {
+ EfiStatus = uefi_call_wrapper (EfiFile->GetPosition, 2,
+ EfiFile, &Current);
+ if (ACPI_EFI_ERROR (EfiStatus))
+ {
+ errno = ERANGE;
+ return (-ERANGE);
+ }
+ Current += Offset;
+ }
+ else if (From == SEEK_END)
+ {
+ Current = Size - Offset;
+ }
+ else
+ {
+ Current = Offset;
+ }
- return (-1);
+ EfiStatus = uefi_call_wrapper (EfiFile->SetPosition, 2,
+ EfiFile, Current);
+ if (ACPI_EFI_ERROR (EfiStatus))
+ {
+ errno = ERANGE;
+ return (-ERANGE);
+ }
+ }
+
+ return (0);
}