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

📄 mode.cpp

📁 Lido PXA270平台开发板的最新BSP,包括源代码
💻 CPP
📖 第 1 页 / 共 2 页
字号:
/***************************************************************************
 * Name        : mode.cpp
 * Title       : MBX WinCE driver GPE class
 * Author(s)   : Imagination Technologies
 * Created	   : 6th January 2003
 *
 * Copyright   : 2003 by Imagination Technologies. All rights reserved.
 *             : No part of this software, either material or conceptual 
 *             : may be copied or distributed, transmitted, transcribed,
 *             : stored in a retrieval system or translated into any 
 *             : human or computer language in any form by any means,
 *             : electronic, mechanical, manual or other-wise, or 
 *             : disclosed to third parties without the express written
 *             : permission of Imagination Technologies Limited, Unit 8,
 *             : HomePark Industrial Estate, King's Langley, Hertfordshire,
 *             : WD4 8LZ, U.K.
 *
 * Description : MBX WinCE driver mode related components of GPE class.
 *
 * Platform    : WinCE
 *
 * Modifications:-
 * $Log: mode.cpp $
 *
 *  --- Revision Logs Removed --- 
 *
 *  --- Revision Logs Removed --- 
 *
 *  --- Revision Logs Removed --- 
 *
 *  --- Revision Logs Removed --- 
 *
 *  --- Revision Logs Removed --- 
 *
 *  --- Revision Logs Removed --- 
 *
 *  --- Revision Logs Removed --- 
 *
 ****************************************************************************/

#include	"precomp.h"

#ifdef SUPPORT_CLEARTYPE
#include   <ctblt.h>
#endif // SUPPORT_CLEARTYPE
#include	<syspal.h>		// for 8Bpp we use the natural palette

#include "regpaths.h"

#undef NEG
#undef POS

//#define PROFILE_ROTATION	1


#define FIX_BACKWARDS_BLT		1


// This sub table contains the various mask arrays for the pixel formats we
// support for the primary surface.

