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

📄 diskmain.cpp

📁 Ep93XX TionProV2 BSP
💻 CPP
📖 第 1 页 / 共 5 页
字号:
    if (pIOReq->pInBuf) {
        if (pIOReq->dwInBufSize != sizeof(DISK_INFO)) 
            return ERROR_INVALID_PARAMETER;
        pInfo = (DISK_INFO *)pIOReq->pInBuf;
    }

    if (pIOReq->pOutBuf) {
        if (pIOReq->dwOutBufSize!= sizeof(DISK_INFO)) 
            return ERROR_INVALID_PARAMETER;
        pInfo = (DISK_INFO *)pIOReq->pOutBuf;
    }
    
    if (!pInfo) {
        DEBUGMSG( ZONE_ERROR | ZONE_IOCTL, (TEXT("ATAPI:GetDiskInfo No valid input buffer or output buffer !!!\r\n")));
        return ERROR_INVALID_PARAMETER;
    }    
    if (IsRemoveableDevice()) {
     }
    if (IsAtapiDevice()) {
        // TODO:
//        AtapiGetDiskInfo();
    }    
    if (ERROR_SUCCESS == dwError) {    
        __try {
            memcpy( pInfo, &m_DiskInfo, sizeof(DISK_INFO));
            pInfo->di_flags |= DISK_INFO_FLAG_PAGEABLE;
            pInfo->di_flags &= ~DISK_INFO_FLAG_UNFORMATTED;
            if (pIOReq->pBytesReturned)
                *(pIOReq->pBytesReturned) = sizeof(DISK_INFO);
        } __except(EXCEPTION_EXECUTE_HANDLER) {
            dwError = ERROR_INVALID_PARAMETER;
        }    
    }    
    return dwError;
}
/*------------------------------------------------------------------------------------------*/

DWORD CDisk::SetDiskInfo(PIOREQ pIOReq)
{
   DWORD dwError = ERROR_SUCCESS;
   DISK_INFO *pInfo = (DISK_INFO *)pIOReq->pInBuf;
    if  ((pIOReq->pInBuf == NULL) ||
        (pIOReq->dwInBufSize != sizeof(DISK_INFO))) {
        return ERROR_INVALID_PARAMETER; 
    }
    memcpy( &m_DiskInfo, pInfo, sizeof(DISK_INFO));
    return dwError;
}

/*------------------------------------------------------------------------------------------*/
DWORD CDisk::GetDeviceInfo(PIOREQ pIOReq)
{
    PSTORAGEDEVICEINFO psdi = (PSTORAGEDEVICEINFO)pIOReq->pInBuf;
    HKEY hKey;
    if ((pIOReq->dwInBufSize== 0) ||
         (pIOReq->pInBuf== NULL))
    {
        return ERROR_INVALID_PARAMETER; 
    }
    
    if (pIOReq->pBytesReturned)
        *(pIOReq->pBytesReturned) = sizeof(STORAGEDEVICEINFO);

    psdi->dwDeviceClass = 0;
    psdi->dwDeviceType = 0;
    psdi->dwDeviceFlags = 0;
    wcscpy( psdi->szProfile, L"Default");
    if (ERROR_SUCCESS != RegOpenKeyEx( HKEY_LOCAL_MACHINE, m_szDeviceKey, 0, 0, &hKey)) {
        hKey = NULL;
    }   
    if (IsAtapiDevice() && IsCDRomDevice()) {
        psdi->dwDeviceClass = STORAGE_DEVICE_CLASS_MULTIMEDIA;
        psdi->dwDeviceType |= STORAGE_DEVICE_TYPE_REMOVABLE_MEDIA;
        psdi->dwDeviceType |= STORAGE_DEVICE_TYPE_ATAPI;
        psdi->dwDeviceType |= STORAGE_DEVICE_TYPE_PCIIDE;
        psdi->dwDeviceFlags |= STORAGE_DEVICE_FLAG_MEDIASENSE;
        psdi->dwDeviceFlags |= STORAGE_DEVICE_FLAG_READONLY;
        if (!hKey || !AtaGetRegistryString( hKey, REG_VALUE_CDPROFILE, (PTSTR *)&psdi->szProfile, sizeof(psdi->szProfile))) {
            wcscpy( psdi->szProfile, REG_VALUE_CDPROFILE);
        }
    } else {
        psdi->dwDeviceClass = STORAGE_DEVICE_CLASS_BLOCK;
        psdi->dwDeviceType |= STORAGE_DEVICE_TYPE_PCIIDE;
        psdi->dwDeviceType |= STORAGE_DEVICE_TYPE_ATA;
        psdi->dwDeviceFlags |= STORAGE_DEVICE_FLAG_READWRITE;
        if (!hKey || !AtaGetRegistryString( hKey, REG_VALUE_HDPROFILE, (PTSTR *)&psdi->szProfile, sizeof(psdi->szProfile))) {
            wcscpy( psdi->szProfile, REG_VALUE_HDPROFILE);
        }
    }
    return ERROR_SUCCESS;
}
/*------------------------------------------------------------------------------------------*/


