]> git.proxmox.com Git - mirror_edk2.git/commitdiff
Add DuetTimerLib and DuetSerialIo library instance.
authorklu2 <klu2@6f19259b-4bc3-4df7-8a09-765794883524>
Mon, 5 May 2008 07:21:29 +0000 (07:21 +0000)
committerklu2 <klu2@6f19259b-4bc3-4df7-8a09-765794883524>
Mon, 5 May 2008 07:21:29 +0000 (07:21 +0000)
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@5162 6f19259b-4bc3-4df7-8a09-765794883524

DuetPkg/DuetPkg.dsc
DuetPkg/Library/DuetSerialIoLib/DuetSerialIoLib.inf [new file with mode: 0644]
DuetPkg/Library/DuetSerialIoLib/SerialPortLib.c [new file with mode: 0644]
DuetPkg/Library/DuetTimerLib/DuetTimerLib.inf [new file with mode: 0644]
DuetPkg/Library/DuetTimerLib/x86TimerLib.c [new file with mode: 0644]

index 6b7916fc2d041671e3bf6764eab0e90174904ce2..76ca7a50da99eafd7cc30e3b76b12e5cb5eea9b2 100644 (file)
@@ -48,7 +48,7 @@
   OemHookStatusCodeLib|IntelFrameworkModulePkg/Library/OemHookStatusCodeLibNull/OemHookStatusCodeLibNull.inf\r
   PrintLib|MdePkg/Library/BasePrintLib/BasePrintLib.inf\r
   IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf\r
-  TimerLib|MdePkg/Library/SecPeiDxeTimerLibCpu/SecPeiDxeTimerLibCpu.inf\r
+  TimerLib|DuetPkg/Library/DuetTimerLib/DuetTimerLib.inf\r
 \r
 [LibraryClasses.common.DXE_DRIVER]\r
   MemoryAllocationLib|MdePkg/Library/DxeMemoryAllocationLib/DxeMemoryAllocationLib.inf\r
@@ -79,7 +79,6 @@
   ReportStatusCodeLib|IntelFrameworkModulePkg/Library/DxeReportStatusCodeLibFramework/DxeReportStatusCodeLib.inf\r
   SerialPortLib|DuetPkg/Library/DuetSerialIoLib/DuetSerialIoLib.inf\r
   IoLib|MdePkg/Library/BaseIoLibIntrinsic/BaseIoLibIntrinsic.inf\r
-  #TimerLib|MdePkg/Library/BaseTimerLibNullTemplate/BaseTimerLibNullTemplate.inf\r
   DebugLib|IntelFrameworkModulePkg/Library/PeiDxeDebugLibReportStatusCode/PeiDxeDebugLibReportStatusCode.inf\r
 \r
 [LibraryClasses.common.UEFI_DRIVER]\r
diff --git a/DuetPkg/Library/DuetSerialIoLib/DuetSerialIoLib.inf b/DuetPkg/Library/DuetSerialIoLib/DuetSerialIoLib.inf
new file mode 100644 (file)
index 0000000..07a7ee9
--- /dev/null
@@ -0,0 +1,36 @@
+#/**@file\r
+#   This library instance produce SerialIo library class for DUET platform.\r
+#\r
+# Copyright (c) 2006 - 2007, Intel Corporation                                                  \r
+# All rights reserved. This program and the accompanying materials                          \r
+# are licensed and made available under the terms and conditions of the BSD License         \r
+# which accompanies this distribution.  The full text of the license may be found at        \r
+# http://opensource.org/licenses/bsd-license.php                                            \r
+#                                                                                           \r
+# THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,                     \r
+# WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.             \r
+# \r
+#\r
+#**/\r
+\r
+[Defines]\r
+  INF_VERSION                    = 0x00010005\r
+  BASE_NAME                      = DuetSerialPortLib\r
+  FILE_GUID                      = 1B25AF84-1EA8-4b52-894E-BFA6880B97FF\r
+  MODULE_TYPE                    = DXE_DRIVER\r
+  VERSION_STRING                 = 1.0\r
+  LIBRARY_CLASS                  = SerialPortLib\r
+  EDK_RELEASE_VERSION            = 0x00020000\r
+  EFI_SPECIFICATION_VERSION      = 0x0002000A\r
+\r
+[Packages]\r
+  MdePkg/MdePkg.dec\r
+\r
+[LibraryClasses]\r
+  SerialPortLib\r
+  IoLib\r
+\r
+[Sources.common]\r
+  SerialPortLib.c\r
+\r
+\r
diff --git a/DuetPkg/Library/DuetSerialIoLib/SerialPortLib.c b/DuetPkg/Library/DuetSerialIoLib/SerialPortLib.c
new file mode 100644 (file)
index 0000000..518172a
--- /dev/null
@@ -0,0 +1,160 @@
+/** @file\r
+  Serial I/O Port library functions with no library constructor/destructor\r
+\r
+  Copyright (c) 2006, Intel Corporation\r
+  All rights reserved. This program and the accompanying materials\r
+  are licensed and made available under the terms and conditions of the BSD License\r
+  which accompanies this distribution.  The full text of the license may be found at\r
+  http://opensource.org/licenses/bsd-license.php\r
+\r
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+\r
+**/\r
+\r
+\r
+#include <Base.h>\r
+\r
+#include <Library/IoLib.h>\r
+#include <Library/SerialPortLib.h>\r
+\r
+//---------------------------------------------\r
+// UART Register Offsets\r
+//---------------------------------------------\r
+#define BAUD_LOW_OFFSET         0x00\r
+#define BAUD_HIGH_OFFSET        0x01\r
+#define IER_OFFSET              0x01\r
+#define LCR_SHADOW_OFFSET       0x01\r
+#define FCR_SHADOW_OFFSET       0x02\r
+#define IR_CONTROL_OFFSET       0x02\r
+#define FCR_OFFSET              0x02\r
+#define EIR_OFFSET              0x02\r
+#define BSR_OFFSET              0x03\r
+#define LCR_OFFSET              0x03\r
+#define MCR_OFFSET              0x04\r
+#define LSR_OFFSET              0x05\r
+#define MSR_OFFSET              0x06\r
+\r
+//---------------------------------------------\r
+// UART Register Bit Defines\r
+//---------------------------------------------\r
+#define LSR_TXRDY               0x20\r
+#define LSR_RXDA                0x01\r
+#define DLAB                    0x01\r
+\r
+UINT16  gComBase = 0x3f8;\r
+UINTN   gBps = 115200;\r
+UINT8   gData = 8;\r
+UINT8   gStop = 1;\r
+UINT8   gParity = 0;\r
+UINT8   gBreakSet = 0;\r
+/*\r
+\r
+  Programmed hardware of Serial port.\r
+\r
+  @return    Always return EFI_UNSUPPORTED.\r
+\r
+**/\r
+RETURN_STATUS\r
+EFIAPI\r
+SerialPortInitialize (\r
+  VOID\r
+  )\r
+{\r
+  UINTN           Divisor;\r
+  UINT8           OutputData;\r
+  UINT8           Data;\r
+\r
+ //\r
+  // Map 5..8 to 0..3\r
+  //\r
+  Data = (UINT8) (gData - (UINT8)5);\r
+\r
+  //\r
+  // Calculate divisor for baud generator\r
+  //\r
+  Divisor = 115200 / gBps; \r
+  \r
+  //\r
+  // Set communications format\r
+  //\r
+  OutputData = (UINT8)((DLAB << 7) | ((gBreakSet << 6) | ((gParity << 3) | ((gStop << 2) | Data))));\r
+  IoWrite8 (gComBase + LCR_OFFSET, OutputData);\r
+\r
+  //\r
+  // Configure baud rate\r
+  //\r
+  IoWrite8 (gComBase + BAUD_HIGH_OFFSET, (UINT8)(Divisor >> 8));\r
+  IoWrite8 (gComBase + BAUD_LOW_OFFSET, (UINT8)(Divisor & 0xff));\r
+\r
+  //\r
+  // Switch back to bank 0\r
+  //\r
+  OutputData = (UINT8)((~DLAB<<7)|((gBreakSet<<6)|((gParity<<3)|((gStop<<2)| Data))));\r
+  IoWrite8 (gComBase + LCR_OFFSET, OutputData);\r
+\r
+  return RETURN_SUCCESS;\r
+}\r
+\r
+/**\r
+  Write data to serial device.\r
+\r
+  @param  Buffer           Point of data buffer which need to be writed.\r
+  @param  NumberOfBytes    Number of output bytes which are cached in Buffer.\r
+\r
+  @retval 0                Write data failed.\r
+  @retval !0               Actual number of bytes writed to serial device.\r
+\r
+**/\r
+UINTN\r
+EFIAPI\r
+SerialPortWrite (\r
+  IN UINT8     *Buffer,\r
+  IN UINTN     NumberOfBytes\r
+)\r
+{\r
+  UINTN Result;\r
+  UINT8 Data;\r
+\r
+  if (NULL == Buffer) {\r
+    return 0;\r
+  }\r
+\r
+  Result = NumberOfBytes;\r
+\r
+  while (NumberOfBytes--) {\r
+      //\r
+      // Wait for the serail port to be ready.\r
+      //\r
+      do {\r
+        Data = IoRead8 (gComBase + LSR_OFFSET);\r
+      } while ((Data & LSR_TXRDY) == 0);\r
+\r
+      IoWrite8 (gComBase, *Buffer++);\r
+  }\r
+\r
+  return Result;\r
+\r
+}\r
+\r
+\r
+/**\r
+  Read data from serial device and save the datas in buffer.\r
+\r
+  @param  Buffer           Point of data buffer which need to be writed.\r
+  @param  NumberOfBytes    Number of output bytes which are cached in Buffer.\r
+\r
+  @retval 0                Read data failed.\r
+  @retval !0               Aactual number of bytes read from serial device.\r
+\r
+**/\r
+UINTN\r
+EFIAPI\r
+SerialPortRead (\r
+  OUT UINT8     *Buffer,\r
+  IN  UINTN     NumberOfBytes\r
+)\r
+{\r
+  return 0;\r
+}\r
+\r
diff --git a/DuetPkg/Library/DuetTimerLib/DuetTimerLib.inf b/DuetPkg/Library/DuetTimerLib/DuetTimerLib.inf
new file mode 100644 (file)
index 0000000..f03c6bd
--- /dev/null
@@ -0,0 +1,68 @@
+#/** @file\r
+# Timer Library implementation for Boot Timer moudles that require timer services.\r
+#\r
+# Timer Library that uses CPU resources to provide calibrated\r
+#  delays on IA-32 and x64, and uses ITC on IPF. Note: Because CpuLocalApci\r
+#  and ITC could be programmed by OS, it cannot be used by SMM drivers\r
+#  and runtime drivers, ACPI timer is recommended for SMM drivers and RUNTIME\r
+#  drivers.\r
+# Copyright (c) 2007, Intel Corporation.\r
+#\r
+#  All rights reserved. This program and the accompanying materials\r
+#  are licensed and made available under the terms and conditions of the BSD License\r
+#  which accompanies this distribution. The full text of the license may be found at\r
+#  http://opensource.org/licenses/bsd-license.php\r
+#  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
+#  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+#\r
+#\r
+#**/\r
+\r
+[Defines]\r
+  INF_VERSION                    = 0x00010005\r
+  BASE_NAME                      = DuetTimerLib\r
+  FILE_GUID                      = 5F9A01F5-726E-4f59-809D-887F4766734E\r
+  MODULE_TYPE                    = BASE\r
+  VERSION_STRING                 = 1.0\r
+  LIBRARY_CLASS                  = TimerLib\r
+  EDK_RELEASE_VERSION            = 0x00020000\r
+  EFI_SPECIFICATION_VERSION      = 0x00020000\r
+\r
+\r
+#\r
+#  VALID_ARCHITECTURES           = IA32 X64\r
+#\r
+\r
+[Sources.Ia32]\r
+  x86TimerLib.c\r
+\r
+[Sources.X64]\r
+  x86TimerLib.c\r
+\r
+\r
+[Packages]\r
+  MdePkg/MdePkg.dec\r
+\r
+\r
+[LibraryClasses]\r
+  BaseLib\r
+\r
+[LibraryClasses.IA32]\r
+  PcdLib\r
+  IoLib\r
+\r
+[LibraryClasses.X64]\r
+  PcdLib\r
+  IoLib\r
+\r
+[LibraryClasses.IPF]\r
+  DebugLib\r
+  PalCallLib\r
+\r
+\r
+[Pcd.IA32]\r
+  gEfiMdePkgTokenSpaceGuid.PcdFSBClock\r
+\r
+[Pcd.X64]\r
+  gEfiMdePkgTokenSpaceGuid.PcdFSBClock\r
+\r
diff --git a/DuetPkg/Library/DuetTimerLib/x86TimerLib.c b/DuetPkg/Library/DuetTimerLib/x86TimerLib.c
new file mode 100644 (file)
index 0000000..263ce9a
--- /dev/null
@@ -0,0 +1,252 @@
+/** @file\r
+  Timer Library functions built upon local APIC on IA32/x64.\r
+\r
+  Copyright (c) 2006 - 2007, Intel Corporation<BR>\r
+  All rights reserved. This program and the accompanying materials\r
+  are licensed and made available under the terms and conditions of the BSD License\r
+  which accompanies this distribution.  The full text of the license may be found at\r
+  http://opensource.org/licenses/bsd-license.php\r
+\r
+  THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,\r
+  WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.\r
+\r
+**/\r
+\r
+#include <Base.h>\r
+#include <Library/TimerLib.h>\r
+#include <Library/BaseLib.h>\r
+#include <Library/IoLib.h>\r
+#include <Library/DebugLib.h>\r
+#include <Library/PcdLib.h>\r
+\r
+\r
+//\r
+// The following array is used in calculating the frequency of local APIC\r
+// timer. Refer to IA-32 developers' manual for more details.\r
+//\r
+GLOBAL_REMOVE_IF_UNREFERENCED\r
+CONST UINT8                           mTimerLibLocalApicDivisor[] = {\r
+  0x02, 0x04, 0x08, 0x10,\r
+  0x02, 0x04, 0x08, 0x10,\r
+  0x20, 0x40, 0x80, 0x01,\r
+  0x20, 0x40, 0x80, 0x01\r
+};\r
+\r
+/**\r
+  Internal function to retrieve the base address of local APIC.\r
+\r
+  Internal function to retrieve the base address of local APIC.\r
+\r
+  @return The base address of local APIC\r
+\r
+**/\r
+STATIC\r
+UINTN\r
+InternalX86GetApicBase (\r
+  VOID\r
+  )\r
+{\r
+  return (UINTN)AsmMsrBitFieldRead64 (27, 12, 35) << 12;\r
+}\r
+\r
+/**\r
+  Internal function to return the frequency of the local APIC timer.\r
+\r
+  Internal function to return the frequency of the local APIC timer.\r
+\r
+  @param  ApicBase  The base address of memory mapped registers of local APIC.\r
+\r
+  @return The frequency of the timer in Hz.\r
+\r
+**/\r
+STATIC\r
+UINT32\r
+InternalX86GetTimerFrequency (\r
+  IN      UINTN                     ApicBase\r
+  )\r
+{\r
+  return\r
+    PcdGet32(PcdFSBClock) /\r
+    mTimerLibLocalApicDivisor[MmioBitFieldRead32 (ApicBase + 0x3e0, 0, 3)];\r
+}\r
+\r
+/**\r
+  Internal function to read the current tick counter of local APIC.\r
+\r
+  Internal function to read the current tick counter of local APIC.\r
+\r
+  @param  ApicBase  The base address of memory mapped registers of local APIC.\r
+\r
+  @return The tick counter read.\r
+\r
+**/\r
+STATIC\r
+INT32\r
+InternalX86GetTimerTick (\r
+  IN      UINTN                     ApicBase\r
+  )\r
+{\r
+  return MmioRead32 (ApicBase + 0x390);\r
+}\r
+\r
+/**\r
+  Stalls the CPU for at least the given number of ticks.\r
+\r
+  Stalls the CPU for at least the given number of ticks. It's invoked by\r
+  MicroSecondDelay() and NanoSecondDelay().\r
+\r
+  @param  ApicBase  The base address of memory mapped registers of local APIC.\r
+  @param  Delay     A period of time to delay in ticks.\r
+\r
+**/\r
+STATIC\r
+VOID\r
+InternalX86Delay (\r
+  IN      UINTN                     ApicBase,\r
+  IN      UINT32                    Delay\r
+  )\r
+{\r
+  INT32                             Ticks;\r
+\r
+  //\r
+  // The target timer count is calculated here\r
+  //\r
+  Ticks = InternalX86GetTimerTick (ApicBase) - Delay;\r
+\r
+  //\r
+  // Wait until time out\r
+  // Delay > 2^31 could not be handled by this function\r
+  // Timer wrap-arounds are handled correctly by this function\r
+  //\r
+  while (InternalX86GetTimerTick (ApicBase) - Ticks >= 0);\r
+}\r
+\r
+/**\r
+  Stalls the CPU for at least the given number of microseconds.\r
+\r
+  Stalls the CPU for the number of microseconds specified by MicroSeconds.\r
+\r
+  @param  MicroSeconds  The minimum number of microseconds to delay.\r
+\r
+  @return MicroSeconds\r
+\r
+**/\r
+UINTN\r
+EFIAPI\r
+MicroSecondDelay (\r
+  IN      UINTN                     MicroSeconds\r
+  )\r
+{\r
+  UINTN                             ApicBase;\r
+\r
+  ApicBase = InternalX86GetApicBase ();\r
+  InternalX86Delay (\r
+    ApicBase,\r
+    (UINT32)DivU64x32 (\r
+              MultU64x64 (\r
+                InternalX86GetTimerFrequency (ApicBase),\r
+                MicroSeconds\r
+                ),\r
+              1000000u\r
+              )\r
+    );\r
+  return MicroSeconds;\r
+}\r
+\r
+/**\r
+  Stalls the CPU for at least the given number of nanoseconds.\r
+\r
+  Stalls the CPU for the number of nanoseconds specified by NanoSeconds.\r
+\r
+  @param  NanoSeconds The minimum number of nanoseconds to delay.\r
+\r
+  @return NanoSeconds\r
+\r
+**/\r
+UINTN\r
+EFIAPI\r
+NanoSecondDelay (\r
+  IN      UINTN                     NanoSeconds\r
+  )\r
+{\r
+  UINTN                             ApicBase;\r
+\r
+  ApicBase = InternalX86GetApicBase ();\r
+  InternalX86Delay (\r
+    ApicBase,\r
+    (UINT32)DivU64x32 (\r
+              MultU64x64 (\r
+                InternalX86GetTimerFrequency (ApicBase),\r
+                NanoSeconds\r
+                ),\r
+              1000000000u\r
+              )\r
+    );\r
+  return NanoSeconds;\r
+}\r
+\r
+/**\r
+  Retrieves the current value of a 64-bit free running performance counter.\r
+\r
+  Retrieves the current value of a 64-bit free running performance counter. The\r
+  counter can either count up by 1 or count down by 1. If the physical\r
+  performance counter counts by a larger increment, then the counter values\r
+  must be translated. The properties of the counter can be retrieved from\r
+  GetPerformanceCounterProperties().\r
+\r
+  @return The current value of the free running performance counter.\r
+\r
+**/\r
+UINT64\r
+EFIAPI\r
+GetPerformanceCounter (\r
+  VOID\r
+  )\r
+{\r
+  return (UINT64)(UINT32)InternalX86GetTimerTick (InternalX86GetApicBase ());\r
+}\r
+\r
+/**\r
+  Retrieves the 64-bit frequency in Hz and the range of performance counter\r
+  values.\r
+\r
+  If StartValue is not NULL, then the value that the performance counter starts\r
+  with immediately after is it rolls over is returned in StartValue. If\r
+  EndValue is not NULL, then the value that the performance counter end with\r
+  immediately before it rolls over is returned in EndValue. The 64-bit\r
+  frequency of the performance counter in Hz is always returned. If StartValue\r
+  is less than EndValue, then the performance counter counts up. If StartValue\r
+  is greater than EndValue, then the performance counter counts down. For\r
+  example, a 64-bit free running counter that counts up would have a StartValue\r
+  of 0 and an EndValue of 0xFFFFFFFFFFFFFFFF. A 24-bit free running counter\r
+  that counts down would have a StartValue of 0xFFFFFF and an EndValue of 0.\r
+\r
+  @param  StartValue  The value the performance counter starts with when it\r
+                      rolls over.\r
+  @param  EndValue    The value that the performance counter ends with before\r
+                      it rolls over.\r
+\r
+  @return The frequency in Hz.\r
+\r
+**/\r
+UINT64\r
+EFIAPI\r
+GetPerformanceCounterProperties (\r
+  OUT      UINT64                    *StartValue,  OPTIONAL\r
+  OUT      UINT64                    *EndValue     OPTIONAL\r
+  )\r
+{\r
+  UINTN                             ApicBase;\r
+\r
+  ApicBase = InternalX86GetApicBase ();\r
+\r
+  if (StartValue != NULL) {\r
+    *StartValue = MmioRead32 (ApicBase + 0x380);\r
+  }\r
+\r
+  if (EndValue != NULL) {\r
+    *EndValue = 0;\r
+  }\r
+\r
+  return (UINT64) InternalX86GetTimerFrequency (ApicBase);;\r
+}\r