ReactOS Fundraising Campaign 2012
 
€ 4,410 / € 30,000

Information | Donate

Home | Info | Community | Development | myReactOS | Contact Us

  1. Home
  2. Community
  3. Development
  4. myReactOS
  5. Fundraiser 2012

  1. Main Page
  2. Alphabetical List
  3. Data Structures
  4. Directories
  5. File List
  6. Data Fields
  7. Globals
  8. Related Pages

ReactOS Development > Doxygen

d3d9_create.c
Go to the documentation of this file.
00001 /*
00002  * COPYRIGHT:       See COPYING in the top level directory
00003  * PROJECT:         ReactOS ReactX
00004  * FILE:            dll/directx/d3d9/d3d9_create.c
00005  * PURPOSE:         d3d9.dll internal create functions and data
00006  * PROGRAMERS:      Gregor Brunmar <gregor (dot) brunmar (at) home (dot) se>
00007  */
00008 
00009 #include <d3d9.h>
00010 #include "d3d9_create.h"
00011 #include "d3d9_helpers.h"
00012 #include "d3d9_caps.h"
00013 #include <debug.h>
00014 #include <ddrawi.h>
00015 #include <ddrawgdi.h>
00016 
00017 static const GUID DISPLAY_GUID = { 0x67685559, 0x3106, 0x11D0, { 0xB9, 0x71, 0x00, 0xAA, 0x00, 0x34, 0x2F, 0x9F } };
00018 
00019 static CHAR D3D9_PrimaryDeviceName[CCHDEVICENAME];
00020 
00021 static BOOL IsDirectDrawSupported()
00022 {
00023     HDC hDC;
00024     DWORD Planes;
00025     DWORD Bpp;
00026 
00027     hDC = GetDC(NULL);
00028     Planes = GetDeviceCaps(hDC, PLANES);
00029     Bpp = GetDeviceCaps(hDC, BITSPIXEL);
00030     ReleaseDC(NULL, hDC);
00031 
00032     if (Planes * Bpp < 8)
00033         return FALSE;
00034 
00035     return TRUE;
00036 }
00037 
00038 static VOID SetAdapterInfo(IN OUT LPDIRECT3D9_DISPLAYADAPTER pDisplayAdapter, IN LPDISPLAY_DEVICEA pDisplayDevice)
00039 {
00040     memcpy(&pDisplayAdapter->DisplayGuid, &DISPLAY_GUID, sizeof(GUID));
00041 
00042     lstrcpynA(pDisplayAdapter->szDeviceName, pDisplayDevice->DeviceName, MAX_PATH);
00043 
00044     pDisplayAdapter->dwStateFlags = pDisplayDevice->StateFlags;
00045     pDisplayAdapter->bInUseFlag = TRUE;
00046 }
00047 
00048 static BOOL IsGDIDriver(HDC hDC)
00049 {
00050     COLORREF NearestBlack = GetNearestColor(hDC, RGB(0, 0, 0));
00051     COLORREF NearestWhite = GetNearestColor(hDC, RGB(255, 255, 255));
00052 
00053     if (NearestBlack != RGB(0, 0, 0) || NearestWhite != RGB(255, 255, 255))
00054         return TRUE;
00055 
00056     return FALSE;
00057 }
00058 
00059 void GetDisplayAdapterFromDevice(IN OUT LPDIRECT3D9_DISPLAYADAPTER pDisplayAdapters, IN DWORD AdapterIndex, IN LPD3D9_DEVICEDATA pDeviceData)
00060 {
00061     LPDIRECT3D9_DISPLAYADAPTER pDisplayAdapter = &pDisplayAdapters[AdapterIndex];
00062     DWORD FormatOpIndex;
00063     DWORD AdapterGroupId;
00064     DWORD NumAdaptersInGroup;
00065     DWORD Index;
00066 
00067     memcpy(&pDisplayAdapter->DriverCaps, &pDeviceData->DriverCaps, sizeof(D3D9_DRIVERCAPS));
00068 
00069     for (FormatOpIndex = 0; FormatOpIndex < pDeviceData->DriverCaps.NumSupportedFormatOps; FormatOpIndex++)
00070     {
00071         LPDDSURFACEDESC pSurfaceDesc = &pDeviceData->DriverCaps.pSupportedFormatOps[FormatOpIndex];
00072         D3DFORMAT Format = pSurfaceDesc->ddpfPixelFormat.dwFourCC;
00073 
00074         if ((pSurfaceDesc->ddpfPixelFormat.dwOperations & D3DFORMAT_OP_DISPLAYMODE) != 0 &&
00075             (Format == D3DFMT_R5G6B5 || Format == D3DFMT_X1R5G5B5))
00076         {
00077             pDisplayAdapter->Supported16bitFormat = Format;
00078             break;
00079         }
00080     }
00081 
00082     NumAdaptersInGroup = 0;
00083     AdapterGroupId = pDeviceData->DriverCaps.ulUniqueAdapterGroupId;
00084     for (Index = 0; Index < AdapterIndex; Index++)
00085     {
00086         if (AdapterGroupId == pDisplayAdapters[Index].DriverCaps.ulUniqueAdapterGroupId)
00087             ++NumAdaptersInGroup;
00088     }
00089     pDisplayAdapter->MasterAdapterIndex = AdapterIndex;
00090     pDisplayAdapter->NumAdaptersInGroup = NumAdaptersInGroup + 1;   /* Add self */
00091     pDisplayAdapter->AdapterIndexInGroup = NumAdaptersInGroup;
00092 
00093     CreateDisplayModeList(
00094         pDisplayAdapter->szDeviceName,
00095         NULL,
00096         &pDisplayAdapter->NumSupportedD3DFormats,
00097         pDisplayAdapter->Supported16bitFormat,
00098         pDeviceData->pUnknown6BC
00099         );
00100 
00101     if (pDisplayAdapter->NumSupportedD3DFormats > 0)
00102     {
00103         pDisplayAdapter->pSupportedD3DFormats = HeapAlloc(GetProcessHeap(), 0, pDisplayAdapter->NumSupportedD3DFormats * sizeof(D3DDISPLAYMODE));
00104 
00105         CreateDisplayModeList(
00106             pDisplayAdapter->szDeviceName,
00107             pDisplayAdapter->pSupportedD3DFormats,
00108             &pDisplayAdapter->NumSupportedD3DFormats,
00109             pDisplayAdapter->Supported16bitFormat,
00110             pDeviceData->pUnknown6BC
00111             );
00112     }
00113 }
00114 
00115 BOOL CreateD3D9DeviceData(IN LPDIRECT3D9_DISPLAYADAPTER pDisplayAdapter, IN LPD3D9_DEVICEDATA pDeviceData)
00116 {
00117     HDC hDC;
00118 
00119     /* Test DC creation for the display device */
00120     if (NULL == (hDC = CreateDCA(NULL, pDisplayAdapter->szDeviceName, NULL, NULL)))
00121     {
00122         DPRINT1("Could not create dc for display adapter: %s", pDisplayAdapter->szDeviceName);
00123         return FALSE;
00124     }
00125 
00126     pDeviceData->hDC = hDC;
00127     pDeviceData->DisplayGuid = pDisplayAdapter->DisplayGuid;
00128     pDeviceData->DeviceType = D3DDEVTYPE_HAL;
00129     lstrcpynA(pDeviceData->szDeviceName, pDisplayAdapter->szDeviceName, CCHDEVICENAME);
00130     pDeviceData->szDeviceName[CCHDEVICENAME-1] = '\0';
00131 
00132     if (pDisplayAdapter->bInUseFlag)
00133     {
00134         pDeviceData->D3D9Callbacks.DeviceType = D3DDEVTYPE_HAL;
00135     }
00136     else if (IsGDIDriver(hDC))
00137     {
00138         pDeviceData->D3D9Callbacks.DeviceType = D3DDEVTYPE_REF;
00139     }
00140 
00141     if (FALSE == GetDeviceData(pDeviceData))
00142     {
00143         DPRINT1("Could not get device data for display adapter: %s", pDisplayAdapter->szDeviceName);
00144         return FALSE;
00145     }
00146 
00147     return TRUE;
00148 }
00149 
00150 VOID DestroyD3D9DeviceData(IN LPD3D9_DEVICEDATA pDeviceData)
00151 {
00152     DeleteDC(pDeviceData->hDC);
00153     HeapFree(GetProcessHeap(), 0, pDeviceData->pUnknown6BC);
00154 }
00155 
00156 static BOOL GetDirect3D9AdapterInfo(IN OUT LPDIRECT3D9_DISPLAYADAPTER pDisplayAdapters, IN DWORD AdapterIndex)
00157 {
00158     LPD3D9_DEVICEDATA pDeviceData;
00159     
00160     pDeviceData = HeapAlloc(GetProcessHeap(), HEAP_ZERO_MEMORY, sizeof(D3D9_DEVICEDATA));
00161     if (NULL == pDeviceData)
00162     {
00163         DPRINT1("Out of memory, could not initialize Direct3D adapter");
00164         return FALSE;
00165     }
00166 
00167     if (FALSE == CreateD3D9DeviceData(&pDisplayAdapters[AdapterIndex], pDeviceData))
00168     {
00169         DPRINT1("Could not create device data for adapter: %d", AdapterIndex);
00170         return FALSE;
00171     }
00172 
00173     GetDisplayAdapterFromDevice(pDisplayAdapters, AdapterIndex, pDeviceData);
00174 
00175     DestroyD3D9DeviceData(pDeviceData);
00176     HeapFree(GetProcessHeap(), 0, pDeviceData);
00177 
00178     return TRUE;
00179 }
00180 
00181 static BOOL GetDisplayDeviceInfo(IN OUT LPDIRECT3D9_INT pDirect3D9)
00182 {
00183     DISPLAY_DEVICEA DisplayDevice;
00184     DWORD AdapterIndex;
00185 
00186     memset(&DisplayDevice, 0, sizeof(DISPLAY_DEVICEA));
00187     DisplayDevice.cb = sizeof(DISPLAY_DEVICEA);   
00188 
00189     pDirect3D9->NumDisplayAdapters = 0;
00190     D3D9_PrimaryDeviceName[0] = '\0';
00191 
00192     AdapterIndex = 0;
00193     while (EnumDisplayDevicesA(NULL, AdapterIndex, &DisplayDevice, 0) == TRUE &&
00194            pDirect3D9->NumDisplayAdapters < D3D9_INT_MAX_NUM_ADAPTERS)
00195     {
00196         if ((DisplayDevice.StateFlags & (DISPLAY_DEVICE_DISCONNECT | DISPLAY_DEVICE_MIRRORING_DRIVER)) == 0 &&
00197             (DisplayDevice.StateFlags & (DISPLAY_DEVICE_PRIMARY_DEVICE | DISPLAY_DEVICE_ATTACHED_TO_DESKTOP)) != 0)
00198         {
00199             SetAdapterInfo(&pDirect3D9->DisplayAdapters[pDirect3D9->NumDisplayAdapters], &DisplayDevice);
00200 
00201             if (pDirect3D9->NumDisplayAdapters == 0)
00202                 lstrcpynA(D3D9_PrimaryDeviceName, DisplayDevice.DeviceName, sizeof(D3D9_PrimaryDeviceName));
00203 
00204             ++pDirect3D9->NumDisplayAdapters;
00205             break;
00206         }
00207 
00208         ++AdapterIndex;
00209     }
00210 
00211     AdapterIndex = 0;
00212     while (EnumDisplayDevicesA(NULL, AdapterIndex, &DisplayDevice, 0) == TRUE &&
00213            pDirect3D9->NumDisplayAdapters < D3D9_INT_MAX_NUM_ADAPTERS)
00214     {
00215         if ((DisplayDevice.StateFlags & DISPLAY_DEVICE_ATTACHED_TO_DESKTOP) != 0 &&
00216             (DisplayDevice.StateFlags & (DISPLAY_DEVICE_MIRRORING_DRIVER | DISPLAY_DEVICE_PRIMARY_DEVICE)) == 0)
00217         {
00218             SetAdapterInfo(&pDirect3D9->DisplayAdapters[pDirect3D9->NumDisplayAdapters], &DisplayDevice);
00219             ++pDirect3D9->NumDisplayAdapters;
00220         }
00221 
00222         ++AdapterIndex;
00223     }
00224 
00225     /* Check if minimum DirectDraw is supported */
00226     if (IsDirectDrawSupported() == FALSE)
00227         return FALSE;
00228 
00229     for (AdapterIndex = 0; AdapterIndex < pDirect3D9->NumDisplayAdapters; AdapterIndex++)
00230     {
00231         GetDirect3D9AdapterInfo(pDirect3D9->DisplayAdapters, AdapterIndex);
00232     }
00233 
00234     return TRUE;
00235 }
00236 
00237 HRESULT CreateD3D9(OUT LPDIRECT3D9 *ppDirect3D9, UINT SDKVersion)
00238 {
00239     LPDIRECT3D9_INT pDirect3D9;
00240 
00241     if (ppDirect3D9 == 0)
00242         return DDERR_INVALIDPARAMS;
00243 
00244     if (AlignedAlloc((LPVOID *)&pDirect3D9, sizeof(DIRECT3D9_INT)) != S_OK)
00245         return DDERR_OUTOFMEMORY;
00246 
00247     if (pDirect3D9 == 0)
00248         return DDERR_OUTOFMEMORY;
00249 
00250     pDirect3D9->lpVtbl = &Direct3D9_Vtbl;
00251     pDirect3D9->dwProcessId = GetCurrentThreadId();
00252     pDirect3D9->lRefCnt = 1;
00253 
00254     pDirect3D9->SDKVersion = SDKVersion;
00255 
00256     pDirect3D9->lpInt = pDirect3D9;
00257     pDirect3D9->unknown000007 = 1;
00258 
00259     InitializeCriticalSection(&pDirect3D9->d3d9_cs);
00260 
00261     if (FALSE == GetDisplayDeviceInfo(pDirect3D9))
00262     {
00263         DPRINT1("Could not create Direct3D9 object");
00264         AlignedFree(pDirect3D9);
00265         return DDERR_GENERIC;
00266     }
00267 
00268     *ppDirect3D9 = (LPDIRECT3D9)&pDirect3D9->lpVtbl;
00269 
00270     return D3D_OK;
00271 }
00272 

Generated on Sun May 27 2012 04:21:13 for ReactOS by doxygen 1.7.6.1

ReactOS is a registered trademark or a trademark of ReactOS Foundation in the United States and other countries.