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

📄 ohcdpdd.c

📁 Intel PXA270 Wince5.0 BSP
💻 C
📖 第 1 页 / 共 4 页
字号:
//
// 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.

Module Name:  
    system.c
    
Abstract:  
    Device dependant part of the USB Universal Host Controller Driver (UHCD).

Notes: 
--*/


#ifdef USBOHCI_DMA_IN_SRAM
#pragma message ("OHCI using Internal SRAM")
#else
#pragma message ("OHCI using SDRAM")
#endif


#include <windows.h>
#include <nkintr.h>
#include <ceddk.h>
#include <devload.h>

#ifndef OSV_LOCAL_MERLIN
// giisr is only supported in Jameson,
// since this is a Merlin build, don't include it.
#include <giisr.h>
#endif

#include <uhcdddsi.h>
#include "bvd1.h"
#include "sa11x1.h"
#include "macros.h"

#ifndef PLAT_LUBBOCK

// Bulverde will use XLLP library to
// access GPIOs and Clocks.

#include "xllp_gpio.h"
#include "xllp_clkmgr.h"
#include "xllp_usbohci.h"
#endif


#ifndef DEBUG
#define ZONE_INIT	1
#endif

// Registry key and value names
#define OHCI_DRIVER_KEY         TEXT("Drivers\\BuiltIn\\OHCI")
#define IRQ_VALUE_NAME          TEXT("Irq")
#define IOBASE_VALUE_NAME       TEXT("MemBase")

extern void usWait(unsigned msVal); 
extern PVOID VirtualAllocCopy(unsigned size,char *str,PVOID pVirtualAddress);
void TurnOnSRAMClocks();

// Amount of memory to use for HCD buffer
extern DWORD gcTotalAvailablePhysicalMemory;// = OHCI_DMA_BUFFER_SIZE; //28672; // 28K
extern DWORD gcHighPriorityPhysicalMemory;// = OHCI_DMA_BUFFER_HIGHPRI_SIZE; //0x5000; // 20K
extern DWORD dwSysIntrOhciMdd;//=SYSINTR_OHCI_MDD;
extern DWORD dwSysIntrOhciPdd;//=SYSINTR_OHCI_PDD

#ifdef PLAT_LUBBOCK
extern DWORD dwSKBase;//=SK_BA
#endif

//Dma Buffer
extern DWORD dwOhciDmaBufferPhysical;//=OHCI_DMA_BUFFER_PHYSICAL
extern PVOID pOhciDmaBufferVirtual;//=OHCI_DMA_BUFFER_U_VIRTUAL
extern DWORD dwOhciDmaBufferSize;//=OHCI_DMA_BUFFER_SIZE


// Daughter card register structures
#ifdef PLAT_LUBBOCK
volatile struct SK_IRQRegisterBlock		*v_pDCIRQReg;
volatile struct SK_SC_PLLRegisterBlock  *v_pDCPLLReg;
volatile struct SK_SMCRegisterBlock		*v_pDCSMCReg;
#endif

#ifndef PLAT_LUBBOCK
volatile XLLP_CLKMGR_T					*v_pDCCLKReg;
volatile XLLP_GPIO_T					*v_pDCGPIOReg;
volatile XLLP_USBOHCI_T					*v_pDCUSBOHCIReg;
#endif

volatile struct SK_USBRegisterBlock		*v_pDCUSBReg;
PVOID									v_pOHCIDMABuffer;

volatile MEMC_STRUCT					*v_pDCMEMCReg;	// on the cotulla, xsc1.h

// Interrupt Service Thread Globals
VOID	*gOHCIPDDIntrEvent;
VOID	*gOHCIPDDIntrThread;

static HANDLE g_IsrHandle = NULL;

typedef struct _SUhcdPdd
{
    LPVOID lpvMemoryObject;
    LPVOID lpvUhcdMddObject;
    PVOID pvVirtualAddress;                        // DMA buffers as seen by the CPU
    PHYSICAL_ADDRESS LogicalAddress;        // DMA buffers as seen by the DMA controller and bus interfaces
#ifndef OSV_LOCAL_MERLIN
    DMA_ADAPTER_OBJECT AdapterObject;
#endif
    TCHAR szDriverRegKey[MAX_PATH];
    PUCHAR ioPortBase;
    DWORD dwSysIntr;
    CRITICAL_SECTION csPdd;                     // serializes access to the PDD object
} SUhcdPdd;

#define UnusedParameter(x)  x = x

