⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 sdslot.cpp

📁 6410BSP3
💻 CPP
📖 第 1 页 / 共 3 页
字号:
// Input: pExternalHCContext - Host controller context that was previously registered
//        SlotNumber - Slot Number
//        Event      - new event
// Output:
// Return: SD_API_STATUS 
// Notes:       
//      A host controller driver calls this api when the slot changes state (i.e.
//      device insertion/deletion).
///////////////////////////////////////////////////////////////////////////////
VOID CSDSlot::SlotStateChange(SD_SLOT_EVENT Event)
{
    switch (Event) {
      case DeviceInterrupting: // We should do interrupt callback at SDHC IST.
      case DeviceInserted:
      case DeviceEjected:
      case SlotDeselectRequest:
      case SlotSelectRequest:
      case SlotResetRequest:
        // post this message to the work item for each slot
        PostEvent(Event);
        break;
      case BusRequestComplete:
        ASSERT(FALSE);
        break;
      default:
        DEBUGCHK(FALSE);
    }
}
///////////////////////////////////////////////////////////////////////////////
//  DelayForPowerUp - Delay for powerup 
//  Input:  pSlot - slot to delay on
//       
//  Output: 
//  Notes:  
//     
///////////////////////////////////////////////////////////////////////////////
VOID CSDSlot::DelayForPowerUp()
{
    // delay for power up
    if (PowerUpDelay != 0) {
        Sleep(PowerUpDelay);
    } else {
        // powerup delay should be set
        DEBUG_CHECK(FALSE, (TEXT("SDBusDriver: Slot Delay is 0!!!\n")));
        Sleep(500);
    }
}
///////////////////////////////////////////////////////////////////////////////
//  SDSetCardInterfaceForSlot - set Card interface for the slot
//  Input:  pSlot - the slot to set the card interface for
//          pSetting - card interface settings
//  Output:
//  Return: SD_API_STATUS
//  Notes:  
//         this function calls the slot option handler in the host controller
//         driver
//         
///////////////////////////////////////////////////////////////////////////////
SD_API_STATUS CSDSlot::SDSetCardInterfaceForSlot(PSD_CARD_INTERFACE_EX pSetting)
{
    SD_API_STATUS   status;             // intermediate status
    DWORD           origClockSetting;   // original clock setting upon entry

    origClockSetting = pSetting->ClockRate;

    status = m_SdHost.SlotSetupInterface(m_dwSlotIndex,pSetting);

    if (SD_API_SUCCESS(status)) {
        if (origClockSetting != pSetting->ClockRate){
            DEBUGMSG(SDCARD_ZONE_WARN, (TEXT("SDSetCardInterfaceForSlot - HC ClockRate differs desired setting: desired: %d Hz, Actual : %d Hz \n"),
                origClockSetting, pSetting->ClockRate));
         }

    }
    return status;
}
///////////////////////////////////////////////////////////////////////////////
//  SDGetOperationalVoltageRange - Get the operation voltage range
//  Input:  OcrValue - OCR bit mask to determine the voltage range
//          pSlot - the slot
//          
//  Output:
//  Return: DWORD bit mask for optimal operational voltage
//  Notes:  
//         This function compares the OcrValue against the desired
//         voltage range of the slot and the capabilities of the slot
//         the operational value (also encoded as an OCR value) is returned
//         A value of zero indicates no usable voltage range.
///////////////////////////////////////////////////////////////////////////////
DWORD CSDSlot::SDGetOperationalVoltageRange(DWORD OcrValue)
{
    ULONG i;            // loop variable 

    // check to see if the voltages can be supported
    if (OcrValue & VoltageWindowMask) {
        // check to see if the voltage meets the desired voltage range
        if (OcrValue & DesiredVoltageMask) {
            DEBUGMSG(SDBUS_ZONE_DEVICE, (TEXT("SDBusDriver: Device Power Range:0x%08X matches HC desired power: 0x%08X \n"), 
                OcrValue, DesiredVoltageMask)); 
            // returned desired voltage range suggested by host controller 
            return DesiredVoltageMask;
        } else {
            // walk through the voltage mask starting at the low end looking for
            // a voltage that will work with the OCR value
            for (i = 0; i < 32; i++) {
                if (OcrValue & VoltageWindowMask & (1 << i)) {
                    DEBUGMSG(SDBUS_ZONE_DEVICE, (TEXT("SDBusDriver: Device Power Range:0x%08X does not match HC desired power 0x%08X \n"),
                        OcrValue, DesiredVoltageMask));
                    DEBUGMSG(SDBUS_ZONE_DEVICE, (TEXT("Using negotiated power range: 0x%08X \n"), 
                        (1 << i))); 
                    // found a match
                    return (1 << i);
                }
            }
            // this should never happen, 
            DEBUGCHK(FALSE);
            return 0;
        }

    } else {
        return 0;
    }
}
///////////////////////////////////////////////////////////////////////////////
//  SlotCardSelectDeselect - Select/Deselect the card in teh slot
//  Input:  SlotIndexWanted - index of slot
//          Event           - SlotDeselectRequest/SlotSelectRequest/SlotResetRequest
//  Output: 
//  Notes:  
///////////////////////////////////////////////////////////////////////////////
BOOL CSDSlot::SlotCardSelectDeselect(SD_SLOT_EVENT Event) 
{
    SD_API_STATUS           status;             // intermediate SD status
    BOOL                    retStatus = FALSE;  // return status
    SD_SET_FEATURE_TYPE     CardFeature;        // card feature code

        // check for a ready device in the slot
    if (m_SlotState == Ready) {        
        CSDDevice *pDevice0 = GetFunctionDevice(0);
        if (NULL != pDevice0) { 

            switch ( Event ) {
              case SlotDeselectRequest:
                CardFeature = SD_CARD_DESELECT_REQUEST;
                break;
              case SlotSelectRequest:
                CardFeature = SD_CARD_SELECT_REQUEST;
                break;
              case SlotResetRequest:
                CardFeature = SD_CARD_FORCE_RESET;
                break;
              default:
                DEBUG_CHECK(FALSE, (TEXT("SDBusDriver: Unknown Slot Event : %d \n"),Event));
                return FALSE;
            }

            // Call API to request the card to be deselected
            status = pDevice0->SDSetCardFeature_I(CardFeature,NULL,0);
            pDevice0->DeRef();

            retStatus  = TRUE;

            if(!SD_API_SUCCESS(status)) {
                DbgPrintZo(SDCARD_ZONE_ERROR,(TEXT("SDBusDriver: Failed to request the card to be deselected\r\n")));
                retStatus = FALSE;
            }
        }
        else {
            retStatus = FALSE;
            DbgPrintZo(SDCARD_ZONE_INIT, (TEXT("Driver not loaded")));
        }
    }
    else {
        retStatus = FALSE;
        DbgPrintZo(SDCARD_ZONE_INIT, (TEXT("Empty Slot")));
    }

    return retStatus;
}

