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

📄 disk.c

📁 freescale i.mx31 BSP CE5.0全部源码
💻 C
字号:
//
// Copyright (c) Microsoft Corporation.  All rights reserved.
//
//
// Use of this source code is subject to the terms of the Microsoft end-user
// license agreement (EULA) under which you licensed this SOFTWARE PRODUCT.
// If you did not accept the terms of the EULA, you are not authorized to use
// this source code. For a copy of the EULA, please see the LICENSE.RTF on your
// install media.
//
/*++
THIS CODE AND INFORMATION IS PROVIDED "AS IS" WITHOUT WARRANTY OF
ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING BUT NOT LIMITED TO
THE IMPLIED WARRANTIES OF MERCHANTABILITY AND/OR FITNESS FOR A
PARTICULAR PURPOSE.
Copyright (c) 1995, 1996, 1997, 1998  Microsoft Corporation
--*/

#include <bsp.h>
#include "pmc_loader.h"
#include "mx31_ata.h"
#include "ata_timing_spec.h"

#define TRACE_DEBUG	1

/*++

Routine Description:

Initializes an ATA device.

Arguments:

CommandBase - ATA command registers base address.

Return Value:

Returns the the device index for the initialized ATA device if successful.
This index is used by the FATFile routines to specifiy which ATA device to
access.  If unsuccessful, 0xFFFFFFFF is returned.

--*/

#define ATASTRIDE(r)                ((r) * LdrAtaDisk.dwATAStride)

// Disk Drive Register Offsets
#define ATA_CMD_REGS_OFFSET			0xA0
#define ATA_REG_DATA				0
#define ATA_REG_ERROR				1
#define ATA_REG_FEATURE				1
#define ATA_REG_SECT_CNT			2
#define ATA_REG_SECT_NUM			3
#define ATA_REG_DRV_HEAD			6			
#define ATA_REG_COMMAND				7
#define ATA_REG_STATUS				7
#define ATA_CNTRL_REGS_OFFSET		0xD8


// MX31 Registers
PCSP_PBC_REGS g_pPBC;
PCSP_CCM_REGS g_pCCM;
PCSP_IOMUX_REGS g_pIOMUX;
PCSP_ATA_REG g_pVAtaReg; // ATA regs



void ATAPadConfiguration()
{
	
	//CPLD registers
	g_pPBC = (PCSP_PBC_REGS)OALPAtoVA((UINT32)BSP_BASE_REG_PA_PBC_BASE, FALSE);
	// IOMUX registers
	g_pIOMUX = (PCSP_IOMUX_REGS) OALPAtoUA(CSP_BASE_REG_PA_IOMUXC);
	
	
	//Clear ATA_EN and ATA_SEL in CPLD regs
	
	#if 0
		OUTREG16(&g_pPBC->BCTRL2_CLEAR, CSP_BITFMASK(PBC_BCTRL2_ATA_EN));
		OUTREG16(&g_pPBC->BCTRL2_CLEAR, CSP_BITFMASK(PBC_BCTRL2_ATA_SEL));
		OUTREG16(&g_pPBC->BCTRL3_SET, 0x10);
		
		INSREG32(&g_pIOMUX->GPR, 0x040007f8, 0x00000488);
	#else
		OUTREG16(&g_pPBC->BCTRL2_CLEAR, CSP_BITFMASK(PBC_BCTRL2_ATA_EN));
		OUTREG16(&g_pPBC->BCTRL2_SET, CSP_BITFMASK(PBC_BCTRL2_ATA_SEL));
		
		INSREG32(&g_pIOMUX->GPR, 0x040007f8, 0x00000318);
	#endif
	
	// ATA IOMUX settings
	OAL_IOMUX_SET_MUX(g_pIOMUX, DDK_IOMUX_PIN_ATA_CS0, DDK_IOMUX_OUT_FUNC, DDK_IOMUX_IN_FUNC);
	OAL_IOMUX_SET_MUX(g_pIOMUX, DDK_IOMUX_PIN_ATA_CS1, DDK_IOMUX_OUT_FUNC, DDK_IOMUX_IN_FUNC);
	OAL_IOMUX_SET_MUX(g_pIOMUX, DDK_IOMUX_PIN_ATA_DIOR, DDK_IOMUX_OUT_FUNC, DDK_IOMUX_IN_FUNC);
	OAL_IOMUX_SET_MUX(g_pIOMUX, DDK_IOMUX_PIN_ATA_DIOW, DDK_IOMUX_OUT_FUNC, DDK_IOMUX_IN_FUNC);
	OAL_IOMUX_SET_MUX(g_pIOMUX, DDK_IOMUX_PIN_ATA_DMACK, DDK_IOMUX_OUT_FUNC, DDK_IOMUX_IN_FUNC);
	OAL_IOMUX_SET_MUX(g_pIOMUX, DDK_IOMUX_PIN_ATA_RESET_B, DDK_IOMUX_OUT_FUNC, DDK_IOMUX_IN_FUNC);	
	
}

