📄 dalmode.c
字号:
ULONG ulControllerVector = VECTORFROMINDEX(DAL_PRIMARY_CONTROLLER) |
VECTORFROMINDEX(DAL_SECONDARY_CONTROLLER);
if ((ulControllerVector & ulControllers) == ulControllerVector)
{
if (!bFindCloneResolution(lpHDE, (LPDEVMODE_INFO)&dmModesSent[i], &ulPanType))
{
DALDEBUG((DALDBG_ENTRY_EXIT, "DALSetMode - Exit"));
return 0;
}
else
bPseudoLargeDesktop = TRUE;
if (lpHDE->aulRefreshRate[i])
{
dmModesSent[i].ulDisplayFrequency = lpHDE->aulRefreshRate[i];
}
}
}
}
else
{
if (lpController->ulFlags & GCO_ACTIVE)
{
// only if the controller is active (on another driver), should we
// include it in the bandwidth calculations.
MOVEMEMORY((LPDEVMODE_INFO)&dmModesSent[i],
(LPDEVMODE_INFO)&lpController->sModeInfo,
sizeof(DEVMODE_INFO));
// fill up the current displays for the controllers on this driver
ulDisplay[i] = lpController->ulDisplays;
// Find the display types to pass to the bandwidth functions.
ulDisplayType[i] = ulGetDisplayTypesFromDisplayVector(lpHDE,
lpController->ulDisplays,
(1 && (lpController->ulFlags & GCO_EXPANSION)));
} else
{
// if the controller is NOT active, zero-initialize
// (not included in bandwidth calculations)
ZEROMEMORY((LPDEVMODE_INFO)&dmModesSent[i],
sizeof(DEVMODE_INFO));
ulDisplay[i] = 0;
ulDisplayType[i] = 0;
}
}
}
for (i = 0; i < lpHDE->ulControllersCount; i++)
{
lpController = (LPDEVGCO) &lpHDE->aControllers[i];
if (VECTORFROMINDEX(i) & ulControllers)
{
ulDisplay[i] = lpController->ulDisplays;
for ( j = 0; j < lpHDE->ulDisplaysCount; j++)
{
if ( ulDisplay[i] & VECTORFROMINDEX(j) )
{
lpDisplay = (LPDEVGDO) &lpHDE->aDisplays[j];
}
}
}
}
if (bForce)
{
if (DALRULE2_DONOTLOWERVIEW & lpHDE->ulDalRule2)
{
ulOptions |= DAL_OPTIONS_DONOTLOWERVIEW;
}
// caller forced the mode, hence DAL will do everything possible
// to find a close and similar mode, otherwise DAL will fail the
// mode call.
if (!(bFindClosestMode(lpHDE, (LPDEVMODE_INFO)&dmModesSent[0],
(LPDEVMODE_INFO)&dmModesRet[0],
ulControllers, (LPULONG)&ulDisplayType[0],
(LPULONG)&ulDisplay[0],
ulOptions)))
{
// wow! DAL cannot find a close mode, this must be one hanus mode
// looks like the DalSetMode call is destined to fail.
bCanSetModes = FALSE;
}
} else
{
// caller didn't force the mode, hence the caller wants the mode
// to explicitly be set. [GG]
if (!(bValidateMode(lpHDE, (LPDEVMODE_INFO)&dmModesRet[0], ulControllers,
(LPULONG)&ulDisplayType[0], (LPULONG)&ulDisplay[0])))
{
bCanSetModes = FALSE;
}
}
if (!bCanModeFitInMemory(lpHDE, lpMode, (lpHDE->ulVideoMemorySizeAvailable +
lpHDE->aDriverData[ulDriverID].ulMemoryUsed)))
{
// is sufficient memory available for this mode?
ulControllers = 0;
}
if (bCanSetModes)
{
// Notify DDL event - driver set mode
{
EVENTINFO sEventInfo;
ZEROMEMORY(&sEventInfo, sizeof(EVENTINFO));
sEventInfo.ulSize = sizeof(EVENTINFO);
sEventInfo.ulDriverID = ulDriverID;
sEventInfo.ulEvent = DAL_EVENT_DRIVERSETMODE;
DDLEventNotification(lpHDE->hDDL, &sEventInfo);
}
// since the DAL will be setting the mode, store the last Surface mode
// as requested by the driver.
lpHDE->aDriverData[ulDriverID].sLastMode.ulModeFlags =
lpHDE->aDriverData[ulDriverID].sMode.ulModeFlags;
lpHDE->aDriverData[ulDriverID].sLastMode.ulPelsWidth =
lpHDE->aDriverData[ulDriverID].sMode.ulPelsWidth;
lpHDE->aDriverData[ulDriverID].sLastMode.ulPelsHeight =
lpHDE->aDriverData[ulDriverID].sMode.ulPelsHeight;
lpHDE->aDriverData[ulDriverID].sLastMode.ulDisplayFrequency =
lpHDE->aDriverData[ulDriverID].sMode.ulDisplayFrequency;
lpHDE->aDriverData[ulDriverID].sLastMode.ulBitsPerPixel =
lpHDE->aDriverData[ulDriverID].sMode.ulBitsPerPixel;
lpHDE->aDriverData[ulDriverID].sMode.ulModeFlags = lpMode->ulModeFlags;
lpHDE->aDriverData[ulDriverID].sMode.ulPelsWidth = lpMode->ulPelsWidth;
lpHDE->aDriverData[ulDriverID].sMode.ulPelsHeight = lpMode->ulPelsHeight;
lpHDE->aDriverData[ulDriverID].sMode.ulDisplayFrequency = lpMode->ulDisplayFrequency;
lpHDE->aDriverData[ulDriverID].sMode.ulBitsPerPixel = lpMode->ulBitsPerPixel;
lpHDE->aDriverData[ulDriverID].ulOffset = ulDisplayOffset;
lpHDE->aDriverData[ulDriverID].ulPitch = ulDisplayPitch;
// found modes which can safely be programmed on the controllers
for (i = 0; i < lpHDE->ulControllersCount; i++)
{
if (VECTORFROMINDEX(i) & ulControllers)
{
// this controller is participating with the mode
GCO_QUERY_STRUCTURE sQueryGCO;
lpController = (LPDEVGCO) &lpHDE->aControllers[i];
lpController->siDesktop.cx = lpMode->ulPelsWidth;
lpController->siDesktop.cy = lpMode->ulPelsHeight;
// DAL releases pan locking on a controller whenever a mode is set
lpController->ulFlags &= ~GCO_PANLOCKED;
// todo: here is where the setup for a large desktop with pan
// locked views into the surface are programmed
// verify registry data
if (( lpHDE->sPanLock[i].top
|| lpHDE->sPanLock[i].left
|| lpHDE->sPanLock[i].bottom
|| lpHDE->sPanLock[i].right )
|| bPseudoLargeDesktop)
{
// validate the value first
lpController->rtPanLock.top = lpHDE->sPanLock[i].top;
lpController->rtPanLock.left = lpHDE->sPanLock[i].left;
lpController->rtPanLock.bottom = lpHDE->sPanLock[i].bottom;
lpController->rtPanLock.right = lpHDE->sPanLock[i].right;
if( bPseudoLargeDesktop &&
((lpHDE->sPanLock[i].bottom ==0)||
(lpHDE->sPanLock[i].right ==0)))
{
//Control panel could overwrite this setting. this is for you can set the largedesktop mode via slide bar.
if (ulPanType == PSEUDO_LARGE_DESKTOP_HORISONTAL)
{
lpController->rtPanLock.left = i * dmModesRet[i].ulPelsWidth;
lpController->rtPanLock.top = 0;
}
else // (ulPanType == PSEUDO_LARGE_DESKTOP_VERTICAL)
{
lpController->rtPanLock.left = 0;
lpController->rtPanLock.top = i * dmModesRet[i].ulPelsHeight;
}
lpController->rtPanLock.right = lpController->rtPanLock.left + dmModesRet[i].ulPelsWidth;
lpController->rtPanLock.bottom = lpController->rtPanLock.top + dmModesRet[i].ulPelsHeight;
}
lpController->rtView.top = (((lpController->rtPanLock.bottom - lpController->rtPanLock.top) -
dmModesRet[i].ulPelsHeight) >> 1) + lpController->rtPanLock.top;
lpController->rtView.left = (((lpController->rtPanLock.right - lpController->rtPanLock.left) -
dmModesRet[i].ulPelsWidth) >> 1) + lpController->rtPanLock.left;
// ensure the offset is aligned on an 8 pixel boundary to meet
// the hardware requirements of ALL chips.
lpController->rtView.left = ((lpController->rtView.left + 0x07) & ~0x07);
lpController->rtView.bottom = dmModesRet[i].ulPelsHeight +
lpController->rtView.top;
lpController->rtView.right = dmModesRet[i].ulPelsWidth +
lpController->rtView.left;
lpController->ulFlags |= GCO_PANLOCKED;
}
else
{
lpController->rtPanLock.top = 0;
lpController->rtPanLock.left = 0;
lpController->rtPanLock.bottom = lpMode->ulPelsHeight;
lpController->rtPanLock.right = lpMode->ulPelsWidth;
lpController->rtView.top = ((lpMode->ulPelsHeight -
dmModesRet[i].ulPelsHeight) >> 1);
lpController->rtView.left = ((lpMode->ulPelsWidth -
dmModesRet[i].ulPelsWidth) >> 1);
// ensure the offset is aligned on an 8 pixel boundary to meet
// the hardware requirements of ALL chips.
lpController->rtView.left = ((lpController->rtView.left + 0x07) & ~0x07);
lpController->rtView.bottom = dmModesRet[i].ulPelsHeight +
lpController->rtView.top;
lpController->rtView.right = dmModesRet[i].ulPelsWidth +
lpController->rtView.left;
}
/* Set the dal view to be bottom-right exclusive same as MS convention
// adjust the rectangles to be zero-based.
lpController->rtPanLock.bottom = (lpController->rtPanLock.bottom > 0) ?
(lpController->rtPanLock.bottom - 1) : 0;
lpController->rtPanLock.right = (lpController->rtPanLock.right > 0) ?
(lpController->rtPanLock.right - 1) : 0;
lpController->rtView.bottom = (lpController->rtView.bottom > 0) ?
(lpController->rtView.bottom - 1) : 0;
lpController->rtView.right = (lpController->rtView.right > 0) ?
(lpController->rtView.right - 1) : 0;
*/
dmModesRet[i].ulModeFlags |= lpHDE->aDriverData[ulDriverID].sMode.ulModeFlags
& (DEVMODEFLAG_USE565 | DEVMODEFLAG_USE4444);
// store the offset to the beginning of the surface, for use later if
// CWDDE function calls resize the view.
if (GCO_HOOK2_SETDISPLAYXYPOS & lpController->lpHWED->ulFunctionHooks2)
{
ulViewOffset = ulDisplayOffset;
lpController->ulOffset = ulDisplayOffset;
}
else
{
//determine if memory tiled situation
ZEROMEMORY((LPGCO_QUERY_STRUCTURE) &sQueryGCO, sizeof(GCO_QUERY_STRUCTURE));
// get the pertinent info from the GCO
(*lpController->lpHWED->pfnGetInfo)
(lpController->hGCO, lpController->ulController,
(LPGCO_QUERY_STRUCTURE) &sQueryGCO);
if (sQueryGCO.ulFlags & GCO_QUERY_STRUCTURE_FLAGS_TILEENABLED)
{
ulViewOffset = ulCalculateOffsetFromCoordinatesInTiledMemory(lpController->rtView.left,
lpController->rtView.top ,(lpMode->ulBitsPerPixel >> 3) ,
lpHDE->aDriverData[ulDriverID].ulPitch ,
sQueryGCO.ulTileWidthBytes ,
sQueryGCO.ulTileHeightLines);
}
else
{
lpController->ulOffset = ulDisplayOffset;
ulViewOffset = (lpController->rtView.top *
lpHDE->aDriverData[ulDriverID].ulPitch);
ulViewOffset += lpController->rtView.left;
ulViewOffset *= (lpMode->ulBitsPerPixel >> 3);
ulViewOffset += lpHDE->aDriverData[ulDriverID].ulOffset;
}
}
// Flag to call DDLPre/PostModeChange. Should reset it after set mode call
lpController->ulFlags |= GCO_CALLDDLPPMODECHANGE;
vControllerSetMode(lpHDE,
(LPDEVMODE_INFO)&dmModesRet[i],
lpController,
lpController->ulDisplays,
ulViewOffset,
ulDisplayPitch);
// Reset DDLPre/PostModeChange flag
lpController->ulFlags &= ~GCO_CALLDDLPPMODECHANGE;
}
}
// Set the flag indicating the mode has been set on this driver
lpHDE->aDriverData[ulDriverID].ulFlags |= DRIVERDATA_ACTIVE;
if ( lpHDE->ulDrivers > 1 ) // Extended desktop case
{
// to support resume with extended desktop need to set EXT_DESKTOP_MODE bit
// in BIOS SCRATCH Register.
lpController = (LPDEVGCO) &lpHDE->aControllers[DAL_PRIMARY_CONTROLLER];
if (lpController->lpHWED->ulFunctionHooks2 & GCO_HOOK2_SETEVENT)
{
(*lpController->lpHWED->pfnGCOSetEvent)(lpController->hGCO, DAL_PRIMARY_CONTROLLER,
GCO_EVENT_ENABLEEXTDESKTOPMODE);
}
}
} else
{
// error occured in validation of the mode on one or more controllers, so
// fail the mode by returning no controllers set by the call.
ulControllers = 0;
}
for (i = 0; i < lpHDE->ulDisplaysCount; i++)
{
lpDisplay = (LPDEVGDO)&lpHDE->aDisplays[i];
if (!(lpDisplay->ulFlags & GDO_ACTIVE))
{
// since the BIOS may have turned on a display the DAL thinks is off,
// the DAL should ensure all displays it things are disabled are
// disabled [GG]
vSetDisplayOff(lpHDE, lpDisplay);
}
}
// Update BIOS with latest device selection
// We don't update connected displays as we didn't do detection
// Do not update CMOS
vUpdateBIOSDisplayInfo(lpHDE, FALSE, FALSE);
DALDEBUG((DALDBG_ENTRY_EXIT, "DALSetMode - Exit"));
return(ulControllers);
}
/******************************Public*Routine******************************\
*
* BOOL DALShareModeTable()
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -