Revision: 14761
          http://sourceforge.net/p/edk2/code/14761
Author:   erictian
Date:     2013-10-10 05:57:50 +0000 (Thu, 10 Oct 2013)
Log Message:
-----------
MdeModulePkg/AtaBus&AtaAtapiPassThru: Update ATA drivers to follow UEFI2.4 new 
request in which it requests ResetEx() to terminate any in-flight non-blocking 
IO request with EFI_ABORTED transaction status.

Signed-off-by: Tian, Feng <[email protected]>
reviewed-by: Ni, Ruiyu <[email protected]>

Modified Paths:
--------------
    trunk/edk2/MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.c
    trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.c
    trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.h
    trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaPassThruExecute.c

Modified: trunk/edk2/MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.c
===================================================================
--- trunk/edk2/MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.c 
2013-10-09 08:30:59 UTC (rev 14760)
+++ trunk/edk2/MdeModulePkg/Bus/Ata/AtaAtapiPassThru/AtaAtapiPassThru.c 
2013-10-10 05:57:50 UTC (rev 14761)
@@ -1764,7 +1764,10 @@
   IN UINT16                     Port
   )
 {
-  return EFI_UNSUPPORTED;
+  //
+  // Return success directly then upper layer driver could think reset port 
operation is done.
+  //
+  return EFI_SUCCESS;
 }
 
 /**
@@ -1806,7 +1809,10 @@
   IN UINT16                     PortMultiplierPort
   )
 {
-  return EFI_UNSUPPORTED;
+  //
+  // Return success directly then upper layer driver could think reset device 
operation is done.
+  //
+  return EFI_SUCCESS;
 }
 
 /**
@@ -2274,7 +2280,10 @@
   IN  EFI_EXT_SCSI_PASS_THRU_PROTOCOL   *This
   )
 {
-  return EFI_UNSUPPORTED;
+  //
+  // Return success directly then upper layer driver could think reset channel 
operation is done.
+  //
+  return EFI_SUCCESS;
 }
 
 /**
@@ -2304,7 +2313,10 @@
   IN UINT64                             Lun
   )
 {
-  return EFI_UNSUPPORTED;
+  //
+  // Return success directly then upper layer driver could think reset target 
LUN operation is done.
+  //
+  return EFI_SUCCESS;
 }
 
 /**

Modified: trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.c
===================================================================
--- trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.c  2013-10-09 08:30:59 UTC 
(rev 14760)
+++ trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.c  2013-10-10 05:57:50 UTC 
(rev 14761)
@@ -90,7 +90,8 @@
   NULL,                        // ControllerNameTable
   {L'\0', },                   // ModelName
   {NULL, NULL},                // AtaTaskList
-  {NULL, NULL}                 // AtaSubTaskList
+  {NULL, NULL},                // AtaSubTaskList
+  FALSE                        // Abort
 };
 
 /**
@@ -172,7 +173,7 @@
        ) {
       DelEntry = Entry;
       Entry    = Entry->ForwardLink;
-      SubTask  = ATA_AYNS_SUB_TASK_FROM_ENTRY (DelEntry);
+      SubTask  = ATA_ASYN_SUB_TASK_FROM_ENTRY (DelEntry);
 
       RemoveEntryList (DelEntry);
       FreeAtaSubTask (SubTask);
@@ -187,7 +188,7 @@
        ) {
       DelEntry = Entry;
       Entry    = Entry->ForwardLink;
-      AtaTask     = ATA_AYNS_TASK_FROM_ENTRY (DelEntry);
+      AtaTask  = ATA_ASYN_TASK_FROM_ENTRY (DelEntry);
 
       RemoveEntryList (DelEntry);
       FreePool (AtaTask);
@@ -1217,6 +1218,8 @@
 
   AtaDevice = ATA_DEVICE_FROM_BLOCK_IO2 (This);
 
+  AtaTerminateNonBlockingTask (AtaDevice);
+
   Status = ResetAtaDevice (AtaDevice);
 
   if (EFI_ERROR (Status)) {

Modified: trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.h
===================================================================
--- trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.h  2013-10-09 08:30:59 UTC 
(rev 14760)
+++ trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaBus.h  2013-10-10 05:57:50 UTC 
(rev 14761)
@@ -4,7 +4,7 @@
   This file defines common data structures, macro definitions and some module
   internal function header files.
 
-  Copyright (c) 2009 - 2012, Intel Corporation. All rights reserved.<BR>
+  Copyright (c) 2009 - 2013, Intel Corporation. All rights reserved.<BR>
   This program and the accompanying materials
   are licensed and made available under the terms and conditions of the BSD 
License
   which accompanies this distribution.  The full text of the license may be 
found at
@@ -148,6 +148,7 @@
 
   LIST_ENTRY                            AtaTaskList;
   LIST_ENTRY                            AtaSubTaskList;
+  BOOLEAN                               Abort;
 } ATA_DEVICE;
 
 //
@@ -181,8 +182,8 @@
 #define ATA_DEVICE_FROM_BLOCK_IO2(a)        CR (a, ATA_DEVICE, BlockIo2, 
ATA_DEVICE_SIGNATURE)
 #define ATA_DEVICE_FROM_DISK_INFO(a)        CR (a, ATA_DEVICE, DiskInfo, 
ATA_DEVICE_SIGNATURE)
 #define ATA_DEVICE_FROM_STORAGE_SECURITY(a) CR (a, ATA_DEVICE, 
StorageSecurity, ATA_DEVICE_SIGNATURE)
-#define ATA_AYNS_SUB_TASK_FROM_ENTRY(a)     CR (a, ATA_BUS_ASYN_SUB_TASK, 
TaskEntry, ATA_SUB_TASK_SIGNATURE)
-#define ATA_AYNS_TASK_FROM_ENTRY(a)         CR (a, ATA_BUS_ASYN_TASK, 
TaskEntry, ATA_TASK_SIGNATURE)
+#define ATA_ASYN_SUB_TASK_FROM_ENTRY(a)     CR (a, ATA_BUS_ASYN_SUB_TASK, 
TaskEntry, ATA_SUB_TASK_SIGNATURE)
+#define ATA_ASYN_TASK_FROM_ENTRY(a)         CR (a, ATA_BUS_ASYN_TASK, 
TaskEntry, ATA_TASK_SIGNATURE)
 
 //
 // Global Variables
@@ -301,6 +302,7 @@
   IN BOOLEAN                        IsWrite,
   IN OUT EFI_BLOCK_IO2_TOKEN        *Token
   );
+
 /**
   Trust transfer data from/to ATA device.
 
@@ -805,6 +807,22 @@
   );
 
 /**
+  Terminate any in-flight non-blocking I/O requests by signaling an EFI_ABORTED
+  in the TransactionStatus member of the EFI_BLOCK_IO2_TOKEN for the 
non-blocking
+  I/O. After that it is safe to free any Token or Buffer data structures that
+  were allocated to initiate the non-blockingI/O requests that were in-flight 
for
+  this device.
+
+  @param[in]  AtaDevice     The ATA child device involved for the operation.
+
+**/
+VOID
+EFIAPI
+AtaTerminateNonBlockingTask (
+  IN ATA_DEVICE               *AtaDevice
+  );
+
+/**
   Provides inquiry information for the controller type.
 
   This function is used by the IDE bus driver to get inquiry data.  Data format
@@ -940,20 +958,20 @@
   return EFI_SUCCESS. If the security protocol command completes with an 
error, the
   function shall return EFI_DEVICE_ERROR.
 
-  @param  This                              Indicates a pointer to the calling 
context.
-  @param  MediaId                           ID of the medium to receive data 
from.
-  @param  Timeout                                 The timeout, in 100ns units, 
to use for the execution
+  @param  This                         Indicates a pointer to the calling 
context.
+  @param  MediaId                      ID of the medium to receive data from.
+  @param  Timeout                      The timeout, in 100ns units, to use for 
the execution
                                        of the security protocol command. A 
Timeout value of 0
                                        means that this function will wait 
indefinitely for the
                                        security protocol command to execute. 
If Timeout is greater
                                        than zero, then this function will 
return EFI_TIMEOUT
-                                                              if the time 
required to execute the receive data command
-                                                              is greater than 
Timeout.
+                                       if the time required to execute the 
receive data command
+                                       is greater than Timeout.
   @param  SecurityProtocolId           The value of the "Security Protocol" 
parameter of
                                        the security protocol command to be 
sent.
   @param  SecurityProtocolSpecificData The value of the "Security Protocol 
Specific" parameter
                                        of the security protocol command to be 
sent.
-  @param  PayloadBufferSize                     Size in bytes of the payload 
data buffer.
+  @param  PayloadBufferSize            Size in bytes of the payload data 
buffer.
   @param  PayloadBuffer                A pointer to a destination buffer to 
store the security
                                        protocol command specific payload data 
for the security
                                        protocol command. The caller is 
responsible for having
@@ -1020,20 +1038,20 @@
   EFI_SUCCESS. If the security protocol command completes with an error, the 
function
   shall return EFI_DEVICE_ERROR.
 
-  @param  This                              Indicates a pointer to the calling 
context.
-  @param  MediaId                           ID of the medium to receive data 
from.
-  @param  Timeout                                 The timeout, in 100ns units, 
to use for the execution
+  @param  This                         Indicates a pointer to the calling 
context.
+  @param  MediaId                      ID of the medium to receive data from.
+  @param  Timeout                      The timeout, in 100ns units, to use for 
the execution
                                        of the security protocol command. A 
Timeout value of 0
                                        means that this function will wait 
indefinitely for the
                                        security protocol command to execute. 
If Timeout is greater
                                        than zero, then this function will 
return EFI_TIMEOUT
-                                                              if the time 
required to execute the receive data command
-                                                              is greater than 
Timeout.
+                                       if the time required to execute the 
receive data command
+                                       is greater than Timeout.
   @param  SecurityProtocolId           The value of the "Security Protocol" 
parameter of
                                        the security protocol command to be 
sent.
   @param  SecurityProtocolSpecificData The value of the "Security Protocol 
Specific" parameter
                                        of the security protocol command to be 
sent.
-  @param  PayloadBufferSize                     Size in bytes of the payload 
data buffer.
+  @param  PayloadBufferSize            Size in bytes of the payload data 
buffer.
   @param  PayloadBuffer                A pointer to a destination buffer to 
store the security
                                        protocol command specific payload data 
for the security
                                        protocol command.

Modified: trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaPassThruExecute.c
===================================================================
--- trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaPassThruExecute.c      
2013-10-09 08:30:59 UTC (rev 14760)
+++ trunk/edk2/MdeModulePkg/Bus/Ata/AtaBusDxe/AtaPassThruExecute.c      
2013-10-10 05:57:50 UTC (rev 14761)
@@ -583,6 +583,62 @@
 }
 
 /**
+  Terminate any in-flight non-blocking I/O requests by signaling an EFI_ABORTED
+  in the TransactionStatus member of the EFI_BLOCK_IO2_TOKEN for the 
non-blocking
+  I/O. After that it is safe to free any Token or Buffer data structures that
+  were allocated to initiate the non-blockingI/O requests that were in-flight 
for
+  this device.
+
+  @param[in]  AtaDevice     The ATA child device involved for the operation.
+
+**/
+VOID
+EFIAPI
+AtaTerminateNonBlockingTask (
+  IN ATA_DEVICE               *AtaDevice
+  )
+{
+  BOOLEAN               SubTaskEmpty;
+  EFI_TPL               OldTpl;
+  ATA_BUS_ASYN_TASK     *AtaTask;
+  LIST_ENTRY            *Entry;
+  LIST_ENTRY            *List;
+
+  OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
+  //
+  // Abort all executing tasks from now.
+  //
+  AtaDevice->Abort = TRUE;
+
+  List = &AtaDevice->AtaTaskList;
+  for (Entry = GetFirstNode (List); !IsNull (List, Entry);) {
+    AtaTask  = ATA_ASYN_TASK_FROM_ENTRY (Entry);
+    AtaTask->Token->TransactionStatus = EFI_ABORTED;
+    gBS->SignalEvent (AtaTask->Token->Event);
+
+    Entry = RemoveEntryList (Entry);
+    FreePool (AtaTask);
+  }
+  gBS->RestoreTPL (OldTpl);
+
+  do {
+    OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
+    //
+    // Wait for executing subtasks done.
+    //
+    SubTaskEmpty = IsListEmpty (&AtaDevice->AtaSubTaskList);
+    gBS->RestoreTPL (OldTpl);
+  } while (!SubTaskEmpty);
+
+  //
+  // Aborting operation has been done. From now on, don't need to abort normal 
operation.
+  //  
+  OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
+  AtaDevice->Abort = FALSE;
+  gBS->RestoreTPL (OldTpl);
+}
+
+/**
   Call back funtion when the event is signaled.
 
   @param[in]  Event     The Event this notify function registered to.
@@ -617,6 +673,11 @@
   if ((!(*Task->IsError)) && ((Task->Packet.Asb->AtaStatus & 0x01) == 0x01)) {
     Task->Token->TransactionStatus = EFI_DEVICE_ERROR;
   }
+
+  if (AtaDevice->Abort) {
+    Task->Token->TransactionStatus = EFI_ABORTED;
+  }
+
   DEBUG ((
     EFI_D_BLKIO,
     "NON-BLOCKING EVENT FINISHED!- STATUS = %r\n",
@@ -652,7 +713,7 @@
     //
     if (!IsListEmpty (&AtaDevice->AtaTaskList)) {
       Entry   = GetFirstNode (&AtaDevice->AtaTaskList);
-      AtaTask = ATA_AYNS_TASK_FROM_ENTRY (Entry);
+      AtaTask = ATA_ASYN_TASK_FROM_ENTRY (Entry);
       DEBUG ((EFI_D_BLKIO, "Start to embark a new Ata Task\n"));
       DEBUG ((EFI_D_BLKIO, "AtaTask->NumberOfBlocks = %x; 
AtaTask->Token=%x\n", AtaTask->NumberOfBlocks, AtaTask->Token));
       Status = AccessAtaDevice (
@@ -737,7 +798,7 @@
   SubTask    = NULL;
   SubEvent   = NULL;
   AtaTask    = NULL;
-  
+
   //
   // Ensure AtaDevice->Lba48Bit is a valid boolean value
   //
@@ -750,6 +811,7 @@
   //
   if ((Token != NULL) && (Token->Event != NULL)) {
     OldTpl = gBS->RaiseTPL (TPL_NOTIFY);
+
     if (!IsListEmpty (&AtaDevice->AtaSubTaskList)) {
       AtaTask = AllocateZeroPool (sizeof (ATA_BUS_ASYN_TASK));
       if (AtaTask == NULL) {
@@ -788,7 +850,7 @@
     DEBUG ((EFI_D_BLKIO, "AccessAtaDevice, NumberOfBlocks=%x\n", 
NumberOfBlocks));
     DEBUG ((EFI_D_BLKIO, "AccessAtaDevice, MaxTransferBlockNumber=%x\n", 
MaxTransferBlockNumber));
     DEBUG ((EFI_D_BLKIO, "AccessAtaDevice, EventCount=%x\n", TempCount));
-  }else {
+  } else {
     while (!IsListEmpty (&AtaDevice->AtaTaskList) || !IsListEmpty 
(&AtaDevice->AtaSubTaskList)) {
       //
       // Stall for 100us.

This was sent by the SourceForge.net collaborative development platform, the 
world's largest Open Source development site.


------------------------------------------------------------------------------
October Webinars: Code for Performance
Free Intel webinars can help you accelerate application performance.
Explore tips for MPI, OpenMP, advanced profiling, and more. Get the most from 
the latest Intel processors and coprocessors. See abstracts and register >
http://pubads.g.doubleclick.net/gampad/clk?id=60134071&iu=/4140/ostg.clktrk
_______________________________________________
edk2-commits mailing list
[email protected]
https://lists.sourceforge.net/lists/listinfo/edk2-commits

Reply via email to