void ATASetPIOModeTimings()
{
	int speed = 0;
	int ClkSpd = 10;
	
	g_pVAtaReg = (PCSP_ATA_REG)OALPAtoVA(CSP_BASE_REG_PA_ATA_CTRL, FALSE);
#if 0
    INSREG32(&g_pVAtaReg->ATA_TIME_CONFIG0, 0x0000ffff, 0x00000303);
	INSREG32(&g_pVAtaReg->ATA_TIME_CONFIG0, 0xffff0000,
			(((t1_spec[speed] + ClkSpd) / ClkSpd) << 16) |
			(((t2_8spec[speed] + ClkSpd) / ClkSpd) << 24)) ;
	INSREG32(&g_pVAtaReg->ATA_TIME_CONFIG1, 0xffffffff,
			(((t2_8spec[speed] + ClkSpd) / ClkSpd) ) |
			((((tA_spec[speed] + ClkSpd) / ClkSpd) + 2) << 8) |
			(1 << 16) |
			(((t4_spec[speed] + ClkSpd) / ClkSpd) << 24)) ;
	INSREG32(&g_pVAtaReg->ATA_TIME_CONFIG2, 0xff, (((t9_spec[speed] + ClkSpd) / ClkSpd)));
#else
				INSREG32(&g_pVAtaReg->ATA_TIME_CONFIG0, 0xffff0000,
				(((t1_spec[speed] + ClkSpd) / ClkSpd) << 16) |
				(((t2_8spec[speed] + ClkSpd) / ClkSpd) << 24)) ;
			INSREG32(&g_pVAtaReg->ATA_TIME_CONFIG1, 0xffffffff,
				(((t2_8spec[speed] + ClkSpd) / ClkSpd) ) |
				((((tA_spec[speed] + ClkSpd) / ClkSpd) + 2) << 8) |
				(1 << 16) |
				(((t4_spec[speed] + ClkSpd) / ClkSpd) << 24)) ;
			INSREG32(&g_pVAtaReg->ATA_TIME_CONFIG2, 0xff, (((t9_spec[speed] + ClkSpd) / ClkSpd)));
#endif
}

ULONG
ATAInitializeDevice(void)
{
	
	ULONG* pAtaControl = (ULONG*)OALPAtoVA(CSP_BASE_REG_PA_ATA_CTRL + 0x24, FALSE);
	
	
	// Clock Enable
	g_pCCM = (PCSP_CCM_REGS) OALPAtoUA(CSP_BASE_REG_PA_CCM);
	// Enable clock to ATA -- bits 12-13 of CGR0
	// Read in current value, "or" it with bits 12-13, write the value back to the register
	OUTREG32( &g_pCCM->CGR[0], ((INREG32(&g_pCCM->CGR[0]) | 0x00003000)) );	

	// Configure CPLD and IOMux for ATA
	ATAPadConfiguration();

    // Configure ATA timings for PIO Mode
    ATASetPIOModeTimings();
	
    // Reset the drive
    *pAtaControl = 0x00;
    // Wait long enough for the drive to reset and for power to stabilize (platform-specific)
    msWait(10);

    // Take out of reset
    *pAtaControl = 0xDC;
    msWait(10);
    
    // Initialize Disk Struct
    LdrAtaDisk.CmdBase = (ULONG)OALPAtoVA(CSP_BASE_REG_PA_ATA_CTRL + ATA_CMD_REGS_OFFSET, FALSE);
    LdrAtaDisk.dwATAStride = 4;
    LdrAtaDisk.CtlBase = (ULONG)(OALPAtoVA(CSP_BASE_REG_PA_ATA_CTRL + ATA_CNTRL_REGS_OFFSET, FALSE));
    LdrAtaDisk.DriveNumberMask = 0xE0;  //ATA_HEAD_DRIVE_0 | ATA_HEAD_LBA_MODE

    if( TRACE_DEBUG )  EdbgOutputDebugString("EBOOT:ATAInitDev: CmdBase:0x%x  CtlBase:0x%x\r\n", LdrAtaDisk.CmdBase, LdrAtaDisk.CtlBase);

    //
    // Set Drive Number Mask of the ATA device that will be used.
    //

    *(PUCHAR)(LdrAtaDisk.CmdBase + ATA_REG_DRV_HEAD * LdrAtaDisk.dwATAStride) = LdrAtaDisk.DriveNumberMask;
	if( TRACE_DEBUG )  EdbgOutputDebugString("EBOOT:ATAInitDev: Wrote the Drive Number Mask at 0x%x.\r\n",(LdrAtaDisk.CmdBase + ATA_REG_DRV_HEAD * LdrAtaDisk.dwATAStride));

    msWait(50);

	if( TRACE_DEBUG )  EdbgOutputDebugString("EBOOT:ATAInitDev: Waited 50 ms. Waiting for 0xFF on Disk status.\r\n");

	// Check disk status
	if( LDRATAWaitForDisk(0xFF) >= 0x80000000 )
	    return ERROR_GEN_FAILURE;
		
	else
	{
		if( TRACE_DEBUG )  EdbgOutputDebugString("EBOOT:ATAInitDev: LDRATAWaitForDisk passed. Doing InitCtrlr.\r\n");
    
		// Test I/F
		if(!LDRATAInitController())
		{
			EdbgOutputDebugString("\r\nERROR: ATA, Initializing controller!\r\n\r\n");
	        return ERROR_GEN_FAILURE;
		}
	}

	if( TRACE_DEBUG )  EdbgOutputDebugString("ATA, Initialized controller successfully.\r\n");
	return ERROR_SUCCESS;
}

⌨️ 快捷键说明

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