DWORD  CDisk::GetDiskName(PIOREQ pIOReq)
{
    static PTCHAR szDefaultDiscDrive = TEXT("External Volume");
    PTCHAR szDiskName = NULL;
    DWORD dwSize;
    DEBUGMSG( ZONE_IOCTL, (TEXT("ATAPI:GeDisktName\r\n")));
    if  ((pIOReq->pBytesReturned == NULL) ||
         (pIOReq->dwOutBufSize == 0) ||
         (pIOReq->pOutBuf == NULL) )
    {
        return ERROR_INVALID_PARAMETER; 
    }
    *(pIOReq->pBytesReturned) = 0;
    if (m_szDiskName) 
    {
        if (wcslen( m_szDiskName)) 
        {    
            szDiskName = m_szDiskName;
        } 
        else 
        {
            return ERROR_NOT_SUPPORTED;
        }    
    } 
    else 
    {
        szDiskName = szDefaultDiscDrive;
    }    
    dwSize = (wcslen( szDiskName)+1) * sizeof(TCHAR);
    if (pIOReq->dwOutBufSize < dwSize) 
    {
        return ERROR_INSUFFICIENT_BUFFER;
    }    
    wcscpy( (PTCHAR) pIOReq->pOutBuf, szDiskName);
    *(pIOReq->pBytesReturned) = dwSize; 
    return ERROR_SUCCESS;
}   


/*------------------------------------------------------------------------------------------*/