static const ULONG ulPixelTableFormats[][4] = {
  { 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, // gpe1Bpp
  { 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, // gpe2Bpp
  { 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, // gpe4Bpp
  { 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, // gpe8Bpp
  { 0x0000F800, 0x000007E0, 0x0000001F, 0x00000000 }, // gpe16Bpp (565)
  { 0x00FF0000, 0x0000FF00, 0x000000FF, 0x00000000 }, // gpe24Bpp (888)
  { 0x00FF0000, 0x0000FF00, 0x000000FF, 0xFF000000 }, // gpe32Bpp (8888)
  { 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, // gpe16YrCb
  { 0x00000000, 0x00000000, 0x00000000, 0x00000000 }, // gpeDeviceCompatible
  { 0x00000000, 0x00000000, 0x00000000, 0x00000000 }  // gpeUndefined
};

const ULONG EGPEFormatToSrcHW[] = { MBX2D_SRC_1_PAL,	//gpe1Bpp
									MBX2D_SRC_2_PAL,	//gpe2Bpp
									MBX2D_SRC_4_PAL,	//gpe4Bpp
									MBX2D_SRC_8_PAL,	//gpe8Bpp
									MBX2D_SRC_565RGB,	//gpe16Bpp
									MBX2D_SRC_888RGB,	//gpe24Bpp
									MBX2D_SRC_8888ARGB,	//gpe32Bpp
									0,					//gpe16YrCb
									0,					//gpeDeviceCompatible
									0					//gpeUndefined
								  };

const ULONG EGPEFormatToDestHW[] = {0,					//gpe1Bpp
									0,					//gpe2Bpp
									0,					//gpe4Bpp
									MBX2D_DST_332RGB,	//gpe8Bpp
									MBX2D_DST_565RGB,	//gpe16Bpp
									MBX2D_DST_888RGB,	//gpe24Bpp
									MBX2D_DST_8888ARGB,	//gpe32Bpp
									0,					//gpe16YrCb
									0,					//gpeDeviceCompatible
									0					//gpeUndefined
								  };

SCODE	MBX::SetMode (INT nModeId, HPALETTE *hPalette)
{
	MBXSurf* pMBXSurf;

	DPFX(PVR_ZONE_INIT,(L"MBX::SetMode"));

#ifdef LOCAL_MEMORY_SELF_REFRESH
	SysLocalMemoryEnable(m_sDevData.psDevInfoKM);
#endif // LOCAL_MEMORY_SELF_REFRESH

	if (nModeId >= m_sEnumerateModesList.wCount)
	{
		DPFERROR((L"MBX::SetMode Want mode %d, only have mode 0", nModeId));
		return	(E_INVALIDARG);
	}

	PrimarySurfaceSetMode(nModeId);

	pMBXSurf = (MBXSurf*)m_pPrimarySurface;

#ifdef ROTATE_ENABLE
	((GPESurfRotate *)m_pPrimarySurface)->SetRotation(m_nScreenWidth, m_nScreenHeight, m_iRotate);

	if (m_iRotate)
	{
		pMBXSurf->m_bIsRotated = TRUE;
	}

	// Save the surface rotation.
	// This is the only surface that will have rotation applied.
	switch (m_iRotate)
	{
		case DMDO_0:
		pMBXSurf->m_lRotationAngle = 0;
		break;

		case DMDO_90:
		pMBXSurf->m_lRotationAngle = 90;
		break;

		case DMDO_180:
		pMBXSurf->m_lRotationAngle = 180;
		break;

		case DMDO_270:
		pMBXSurf->m_lRotationAngle = 270;
		break;
	}

	// Primary rotation in degrees, if it's 0 then no rotation of any surface is ever needed.
	m_lPrimaryRotation = pMBXSurf->m_lRotationAngle;

#endif
	// Default
	m_ulBltRotationHw = MBX2D_TEXTROT_NONE;

	if (hPalette)
	{
		switch (m_ulColorDepth)
		{
			case 8:
#ifdef SUPPORT_CLEARTYPE
				SetClearTypeBltPalette(_rgbIdentity, 256);
#endif
				*hPalette = EngCreatePalette (PAL_INDEXED,
											 PALETTE_SIZE,
											 (ULONG*)_rgbIdentity,
											 0,
											 0,
											 0);
				m_clDisplay.PDP_Palette((PPDP_PALETTE)&_rgbIdentity, 0, 256, FALSE);
				break;

			case 16:
			case 24:
			case 32:
#ifdef SUPPORT_CLEARTYPE
				SetClearTypeBltMasks(m_ulPixelTableFormats[0],
									 m_ulPixelTableFormats[1],
									 m_ulPixelTableFormats[2]);
#endif
				*hPalette = EngCreatePalette (PAL_BITFIELDS,
											 0,
											 NULL,
											 m_ulPixelTableFormats[0],
											 m_ulPixelTableFormats[1],
											 m_ulPixelTableFormats[2]);
				break;
		}
	}

	AllocGAPISurf(m_sModeInfo.format);

#ifdef LOCAL_MEMORY_SELF_REFRESH
	SysLocalMemoryDisable(m_sDevData.psDevInfoKM);
#endif // LOCAL_MEMORY_SELF_REFRESH

	return (S_OK);
}


/*****************************************************************************
 FUNCTION	: 	GetDisplayModeGPEFormat
 PURPOSE	:	Returns the gpe format in the pixel format
				associated with the display mode whose number is passed.
				This is inline, hence no Enter/Exit calls.
 PARAMETERS	: 	
 RETURNS	: 	
*****************************************************************************/
EGPEFormat GetDisplayModeGPEFormat (USHORT usBpp)
{
	EGPEFormat eFmt = gpeUndefined;

	switch(usBpp)
	{
		case 1:
			eFmt = gpe1Bpp;
			break;
		case 2:
			eFmt = gpe2Bpp;
			break;
		case 4:
			eFmt = gpe4Bpp;
			break;
		case 8:
			eFmt = gpe8Bpp;
			break;
		case 16:
			eFmt = gpe16Bpp;
			break;
		case 24:
			eFmt = gpe24Bpp;
			break;
		case 32:
			eFmt = gpe32Bpp;
			break;
	}

	return (eFmt);
}


/*****************************************************************************
 FUNCTION	: 	PrimarySurfaceSetMode
 PURPOSE	:	This function handles allocating a primary surface for the given display
				mode. It also programs the RAMDAC to use the new primary. This function
				is not intended to be reused. Rather, it makes the SetMode function easir
				to read.
 PARAMETERS	: 	
 RETURNS	: 	TRUE = OK, FALSE = Failure
*****************************************************************************/
BOOL MBX::PrimarySurfaceSetMode( INT nModeId )
{
	BOOL	bRtn = TRUE;
	PPDP_EnumTableEntry psModeEntry = &m_sEnumerateModesList.psModeList[nModeId];

	m_sModeInfo.format = GetDisplayModeGPEFormat(psModeEntry->byBPP);
	m_nScreenWidth     = psModeEntry->wXRes;
	m_nScreenHeight    = psModeEntry->wYRes;
	m_ulColorDepth     = psModeEntry->byBPP;
	m_ulDstHWFormat    = EGPEFormatToDestHW[m_sModeInfo.format];

#if defined PROFILE_ROTATION
/***********************************************************************************/
	ProfileVidMemBlts();
/***********************************************************************************/
#endif

#ifndef SUPPORT_VIRTUAL_MODES
	m_ulPhysicalScreenX = m_nScreenWidth;
	m_ulPhysicalScreenY = m_nScreenHeight;
#endif

	#ifdef ROTATE_ENABLE
	// do rotation if needed
	SetRotateParams();
	#endif

	m_sModeInfo.width  = m_nScreenWidth;
	m_sModeInfo.height = m_nScreenHeight;
	m_sModeInfo.Bpp    = m_ulColorDepth;

	m_sModeInfo.frequency = psModeEntry->wRefresh;
	m_ulScanLineLength    = psModeEntry->wStride;

	//////////DPFENTER((L"->PrimarySurfaceSetMode"));
	DPFINFO((L"----------------------------------------"));
	DPFINFO((L"--- DISPLAY MODE : %4d x %4d x %2d ----", m_nScreenWidth, m_nScreenHeight, m_ulColorDepth ));
	DPFINFO((L"----------------------------------------"));
	

	// Free up the previous primary surface.
	if (m_pPrimarySurface && m_pPrimarySurface->Buffer() != NULL)
	{
		delete m_pPrimarySurface;
	}


	#ifndef ROTATE_ENABLE
	if(FAILED(AllocSurface(&m_pPrimarySurface, m_nScreenWidth, m_nScreenHeight, m_sModeInfo.format, GPE_REQUIRE_VIDEO_MEMORY)))
	#else
	if(FAILED(AllocSurface(&m_pPrimarySurface, m_nScreenWidthSave, m_nScreenHeightSave, m_sModeInfo.format, GPE_REQUIRE_VIDEO_MEMORY)))
	#endif
	{
		DPFERROR((L"Couldn't allocate primary surface"));
		bRtn = FALSE;
	}
	else
	{
		PDP_SETMODE sSetMode;

		memcpy(m_ulPixelTableFormats, ulPixelTableFormats[m_sModeInfo.format], sizeof(m_ulPixelTableFormats));

		sSetMode.wDisplayX     = (WORD) m_ulPhysicalScreenX;
		sSetMode.wDisplayY     = (WORD) m_ulPhysicalScreenY;
		sSetMode.wStride       = (WORD) m_ulScanLineLength;
		sSetMode.wBitsPerPixel = (WORD) m_sModeInfo.Bpp;
		sSetMode.psMemInfo     = ((MBXSurf*)m_pPrimarySurface)->GetMemInfo();	/* base of Display surface */

		/* Get the physical address of the frame buffer. Note: the frame buffer is not allocated  
		from the start of the marathon address space in all cases. */
		m_pbyFBPhysBase = (PBYTE) sSetMode.psMemInfo->sMemBlk.sSysPhysAddr.uiAddr;

#if FIX_BACKWARDS_BLT

		/*
			Backwards blt fix :
			The first backwards blt goes wrong in early silicon,
			so we do a small backwards blt here to flush out the bug.
			To test this, with a 640x480 panel and a fixed rotation of 270 degrees,
			run the following test kit GDI test : tux -o -d gdiapi -x 207 -r 26314
		*/

		LONG lTop=2,lLeft=2,lRight=4,lBottom=4;

		/* Bug fix : 
		 * Dummy backwards blt */

		SlavePortInitWrites();

		/* acquire slave port */
		PVRSRVAcquireSlavePort(m_sDevData.psDevInfoKM, PVRSRV_SLAVEPORT_2D, IMG_TRUE);

		/* -- 2D Dest surface */
		SlavePortWrite(0xA0050500);

		SlavePortWrite((( sSetMode.psMemInfo->uiDevAddr.uiAddr		/* Dest surface address */
					>>	MBX2D_DST_ADDR_ALIGNSHIFT)
					<<	MBX2D_DST_ADDR_SHIFT)
					&	MBX2D_DST_ADDR_MASK );

		/* -- 2D Source Surface */
		SlavePortWrite(0x94050500);									/* Src format and stride */

		SlavePortWrite((( sSetMode.psMemInfo->uiDevAddr.uiAddr		/* Source address */
							>>	MBX2D_SRC_ADDR_ALIGNSHIFT)
							<<	MBX2D_SRC_ADDR_SHIFT)
							&	MBX2D_SRC_ADDR_MASK );

		/* -- Source Offset : Specify the starting pixel coordinate */
		SlavePortWrite( MBX2D_SRC_OFF_BH
							| (( (lLeft-1) <<MBX2D_SRCOFF_XSTART_SHIFT) & MBX2D_SRCOFF_XSTART_MASK)	/* left */
							| ((lTop<<MBX2D_SRCOFF_YSTART_SHIFT) & MBX2D_SRCOFF_YSTART_MASK) );		/* top */

		/* -- Stretch Control */
		SlavePortWrite(0x60800200); /* no stretch */

		/* - Clipping */
		SlavePortWrite(0x00000001); /* 1 clip rect */

		/* Dest clipping rectangle */
		SlavePortWrite(
			(((SHORT)lRight << MBX2D_CLIP_XMAX_SHIFT) & MBX2D_CLIP_XMAX_MASK) |	/* right */
			(((SHORT)lLeft << MBX2D_CLIP_XMIN_SHIFT) & MBX2D_CLIP_XMIN_MASK)	/* left */
			);
		SlavePortWrite(
			(((SHORT)lTop << MBX2D_CLIP_YMIN_SHIFT) & MBX2D_CLIP_YMIN_MASK) |	/* top */
			(((SHORT)lBottom << MBX2D_CLIP_YMAX_SHIFT) & MBX2D_CLIP_YMAX_MASK)	/* bottom */
			);

		/* -- 2D Control */
		SlavePortWrite(0x20000001);		/* old bug fix */
		SlavePortWrite(0x00000000);
		SlavePortWrite(0x00000000);

		/* -- Blit Command */
		SlavePortWrite(0x8184CCCC);		/* SrcCopy with backwards blt flag */
		SlavePortWrite(0x0000FFFF);

		/* Dest rectangle */
		SlavePortWrite(  ((SHORT)lTop  &  MBX2D_DST_YSTART_MASK)			/* top */
						|	 (((SHORT)lLeft << MBX2D_DST_XSTART_SHIFT)		/* left */
								& MBX2D_DST_XSTART_MASK) );

		SlavePortWrite(  ((SHORT)lBottom & MBX2D_DST_YEND_MASK)				/* bottom */
						|	 (((SHORT)lRight << MBX2D_DST_XEND_SHIFT)		/* right */
								& MBX2D_DST_XEND_MASK) );

		SlavePortFlushWrites();
		PVRSRVReleaseSlavePort(	m_sDevData.psDevInfoKM, PVRSRV_SLAVEPORT_2D);

#endif /* FIX_BACKWARDS_BLT */

		/* clear primary surface */
		memset (sSetMode.psMemInfo->pvLinAddr, 0, (sSetMode.wStride * sSetMode.wDisplayY));

		m_clDisplay.PDP_SetMode (&sSetMode, FALSE);

#ifdef ROTATE_ENABLE
		// notify PDP of rotation
		m_clDisplay.PDP_SetCursorRotation(m_iRotate);

		// notify surface of rotation
		((GPESurfRotate *)m_pPrimarySurface)->SetRotation(m_nScreenWidth, m_nScreenHeight, m_iRotate);
#endif

#if HW_VERIFY
		m_clHwVer.EnableHwVerForMode(m_nScreenHeight * m_ulScanLineLength);
#endif /* #ifdef HW_VERIFY */

		ULONG ulStripeSize = ((((m_ulPhysicalScreenY * m_ulScanLineLength) >> 3) + 0x0FFF) & 0xFFFFF000);
		m_pbyStripeLinBase = (unsigned char *)VideoAlloc(ulStripeSize, sizeof(ULONG), &m_ulStripePhyBase);

		m_ulStripeSize = ulStripeSize / NUM_OF_STRIPED_BUFFERS;

		/* alloc space for small surfaces */
		ULONG		ulBufPhys;
		SMALLSURFS	*psBufLin;

		psBufLin = (SMALLSURFS *)VideoAlloc(sizeof(SMALLSURFS), sizeof(ULONG), &ulBufPhys);

		if (!psBufLin)
		{ 
			DPFERROR((L"small buffers allocation failed"));
			bRtn = FALSE;
		}
		else
		{
			m_sPaletteInfo.prgbqSrcPalette  = (RGBQUAD *)&psBufLin->aSrcPal;
			m_sPaletteInfo.ulSrcPalettePhys = ulBufPhys + ((ULONG)m_sPaletteInfo.prgbqSrcPalette - (ULONG)psBufLin);
			m_sPaletteInfo.prgbqPatPalette  = (RGBQUAD *)&psBufLin->aPatPal;
			m_sPaletteInfo.ulPatPalettePhys = ulBufPhys + ((ULONG)m_sPaletteInfo.prgbqPatPalette - (ULONG)psBufLin);

			#if HW_VERIFY
			m_clHwVer.UpdatePaletteAddr(&m_sPaletteInfo);
			#endif

			m_pbyPatternFBMem = (BYTE *)&psBufLin->byPatBuf;
			m_ulPatternFBMemPhys = ulBufPhys + ((ULONG)m_pbyPatternFBMem - (ULONG)psBufLin);
			m_ulPatternBufSize   = MAX_PATTERN_BUFFER_SIZE;

			m_sCallbacks.sBltComplete.pulLinAddr = &psBufLin->ulBltComplete;
			m_sCallbacks.sBltComplete.ulPhysAddr = ulBufPhys + ((ULONG)m_sCallbacks.sBltComplete.pulLinAddr - (ULONG)psBufLin);
			m_sCallbacks.sStripeComplete.pulLinAddr = &psBufLin->ulStripeComplete;
			m_sCallbacks.sStripeComplete.ulPhysAddr = ulBufPhys + ((ULONG)m_sCallbacks.sStripeComplete.pulLinAddr - (ULONG)psBufLin);
			m_sCallbacks.sGAPIComplete.pulLinAddr = &psBufLin->ulGAPIComplete;
			m_sCallbacks.sGAPIComplete.ulPhysAddr = ulBufPhys + ((ULONG)m_sCallbacks.sGAPIComplete.pulLinAddr - (ULONG)psBufLin);

			*m_sCallbacks.sStripeComplete.pulLinAddr = 0;
			*m_sCallbacks.sBltComplete.pulLinAddr = 0;
			*m_sCallbacks.sGAPIComplete.pulLinAddr = 0;
			m_ulStrideBufSig = 0;

			/* alloc space for a mask buffer */
			ULONG ulStripeSize = (((m_nScreenWidth * m_nScreenHeight)>>4) & 0xFFFFF000);
			m_pulMaskBufLin    = (ULONG*)VideoAlloc(ulStripeSize, sizeof (ULONG), &m_ulMaskBufPhys);
			m_ulMaskBufferSize = (m_pulMaskBufLin) ? ulStripeSize : 0;
		}
	}

⌨️ 快捷键说明

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