📄 s3c6410_disp.cpp
字号:
//
// 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:
Abstract:
Functions:
Notes:
--*/
#include "precomp.h"
#include "pmplatform.h"
#include <DrvLib.h>
#include <nkintr.h>
#include <syspal.h> // for 8Bpp we use the natural palette
#include <gxinfo.h>
#define DISPPERF_DECLARE
#include "dispperf.h"
#define PRIMARY_WINDOW (DISP_WIN1)
#define PRIMARY_WINDOW_MODE (DISP_WIN1_DMA)
#define OVERLAY_WINDOW (DISP_WIN0)
#define OVERLAY_WINDOW_DMA (DISP_WIN0_DMA)
#define OVERLAY_WINDOW_FIFO (DISP_WIN0_POST_RGB)
#define ESC_SUCCESS 0x00000001
#define ESC_FAILED 0xFFFFFFFF
#define ESC_NOT_SUPPORTED 0x00000000
#define TV_DST_WIDTH (640)
#define TV_DST_HEIGHT (448)
DDGPE * gGPE = (DDGPE *)NULL;
#if (LCD_BPP == 16)
ULONG gBitMasks[] = {0xF800, 0x07E0, 0x001F};
#elif (LCD_BPP == 32)
ULONG gBitMasks[] = {0x00FF0000, 0x0000FF00, 0x000000FF};
#else
#error LCD_BPP_UNDEFINED
#endif
// NOTE: One file should use INSTANTIATE_GPE_ZONES. This allows it to be pre-compiled
// initialZones should typically be 0x0003 (refer to "gpe.h")
INSTANTIATE_GPE_ZONES(0x0003, "DisplayDriver", "Unused1", "Unused2")
// This prototype avoids problems exporting from .lib
BOOL APIENTRY GPEEnableDriver(ULONG engineVersion, ULONG cj, DRVENABLEDATA * data, PENGCALLBACKS engineCallbacks);
BOOL AdvertisePowerInterface(HMODULE hInst);
BOOL ConvertStringToGuid (LPCTSTR pszGuid, GUID *pGuid);
CEDEVICE_POWER_STATE VideoToPmPowerState(VIDEO_POWER_STATE vps);
VIDEO_POWER_STATE PmToVideoPowerState(CEDEVICE_POWER_STATE pmDx);
BOOL
APIENTRY
DrvEnableDriver(
ULONG engineVersion,
ULONG cj,
DRVENABLEDATA * data,
PENGCALLBACKS engineCallbacks
)
{
return GPEEnableDriver(engineVersion, cj, data, engineCallbacks);
}
GPE *
GetGPE()
{
if (!gGPE)
{
gGPE = new S3C6410Disp();
}
return gGPE;
}
S3C6410Disp::S3C6410Disp()
{
DWORD dwSplashFrameBufferSize;
DISPDRV_MSG((_T("[DISPDRV] ++S3C6410Disp::S3C6410Disp()\n\r")));
m_pDispConReg = NULL;
m_pGPIOReg = NULL;
m_pSPIReg = NULL;
m_VideoMemoryPhysicalBase = NULL;
m_VideoMemoryVirtualBase = NULL;
m_VideoMemorySize = 0;
m_pVideoMemoryHeap = NULL;
m_hVideoDrv = NULL;
m_CursorVisible = FALSE;
m_CursorDisabled = TRUE;
m_CursorForcedOff = FALSE;
memset (&m_CursorRect, 0x0, sizeof(m_CursorRect));
m_InDDraw = FALSE;
InitalizeOverlayContext();
m_bTVDMARunning = FALSE;
m_TVDMACtxt.dwSourceFormat = 0;
m_TVDMACtxt.uiSrcBaseWidth = 0;
m_TVDMACtxt.uiSrcBaseHeight = 0;
m_TVDMACtxt.uiSrcWidth = 0;
m_TVDMACtxt.uiSrcHeight = 0;
m_TVDMACtxt.uiSrcOffsetX = 0;
m_TVDMACtxt.uiSrcOffsetY = 0;
//---------------------
// Setup Mode Information
//---------------------
// Initial Output Interface
m_eOutputInterface = OUTPUT_IF_RGB;
//m_eOutputInterface = OUTPUT_IF_TV;
m_eTVDMAMode = TV_DMA_DISABLE;
// Initialize Screen Dimensions
m_dwDeviceScreenWidth = LCD_WIDTH;
m_dwDeviceScreenHeight = LCD_HEIGHT;
m_nScreenWidthSave = m_dwDeviceScreenWidth;
m_nScreenHeightSave = m_dwDeviceScreenHeight;
// Initialize Rotate Mode
m_iRotate = GetRotateModeFromReg();
SetRotateParams();
//----------------------------------------
// Initialize ModeInfoEX, modeInfo Data Structure
//----------------------------------------
//Setup ModeInfoEx, ModeInfo
m_pModeEx = &m_ModeInfoEx;
m_pMode = &m_ModeInfoEx.modeInfo;
memset(m_pModeEx, 0, sizeof(GPEModeEx));
#if (LCD_BPP == 16)
m_pModeEx->ePixelFormat = ddgpePixelFormat_565;
#elif (LCD_BPP == 32)
m_pModeEx->ePixelFormat = ddgpePixelFormat_8888;
#endif
// Fill GPEMode modeInfo
m_pMode->modeId = 0;
m_pMode->width = m_nScreenWidth;
m_pMode->height = m_nScreenHeight;
m_pMode->format = EDDGPEPixelFormatToEGPEFormat[m_pModeEx->ePixelFormat];
m_pMode->Bpp = EGPEFormatToBpp[m_pMode->format];
m_pMode->frequency = 60; // Usually LCD Panel require 60Hz
// Fill DDGPEStandardHeader
m_pModeEx->dwSize = sizeof(GPEModeEx);
m_pModeEx->dwVersion = GPEMODEEX_CURRENTVERSION;
// Fill ModeInfoEX
m_pModeEx->dwPixelFourCC = 0; // Should be Zero
m_pModeEx->dwPixelFormatData = 0; // Don't care
m_pModeEx->lPitch = m_dwDeviceScreenWidth*(m_pMode->Bpp/8);
m_pModeEx->dwFlags = 0; // Should be Zero
m_pModeEx->dwRBitMask = gBitMasks[0];
m_pModeEx->dwGBitMask = gBitMasks[1];
m_pModeEx->dwBBitMask = gBitMasks[2];
m_pModeEx->dwAlphaBitMask = 0x00000000;
// Initialize Power State
m_VideoPowerState = VideoPowerOn;
// Mapping Virtual Address (SFR, VideoMemory)
if (AllocResource() == FALSE)
{
DISPDRV_ERR((_T("[DISPDRV:ERR] S3C6410Disp() : AllocResource() Fail\n\r")));
return;
}
// Clear Video Memory (Leave frame buffer for splash image)
dwSplashFrameBufferSize = m_dwDeviceScreenWidth*m_dwDeviceScreenHeight*m_pMode->Bpp/8;
memset ((void *)(m_VideoMemoryVirtualBase+dwSplashFrameBufferSize), 0x0, m_VideoMemorySize-dwSplashFrameBufferSize);
#if G2D_ACCELERATE
// Enable Block Power and Clock Source
// Todo : Power Management in Video Driver
// DevHWPowerGating(HWPWR_2D_ON);
// DevHWClockGating(HWCLK_2D_ON);
m_oG2D = new FIMGSE2D;
if(m_oG2D == NULL)
{
DISPDRV_MSG((_T("[DISPDRV:ERR] S3C6410Disp() : 2D Accelerator Initialization Fail\n\r")));
}
// Initialize Interrupt (Event, Interrupt)
if (m_oG2D)
{
BOOL bResult;
bResult = m_oG2D->InitializeInterrupt();
if(bResult==FALSE)
{
DISPDRV_ERR((_T("[DISPDRV:ERR] InitializeInterrupt() 2D Object is failed.\n\r")));
}
}
else
{
DISPDRV_ERR((_T("[DISPDRV:ERR] InitializeInterrupt() : 2D Object is not created.\n\r")));
}
#endif
// Initialize Critical Section
InitializeCriticalSection(&m_csDevice);
InitializeCriticalSection(&m_cs2D);
// Initialize Display Controller
if (DevInitialize() == FALSE)
{
DISPDRV_ERR((_T("[DISPDRV:ERR] S3C6410Disp() : InitializeDevice() Fail\n\r")));
return;
}
AdvertisePowerInterface(g_hmodDisplayDll);
DISPDRV_MSG((_T("[DISPDRV] --S3C6410Disp::S3C6410Disp()\n\r")));
}
S3C6410Disp::~S3C6410Disp()
{
DISPDRV_MSG((_T("[DISPDRV] ++S3C6410Disp::~S3C6410Disp()\n\r")));
#if G2D_ACCELERATE
if (m_oG2D)
{
delete m_oG2D;
}
// Disable Block Power and Clock Source
// Todo : implement power management
// DevHWClockGating(HWCLK_2D_OFF);
// DevHWPowerGating(HWPWR_2D_OFF);
if (m_oG2D)
{
m_oG2D->DeinitInterrupt();
}
else
{
DISPDRV_ERR((_T("[DISPDRV:ERR] DeinitInterrupt() : 2D Object is not created.\n\r")));
}
#endif
ReleaseResource();
DISPDRV_MSG((_T("[DISPDRV] --S3C6410Disp::~S3C6410Disp()\n\r")));
}
SCODE
S3C6410Disp::SetMode (INT modeId, HPALETTE *palette)
{
SCODE scRet = S_OK;
DISPDRV_MSG((_T("[DISPDRV] ++S3C6410Disp::SetMode(%d)\n\r"), modeId));
if (modeId == 0)
{
m_dwPhysicalModeID = m_pMode->modeId;
// Create Palette
if (palette)
{
*palette = EngCreatePalette(PAL_BITFIELDS, 0, NULL, gBitMasks[0], gBitMasks[1], gBitMasks[2]);
}
//Allocate Primary Surface
if (NULL == m_pPrimarySurface)
{
if (FAILED(AllocSurface((DDGPESurf **)&m_pPrimarySurface,
m_nScreenWidthSave, m_nScreenHeightSave,
m_pMode->format, m_pModeEx->ePixelFormat,
GPE_REQUIRE_VIDEO_MEMORY)))
{
DISPDRV_ERR((_T("[DISPDRV:ERR] SetMode() : m_pPrimarySurface AllocSurface() Fail\n\r")));
scRet = E_INVALIDARG;
}
else
{
m_pVisibleSurface = (S3C6410Surf*)m_pPrimarySurface;
}
}
m_pPrimarySurface->SetRotation(m_nScreenWidth, m_nScreenHeight, m_iRotate);
//DynRotate(m_iRotate);
}
else
{
DISPDRV_ERR((_T("[DISPDRV:ERR] SetMode() : modeId = %d, Driver Support Only Mode 0\n\r"), modeId));
scRet = E_INVALIDARG;
}
DISPDRV_MSG((_T("[DISPDRV] --S3C6410Disp::SetMode()\n\r")));
return scRet;
}
SCODE
S3C6410Disp::GetModeInfo(GPEMode *mode, int modeNo)
{
//DISPDRV_MSG((_T("[DISPDRV] S3C6410Disp::GetModeInfo()\n\r")));
if (modeNo != 0)
{
DISPDRV_ERR((_T("[DISPDRV:ERR] GetModeInfo() : modeNo = %d, Driver Support Only Mode 0\n\r"), modeNo));
return E_INVALIDARG;
}
*mode = *m_pMode;
return S_OK;
}
SCODE
S3C6410Disp::GetModeInfoEx(GPEModeEx *pModeEx, int modeNo)
{
//DISPDRV_MSG((_T("[DISPDRV] S3C6410Disp::GetModeInfoEx()\n\r")));
if (modeNo != 0)
{
DISPDRV_ERR((_T("[DISPDRV:ERR] GetModeInfoEx() : modeNo = %d, Driver Support Only Mode 0\n\r"), modeNo));
return E_INVALIDARG;
}
*pModeEx = *m_pModeEx;
return S_OK;
}
int
S3C6410Disp::NumModes()
{
DISPDRV_MSG((_T("[DISPDRV] S3C6410Disp::NumModes()\n\r")));
return 1;
}
void
S3C6410Disp::CursorOn (void)
{
UCHAR *ptrScreen = (UCHAR*)m_pPrimarySurface->Buffer();
UCHAR *ptrLine;
UCHAR *cbsLine;
int x, y;
if (!m_CursorForcedOff && !m_CursorDisabled && !m_CursorVisible)
{
RECTL cursorRectSave = m_CursorRect;
int iRotate;
RotateRectl(&m_CursorRect);
for (y = m_CursorRect.top; y < m_CursorRect.bottom; y++)
{
if (y < 0)
{
continue;
}
if (y >= m_nScreenHeightSave)
{
break;
}
ptrLine = &ptrScreen[y * m_pPrimarySurface->Stride()];
cbsLine = &m_CursorBackingStore[(y - m_CursorRect.top) * (m_CursorSize.x * (m_pMode->Bpp >> 3))];
for (x = m_CursorRect.left; x < m_CursorRect.right; x++)
{
if (x < 0)
{
continue;
}
if (x >= m_nScreenWidthSave)
{
break;
}
// x' = x - m_CursorRect.left; y' = y - m_CursorRect.top;
// Width = m_CursorSize.x; Height = m_CursorSize.y;
switch (m_iRotate)
{
case DMDO_0:
iRotate = (y - m_CursorRect.top)*m_CursorSize.x + x - m_CursorRect.left;
break;
case DMDO_90:
iRotate = (x - m_CursorRect.left)*m_CursorSize.x + m_CursorSize.y - 1 - (y - m_CursorRect.top);
break;
case DMDO_180:
iRotate = (m_CursorSize.y - 1 - (y - m_CursorRect.top))*m_CursorSize.x + m_CursorSize.x - 1 - (x - m_CursorRect.left);
break;
case DMDO_270:
iRotate = (m_CursorSize.x -1 - (x - m_CursorRect.left))*m_CursorSize.x + y - m_CursorRect.top;
break;
default:
iRotate = (y - m_CursorRect.top)*m_CursorSize.x + x - m_CursorRect.left;
break;
}
cbsLine[(x - m_CursorRect.left) * (m_pMode->Bpp >> 3)] = ptrLine[x * (m_pMode->Bpp >> 3)];
ptrLine[x * (m_pMode->Bpp >> 3)] &= m_CursorAndShape[iRotate];
ptrLine[x * (m_pMode->Bpp >> 3)] ^= m_CursorXorShape[iRotate];
if (m_pMode->Bpp > 8)
{
cbsLine[(x - m_CursorRect.left) * (m_pMode->Bpp >> 3) + 1] = ptrLine[x * (m_pMode->Bpp >> 3) + 1];
ptrLine[x * (m_pMode->Bpp >> 3) + 1] &= m_CursorAndShape[iRotate];
ptrLine[x * (m_pMode->Bpp >> 3) + 1] ^= m_CursorXorShape[iRotate];
if (m_pMode->Bpp > 16)
{
cbsLine[(x - m_CursorRect.left) * (m_pMode->Bpp >> 3) + 2] = ptrLine[x * (m_pMode->Bpp >> 3) + 2];
ptrLine[x * (m_pMode->Bpp >> 3) + 2] &= m_CursorAndShape[iRotate];
ptrLine[x * (m_pMode->Bpp >> 3) + 2] ^= m_CursorXorShape[iRotate];
}
}
}
}
m_CursorRect = cursorRectSave;
m_CursorVisible = TRUE;
}
}
void
S3C6410Disp::CursorOff (void)
{
UCHAR *ptrScreen = (UCHAR*)m_pPrimarySurface->Buffer();
UCHAR *ptrLine;
UCHAR *cbsLine;
int x, y;
if (!m_CursorForcedOff && !m_CursorDisabled && m_CursorVisible)
{
RECTL rSave = m_CursorRect;
RotateRectl(&m_CursorRect);
for (y = m_CursorRect.top; y < m_CursorRect.bottom; y++)
{
// clip to displayable screen area (top/bottom)
if (y < 0)
{
continue;
}
if (y >= m_nScreenHeightSave)
{
break;
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -