2 This driver is used to manage SD/MMC PCI host controllers which are compliance
3 with SD Host Controller Simplified Specification version 3.00.
5 It would expose EFI_SD_MMC_PASS_THRU_PROTOCOL for upper layer use.
7 Copyright (c) 2015 - 2017, Intel Corporation. All rights reserved.<BR>
8 This program and the accompanying materials
9 are licensed and made available under the terms and conditions of the BSD License
10 which accompanies this distribution. The full text of the license may be found at
11 http://opensource.org/licenses/bsd-license.php
13 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
14 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
18 #include "SdMmcPciHcDxe.h"
21 Dump the content of SD/MMC host controller's Capability Register.
23 @param[in] Slot The slot number of the SD card to send the command to.
24 @param[in] Capability The buffer to store the capability data.
30 IN SD_MMC_HC_SLOT_CAP
*Capability
34 // Dump Capability Data
36 DEBUG ((DEBUG_INFO
, " == Slot [%d] Capability is 0x%x ==\n", Slot
, Capability
));
37 DEBUG ((DEBUG_INFO
, " Timeout Clk Freq %d%a\n", Capability
->TimeoutFreq
, (Capability
->TimeoutUnit
) ? "MHz" : "KHz"));
38 DEBUG ((DEBUG_INFO
, " Base Clk Freq %dMHz\n", Capability
->BaseClkFreq
));
39 DEBUG ((DEBUG_INFO
, " Max Blk Len %dbytes\n", 512 * (1 << Capability
->MaxBlkLen
)));
40 DEBUG ((DEBUG_INFO
, " 8-bit Support %a\n", Capability
->BusWidth8
? "TRUE" : "FALSE"));
41 DEBUG ((DEBUG_INFO
, " ADMA2 Support %a\n", Capability
->Adma2
? "TRUE" : "FALSE"));
42 DEBUG ((DEBUG_INFO
, " HighSpeed Support %a\n", Capability
->HighSpeed
? "TRUE" : "FALSE"));
43 DEBUG ((DEBUG_INFO
, " SDMA Support %a\n", Capability
->Sdma
? "TRUE" : "FALSE"));
44 DEBUG ((DEBUG_INFO
, " Suspend/Resume %a\n", Capability
->SuspRes
? "TRUE" : "FALSE"));
45 DEBUG ((DEBUG_INFO
, " Voltage 3.3 %a\n", Capability
->Voltage33
? "TRUE" : "FALSE"));
46 DEBUG ((DEBUG_INFO
, " Voltage 3.0 %a\n", Capability
->Voltage30
? "TRUE" : "FALSE"));
47 DEBUG ((DEBUG_INFO
, " Voltage 1.8 %a\n", Capability
->Voltage18
? "TRUE" : "FALSE"));
48 DEBUG ((DEBUG_INFO
, " 64-bit Sys Bus %a\n", Capability
->SysBus64
? "TRUE" : "FALSE"));
49 DEBUG ((DEBUG_INFO
, " Async Interrupt %a\n", Capability
->AsyncInt
? "TRUE" : "FALSE"));
50 DEBUG ((DEBUG_INFO
, " SlotType "));
51 if (Capability
->SlotType
== 0x00) {
52 DEBUG ((DEBUG_INFO
, "%a\n", "Removable Slot"));
53 } else if (Capability
->SlotType
== 0x01) {
54 DEBUG ((DEBUG_INFO
, "%a\n", "Embedded Slot"));
55 } else if (Capability
->SlotType
== 0x02) {
56 DEBUG ((DEBUG_INFO
, "%a\n", "Shared Bus Slot"));
58 DEBUG ((DEBUG_INFO
, "%a\n", "Reserved"));
60 DEBUG ((DEBUG_INFO
, " SDR50 Support %a\n", Capability
->Sdr50
? "TRUE" : "FALSE"));
61 DEBUG ((DEBUG_INFO
, " SDR104 Support %a\n", Capability
->Sdr104
? "TRUE" : "FALSE"));
62 DEBUG ((DEBUG_INFO
, " DDR50 Support %a\n", Capability
->Ddr50
? "TRUE" : "FALSE"));
63 DEBUG ((DEBUG_INFO
, " Driver Type A %a\n", Capability
->DriverTypeA
? "TRUE" : "FALSE"));
64 DEBUG ((DEBUG_INFO
, " Driver Type C %a\n", Capability
->DriverTypeC
? "TRUE" : "FALSE"));
65 DEBUG ((DEBUG_INFO
, " Driver Type D %a\n", Capability
->DriverTypeD
? "TRUE" : "FALSE"));
66 DEBUG ((DEBUG_INFO
, " Driver Type 4 %a\n", Capability
->DriverType4
? "TRUE" : "FALSE"));
67 if (Capability
->TimerCount
== 0) {
68 DEBUG ((DEBUG_INFO
, " Retuning TimerCnt Disabled\n", 2 * (Capability
->TimerCount
- 1)));
70 DEBUG ((DEBUG_INFO
, " Retuning TimerCnt %dseconds\n", 2 * (Capability
->TimerCount
- 1)));
72 DEBUG ((DEBUG_INFO
, " SDR50 Tuning %a\n", Capability
->TuningSDR50
? "TRUE" : "FALSE"));
73 DEBUG ((DEBUG_INFO
, " Retuning Mode Mode %d\n", Capability
->RetuningMod
+ 1));
74 DEBUG ((DEBUG_INFO
, " Clock Multiplier M = %d\n", Capability
->ClkMultiplier
+ 1));
75 DEBUG ((DEBUG_INFO
, " HS 400 %a\n", Capability
->Hs400
? "TRUE" : "FALSE"));
80 Read SlotInfo register from SD/MMC host controller pci config space.
82 @param[in] PciIo The PCI IO protocol instance.
83 @param[out] FirstBar The buffer to store the first BAR value.
84 @param[out] SlotNum The buffer to store the supported slot number.
86 @retval EFI_SUCCESS The operation succeeds.
87 @retval Others The operation fails.
93 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
99 SD_MMC_HC_SLOT_INFO SlotInfo
;
101 Status
= PciIo
->Pci
.Read (
104 SD_MMC_HC_SLOT_OFFSET
,
108 if (EFI_ERROR (Status
)) {
112 *FirstBar
= SlotInfo
.FirstBar
;
113 *SlotNum
= SlotInfo
.SlotNum
+ 1;
114 ASSERT ((*FirstBar
+ *SlotNum
) < SD_MMC_HC_MAX_SLOT
);
119 Read/Write specified SD/MMC host controller mmio register.
121 @param[in] PciIo The PCI IO protocol instance.
122 @param[in] BarIndex The BAR index of the standard PCI Configuration
123 header to use as the base address for the memory
124 operation to perform.
125 @param[in] Offset The offset within the selected BAR to start the
127 @param[in] Read A boolean to indicate it's read or write operation.
128 @param[in] Count The width of the mmio register in bytes.
129 Must be 1, 2 , 4 or 8 bytes.
130 @param[in, out] Data For read operations, the destination buffer to store
131 the results. For write operations, the source buffer
132 to write data from. The caller is responsible for
133 having ownership of the data buffer and ensuring its
134 size not less than Count bytes.
136 @retval EFI_INVALID_PARAMETER The PciIo or Data is NULL or the Count is not valid.
137 @retval EFI_SUCCESS The read/write operation succeeds.
138 @retval Others The read/write operation fails.
144 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
154 if ((PciIo
== NULL
) || (Data
== NULL
)) {
155 return EFI_INVALID_PARAMETER
;
158 if ((Count
!= 1) && (Count
!= 2) && (Count
!= 4) && (Count
!= 8)) {
159 return EFI_INVALID_PARAMETER
;
163 Status
= PciIo
->Mem
.Read (
172 Status
= PciIo
->Mem
.Write (
186 Do OR operation with the value of the specified SD/MMC host controller mmio register.
188 @param[in] PciIo The PCI IO protocol instance.
189 @param[in] BarIndex The BAR index of the standard PCI Configuration
190 header to use as the base address for the memory
191 operation to perform.
192 @param[in] Offset The offset within the selected BAR to start the
194 @param[in] Count The width of the mmio register in bytes.
195 Must be 1, 2 , 4 or 8 bytes.
196 @param[in] OrData The pointer to the data used to do OR operation.
197 The caller is responsible for having ownership of
198 the data buffer and ensuring its size not less than
201 @retval EFI_INVALID_PARAMETER The PciIo or OrData is NULL or the Count is not valid.
202 @retval EFI_SUCCESS The OR operation succeeds.
203 @retval Others The OR operation fails.
209 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
220 Status
= SdMmcHcRwMmio (PciIo
, BarIndex
, Offset
, TRUE
, Count
, &Data
);
221 if (EFI_ERROR (Status
)) {
226 Or
= *(UINT8
*) OrData
;
227 } else if (Count
== 2) {
228 Or
= *(UINT16
*) OrData
;
229 } else if (Count
== 4) {
230 Or
= *(UINT32
*) OrData
;
231 } else if (Count
== 8) {
232 Or
= *(UINT64
*) OrData
;
234 return EFI_INVALID_PARAMETER
;
238 Status
= SdMmcHcRwMmio (PciIo
, BarIndex
, Offset
, FALSE
, Count
, &Data
);
244 Do AND operation with the value of the specified SD/MMC host controller mmio register.
246 @param[in] PciIo The PCI IO protocol instance.
247 @param[in] BarIndex The BAR index of the standard PCI Configuration
248 header to use as the base address for the memory
249 operation to perform.
250 @param[in] Offset The offset within the selected BAR to start the
252 @param[in] Count The width of the mmio register in bytes.
253 Must be 1, 2 , 4 or 8 bytes.
254 @param[in] AndData The pointer to the data used to do AND operation.
255 The caller is responsible for having ownership of
256 the data buffer and ensuring its size not less than
259 @retval EFI_INVALID_PARAMETER The PciIo or AndData is NULL or the Count is not valid.
260 @retval EFI_SUCCESS The AND operation succeeds.
261 @retval Others The AND operation fails.
267 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
278 Status
= SdMmcHcRwMmio (PciIo
, BarIndex
, Offset
, TRUE
, Count
, &Data
);
279 if (EFI_ERROR (Status
)) {
284 And
= *(UINT8
*) AndData
;
285 } else if (Count
== 2) {
286 And
= *(UINT16
*) AndData
;
287 } else if (Count
== 4) {
288 And
= *(UINT32
*) AndData
;
289 } else if (Count
== 8) {
290 And
= *(UINT64
*) AndData
;
292 return EFI_INVALID_PARAMETER
;
296 Status
= SdMmcHcRwMmio (PciIo
, BarIndex
, Offset
, FALSE
, Count
, &Data
);
302 Wait for the value of the specified MMIO register set to the test value.
304 @param[in] PciIo The PCI IO protocol instance.
305 @param[in] BarIndex The BAR index of the standard PCI Configuration
306 header to use as the base address for the memory
307 operation to perform.
308 @param[in] Offset The offset within the selected BAR to start the
310 @param[in] Count The width of the mmio register in bytes.
311 Must be 1, 2, 4 or 8 bytes.
312 @param[in] MaskValue The mask value of memory.
313 @param[in] TestValue The test value of memory.
315 @retval EFI_NOT_READY The MMIO register hasn't set to the expected value.
316 @retval EFI_SUCCESS The MMIO register has expected value.
317 @retval Others The MMIO operation fails.
322 SdMmcHcCheckMmioSet (
323 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
335 // Access PCI MMIO space to see if the value is the tested one.
338 Status
= SdMmcHcRwMmio (PciIo
, BarIndex
, Offset
, TRUE
, Count
, &Value
);
339 if (EFI_ERROR (Status
)) {
345 if (Value
== TestValue
) {
349 return EFI_NOT_READY
;
353 Wait for the value of the specified MMIO register set to the test value.
355 @param[in] PciIo The PCI IO protocol instance.
356 @param[in] BarIndex The BAR index of the standard PCI Configuration
357 header to use as the base address for the memory
358 operation to perform.
359 @param[in] Offset The offset within the selected BAR to start the
361 @param[in] Count The width of the mmio register in bytes.
362 Must be 1, 2, 4 or 8 bytes.
363 @param[in] MaskValue The mask value of memory.
364 @param[in] TestValue The test value of memory.
365 @param[in] Timeout The time out value for wait memory set, uses 1
366 microsecond as a unit.
368 @retval EFI_TIMEOUT The MMIO register hasn't expected value in timeout
370 @retval EFI_SUCCESS The MMIO register has expected value.
371 @retval Others The MMIO operation fails.
377 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
387 BOOLEAN InfiniteWait
;
392 InfiniteWait
= FALSE
;
395 while (InfiniteWait
|| (Timeout
> 0)) {
396 Status
= SdMmcHcCheckMmioSet (
404 if (Status
!= EFI_NOT_READY
) {
409 // Stall for 1 microsecond.
420 Software reset the specified SD/MMC host controller and enable all interrupts.
422 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
423 @param[in] Slot The slot number of the SD card to send the command to.
425 @retval EFI_SUCCESS The software reset executes successfully.
426 @retval Others The software reset fails.
431 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
437 EFI_PCI_IO_PROTOCOL
*PciIo
;
440 // Notify the SD/MMC override protocol that we are about to reset
441 // the SD/MMC host controller.
443 if (mOverride
!= NULL
&& mOverride
->NotifyPhase
!= NULL
) {
444 Status
= mOverride
->NotifyPhase (
445 Private
->ControllerHandle
,
449 if (EFI_ERROR (Status
)) {
451 "%a: SD/MMC pre reset notifier callback failed - %r\n",
452 __FUNCTION__
, Status
));
457 PciIo
= Private
->PciIo
;
459 Status
= SdMmcHcOrMmio (PciIo
, Slot
, SD_MMC_HC_SW_RST
, sizeof (SwReset
), &SwReset
);
461 if (EFI_ERROR (Status
)) {
462 DEBUG ((DEBUG_ERROR
, "SdMmcHcReset: write SW Reset for All fails: %r\n", Status
));
466 Status
= SdMmcHcWaitMmioSet (
473 SD_MMC_HC_GENERIC_TIMEOUT
475 if (EFI_ERROR (Status
)) {
476 DEBUG ((DEBUG_INFO
, "SdMmcHcReset: reset done with %r\n", Status
));
481 // Enable all interrupt after reset all.
483 Status
= SdMmcHcEnableInterrupt (PciIo
, Slot
);
484 if (EFI_ERROR (Status
)) {
485 DEBUG ((DEBUG_INFO
, "SdMmcHcReset: SdMmcHcEnableInterrupt done with %r\n",
491 // Notify the SD/MMC override protocol that we have just reset
492 // the SD/MMC host controller.
494 if (mOverride
!= NULL
&& mOverride
->NotifyPhase
!= NULL
) {
495 Status
= mOverride
->NotifyPhase (
496 Private
->ControllerHandle
,
500 if (EFI_ERROR (Status
)) {
502 "%a: SD/MMC post reset notifier callback failed - %r\n",
503 __FUNCTION__
, Status
));
511 Set all interrupt status bits in Normal and Error Interrupt Status Enable
514 @param[in] PciIo The PCI IO protocol instance.
515 @param[in] Slot The slot number of the SD card to send the command to.
517 @retval EFI_SUCCESS The operation executes successfully.
518 @retval Others The operation fails.
522 SdMmcHcEnableInterrupt (
523 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
531 // Enable all bits in Error Interrupt Status Enable Register
534 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_ERR_INT_STS_EN
, FALSE
, sizeof (IntStatus
), &IntStatus
);
535 if (EFI_ERROR (Status
)) {
539 // Enable all bits in Normal Interrupt Status Enable Register
542 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_NOR_INT_STS_EN
, FALSE
, sizeof (IntStatus
), &IntStatus
);
548 Get the capability data from the specified slot.
550 @param[in] PciIo The PCI IO protocol instance.
551 @param[in] Slot The slot number of the SD card to send the command to.
552 @param[out] Capability The buffer to store the capability data.
554 @retval EFI_SUCCESS The operation executes successfully.
555 @retval Others The operation fails.
559 SdMmcHcGetCapability (
560 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
562 OUT SD_MMC_HC_SLOT_CAP
*Capability
568 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_CAP
, TRUE
, sizeof (Cap
), &Cap
);
569 if (EFI_ERROR (Status
)) {
573 CopyMem (Capability
, &Cap
, sizeof (Cap
));
579 Get the maximum current capability data from the specified slot.
581 @param[in] PciIo The PCI IO protocol instance.
582 @param[in] Slot The slot number of the SD card to send the command to.
583 @param[out] MaxCurrent The buffer to store the maximum current capability data.
585 @retval EFI_SUCCESS The operation executes successfully.
586 @retval Others The operation fails.
590 SdMmcHcGetMaxCurrent (
591 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
593 OUT UINT64
*MaxCurrent
598 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_MAX_CURRENT_CAP
, TRUE
, sizeof (UINT64
), MaxCurrent
);
604 Detect whether there is a SD/MMC card attached at the specified SD/MMC host controller
607 Refer to SD Host Controller Simplified spec 3.0 Section 3.1 for details.
609 @param[in] PciIo The PCI IO protocol instance.
610 @param[in] Slot The slot number of the SD card to send the command to.
611 @param[out] MediaPresent The pointer to the media present boolean value.
613 @retval EFI_SUCCESS There is no media change happened.
614 @retval EFI_MEDIA_CHANGED There is media change happened.
615 @retval Others The detection fails.
620 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
622 OUT BOOLEAN
*MediaPresent
630 // Check Present State Register to see if there is a card presented.
632 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_PRESENT_STATE
, TRUE
, sizeof (PresentState
), &PresentState
);
633 if (EFI_ERROR (Status
)) {
637 if ((PresentState
& BIT16
) != 0) {
638 *MediaPresent
= TRUE
;
640 *MediaPresent
= FALSE
;
644 // Check Normal Interrupt Status Register
646 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_NOR_INT_STS
, TRUE
, sizeof (Data
), &Data
);
647 if (EFI_ERROR (Status
)) {
651 if ((Data
& (BIT6
| BIT7
)) != 0) {
653 // Clear BIT6 and BIT7 by writing 1 to these two bits if set.
656 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_NOR_INT_STS
, FALSE
, sizeof (Data
), &Data
);
657 if (EFI_ERROR (Status
)) {
661 return EFI_MEDIA_CHANGED
;
668 Stop SD/MMC card clock.
670 Refer to SD Host Controller Simplified spec 3.0 Section 3.2.2 for details.
672 @param[in] PciIo The PCI IO protocol instance.
673 @param[in] Slot The slot number of the SD card to send the command to.
675 @retval EFI_SUCCESS Succeed to stop SD/MMC clock.
676 @retval Others Fail to stop SD/MMC clock.
681 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
690 // Ensure no SD transactions are occurring on the SD Bus by
691 // waiting for Command Inhibit (DAT) and Command Inhibit (CMD)
692 // in the Present State register to be 0.
694 Status
= SdMmcHcWaitMmioSet (
697 SD_MMC_HC_PRESENT_STATE
,
698 sizeof (PresentState
),
701 SD_MMC_HC_GENERIC_TIMEOUT
703 if (EFI_ERROR (Status
)) {
708 // Set SD Clock Enable in the Clock Control register to 0
710 ClockCtrl
= (UINT16
)~BIT2
;
711 Status
= SdMmcHcAndMmio (PciIo
, Slot
, SD_MMC_HC_CLOCK_CTRL
, sizeof (ClockCtrl
), &ClockCtrl
);
717 SD/MMC card clock supply.
719 Refer to SD Host Controller Simplified spec 3.0 Section 3.2.1 for details.
721 @param[in] PciIo The PCI IO protocol instance.
722 @param[in] Slot The slot number of the SD card to send the command to.
723 @param[in] ClockFreq The max clock frequency to be set. The unit is KHz.
724 @param[in] Capability The capability of the slot.
726 @retval EFI_SUCCESS The clock is supplied successfully.
727 @retval Others The clock isn't supplied successfully.
732 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
735 IN SD_MMC_HC_SLOT_CAP Capability
743 UINT16 ControllerVer
;
747 // Calculate a divisor for SD clock frequency
749 ASSERT (Capability
.BaseClkFreq
!= 0);
751 BaseClkFreq
= Capability
.BaseClkFreq
;
752 if (ClockFreq
== 0) {
753 return EFI_INVALID_PARAMETER
;
756 if (ClockFreq
> (BaseClkFreq
* 1000)) {
757 ClockFreq
= BaseClkFreq
* 1000;
761 // Calculate the divisor of base frequency.
764 SettingFreq
= BaseClkFreq
* 1000;
765 while (ClockFreq
< SettingFreq
) {
768 SettingFreq
= (BaseClkFreq
* 1000) / (2 * Divisor
);
769 Remainder
= (BaseClkFreq
* 1000) % (2 * Divisor
);
770 if ((ClockFreq
== SettingFreq
) && (Remainder
== 0)) {
773 if ((ClockFreq
== SettingFreq
) && (Remainder
!= 0)) {
778 DEBUG ((DEBUG_INFO
, "BaseClkFreq %dMHz Divisor %d ClockFreq %dKhz\n", BaseClkFreq
, Divisor
, ClockFreq
));
780 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_CTRL_VER
, TRUE
, sizeof (ControllerVer
), &ControllerVer
);
781 if (EFI_ERROR (Status
)) {
785 // Set SDCLK Frequency Select and Internal Clock Enable fields in Clock Control register.
787 if (((ControllerVer
& 0xFF) >= SD_MMC_HC_CTRL_VER_300
) &&
788 ((ControllerVer
& 0xFF) <= SD_MMC_HC_CTRL_VER_420
)) {
789 ASSERT (Divisor
<= 0x3FF);
790 ClockCtrl
= ((Divisor
& 0xFF) << 8) | ((Divisor
& 0x300) >> 2);
791 } else if (((ControllerVer
& 0xFF) == 0) || ((ControllerVer
& 0xFF) == 1)) {
793 // Only the most significant bit can be used as divisor.
795 if (((Divisor
- 1) & Divisor
) != 0) {
796 Divisor
= 1 << (HighBitSet32 (Divisor
) + 1);
798 ASSERT (Divisor
<= 0x80);
799 ClockCtrl
= (Divisor
& 0xFF) << 8;
801 DEBUG ((DEBUG_ERROR
, "Unknown SD Host Controller Spec version [0x%x]!!!\n", ControllerVer
));
802 return EFI_UNSUPPORTED
;
806 // Stop bus clock at first
808 Status
= SdMmcHcStopClock (PciIo
, Slot
);
809 if (EFI_ERROR (Status
)) {
814 // Supply clock frequency with specified divisor
817 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_CLOCK_CTRL
, FALSE
, sizeof (ClockCtrl
), &ClockCtrl
);
818 if (EFI_ERROR (Status
)) {
819 DEBUG ((DEBUG_ERROR
, "Set SDCLK Frequency Select and Internal Clock Enable fields fails\n"));
824 // Wait Internal Clock Stable in the Clock Control register to be 1
826 Status
= SdMmcHcWaitMmioSet (
829 SD_MMC_HC_CLOCK_CTRL
,
833 SD_MMC_HC_GENERIC_TIMEOUT
835 if (EFI_ERROR (Status
)) {
840 // Set SD Clock Enable in the Clock Control register to 1
843 Status
= SdMmcHcOrMmio (PciIo
, Slot
, SD_MMC_HC_CLOCK_CTRL
, sizeof (ClockCtrl
), &ClockCtrl
);
849 SD/MMC bus power control.
851 Refer to SD Host Controller Simplified spec 3.0 Section 3.3 for details.
853 @param[in] PciIo The PCI IO protocol instance.
854 @param[in] Slot The slot number of the SD card to send the command to.
855 @param[in] PowerCtrl The value setting to the power control register.
857 @retval TRUE There is a SD/MMC card attached.
858 @retval FALSE There is no a SD/MMC card attached.
862 SdMmcHcPowerControl (
863 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
873 PowerCtrl
&= (UINT8
)~BIT0
;
874 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_POWER_CTRL
, FALSE
, sizeof (PowerCtrl
), &PowerCtrl
);
875 if (EFI_ERROR (Status
)) {
880 // Set SD Bus Voltage Select and SD Bus Power fields in Power Control Register
883 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_POWER_CTRL
, FALSE
, sizeof (PowerCtrl
), &PowerCtrl
);
889 Set the SD/MMC bus width.
891 Refer to SD Host Controller Simplified spec 3.0 Section 3.4 for details.
893 @param[in] PciIo The PCI IO protocol instance.
894 @param[in] Slot The slot number of the SD card to send the command to.
895 @param[in] BusWidth The bus width used by the SD/MMC device, it must be 1, 4 or 8.
897 @retval EFI_SUCCESS The bus width is set successfully.
898 @retval Others The bus width isn't set successfully.
903 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
912 HostCtrl1
= (UINT8
)~(BIT5
| BIT1
);
913 Status
= SdMmcHcAndMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL1
, sizeof (HostCtrl1
), &HostCtrl1
);
914 } else if (BusWidth
== 4) {
915 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL1
, TRUE
, sizeof (HostCtrl1
), &HostCtrl1
);
916 if (EFI_ERROR (Status
)) {
920 HostCtrl1
&= (UINT8
)~BIT5
;
921 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL1
, FALSE
, sizeof (HostCtrl1
), &HostCtrl1
);
922 } else if (BusWidth
== 8) {
923 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL1
, TRUE
, sizeof (HostCtrl1
), &HostCtrl1
);
924 if (EFI_ERROR (Status
)) {
927 HostCtrl1
&= (UINT8
)~BIT1
;
929 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL1
, FALSE
, sizeof (HostCtrl1
), &HostCtrl1
);
932 return EFI_INVALID_PARAMETER
;
939 Supply SD/MMC card with lowest clock frequency at initialization.
941 @param[in] PciIo The PCI IO protocol instance.
942 @param[in] Slot The slot number of the SD card to send the command to.
943 @param[in] Capability The capability of the slot.
945 @retval EFI_SUCCESS The clock is supplied successfully.
946 @retval Others The clock isn't supplied successfully.
950 SdMmcHcInitClockFreq (
951 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
953 IN SD_MMC_HC_SLOT_CAP Capability
960 // Calculate a divisor for SD clock frequency
962 if (Capability
.BaseClkFreq
== 0) {
964 // Don't support get Base Clock Frequency information via another method
966 return EFI_UNSUPPORTED
;
969 // Supply 400KHz clock frequency at initialization phase.
972 Status
= SdMmcHcClockSupply (PciIo
, Slot
, InitFreq
, Capability
);
977 Supply SD/MMC card with maximum voltage at initialization.
979 Refer to SD Host Controller Simplified spec 3.0 Section 3.3 for details.
981 @param[in] PciIo The PCI IO protocol instance.
982 @param[in] Slot The slot number of the SD card to send the command to.
983 @param[in] Capability The capability of the slot.
985 @retval EFI_SUCCESS The voltage is supplied successfully.
986 @retval Others The voltage isn't supplied successfully.
990 SdMmcHcInitPowerVoltage (
991 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
993 IN SD_MMC_HC_SLOT_CAP Capability
1001 // Calculate supported maximum voltage according to SD Bus Voltage Select
1003 if (Capability
.Voltage33
!= 0) {
1008 } else if (Capability
.Voltage30
!= 0) {
1013 } else if (Capability
.Voltage18
!= 0) {
1019 Status
= SdMmcHcOrMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL2
, sizeof (HostCtrl2
), &HostCtrl2
);
1021 if (EFI_ERROR (Status
)) {
1026 return EFI_DEVICE_ERROR
;
1030 // Set SD Bus Voltage Select and SD Bus Power fields in Power Control Register
1032 Status
= SdMmcHcPowerControl (PciIo
, Slot
, MaxVoltage
);
1038 Initialize the Timeout Control register with most conservative value at initialization.
1040 Refer to SD Host Controller Simplified spec 3.0 Section 2.2.15 for details.
1042 @param[in] PciIo The PCI IO protocol instance.
1043 @param[in] Slot The slot number of the SD card to send the command to.
1045 @retval EFI_SUCCESS The timeout control register is configured successfully.
1046 @retval Others The timeout control register isn't configured successfully.
1050 SdMmcHcInitTimeoutCtrl (
1051 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
1059 Status
= SdMmcHcRwMmio (PciIo
, Slot
, SD_MMC_HC_TIMEOUT_CTRL
, FALSE
, sizeof (Timeout
), &Timeout
);
1065 Initial SD/MMC host controller with lowest clock frequency, max power and max timeout value
1068 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
1069 @param[in] Slot The slot number of the SD card to send the command to.
1071 @retval EFI_SUCCESS The host controller is initialized successfully.
1072 @retval Others The host controller isn't initialized successfully.
1077 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
1082 EFI_PCI_IO_PROTOCOL
*PciIo
;
1083 SD_MMC_HC_SLOT_CAP Capability
;
1086 // Notify the SD/MMC override protocol that we are about to initialize
1087 // the SD/MMC host controller.
1089 if (mOverride
!= NULL
&& mOverride
->NotifyPhase
!= NULL
) {
1090 Status
= mOverride
->NotifyPhase (
1091 Private
->ControllerHandle
,
1093 EdkiiSdMmcInitHostPre
,
1095 if (EFI_ERROR (Status
)) {
1097 "%a: SD/MMC pre init notifier callback failed - %r\n",
1098 __FUNCTION__
, Status
));
1103 PciIo
= Private
->PciIo
;
1104 Capability
= Private
->Capability
[Slot
];
1106 Status
= SdMmcHcInitClockFreq (PciIo
, Slot
, Capability
);
1107 if (EFI_ERROR (Status
)) {
1111 Status
= SdMmcHcInitPowerVoltage (PciIo
, Slot
, Capability
);
1112 if (EFI_ERROR (Status
)) {
1116 Status
= SdMmcHcInitTimeoutCtrl (PciIo
, Slot
);
1117 if (EFI_ERROR (Status
)) {
1122 // Notify the SD/MMC override protocol that we are have just initialized
1123 // the SD/MMC host controller.
1125 if (mOverride
!= NULL
&& mOverride
->NotifyPhase
!= NULL
) {
1126 Status
= mOverride
->NotifyPhase (
1127 Private
->ControllerHandle
,
1129 EdkiiSdMmcInitHostPost
,
1131 if (EFI_ERROR (Status
)) {
1133 "%a: SD/MMC post init notifier callback failed - %r\n",
1134 __FUNCTION__
, Status
));
1143 @param[in] PciIo The PCI IO protocol instance.
1144 @param[in] Slot The slot number of the SD card to send the command to.
1145 @param[in] On The boolean to turn on/off LED.
1147 @retval EFI_SUCCESS The LED is turned on/off successfully.
1148 @retval Others The LED isn't turned on/off successfully.
1153 IN EFI_PCI_IO_PROTOCOL
*PciIo
,
1163 Status
= SdMmcHcOrMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL1
, sizeof (HostCtrl1
), &HostCtrl1
);
1165 HostCtrl1
= (UINT8
)~BIT0
;
1166 Status
= SdMmcHcAndMmio (PciIo
, Slot
, SD_MMC_HC_HOST_CTRL1
, sizeof (HostCtrl1
), &HostCtrl1
);
1173 Build ADMA descriptor table for transfer.
1175 Refer to SD Host Controller Simplified spec 3.0 Section 1.13 for details.
1177 @param[in] Trb The pointer to the SD_MMC_HC_TRB instance.
1179 @retval EFI_SUCCESS The ADMA descriptor table is created successfully.
1180 @retval Others The ADMA descriptor table isn't created successfully.
1184 BuildAdmaDescTable (
1185 IN SD_MMC_HC_TRB
*Trb
1188 EFI_PHYSICAL_ADDRESS Data
;
1195 EFI_PCI_IO_PROTOCOL
*PciIo
;
1199 Data
= Trb
->DataPhy
;
1200 DataLen
= Trb
->DataLen
;
1201 PciIo
= Trb
->Private
->PciIo
;
1203 // Only support 32bit ADMA Descriptor Table
1205 if ((Data
>= 0x100000000ul
) || ((Data
+ DataLen
) > 0x100000000ul
)) {
1206 return EFI_INVALID_PARAMETER
;
1209 // Address field shall be set on 32-bit boundary (Lower 2-bit is always set to 0)
1210 // for 32-bit address descriptor table.
1212 if ((Data
& (BIT0
| BIT1
)) != 0) {
1213 DEBUG ((DEBUG_INFO
, "The buffer [0x%x] to construct ADMA desc is not aligned to 4 bytes boundary!\n", Data
));
1216 Entries
= DivU64x32 ((DataLen
+ ADMA_MAX_DATA_PER_LINE
- 1), ADMA_MAX_DATA_PER_LINE
);
1217 TableSize
= (UINTN
)MultU64x32 (Entries
, sizeof (SD_MMC_HC_ADMA_DESC_LINE
));
1218 Trb
->AdmaPages
= (UINT32
)EFI_SIZE_TO_PAGES (TableSize
);
1219 Status
= PciIo
->AllocateBuffer (
1222 EfiBootServicesData
,
1223 EFI_SIZE_TO_PAGES (TableSize
),
1224 (VOID
**)&Trb
->AdmaDesc
,
1227 if (EFI_ERROR (Status
)) {
1228 return EFI_OUT_OF_RESOURCES
;
1230 ZeroMem (Trb
->AdmaDesc
, TableSize
);
1232 Status
= PciIo
->Map (
1234 EfiPciIoOperationBusMasterCommonBuffer
,
1241 if (EFI_ERROR (Status
) || (Bytes
!= TableSize
)) {
1243 // Map error or unable to map the whole RFis buffer into a contiguous region.
1247 EFI_SIZE_TO_PAGES (TableSize
),
1250 return EFI_OUT_OF_RESOURCES
;
1253 if ((UINT64
)(UINTN
)Trb
->AdmaDescPhy
> 0x100000000ul
) {
1255 // The ADMA doesn't support 64bit addressing.
1263 EFI_SIZE_TO_PAGES (TableSize
),
1266 return EFI_DEVICE_ERROR
;
1269 Remaining
= DataLen
;
1270 Address
= (UINT32
)Data
;
1271 for (Index
= 0; Index
< Entries
; Index
++) {
1272 if (Remaining
<= ADMA_MAX_DATA_PER_LINE
) {
1273 Trb
->AdmaDesc
[Index
].Valid
= 1;
1274 Trb
->AdmaDesc
[Index
].Act
= 2;
1275 Trb
->AdmaDesc
[Index
].Length
= (UINT16
)Remaining
;
1276 Trb
->AdmaDesc
[Index
].Address
= Address
;
1279 Trb
->AdmaDesc
[Index
].Valid
= 1;
1280 Trb
->AdmaDesc
[Index
].Act
= 2;
1281 Trb
->AdmaDesc
[Index
].Length
= 0;
1282 Trb
->AdmaDesc
[Index
].Address
= Address
;
1285 Remaining
-= ADMA_MAX_DATA_PER_LINE
;
1286 Address
+= ADMA_MAX_DATA_PER_LINE
;
1290 // Set the last descriptor line as end of descriptor table
1292 Trb
->AdmaDesc
[Index
].End
= 1;
1297 Create a new TRB for the SD/MMC cmd request.
1299 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
1300 @param[in] Slot The slot number of the SD card to send the command to.
1301 @param[in] Packet A pointer to the SD command data structure.
1302 @param[in] Event If Event is NULL, blocking I/O is performed. If Event is
1303 not NULL, then nonblocking I/O is performed, and Event
1304 will be signaled when the Packet completes.
1306 @return Created Trb or NULL.
1311 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
1313 IN EFI_SD_MMC_PASS_THRU_COMMAND_PACKET
*Packet
,
1320 EFI_PCI_IO_PROTOCOL_OPERATION Flag
;
1321 EFI_PCI_IO_PROTOCOL
*PciIo
;
1324 Trb
= AllocateZeroPool (sizeof (SD_MMC_HC_TRB
));
1329 Trb
->Signature
= SD_MMC_HC_TRB_SIG
;
1331 Trb
->BlockSize
= 0x200;
1332 Trb
->Packet
= Packet
;
1334 Trb
->Started
= FALSE
;
1335 Trb
->Timeout
= Packet
->Timeout
;
1336 Trb
->Private
= Private
;
1338 if ((Packet
->InTransferLength
!= 0) && (Packet
->InDataBuffer
!= NULL
)) {
1339 Trb
->Data
= Packet
->InDataBuffer
;
1340 Trb
->DataLen
= Packet
->InTransferLength
;
1342 } else if ((Packet
->OutTransferLength
!= 0) && (Packet
->OutDataBuffer
!= NULL
)) {
1343 Trb
->Data
= Packet
->OutDataBuffer
;
1344 Trb
->DataLen
= Packet
->OutTransferLength
;
1346 } else if ((Packet
->InTransferLength
== 0) && (Packet
->OutTransferLength
== 0)) {
1353 if ((Trb
->DataLen
!= 0) && (Trb
->DataLen
< Trb
->BlockSize
)) {
1354 Trb
->BlockSize
= (UINT16
)Trb
->DataLen
;
1357 if (((Private
->Slot
[Trb
->Slot
].CardType
== EmmcCardType
) &&
1358 (Packet
->SdMmcCmdBlk
->CommandIndex
== EMMC_SEND_TUNING_BLOCK
)) ||
1359 ((Private
->Slot
[Trb
->Slot
].CardType
== SdCardType
) &&
1360 (Packet
->SdMmcCmdBlk
->CommandIndex
== SD_SEND_TUNING_BLOCK
))) {
1361 Trb
->Mode
= SdMmcPioMode
;
1364 Flag
= EfiPciIoOperationBusMasterWrite
;
1366 Flag
= EfiPciIoOperationBusMasterRead
;
1369 PciIo
= Private
->PciIo
;
1370 if (Trb
->DataLen
!= 0) {
1371 MapLength
= Trb
->DataLen
;
1372 Status
= PciIo
->Map (
1380 if (EFI_ERROR (Status
) || (Trb
->DataLen
!= MapLength
)) {
1381 Status
= EFI_BAD_BUFFER_SIZE
;
1386 if (Trb
->DataLen
== 0) {
1387 Trb
->Mode
= SdMmcNoData
;
1388 } else if (Private
->Capability
[Slot
].Adma2
!= 0) {
1389 Trb
->Mode
= SdMmcAdmaMode
;
1390 Status
= BuildAdmaDescTable (Trb
);
1391 if (EFI_ERROR (Status
)) {
1392 PciIo
->Unmap (PciIo
, Trb
->DataMap
);
1395 } else if (Private
->Capability
[Slot
].Sdma
!= 0) {
1396 Trb
->Mode
= SdMmcSdmaMode
;
1398 Trb
->Mode
= SdMmcPioMode
;
1402 if (Event
!= NULL
) {
1403 OldTpl
= gBS
->RaiseTPL (TPL_NOTIFY
);
1404 InsertTailList (&Private
->Queue
, &Trb
->TrbList
);
1405 gBS
->RestoreTPL (OldTpl
);
1416 Free the resource used by the TRB.
1418 @param[in] Trb The pointer to the SD_MMC_HC_TRB instance.
1423 IN SD_MMC_HC_TRB
*Trb
1426 EFI_PCI_IO_PROTOCOL
*PciIo
;
1428 PciIo
= Trb
->Private
->PciIo
;
1430 if (Trb
->AdmaMap
!= NULL
) {
1436 if (Trb
->AdmaDesc
!= NULL
) {
1443 if (Trb
->DataMap
!= NULL
) {
1454 Check if the env is ready for execute specified TRB.
1456 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
1457 @param[in] Trb The pointer to the SD_MMC_HC_TRB instance.
1459 @retval EFI_SUCCESS The env is ready for TRB execution.
1460 @retval EFI_NOT_READY The env is not ready for TRB execution.
1461 @retval Others Some erros happen.
1466 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
1467 IN SD_MMC_HC_TRB
*Trb
1471 EFI_SD_MMC_PASS_THRU_COMMAND_PACKET
*Packet
;
1472 EFI_PCI_IO_PROTOCOL
*PciIo
;
1473 UINT32 PresentState
;
1475 Packet
= Trb
->Packet
;
1477 if ((Packet
->SdMmcCmdBlk
->CommandType
== SdMmcCommandTypeAdtc
) ||
1478 (Packet
->SdMmcCmdBlk
->ResponseType
== SdMmcResponseTypeR1b
) ||
1479 (Packet
->SdMmcCmdBlk
->ResponseType
== SdMmcResponseTypeR5b
)) {
1481 // Wait Command Inhibit (CMD) and Command Inhibit (DAT) in
1482 // the Present State register to be 0
1484 PresentState
= BIT0
| BIT1
;
1487 // Wait Command Inhibit (CMD) in the Present State register
1490 PresentState
= BIT0
;
1493 PciIo
= Private
->PciIo
;
1494 Status
= SdMmcHcCheckMmioSet (
1497 SD_MMC_HC_PRESENT_STATE
,
1498 sizeof (PresentState
),
1507 Wait for the env to be ready for execute specified TRB.
1509 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
1510 @param[in] Trb The pointer to the SD_MMC_HC_TRB instance.
1512 @retval EFI_SUCCESS The env is ready for TRB execution.
1513 @retval EFI_TIMEOUT The env is not ready for TRB execution in time.
1514 @retval Others Some erros happen.
1519 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
1520 IN SD_MMC_HC_TRB
*Trb
1524 EFI_SD_MMC_PASS_THRU_COMMAND_PACKET
*Packet
;
1526 BOOLEAN InfiniteWait
;
1529 // Wait Command Complete Interrupt Status bit in Normal Interrupt Status Register
1531 Packet
= Trb
->Packet
;
1532 Timeout
= Packet
->Timeout
;
1534 InfiniteWait
= TRUE
;
1536 InfiniteWait
= FALSE
;
1539 while (InfiniteWait
|| (Timeout
> 0)) {
1541 // Check Trb execution result by reading Normal Interrupt Status register.
1543 Status
= SdMmcCheckTrbEnv (Private
, Trb
);
1544 if (Status
!= EFI_NOT_READY
) {
1548 // Stall for 1 microsecond.
1559 Execute the specified TRB.
1561 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
1562 @param[in] Trb The pointer to the SD_MMC_HC_TRB instance.
1564 @retval EFI_SUCCESS The TRB is sent to host controller successfully.
1565 @retval Others Some erros happen when sending this request to the host controller.
1570 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
1571 IN SD_MMC_HC_TRB
*Trb
1575 EFI_SD_MMC_PASS_THRU_COMMAND_PACKET
*Packet
;
1576 EFI_PCI_IO_PROTOCOL
*PciIo
;
1587 Packet
= Trb
->Packet
;
1588 PciIo
= Trb
->Private
->PciIo
;
1590 // Clear all bits in Error Interrupt Status Register
1593 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_ERR_INT_STS
, FALSE
, sizeof (IntStatus
), &IntStatus
);
1594 if (EFI_ERROR (Status
)) {
1598 // Clear all bits in Normal Interrupt Status Register excepts for Card Removal & Card Insertion bits.
1601 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_NOR_INT_STS
, FALSE
, sizeof (IntStatus
), &IntStatus
);
1602 if (EFI_ERROR (Status
)) {
1606 // Set Host Control 1 register DMA Select field
1608 if (Trb
->Mode
== SdMmcAdmaMode
) {
1610 Status
= SdMmcHcOrMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_HOST_CTRL1
, sizeof (HostCtrl1
), &HostCtrl1
);
1611 if (EFI_ERROR (Status
)) {
1616 SdMmcHcLedOnOff (PciIo
, Trb
->Slot
, TRUE
);
1618 if (Trb
->Mode
== SdMmcSdmaMode
) {
1619 if ((UINT64
)(UINTN
)Trb
->DataPhy
>= 0x100000000ul
) {
1620 return EFI_INVALID_PARAMETER
;
1623 SdmaAddr
= (UINT32
)(UINTN
)Trb
->DataPhy
;
1624 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_SDMA_ADDR
, FALSE
, sizeof (SdmaAddr
), &SdmaAddr
);
1625 if (EFI_ERROR (Status
)) {
1628 } else if (Trb
->Mode
== SdMmcAdmaMode
) {
1629 AdmaAddr
= (UINT64
)(UINTN
)Trb
->AdmaDescPhy
;
1630 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_ADMA_SYS_ADDR
, FALSE
, sizeof (AdmaAddr
), &AdmaAddr
);
1631 if (EFI_ERROR (Status
)) {
1636 BlkSize
= Trb
->BlockSize
;
1637 if (Trb
->Mode
== SdMmcSdmaMode
) {
1639 // Set SDMA boundary to be 512K bytes.
1644 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_BLK_SIZE
, FALSE
, sizeof (BlkSize
), &BlkSize
);
1645 if (EFI_ERROR (Status
)) {
1650 if (Trb
->Mode
!= SdMmcNoData
) {
1652 // Calcuate Block Count.
1654 BlkCount
= (UINT16
)(Trb
->DataLen
/ Trb
->BlockSize
);
1656 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_BLK_COUNT
, FALSE
, sizeof (BlkCount
), &BlkCount
);
1657 if (EFI_ERROR (Status
)) {
1661 Argument
= Packet
->SdMmcCmdBlk
->CommandArgument
;
1662 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_ARG1
, FALSE
, sizeof (Argument
), &Argument
);
1663 if (EFI_ERROR (Status
)) {
1668 if (Trb
->Mode
!= SdMmcNoData
) {
1669 if (Trb
->Mode
!= SdMmcPioMode
) {
1676 TransMode
|= BIT5
| BIT1
;
1679 // Only SD memory card needs to use AUTO CMD12 feature.
1681 if (Private
->Slot
[Trb
->Slot
].CardType
== SdCardType
) {
1688 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_TRANS_MOD
, FALSE
, sizeof (TransMode
), &TransMode
);
1689 if (EFI_ERROR (Status
)) {
1693 Cmd
= (UINT16
)LShiftU64(Packet
->SdMmcCmdBlk
->CommandIndex
, 8);
1694 if (Packet
->SdMmcCmdBlk
->CommandType
== SdMmcCommandTypeAdtc
) {
1698 // Convert ResponseType to value
1700 if (Packet
->SdMmcCmdBlk
->CommandType
!= SdMmcCommandTypeBc
) {
1701 switch (Packet
->SdMmcCmdBlk
->ResponseType
) {
1702 case SdMmcResponseTypeR1
:
1703 case SdMmcResponseTypeR5
:
1704 case SdMmcResponseTypeR6
:
1705 case SdMmcResponseTypeR7
:
1706 Cmd
|= (BIT1
| BIT3
| BIT4
);
1708 case SdMmcResponseTypeR2
:
1709 Cmd
|= (BIT0
| BIT3
);
1711 case SdMmcResponseTypeR3
:
1712 case SdMmcResponseTypeR4
:
1715 case SdMmcResponseTypeR1b
:
1716 case SdMmcResponseTypeR5b
:
1717 Cmd
|= (BIT0
| BIT1
| BIT3
| BIT4
);
1727 Status
= SdMmcHcRwMmio (PciIo
, Trb
->Slot
, SD_MMC_HC_COMMAND
, FALSE
, sizeof (Cmd
), &Cmd
);
1732 Check the TRB execution result.
1734 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
1735 @param[in] Trb The pointer to the SD_MMC_HC_TRB instance.
1737 @retval EFI_SUCCESS The TRB is executed successfully.
1738 @retval EFI_NOT_READY The TRB is not completed for execution.
1739 @retval Others Some erros happen when executing this request.
1743 SdMmcCheckTrbResult (
1744 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
1745 IN SD_MMC_HC_TRB
*Trb
1749 EFI_SD_MMC_PASS_THRU_COMMAND_PACKET
*Packet
;
1758 Packet
= Trb
->Packet
;
1760 // Check Trb execution result by reading Normal Interrupt Status register.
1762 Status
= SdMmcHcRwMmio (
1765 SD_MMC_HC_NOR_INT_STS
,
1770 if (EFI_ERROR (Status
)) {
1774 // Check Transfer Complete bit is set or not.
1776 if ((IntStatus
& BIT1
) == BIT1
) {
1777 if ((IntStatus
& BIT15
) == BIT15
) {
1779 // Read Error Interrupt Status register to check if the error is
1780 // Data Timeout Error.
1781 // If yes, treat it as success as Transfer Complete has higher
1782 // priority than Data Timeout Error.
1784 Status
= SdMmcHcRwMmio (
1787 SD_MMC_HC_ERR_INT_STS
,
1792 if (!EFI_ERROR (Status
)) {
1793 if ((IntStatus
& BIT4
) == BIT4
) {
1794 Status
= EFI_SUCCESS
;
1796 Status
= EFI_DEVICE_ERROR
;
1804 // Check if there is a error happened during cmd execution.
1805 // If yes, then do error recovery procedure to follow SD Host Controller
1806 // Simplified Spec 3.0 section 3.10.1.
1808 if ((IntStatus
& BIT15
) == BIT15
) {
1809 Status
= SdMmcHcRwMmio (
1812 SD_MMC_HC_ERR_INT_STS
,
1817 if (EFI_ERROR (Status
)) {
1820 if ((IntStatus
& 0x0F) != 0) {
1823 if ((IntStatus
& 0xF0) != 0) {
1827 Status
= SdMmcHcRwMmio (
1835 if (EFI_ERROR (Status
)) {
1838 Status
= SdMmcHcWaitMmioSet (
1845 SD_MMC_HC_GENERIC_TIMEOUT
1847 if (EFI_ERROR (Status
)) {
1851 Status
= EFI_DEVICE_ERROR
;
1855 // Check if DMA interrupt is signalled for the SDMA transfer.
1857 if ((Trb
->Mode
== SdMmcSdmaMode
) && ((IntStatus
& BIT3
) == BIT3
)) {
1859 // Clear DMA interrupt bit.
1862 Status
= SdMmcHcRwMmio (
1865 SD_MMC_HC_NOR_INT_STS
,
1870 if (EFI_ERROR (Status
)) {
1874 // Update SDMA Address register.
1876 SdmaAddr
= SD_MMC_SDMA_ROUND_UP ((UINT32
)(UINTN
)Trb
->DataPhy
, SD_MMC_SDMA_BOUNDARY
);
1877 Status
= SdMmcHcRwMmio (
1880 SD_MMC_HC_SDMA_ADDR
,
1885 if (EFI_ERROR (Status
)) {
1888 Trb
->DataPhy
= (UINT32
)(UINTN
)SdmaAddr
;
1891 if ((Packet
->SdMmcCmdBlk
->CommandType
!= SdMmcCommandTypeAdtc
) &&
1892 (Packet
->SdMmcCmdBlk
->ResponseType
!= SdMmcResponseTypeR1b
) &&
1893 (Packet
->SdMmcCmdBlk
->ResponseType
!= SdMmcResponseTypeR5b
)) {
1894 if ((IntStatus
& BIT0
) == BIT0
) {
1895 Status
= EFI_SUCCESS
;
1900 if (((Private
->Slot
[Trb
->Slot
].CardType
== EmmcCardType
) &&
1901 (Packet
->SdMmcCmdBlk
->CommandIndex
== EMMC_SEND_TUNING_BLOCK
)) ||
1902 ((Private
->Slot
[Trb
->Slot
].CardType
== SdCardType
) &&
1903 (Packet
->SdMmcCmdBlk
->CommandIndex
== SD_SEND_TUNING_BLOCK
))) {
1905 // When performing tuning procedure (Execute Tuning is set to 1) through PIO mode,
1906 // wait Buffer Read Ready bit of Normal Interrupt Status Register to be 1.
1907 // Refer to SD Host Controller Simplified Specification 3.0 figure 2-29 for details.
1909 if ((IntStatus
& BIT5
) == BIT5
) {
1911 // Clear Buffer Read Ready interrupt at first.
1914 SdMmcHcRwMmio (Private
->PciIo
, Trb
->Slot
, SD_MMC_HC_NOR_INT_STS
, FALSE
, sizeof (IntStatus
), &IntStatus
);
1916 // Read data out from Buffer Port register
1918 for (PioLength
= 0; PioLength
< Trb
->DataLen
; PioLength
+= 4) {
1919 SdMmcHcRwMmio (Private
->PciIo
, Trb
->Slot
, SD_MMC_HC_BUF_DAT_PORT
, TRUE
, 4, (UINT8
*)Trb
->Data
+ PioLength
);
1921 Status
= EFI_SUCCESS
;
1926 Status
= EFI_NOT_READY
;
1929 // Get response data when the cmd is executed successfully.
1931 if (!EFI_ERROR (Status
)) {
1932 if (Packet
->SdMmcCmdBlk
->CommandType
!= SdMmcCommandTypeBc
) {
1933 for (Index
= 0; Index
< 4; Index
++) {
1934 Status
= SdMmcHcRwMmio (
1937 SD_MMC_HC_RESPONSE
+ Index
* 4,
1942 if (EFI_ERROR (Status
)) {
1943 SdMmcHcLedOnOff (Private
->PciIo
, Trb
->Slot
, FALSE
);
1947 CopyMem (Packet
->SdMmcStatusBlk
, Response
, sizeof (Response
));
1951 if (Status
!= EFI_NOT_READY
) {
1952 SdMmcHcLedOnOff (Private
->PciIo
, Trb
->Slot
, FALSE
);
1959 Wait for the TRB execution result.
1961 @param[in] Private A pointer to the SD_MMC_HC_PRIVATE_DATA instance.
1962 @param[in] Trb The pointer to the SD_MMC_HC_TRB instance.
1964 @retval EFI_SUCCESS The TRB is executed successfully.
1965 @retval Others Some erros happen when executing this request.
1969 SdMmcWaitTrbResult (
1970 IN SD_MMC_HC_PRIVATE_DATA
*Private
,
1971 IN SD_MMC_HC_TRB
*Trb
1975 EFI_SD_MMC_PASS_THRU_COMMAND_PACKET
*Packet
;
1977 BOOLEAN InfiniteWait
;
1979 Packet
= Trb
->Packet
;
1981 // Wait Command Complete Interrupt Status bit in Normal Interrupt Status Register
1983 Timeout
= Packet
->Timeout
;
1985 InfiniteWait
= TRUE
;
1987 InfiniteWait
= FALSE
;
1990 while (InfiniteWait
|| (Timeout
> 0)) {
1992 // Check Trb execution result by reading Normal Interrupt Status register.
1994 Status
= SdMmcCheckTrbResult (Private
, Trb
);
1995 if (Status
!= EFI_NOT_READY
) {
1999 // Stall for 1 microsecond.