///////////////////////////////////////////////////////////////////////////////
//  SelectSlotInterface - select slot interface based on default interface 
//                        information of all devices.
//  Input:  pSlot - the slot
//          
//  Output: 
//  Return: SD_API_STATUS code
//  Notes:  This function sets the slot's default interface in the slot structure,
//          the result interface will fit for all functions of the card.
///////////////////////////////////////////////////////////////////////////////
SD_API_STATUS CSDSlot::SelectSlotInterface()
{
  // Try slot interface at full speed and 4 bit mode (highest bus mode except High Speed)
  memset(&m_SlotInterfaceEx,0, sizeof(m_SlotInterfaceEx));
  m_SlotInterfaceEx.InterfaceModeEx.bit.sd4Bit = 1;
#ifdef _MMC_SPEC_42_
  /**
   * Description : HSMMC slot supports up to 52MHz
   */
  m_SlotInterfaceEx.ClockRate = HSMMC_FULL_SPEED_RATE;
#else
  m_SlotInterfaceEx.ClockRate = SD_FULL_SPEED_RATE;
#endif


  m_SlotLock.Lock();
  for (DWORD dwIndex=0; dwIndex<SD_MAXIMUM_DEVICE_PER_SLOT; dwIndex ++) {
    CSDDevice * psdDevice = m_pFuncDevice[dwIndex];
    // for each device set it's card interface
    if (psdDevice) {
#ifdef _MMC_SPEC_42_
      /**
       * Description : HSMMC Slot supports up to 52MHz
       */
      m_SlotInterfaceEx.InterfaceModeEx.bit.hsmmc8Bit = psdDevice->GetCardInterface().InterfaceModeEx.bit.hsmmc8Bit;

#endif                
      m_SlotInterfaceEx.InterfaceModeEx.bit.sd4Bit = psdDevice->GetCardInterface().InterfaceModeEx.bit.sd4Bit;
      m_SlotInterfaceEx.InterfaceModeEx.bit.sdWriteProtected = psdDevice->GetCardInterface().InterfaceModeEx.bit.sdWriteProtected;
      if ( psdDevice->GetCardInterface().ClockRate < m_SlotInterfaceEx.ClockRate ) {
        m_SlotInterfaceEx.ClockRate = psdDevice->GetCardInterface().ClockRate;
      }
    }
  }
  m_SlotLock.Unlock();
  return SD_API_STATUS_SUCCESS;
}

BOOL CSDSlot::SDSlotEnableSDIOInterrupts() 
{
    BOOL fRet = FALSE;
    m_SlotLock.Lock();
    if (!IsSlotInterruptOn()) {
        SD_API_STATUS status = m_SdHost.SlotOptionHandler(m_dwSlotIndex,SDHCDEnableSDIOInterrupts, NULL, 0);
        if (SD_API_SUCCESS(status)) {
            m_Flags|=SD_SLOT_FLAG_SDIO_INTERRUPTS_ENABLED;
            fRet = TRUE;
        };
    }
    m_SlotLock.Unlock();
    return fRet;
}

