Modify for enabling native VISTA
authorjchen20 <jchen20@6f19259b-4bc3-4df7-8a09-765794883524>
Wed, 13 Sep 2006 02:22:42 +0000 (02:22 +0000)
committerjchen20 <jchen20@6f19259b-4bc3-4df7-8a09-765794883524>
Wed, 13 Sep 2006 02:22:42 +0000 (02:22 +0000)
git-svn-id: https://edk2.svn.sourceforge.net/svnroot/edk2/trunk/edk2@1520 6f19259b-4bc3-4df7-8a09-765794883524

EdkModulePkg/Bus/Pci/IdeBus/Dxe/ide.c
EdkModulePkg/Bus/Pci/IdeBus/Dxe/ide.h
EdkModulePkg/Bus/Pci/IdeBus/Dxe/idebus.c

index 5a65995..80ee854 100644 (file)
@@ -1769,3 +1769,100 @@ EnableInterrupt (
 \r
   return EFI_SUCCESS;\r
 }\r
+/**\r
+  Clear pending IDE interrupt before OS loader/kernel take control of the IDE device.\r
+\r
+  @param[in]  Event   Pointer to this event\r
+  @param[in]  Context Event hanlder private data\r
+\r
+  @retval  EFI_SUCCESS - Interrupt cleared\r
+\r
+**/\r
+EFI_STATUS\r
+ClearInterrupt (\r
+  IN EFI_EVENT  Event,\r
+  IN VOID       *Context\r
+  )\r
+{\r
+  EFI_STATUS      Status;\r
+  UINT64          IoPortForBmis;\r
+  UINT8           RegisterValue;\r
+  IDE_BLK_IO_DEV  *IdeDev;\r
+\r
+  //\r
+  // Get our context\r
+  //\r
+  IdeDev = (IDE_BLK_IO_DEV *) Context;\r
+\r
+  //\r
+  // Obtain IDE IO port registers' base addresses\r
+  //\r
+  Status = ReassignIdeResources (IdeDev);\r
+  if (EFI_ERROR (Status)) {\r
+    return Status;\r
+  }\r
+\r
+  //\r
+  // Check whether interrupt is pending\r
+  //\r
+\r
+  //\r
+  // Reset IDE device to force it de-assert interrupt pin\r
+  // Note: this will reset all devices on this IDE channel\r
+  //\r
+  AtaSoftReset (IdeDev);\r
+  if (EFI_ERROR (Status)) {\r
+    return Status;\r
+  }\r
+\r
+  //\r
+  // Get base address of IDE Bus Master Status Regsiter\r
+  //\r
+  if (IdePrimary == IdeDev->Channel) {\r
+    IoPortForBmis = IdeDev->IoPort->BusMasterBaseAddr + BMISP_OFFSET;\r
+  } else {\r
+    if (IdeSecondary == IdeDev->Channel) {\r
+      IoPortForBmis = IdeDev->IoPort->BusMasterBaseAddr + BMISS_OFFSET;\r
+    } else {\r
+      return EFI_UNSUPPORTED;\r
+    }\r
+  }\r
+  //\r
+  // Read BMIS register and clear ERROR and INTR bit\r
+  //\r
+  IdeDev->PciIo->Io.Read (\r
+                      IdeDev->PciIo,\r
+                      EfiPciIoWidthUint8,\r
+                      EFI_PCI_IO_PASS_THROUGH_BAR,\r
+                      IoPortForBmis,\r
+                      1,\r
+                      &RegisterValue\r
+                      );\r
+\r
+  RegisterValue |= (BMIS_INTERRUPT | BMIS_ERROR);\r
+\r
+  IdeDev->PciIo->Io.Write (\r
+                      IdeDev->PciIo,\r
+                      EfiPciIoWidthUint8,\r
+                      EFI_PCI_IO_PASS_THROUGH_BAR,\r
+                      IoPortForBmis,\r
+                      1,\r
+                      &RegisterValue\r
+                      );\r
+\r
+  //\r
+  // Select the other device on this channel to ensure this device to release the interrupt pin\r
+  //\r
+  if (IdeDev->Device == 0) {\r
+    RegisterValue = (1 << 4) | 0xe0;\r
+  } else {\r
+    RegisterValue = (0 << 4) | 0xe0;\r
+  }\r
+  IDEWritePortB (\r
+    IdeDev->PciIo,\r
+    IdeDev->IoPort->Head,\r
+    RegisterValue\r
+    );\r
+\r
+  return EFI_SUCCESS;\r
+}\r
index 177e842..b3e54ef 100644 (file)
@@ -1304,5 +1304,20 @@ EnableInterrupt (
   IN IDE_BLK_IO_DEV       *IdeDev\r
   )\r
 ;\r
+/**\r
+  Clear pending IDE interrupt before OS loader/kernel take control of the IDE device.\r
+\r
+  @param[in]  Event   Pointer to this event\r
+  @param[in]  Context Event hanlder private data\r
+\r
+  @retval  EFI_SUCCESS - Interrupt cleared\r
+\r
+**/\r
+EFI_STATUS\r
+ClearInterrupt (\r
+  IN EFI_EVENT  Event,\r
+  IN VOID       *Context\r
+  )\r
+;\r
 \r
 #endif\r
index e5157da..45baa9e 100644 (file)
@@ -183,6 +183,7 @@ IDEBusDriverBindingStart (
   UINTN                             DataSize;\r
   UINT32                            Attributes;\r
   IDE_BUS_DRIVER_PRIVATE_DATA       *IdeBusDriverPrivateData;\r
+  EFI_EVENT                         Event;\r
 \r
   //\r
   // Local variables declaration for IdeControllerInit support\r
@@ -696,6 +697,19 @@ IDEBusDriverBindingStart (
         (EFI_IO_BUS_ATA_ATAPI | EFI_P_PC_ENABLE),\r
         IdeBlkIoDevicePtr->DevicePath\r
         );\r
+      \r
+      //\r
+      // Create event to clear pending IDE interrupt\r
+      //\r
+      Status = gBS->CreateEvent (\r
+                      EFI_EVENT_SIGNAL_EXIT_BOOT_SERVICES,\r
+                      EFI_TPL_NOTIFY,\r
+                      ClearInterrupt,\r
+                      IdeBlkIoDevicePtr,\r
+                      &Event\r
+                      );\r
+\r
+  \r
       //\r
       // end of 2nd inner loop ----\r
       //\r