// set up virtual addresses for registers on the sa11x1
BOOL
OhcdPddInitializeAddresses(void)
{
#ifdef PLAT_LUBBOCK
    v_pDCPLLReg = (volatile struct SK_SC_PLLRegisterBlock  *)
        VirtualAllocCopy(SK_SC_PLL_SPACE,"OHCI v_pDCPLLReg: ",(PVOID)(dwSKBase + SK_PLL_BASE));
    if (v_pDCPLLReg == NULL) {
        goto error_return;
    }
    
    v_pDCIRQReg = (volatile struct SK_IRQRegisterBlock *)
        VirtualAllocCopy(SK_IRQ_SPACE,"OHCI v_pDCIRQReg",(PVOID)(dwSKBase + SK_IRQ_BASE));
    if (v_pDCIRQReg == NULL) {
        goto error_return;
    }
    
    v_pDCSMCReg = (volatile struct SK_SMCRegisterBlock *)
        VirtualAllocCopy(SK_SMC_SPACE,"OHCI v_pDCSMCReg",(PVOID)(dwSKBase + SMC_BASE));
    if (v_pDCSMCReg == NULL) {
        goto error_return;
    }
    
    v_pDCMEMCReg = (volatile MEMC_STRUCT *)
        VirtualAllocCopy(sizeof(MEMC_STRUCT),"OHCI v_pDCMEMCReg",(PVOID)(MEMC_BASE_U_VIRTUAL));
    if (v_pDCMEMCReg == NULL) {
        goto error_return;
    }

    v_pDCUSBReg = (volatile struct SK_USBRegisterBlock  *)
        VirtualAllocCopy(SK_USB_HCI_SPACE,"OHCI v_pDCUSBReg: ",(PVOID)(dwSKBase +USB_BASE));
    if (v_pDCUSBReg == NULL) {
		goto error_return;
    }

    v_pOHCIDMABuffer = 
        //		VirtualAllocCopy(OHCI_DMA_BUFFER_SIZE,"OHCI v_pOHCIDMABuffer", (PVOID) OHCI_DMA_BUFFER_U_VIRTUAL);
        VirtualAllocCopy(dwOhciDmaBufferSize,"OHCI v_pOHCIDMABuffer", pOhciDmaBufferVirtual);
    if (v_pOHCIDMABuffer == NULL) {
        goto error_return;
    }

#endif
    
#ifndef PLAT_LUBBOCK
	// the bulverde needs access to the clkmgr to enable the USBHOST clock 
	v_pDCCLKReg = (volatile XLLP_CLKMGR_T*)
		VirtualAllocCopy(sizeof(XLLP_CLKMGR_T), "OHCI v_pDCCLKReg", (PVOID)(CLK_BASE_U_VIRTUAL));
	if( v_pDCCLKReg == NULL ) {
		goto error_return;
	}

	// the bulverde needs access to the gpio regs to set up the gpios that
	// are tied to the external MAX1693EUB USB Power Switch
	v_pDCGPIOReg = (volatile XLLP_GPIO_T*)
		VirtualAllocCopy(sizeof(XLLP_GPIO_T), "OHCI v_pDCGPIOReg", (PVOID)(GPIO_BASE_U_VIRTUAL));
	if( v_pDCCLKReg == NULL ) {
		goto error_return;
	}

	// map the usb ohci register block.
	// use the old cotulla global pointer for now.
	// later, during code clean up, consolidate the two pointers into one
	// and reconcile their usage differences.
    v_pDCUSBReg = (volatile struct SK_USBRegisterBlock  *)
        VirtualAllocCopy(SK_USB_HCI_SPACE,"OHCI v_pDCUSBReg: ",(PVOID)(USBH_BASE_U_VIRTUAL));
    if (v_pDCUSBReg == NULL) {
		goto error_return;
    }

	v_pDCUSBOHCIReg = (volatile XLLP_USBOHCI_T*)v_pDCUSBReg;

#ifdef USBOHCI_DMA_IN_SRAM
	// initialize the sram here.
	{
		volatile unsigned long	*v_pDCIMReg = NULL;

		// map the memory
		v_pDCIMReg = (volatile unsigned long*)VirtualAllocCopy( 
													sizeof( 64 * sizeof( volatile unsigned long ) ), 
													"OHCI v_pDCIMReg: ", 
													(PVOID)(IM_CONTROL_BASE_U_VIRTUAL)
													);
		if( v_pDCIMReg == NULL )
		{
			// error
			RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: failed mapping v_pDCIMReg to %08x.\r\n"), IM_CONTROL_BASE_U_VIRTUAL));
		}
		else
		{
			RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCIMReg:       %08x = %08x.\r\n"), v_pDCIMReg,IM_CONTROL_BASE_U_VIRTUAL));

			RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCIMReg: impmr %08x.\r\n"), v_pDCIMReg[0] ));
			RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCIMReg: impsr %08x.\r\n"), v_pDCIMReg[2] ));
			// I don't think the imrmr register really exists
			//RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCIMReg: imrmr %08x.\r\n"), v_pDCIMReg[4] ));

			// test access to this memory
			v_pDCIMReg[0] = 188;		// the control register, 0 enables all internal sram banks, disables auto-wake and disables entry to standby
			RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCIMReg:Mimpmr %08x.\r\n"), v_pDCIMReg[0] ));

			// set the bank power control, auto wake enable, and DST fields
			v_pDCIMReg[0] = 0;		// the control register, 0 enables all internal sram banks, disables auto-wake and disables entry to standby
			RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCIMReg:Fimpmr %08x.\r\n"), v_pDCIMReg[0] ));


			// free the mapped memory
			VirtualFree((PVOID)v_pDCIMReg,0,MEM_RELEASE);
		}
	}

    v_pOHCIDMABuffer = 
        //		VirtualAllocCopy(OHCI_DMA_BUFFER_SIZE,"OHCI v_pOHCIDMABuffer", (PVOID) OHCI_DMA_BUFFER_U_VIRTUAL);
        VirtualAllocCopy(dwOhciDmaBufferSize,"OHCI v_pOHCIDMABuffer", (PVOID)IM_STORAGE_BASE_U_VIRTUAL);
    if (v_pOHCIDMABuffer == NULL) {
        goto error_return;
    }

	{
		// Test access to the OHCIDMABuffer:
		volatile unsigned long	*pulTemp = (volatile unsigned long*)v_pOHCIDMABuffer;

		// the SRAM needs to be clocked, just like other memory and peripherals.
		TurnOnSRAMClocks();

		RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: testing access to OHCIDMABuffer %08x mapped to %08x.\r\n"), IM_STORAGE_BASE_U_VIRTUAL, pulTemp ));
		RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: 00-0f: %08x %08x %08x %08x\r\n"), pulTemp[0], pulTemp[1], pulTemp[2], pulTemp[3] ));
		RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: 10-1f: %08x %08x %08x %08x\r\n"), pulTemp[4], pulTemp[5], pulTemp[6], pulTemp[7] ));
		
		pulTemp[0] = 188;
		pulTemp[1] = 189;
		pulTemp[2] = 190;
		pulTemp[3] = 191;
		pulTemp[4] = 192;
		pulTemp[5] = 193;
		pulTemp[6] = 194;
		pulTemp[7] = 195;

		RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses:M00-0f: %08x %08x %08x %08x\r\n"), pulTemp[0], pulTemp[1], pulTemp[2], pulTemp[3] ));
		RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses:M10-1f: %08x %08x %08x %08x\r\n"), pulTemp[4], pulTemp[5], pulTemp[6], pulTemp[7] ));
	}

	// change the value of a global pointer that contains the uncached virtual address
	// of the memory buffer used to hold the usb structures. usb structures are built
	// in this area, and the USB OHCI reads and writes to this area, also.
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: dwohciBPhy: old   %08x.\r\n"), dwOhciDmaBufferPhysical));
	dwOhciDmaBufferPhysical = IM_STORAGE_BASE_PHYSICAL;
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: dwohciBPhy: new   %08x.\r\n"), dwOhciDmaBufferPhysical));


#else
    v_pOHCIDMABuffer = 
        //		VirtualAllocCopy(OHCI_DMA_BUFFER_SIZE,"OHCI v_pOHCIDMABuffer", (PVOID) OHCI_DMA_BUFFER_U_VIRTUAL);
        VirtualAllocCopy(dwOhciDmaBufferSize,"OHCI v_pOHCIDMABuffer", pOhciDmaBufferVirtual);
    if (v_pOHCIDMABuffer == NULL) {
        goto error_return;
    }
#endif


#endif



#ifdef PLAT_LUBBOCK	
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCPLLReg:      %08x = %08x.\r\n"), v_pDCPLLReg,(dwSKBase + SK_PLL_BASE)));
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCIRQReg:      %08x = %08x.\r\n"), v_pDCIRQReg,(dwSKBase + SK_IRQ_BASE)));
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCSMCReg:      %08x = %08x.\r\n"), v_pDCSMCReg,(dwSKBase + SMC_BASE)));
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCMEMCReg:     %08x = %08x.\r\n"), v_pDCMEMCReg,MEMC_BASE_U_VIRTUAL));
#endif

#ifndef PLAT_LUBBOCK
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCCLKReg:      %08x = %08x.\r\n"), v_pDCCLKReg,CLK_BASE_U_VIRTUAL));
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCGPIOReg:     %08x = %08x.\r\n"), v_pDCGPIOReg,GPIO_BASE_U_VIRTUAL));
#endif

#ifdef USBOHCI_DMA_IN_SRAM
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pOHCIDMABuffer: %08x = %08x.\r\n"), v_pOHCIDMABuffer,IM_STORAGE_BASE_U_VIRTUAL));
#else
	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pOHCIDMABuffer: %08x = %08x.\r\n"), v_pOHCIDMABuffer,pOhciDmaBufferVirtual));
#endif

	RETAILMSG(ZONE_INIT,(TEXT("OhcdPddInitializeAddresses: v_pDCUSBReg:      %08x = %08x.\r\n"), v_pDCUSBReg,USBH_BASE_U_VIRTUAL));

    return TRUE;

error_return:
    ERRORMSG(1,(TEXT("OHCI Driver InitializeAddresses: Failed!.\r\n")));  
#ifdef PLAT_LUBBOCK
    if (v_pDCPLLReg)	VirtualFree((PVOID)v_pDCPLLReg,0,MEM_RELEASE);
    if (v_pDCIRQReg)	VirtualFree((PVOID)v_pDCIRQReg,0,MEM_RELEASE);
    if (v_pDCSMCReg)	VirtualFree((PVOID)v_pDCSMCReg,0,MEM_RELEASE);
	if (v_pDCMEMCReg)	VirtualFree((PVOID)v_pDCMEMCReg,0,MEM_RELEASE);
#endif

#ifndef PLAT_LUBBOCK
	if (v_pDCCLKReg)	VirtualFree((PVOID)v_pDCCLKReg,0,MEM_RELEASE);
	if (v_pDCGPIOReg)	VirtualFree((PVOID)v_pDCGPIOReg,0,MEM_RELEASE);
#endif

    if (v_pDCUSBReg)	VirtualFree((PVOID)v_pDCUSBReg,0,MEM_RELEASE);
    if (v_pOHCIDMABuffer)	VirtualFree((PVOID)v_pOHCIDMABuffer,0,MEM_RELEASE);

#ifdef PLAT_LUBBOCK
	v_pDCMEMCReg   = 0;
    v_pDCSMCReg    = 0;	
    v_pDCIRQReg    = 0;
    v_pDCPLLReg    = 0;
#endif

#ifndef PLAT_LUBBOCK
	v_pDCCLKReg		= 0;
	v_pDCGPIOReg	= 0;
#endif

	v_pDCUSBReg	   = 0;
	v_pOHCIDMABuffer = 0;
    
    return 0;	
}