BOOL CSDSlot::SDSlotDisableSDIOInterrupts()
{
    BOOL fRet = FALSE;
    m_SlotLock.Lock();
    if (IsSlotInterruptOn()) {
        SD_API_STATUS status = m_SdHost.SlotOptionHandler(m_dwSlotIndex,SDHCDDisableSDIOInterrupts, NULL, 0);
        if (SD_API_SUCCESS(status)) {
            m_Flags&=~SD_SLOT_FLAG_SDIO_INTERRUPTS_ENABLED;
            fRet = TRUE;
        };
    }
    m_SlotLock.Unlock();
    return fRet;
}
BOOL CSDSlot::HandleSlotSelectDeselect(SD_SLOT_EVENT SlotEvent)
{
    SD_API_STATUS          status = SD_API_STATUS_SUCCESS;
    SD_CARD_INTERFACE_EX   CurrentSlotInterface;


    DbgPrintZo(SDBUS_ZONE_DEVICE, (TEXT("CSDSlot: HandleSlotSelectDeselect++: %d \n"),SlotEvent));            
    // Deselect the card
    if ((SlotEvent == SlotResetRequest) || (SlotEvent == SlotDeselectRequest)) {
        DbgPrintZo(SDBUS_ZONE_DEVICE, (TEXT("CSDSlot: Deselect the card\n")));
        // Update RCA for all devices, start from parent device
        for (DWORD dwIndex=0; dwIndex <= SD_MAXIMUM_DEVICE_PER_SLOT && SD_API_SUCCESS(status); dwIndex++) {
            CSDDevice * pCurrentDevice = GetFunctionDevice(dwIndex);
            if (pCurrentDevice != NULL) {
                status = pCurrentDevice->HandleDeviceSelectDeselect(SlotEvent, FALSE);  
                if (SD_API_SUCCESS(status)) {
                    pCurrentDevice->NotifyClient(SDCardDeselected);
                }
                pCurrentDevice->DeRef();
            }
        }
        if (SD_API_SUCCESS(status)) {
            m_SlotState = SlotDeselected; // Mark the slot as SlotDeselected to prevent further requests
            m_AllocatedPower = 0;
        }
        else {
            DbgPrintZo(SDCARD_ZONE_ERROR, (TEXT("CSDSlot: Failed to deselect card status =%x\n"),status));  
        }
    }


    // Select the card
    if (SD_API_SUCCESS(status) &&
            ((SlotEvent == SlotResetRequest) || (SlotEvent == SlotSelectRequest))) {
        DbgPrintZo(SDBUS_ZONE_DEVICE, (TEXT("SDBusDriver: Select the card\n")));  

        // Save the current slot interface
        CurrentSlotInterface.InterfaceModeEx = m_SlotInterfaceEx.InterfaceModeEx;
        CurrentSlotInterface.ClockRate = m_SlotInterfaceEx.ClockRate;

        // set the slot for 1 bit mode
        m_SlotInterfaceEx.InterfaceModeEx.bit.sd4Bit = 0 ;
        m_SlotInterfaceEx.ClockRate = SD_DEFAULT_CARD_ID_CLOCK_RATE;

        // set the card interface for the slot
        status = SDSetCardInterfaceForSlot(&m_SlotInterfaceEx);
        // Mark slot status as SlotReseting, only this thread can send bus request.
        m_SlotState = SlotResetting;

        for (DWORD dwIndex=0; dwIndex <= SD_MAXIMUM_DEVICE_PER_SLOT && SD_API_SUCCESS(status); dwIndex++) {
            CSDDevice * pCurrentDevice = GetFunctionDevice(dwIndex);
            if (pCurrentDevice != NULL) {
                status = pCurrentDevice->HandleDeviceSelectDeselect(SlotEvent, TRUE);  
                pCurrentDevice->DeRef();
            }
        }
        if (SD_API_SUCCESS(status)) {
            // Set Slot state as ready
            m_SlotState = Ready;
            m_SlotInterfaceEx.InterfaceModeEx = CurrentSlotInterface.InterfaceModeEx;
            m_SlotInterfaceEx.ClockRate = CurrentSlotInterface.ClockRate;
            for (DWORD dwIndex=0; dwIndex <SD_MAXIMUM_DEVICE_PER_SLOT  && SD_API_SUCCESS(status); dwIndex++) {
                CSDDevice * pDevice = GetFunctionDevice(dwIndex);
                if (pDevice) {
                    status  =  pDevice->SetCardInterface(&CurrentSlotInterface);                    
                    pDevice->DeRef();
                }
                
            }
            status = SDSetCardInterfaceForSlot(&m_SlotInterfaceEx);
                
            for (DWORD dwIndex = 0 ; dwIndex <SD_MAXIMUM_DEVICE_PER_SLOT && SD_API_SUCCESS(status) ; dwIndex++) {
                CSDDevice * pDevice = GetFunctionDevice(dwIndex);
                if (pDevice) {
                    pDevice->NotifyClient(SDCardSelected);
                    pDevice->DeRef();
                }
                
            }
        }
    }
    ASSERT(SD_API_SUCCESS(status));
    DbgPrintZo(SDBUS_ZONE_DEVICE, (TEXT("SDBusDriver: HandleSlotSelectDeselect--status =%X\n"),status));  
    return (SD_API_SUCCESS(status));
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -