You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
287 lines
8.8 KiB
287 lines
8.8 KiB
#ifndef __ENUM_HPP__
|
|
#define __ENUM_HPP__
|
|
|
|
/*==========================================================================;
|
|
*
|
|
* Copyright (C) 1999-2000 Microsoft Corporation. All Rights Reserved.
|
|
*
|
|
* File: enum.hpp
|
|
* Content: Class for the enumerator object.
|
|
*
|
|
***************************************************************************/
|
|
|
|
// HACK: this belongs elsewhere
|
|
#define DXGASSERT(x) DDASSERT(x)
|
|
|
|
#define HALFLAG_8BITHAL 0x00000001
|
|
#define HALFLAG_16BITHAL 0x00000004
|
|
#define HALFLAG_24BITHAL 0x00000010
|
|
#define HALFLAG_32BITHAL 0x00000040
|
|
class CBaseDevice;
|
|
|
|
// Base class for objects that own their own critical section
|
|
class CLockOwner
|
|
{
|
|
public:
|
|
CLockOwner() :
|
|
m_bTakeCriticalSection(FALSE),
|
|
m_punkSelf(NULL)
|
|
{
|
|
m_dwOwnerThread = ::GetCurrentThreadId();
|
|
|
|
#ifdef DEBUG
|
|
// Prepare IsValid debug helper
|
|
for (int i = 0; i < 8; i++)
|
|
{
|
|
// Set some magic numbers to check
|
|
// object validity in debug
|
|
m_dwDebugArray[i] = D3D8MagicNumber + i;
|
|
}
|
|
DXGASSERT(IsValid());
|
|
#endif // DEBUG
|
|
} // CLockOwner
|
|
|
|
~CLockOwner()
|
|
{
|
|
DXGASSERT(IsValid());
|
|
DXGASSERT(m_bTakeCriticalSection == TRUE ||
|
|
m_bTakeCriticalSection == FALSE);
|
|
if (m_bTakeCriticalSection)
|
|
{
|
|
::DeleteCriticalSection(&m_CriticalSection);
|
|
}
|
|
} // ~CLockOwner
|
|
|
|
void EnableCriticalSection()
|
|
{
|
|
DXGASSERT(m_bTakeCriticalSection == FALSE);
|
|
m_bTakeCriticalSection = TRUE;
|
|
::InitializeCriticalSection(&m_CriticalSection);
|
|
} // EnableCriticalSection()
|
|
|
|
#ifdef DEBUG
|
|
BOOL IsValid() const
|
|
{
|
|
for (int i = 0; i < 8; i++)
|
|
{
|
|
if ((INT)m_dwDebugArray[i] != D3D8MagicNumber + i)
|
|
return FALSE;
|
|
}
|
|
|
|
// If we are not locking then warn if we are
|
|
// not being called on the same thread
|
|
if (!m_bTakeCriticalSection)
|
|
{
|
|
if (!CheckThread())
|
|
{
|
|
D3D_WARN(0, "Device that was created without D3DCREATE_MULTITHREADED "
|
|
"is being used by a thread other than the creation thread.");
|
|
}
|
|
}
|
|
|
|
return TRUE;
|
|
} // IsValid
|
|
|
|
#endif // DEBUG
|
|
BOOL CheckThread() const
|
|
{
|
|
if (::GetCurrentThreadId() == m_dwOwnerThread)
|
|
{
|
|
return TRUE;
|
|
}
|
|
else
|
|
{
|
|
return FALSE;
|
|
}
|
|
} // CheckThread
|
|
|
|
|
|
// Critical Section Locking
|
|
void Lock()
|
|
{
|
|
if (m_bTakeCriticalSection)
|
|
{
|
|
DXGASSERT(m_bTakeCriticalSection == TRUE);
|
|
::EnterCriticalSection(&m_CriticalSection);
|
|
}
|
|
else
|
|
{
|
|
DXGASSERT(m_bTakeCriticalSection == FALSE);
|
|
}
|
|
DXGASSERT(IsValid());
|
|
}; // Lock
|
|
|
|
void Unlock()
|
|
{
|
|
DXGASSERT(IsValid());
|
|
if (m_bTakeCriticalSection)
|
|
{
|
|
DXGASSERT(m_bTakeCriticalSection == TRUE);
|
|
::LeaveCriticalSection(&m_CriticalSection);
|
|
}
|
|
else
|
|
{
|
|
DXGASSERT(m_bTakeCriticalSection == FALSE);
|
|
}
|
|
}; // Unlock
|
|
|
|
// Methods to help the API_ENTER_SUBOBJECT_RELEASE case
|
|
ULONG AddRefOwner()
|
|
{
|
|
DXGASSERT(m_punkSelf);
|
|
return m_punkSelf->AddRef();
|
|
} // AddRefOwner
|
|
ULONG ReleaseOwner()
|
|
{
|
|
DXGASSERT(m_punkSelf);
|
|
return m_punkSelf->Release();
|
|
} // ReleaseOwner
|
|
|
|
void SetOwner(IUnknown *punkSelf)
|
|
{
|
|
DXGASSERT(punkSelf);
|
|
m_punkSelf = punkSelf;
|
|
} // SetOwner
|
|
|
|
private:
|
|
CRITICAL_SECTION m_CriticalSection;
|
|
BOOL m_bTakeCriticalSection;
|
|
DWORD m_dwOwnerThread;
|
|
IUnknown *m_punkSelf;
|
|
|
|
#ifdef DEBUG
|
|
// Set some magic numbers to check
|
|
// object validity in debug
|
|
enum
|
|
{
|
|
D3D8MagicNumber = 0xD3D8D3D8
|
|
};
|
|
DWORD m_dwDebugArray[8];
|
|
#endif
|
|
|
|
}; // class CLockOwner
|
|
|
|
|
|
// Device Caps/Modes Enumeration Object
|
|
class CEnum : public CLockOwner, public IDirect3D8
|
|
{
|
|
public:
|
|
/*** IUnknown methods ***/
|
|
STDMETHOD(QueryInterface)(REFIID riid, LPVOID * ppvObj);
|
|
STDMETHOD_(ULONG,AddRef)();
|
|
STDMETHOD_(ULONG,Release)();
|
|
|
|
STDMETHODIMP RegisterSoftwareDevice(void * pInitFunction);
|
|
STDMETHODIMP_(UINT) GetAdapterCount();
|
|
STDMETHODIMP GetAdapterIdentifier(UINT Adapter,DWORD Flags,D3DADAPTER_IDENTIFIER8 *pIdentifier);
|
|
STDMETHODIMP_(UINT) GetAdapterModeCount(UINT Adapter);
|
|
STDMETHODIMP EnumAdapterModes(UINT iAdapter,UINT iMode,D3DDISPLAYMODE *pMode);
|
|
STDMETHODIMP CheckDeviceType(UINT Adapter,D3DDEVTYPE CheckType, D3DFORMAT AdapterFormat, D3DFORMAT BackBufferFormat, BOOL Windowed);
|
|
STDMETHODIMP CheckDeviceFormat(UINT Adapter,D3DDEVTYPE DeviceType,D3DFORMAT DisplayFormat,DWORD Usage,D3DRESOURCETYPE RType, D3DFORMAT CheckFormat);
|
|
STDMETHODIMP GetAdapterDisplayMode(UINT Adapter, D3DDISPLAYMODE* pMode);
|
|
STDMETHODIMP CheckDeviceMultiSampleType(UINT Adapter,D3DDEVTYPE DeviceType,D3DFORMAT RenderTargetFormat,BOOL Windowed,D3DMULTISAMPLE_TYPE MultiSampleType);
|
|
STDMETHODIMP CheckDepthStencilMatch(UINT Adapter, D3DDEVTYPE DeviceType, D3DFORMAT AdapterFormat, D3DFORMAT RenderTargetFormat, D3DFORMAT DepthStencilFormat);
|
|
STDMETHODIMP GetDeviceCaps(UINT iAdapter, D3DDEVTYPE DeviceType, D3DCAPS8 *pCaps);
|
|
STDMETHODIMP_(HMONITOR) GetAdapterMonitor(UINT iAdapter);
|
|
|
|
STDMETHOD(CreateDevice)(
|
|
UINT iAdapter,
|
|
D3DDEVTYPE DeviceType,
|
|
HWND hwndFocusWindow,
|
|
DWORD dwBehaviorFlags,
|
|
D3DPRESENT_PARAMETERS *pPresentationParams,
|
|
IDirect3DDevice8 **ppDevice);
|
|
|
|
// Public constructor for Direct3DCreate8 to call
|
|
CEnum(UINT AppSdkVersion);
|
|
|
|
D3DDISPLAYMODE* GetModeTable(UINT iAdapter) const
|
|
{
|
|
return m_AdapterInfo[iAdapter].pModeTable;
|
|
}
|
|
|
|
const DWORD GetNumModes(UINT iAdapter) const
|
|
{
|
|
return m_AdapterInfo[iAdapter].NumModes;
|
|
}
|
|
|
|
const BOOL NoDDrawSupport(UINT iAdapter) const
|
|
{
|
|
return m_AdapterInfo[iAdapter].bNoDDrawSupport;
|
|
}
|
|
void FillInCaps(D3DCAPS8 *pCaps,
|
|
const D3D8_DRIVERCAPS *pDriverCaps,
|
|
D3DDEVTYPE Type,
|
|
UINT AdapterOrdinal) const;
|
|
|
|
D3DFORMAT MapDepthStencilFormat(UINT iAdapter,
|
|
D3DDEVTYPE Type,
|
|
D3DFORMAT Format) const;
|
|
|
|
D3DFORMAT GetUnknown16(UINT iAdapter)
|
|
{
|
|
return m_AdapterInfo[iAdapter].Unknown16;
|
|
}
|
|
|
|
DDSURFACEDESC* GetHalOpList(UINT iAdapter)
|
|
{
|
|
return m_AdapterInfo[iAdapter].HALCaps.pGDD8SupportedFormatOps;
|
|
}
|
|
|
|
DWORD GetNumHalOps(UINT iAdapter)
|
|
{
|
|
return m_AdapterInfo[iAdapter].HALCaps.GDD8NumSupportedFormatOps;
|
|
}
|
|
|
|
#ifdef WINNT
|
|
void SetFullScreenDevice(UINT iAdapter,
|
|
CBaseDevice *pDevice);
|
|
|
|
HWND ExclusiveOwnerWindow();
|
|
BOOL CheckExclusiveMode(
|
|
CBaseDevice* pDevice,
|
|
LPBOOL pbThisDeviceOwnsExclusive,
|
|
BOOL bKeepMutex);
|
|
void DoneExclusiveMode();
|
|
void StartExclusiveMode();
|
|
#endif // WINNT
|
|
|
|
// Gamma calibrator is owned by the enumerator
|
|
void LoadAndCallGammaCalibrator(
|
|
D3DGAMMARAMP *pRamp,
|
|
UCHAR * pDeviceName);
|
|
|
|
void GetRefCaps(UINT iAdapter);
|
|
void GetSwCaps(UINT iAdapter);
|
|
|
|
void * GetInitFunction() const
|
|
{
|
|
return m_pSwInitFunction;
|
|
}
|
|
UINT GetAppSdkVersion() {return m_AppSdkVersion;}
|
|
|
|
private:
|
|
|
|
HRESULT GetAdapterCaps(UINT iAdapter,
|
|
D3DDEVTYPE Type,
|
|
D3D8_DRIVERCAPS** ppCaps);
|
|
|
|
DWORD m_cRef;
|
|
UINT m_cAdapter;
|
|
ADAPTERINFO m_AdapterInfo[MAX_DX8_ADAPTERS];
|
|
CBaseDevice *m_pFullScreenDevice[MAX_DX8_ADAPTERS];
|
|
D3D8_DRIVERCAPS m_REFCaps[MAX_DX8_ADAPTERS];
|
|
D3D8_DRIVERCAPS m_SwCaps[MAX_DX8_ADAPTERS];
|
|
VOID* m_pSwInitFunction;
|
|
BOOL m_bDisableHAL;
|
|
BOOL m_bHasExclusive;
|
|
HINSTANCE m_hGammaCalibrator;
|
|
LPDDGAMMACALIBRATORPROC m_pGammaCalibratorProc;
|
|
BOOL m_bAttemptedGammaCalibrator;
|
|
BOOL m_bGammaCalibratorExists;
|
|
UCHAR m_szGammaCalibrator[MAX_PATH];
|
|
UINT m_AppSdkVersion;
|
|
|
|
}; // class CEnum
|
|
|
|
#endif // __ENUM_HPP__
|