VOID OHCI_Reset()
{

#ifdef PLAT_LUBBOCK
  // go through USB initialization sequence SA-1111 TRM p. 6-1
   //WRITE_BITFIELD(struct  skpcrBITS,&v_pDCPLLReg->skpcr,DCLKEn,1);  //Enable DMA Clocks 

   WRITE_BITFIELD(struct  skpcrBITS,&v_pDCPLLReg->skpcr,UCLKEn,1);  //Enable USB Clocks
   usWait(10);   

   // Force reset
   WRITE_BITFIELD(struct resetBITS,&v_pDCUSBReg->Reset,forceIfReset,1);
   WRITE_BITFIELD(struct resetBITS,&v_pDCUSBReg->Reset,forceHcReset,1);
   usWait(100);   

   WRITE_BITFIELD(struct resetBITS,&v_pDCUSBReg->Reset,forceIfReset,0);
   WRITE_BITFIELD(struct resetBITS,&v_pDCUSBReg->Reset,forceHcReset,0);
   WRITE_BITFIELD(struct resetBITS,&v_pDCUSBReg->Reset,clkGenReset,0);   

   WRITE_BITFIELD(struct resetBITS,&v_pDCUSBReg->Reset,uSleepStandbyEn,0);

⌨️ 快捷键说明

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