DWORD CDisk::ReadWriteDisk(PIOREQ pIOReq, BOOL fRead)
{
    DWORD dwError = ERROR_SUCCESS;
    PBYTE pBuffer;
    PSG_REQ pSgReq = (PSG_REQ)pIOReq->pInBuf;
    DWORD dwStartSector, dwNumSectors, dwSectorsToTransfer, dwSectorsPerBlock, dwSgLeft, dwSgLen;
    DWORD dwMaxPerBlock = m_bSectorsPerBlock;

    PSG_BUF pSgBuf;

 
    BYTE bCmd = fRead ? m_bReadCommand : m_bWriteCommand;

    //* * * CAMSDB040504 - Changed the debug port. (START)
    //DEBUGMSG( ZONE_IOCTL, (TEXT("ATAPI:ReadWriteDisk Entered\r\n")));
    //DEBUGMSG( 1, (TEXT("ATAPI:ReadWriteDisk Entered\r\n")));
    //* * * CAMSDB040504 - Changed the debug port. (START)
    
    //* * * Manual BREAK (START) * * *
    //DebugBreak(); 
    //* * * Manual BREAK (END) * * *

    if ((pSgReq == NULL) ||
       (pIOReq->dwInBufSize < sizeof(SG_REQ))) 
    {
        return ERROR_INVALID_PARAMETER;
    } 
    if ((pSgReq->sr_num_sec == 0) || 
       (pSgReq->sr_num_sg == 0)) 
    {
        return  ERROR_INVALID_PARAMETER;
    }       
    
    //
    // Gets the status and calls Interrupt Done.
    //
    EnableInterrupt();

    
    dwSgLeft = pSgReq->sr_num_sg;           //  The number of SG segments 
    dwNumSectors = pSgReq->sr_num_sec;
    dwStartSector = pSgReq->sr_start;   // Get the Start Sector 
    pSgBuf = &(pSgReq->sr_sglist[0]);

	dwSgLen = pSgBuf->sb_len;

    pBuffer = (PBYTE)MapPtrToProcess((LPVOID)pSgBuf->sb_buf, GetCallerProcess());

/*
	if( fRead )
		RETAILMSG( 1, (TEXT("ATAPI: READ StartSector=%ld NumSectors=%ld NumSg=%ld\r\n"), 
			 dwStartSector, dwNumSectors, dwSgLeft));
	else
		RETAILMSG( 1, (TEXT("ATAPI: WRITE StartSector=%ld NumSectors=%ld NumSg=%ld\r\n"),
			 dwStartSector, dwNumSectors, dwSgLeft));

	RETAILMSG( 1, (TEXT("ATAPI:ReadWriteDisk SG len %d\r\n"), dwSgLen));
*/    

    m_wNextByte = 0xFFFF;

    DEBUGMSG( ZONE_IO, (TEXT("ATAPI:ReadWriteDisk StartSector=%ld NumSectors=%ld NumSg=%ld\r\n"), dwStartSector, dwNumSectors, dwSgLeft));
    
    while(dwNumSectors) 
    {
        if (dwNumSectors > dwMaxPerBlock)    
            dwSectorsToTransfer = dwMaxPerBlock;
        //  The Maximal Number of Sectors per Command is 256.
//      if (dwNumSectors > MAX_SECT_PER_COMMAND)    
//          dwSectorsToTransfer = MAX_SECT_PER_COMMAND;
        else    
            dwSectorsToTransfer = dwNumSectors;

        dwNumSectors -= dwSectorsToTransfer;

        if (!SendIOCommand(dwStartSector,dwSectorsToTransfer, bCmd)) 
        {

            HardResetAndForcePIOMode();

            //
            // Interrupt gets set during atapi reset.
            // Gets the status and calls Interrupt Done.
            //
            EnableInterrupt();
            if (!SendIOCommand(dwStartSector,dwSectorsToTransfer, bCmd)) 
            {
                dwError = fRead ? ERROR_READ_FAULT : ERROR_WRITE_FAULT;

				//RETAILMSG( 1, (TEXT("ATAPI:ReadWriteDisk SendCommand Failed\r\n")));
                break;
            }
        }

        dwStartSector += dwSectorsToTransfer;

        //  The read command expects an interrupt before data transfer.
        //  The write command, on the other side, expects an interrupt after

//        dwSectorsPerBlock = dwMaxPerBlock;

        while(dwSectorsToTransfer && (dwSgLeft > 0)) 
        {
	        dwSectorsPerBlock = MIN( dwMaxPerBlock, dwSectorsToTransfer );
/*            
            if (dwSectorsPerBlock > dwSectorsToTransfer)
            {
                dwSectorsPerBlock = dwSectorsToTransfer;
            }
*/
            dwSectorsToTransfer -= dwSectorsPerBlock;
            
            if (fRead && m_fInterruptSupported) 
            {       
                if (!WaitForInterrupt(DISK_IO_TIME_OUT) || (CheckIntrState() == ATA_INTR_ERROR)) 
                {  
                    DEBUGMSG( ZONE_IO, (TEXT("ATAPI:ReadWrite- WaitforInterrupt failed (DevId %x) \r\n"),m_dwDeviceId));

					RETAILMSG( 1, (TEXT("ATAPI:ReadWriteDisk SendCommand Failed 22222\r\n")));
                    dwError = ERROR_READ_FAULT;
                    break;
                } 
            }   
            if (!WaitForDRQ()) 
            {
                DEBUGMSG( ZONE_IO, (TEXT("ATAPI:ReadWrite- WaitforDRQ failed (DevId %x) \r\n"),m_dwDeviceId));
                dwError = ERROR_READ_FAULT;

				//RETAILMSG( 1, (TEXT("ATAPI:ReadWriteDisk SendCommand Failed 333333\r\n")));
                break;
            }

            DWORD dwBytesPerBlock = dwSectorsPerBlock * m_DiskInfo.di_bytes_per_sect;

            while ((dwBytesPerBlock>0) && (dwSgLeft >0))
            {
                DWORD dwReadThisTime = MIN(dwSgLen, dwBytesPerBlock); //(dwSgLen < dwBytesPerBlock) ? dwSgLen : dwBytesPerBlock;

				//RETAILMSG( 1, (TEXT("ATAPI:get %d (len %d--%d)\r\n"), dwReadThisTime,dwSgLen,dwBytesPerBlock));

                dwSgLen -= dwReadThisTime;
                dwBytesPerBlock -= dwReadThisTime;

                fRead ?   ReadBuffer(pBuffer,dwReadThisTime) 
						: WriteBuffer(pBuffer,dwReadThisTime);
                    
                pBuffer += dwReadThisTime; //


                // Go to the next scatter/gather if no more space left

                if ((dwSgLen == 0) && ( --dwSgLeft > 0)) {

                    pSgBuf++;
                    pBuffer = (PBYTE)MapPtrToProcess((LPVOID)pSgBuf->sb_buf, GetCallerProcess());
                    dwSgLen = pSgBuf->sb_len;

					//RETAILMSG( 1, (TEXT("ATAPI:ReadWriteDisk SG len %d\r\n"), dwSgLen));
                }
            }   

            if (fRead) {

                while (dwBytesPerBlock > 0)  {

                    (void) ReadWord();
                    dwBytesPerBlock-=2 ;            
                }
            }
                
        }

        if (ERROR_SUCCESS != dwError)
            break;

        //  In case of write command an interrupt is generated upon each block.
        //  We can either wait for the interrupt or simply ignore it.
        //  However this is danger because an interrupt is pending and blocks all
        //  other interrupts on the same or lower level.

        if ( !fRead && m_fInterruptSupported) {     
            if (!WaitForInterrupt(DISK_IO_TIME_OUT) || (CheckIntrState() == ATA_INTR_ERROR)) {  
                DEBUGMSG( ZONE_IO, (TEXT("ATAPI:ReadWrite- WaitforInterrupt failed (DevId %x) \r\n"),m_dwDeviceId));

				//RETAILMSG( 1, (TEXT("ATAPI:ReadWriteDisk SendCommand Failed 44444\r\n")));
                dwError = ERROR_WRITE_FAULT;
                break;
            } 
        }            
    }
    
    // if (ERROR_SUCCESS != dwError) 
    // {
        //
        // TODO TODO TODO - Reset Device and setup the dma again.
        //
        // ResetController();
        


        //if (!(m_Id.Capabilities & 0x0200) && m_fLBAMode) 
        //{
        //    m_fLBAMode = FALSE;
        //    dwError = ReadWriteDisk(pIOReq, fRead);
        //} 
        //else 
        //{
        //}   
    // }    

    pSgReq->sr_status = dwError;
    return dwError;

}

/*------------------------------------------------------------------------------------------*/

DWORD CDisk::ReadWriteDiskDMA(PIOREQ pIOReq, BOOL fRead)
{
    DWORD   dwError = ERROR_SUCCESS;
    PSG_REQ pSgReq = (PSG_REQ)pIOReq->pInBuf;
    DWORD   dwSectorsToTransfer;
    SG_BUF  CurBuffer[MAX_SG_BUF];
    BYTE    bCmd;
    BOOL    bRetryUsingPIO = FALSE;
    ULONG   ulWaitReturn;
    BOOL    bRet;
    

    DEBUGMSG( ZONE_DMA, (TEXT("+CDisk::ReadWriteDiskDMA\r\n")));

    if ((pSgReq == NULL) || (pIOReq->dwInBufSize < sizeof(SG_REQ))) 
    {
        return ERROR_INVALID_PARAMETER;
    }   
    if ((pSgReq->sr_num_sec == 0) || 
       (pSgReq->sr_num_sg == 0)) 
    {
        return ERROR_INVALID_PARAMETER;
    }       

    DEBUGMSG
    ( 

⌨️ 快捷键说明

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