Leaked source code of windows server 2003
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.

432 lines
11 KiB

  1. /*==========================================================================
  2. *
  3. * Copyright (C) 1995 Microsoft Corporation. All Rights Reserved.
  4. *
  5. * File: ddfake.c
  6. * Content: fake out that we are a driver (for HEL)
  7. * History:
  8. * Date By Reason
  9. * ==== == ======
  10. * 06-mar-95 craige initial implementation
  11. * 01-apr-95 craige happy fun joy updated header file
  12. * 30-jun-95 craige turned off > 16bpp
  13. * 04-jul-95 craige YEEHAW: new driver struct
  14. * 15-jul-95 craige set DDCAPS_NOHARDWARE
  15. * 20-jul-95 craige internal reorg to prevent thunking during modeset
  16. * 22-jul-95 craige emulation only needs to initialize correctly
  17. * 19-dec-95 jeffno Counting number of modes in BuildModes fails if only 1 mode available\
  18. * 09-jan-96 kylej re-enable > 16bpp modes
  19. * 13-mar-96 jeffno Buildmodes not called under NT. Fix a >16bpp problem.
  20. * 19-apr-96 colinmc Bug 18059: New driver caps bit to indicate that a
  21. * driver can't interleave 2D and 3D operations in a
  22. * 3D scene
  23. * 12-oct-96 colinmc Improvements to Win16 locking code to reduce virtual
  24. * memory usage
  25. * 15-oct-96 toddla multimonitor support
  26. * 17-jan-97 colinmc Fixed problem with multimonitor on emulated displays
  27. *
  28. ***************************************************************************/
  29. #include "ddrawpr.h"
  30. static DWORD ropsSupported[DD_ROP_SPACE] = {
  31. 0,
  32. 0,
  33. 0,
  34. 0,
  35. 0,
  36. 0,
  37. 0,
  38. 0
  39. };
  40. /*
  41. * getBitMask
  42. */
  43. BOOL getBitMask( LPDDHALMODEINFO pmi )
  44. {
  45. pmi->wFlags = 0;
  46. if( pmi->dwBPP == 8 )
  47. {
  48. pmi->wFlags |= DDMODEINFO_PALETTIZED;
  49. }
  50. switch( pmi->dwBPP )
  51. {
  52. case 8:
  53. pmi->dwRBitMask = 0;
  54. pmi->dwGBitMask = 0;
  55. pmi->dwBBitMask = 0;
  56. break;
  57. case 16:
  58. pmi->dwRBitMask = 0xf800;
  59. pmi->dwGBitMask = 0x07e0;
  60. pmi->dwBBitMask = 0x001f;
  61. break;
  62. case 24:
  63. pmi->dwRBitMask = 0xff0000;
  64. pmi->dwGBitMask = 0x00ff00;
  65. pmi->dwBBitMask = 0x0000ff;
  66. break;
  67. case 32:
  68. pmi->dwRBitMask = 0xff0000;
  69. pmi->dwGBitMask = 0x00ff00;
  70. pmi->dwBBitMask = 0x0000ff;
  71. break;
  72. default:
  73. return FALSE;
  74. }
  75. return TRUE;
  76. } /* getBitMask */
  77. /*
  78. * getDisplayMode
  79. *
  80. * get the current display settings
  81. */
  82. static BOOL getDisplayMode( HDC hdc, LPDDHALMODEINFO pmi, DWORD FAR *pfreq )
  83. {
  84. if( hdc != NULL )
  85. {
  86. pmi->dwBPP = GetDeviceCaps( hdc, BITSPIXEL ) * GetDeviceCaps( hdc, PLANES );
  87. *pfreq = GetDeviceCaps( hdc, VREFRESH );
  88. pmi->dwWidth = GetDeviceCaps( hdc, HORZRES );
  89. pmi->dwHeight = GetDeviceCaps( hdc, VERTRES );
  90. pmi->lPitch = GetDeviceCaps( hdc, DESKTOPHORZRES );
  91. DPF( 5, "getDisplayMode:" );
  92. DPF( 5, " bpp=%ld, refresh=%ld", pmi->dwBPP, *pfreq );
  93. DPF( 5, " dwHeight=%ld, dwWidth=%ld", pmi->dwHeight, pmi->dwWidth );
  94. DPF( 5, " lStride=%ld", pmi->lPitch );
  95. getBitMask( pmi );
  96. }
  97. else
  98. {
  99. return FALSE;
  100. }
  101. return TRUE ;
  102. } /* getDisplayMode */
  103. /*
  104. * BuildModes
  105. *
  106. * build a HAL mode info array by using EnumDisplaySettings
  107. */
  108. DWORD BuildModes( LPSTR szDevice, LPDDHALMODEINFO FAR *ppddhmi )
  109. {
  110. DWORD nummodes;
  111. DWORD maxmodes;
  112. DWORD cmode;
  113. DEVMODE dm0;
  114. DEVMODE dm;
  115. LPDDHALMODEINFO pmi;
  116. ZeroMemory(&dm0,sizeof(dm0));
  117. ZeroMemory(&dm,sizeof(dm));
  118. dm0.dmSize = dm.dmSize = sizeof(dm0);
  119. /*
  120. * count the number of modes
  121. */
  122. nummodes = 0;
  123. cmode = 0;
  124. while( 1 )
  125. {
  126. if( cmode == 0 )
  127. {
  128. if( !EnumDisplaySettings( szDevice, cmode, &dm0 ) )
  129. {
  130. break;
  131. }
  132. }
  133. else
  134. {
  135. if( !EnumDisplaySettings( szDevice, cmode, &dm ) )
  136. {
  137. break;
  138. }
  139. }
  140. cmode++;
  141. if( cmode==1 ? dm0.dmBitsPerPel >= 8 : dm.dmBitsPerPel >= 8 ) //was incorrectly counting when only 1 mode.
  142. {
  143. nummodes++;
  144. }
  145. }
  146. DPF( 5, "Driver says nummodes=%d", nummodes );
  147. if( nummodes == 0 )
  148. {
  149. *ppddhmi = NULL;
  150. return 0;
  151. }
  152. /*
  153. * allocate some memory to hold all the mode data
  154. */
  155. pmi = MemAlloc( nummodes * sizeof( DDHALMODEINFO ) );
  156. if( pmi == NULL )
  157. {
  158. *ppddhmi = NULL;
  159. return 0;
  160. }
  161. /*
  162. * go get the mode data
  163. */
  164. cmode = 0;
  165. maxmodes = nummodes;
  166. nummodes = 0;
  167. while( 1 )
  168. {
  169. if (nummodes >= maxmodes)
  170. {
  171. break;
  172. }
  173. if( cmode == 0 )
  174. {
  175. dm = dm0;
  176. }
  177. else
  178. {
  179. if( !EnumDisplaySettings( szDevice, cmode, &dm ) )
  180. {
  181. break;
  182. }
  183. }
  184. cmode++;
  185. /*
  186. * don't care about 4bpp or 1bpp modes...
  187. */
  188. if( dm.dmBitsPerPel < 8 )
  189. {
  190. continue;
  191. }
  192. pmi[nummodes].dwWidth = dm.dmPelsWidth;
  193. pmi[nummodes].dwHeight = dm.dmPelsHeight;
  194. pmi[nummodes].lPitch = dm.dmPelsWidth;
  195. pmi[nummodes].dwBPP = dm.dmBitsPerPel;
  196. pmi[nummodes].dwAlphaBitMask = 0;
  197. getBitMask( &pmi[nummodes] );
  198. nummodes++;
  199. }
  200. DPF( 5, "Enum Display Settings says nummodes=%d", nummodes );
  201. *ppddhmi = pmi;
  202. return nummodes;
  203. } /* BuildModes */
  204. /*
  205. * BuildPixelFormat
  206. *
  207. * generate a pixel format structure based on the mode
  208. */
  209. void BuildPixelFormat(
  210. HDC hdc,
  211. LPDDHALMODEINFO pmi,
  212. LPDDPIXELFORMAT pdpf )
  213. {
  214. HBITMAP hbm;
  215. BITMAPINFO *pbmi;
  216. pdpf->dwSize = sizeof( DDPIXELFORMAT );
  217. pdpf->dwYUVBitCount = 0;
  218. pdpf->dwYBitMask = 0;
  219. pdpf->dwUBitMask = 0;
  220. pdpf->dwVBitMask = 0;
  221. pdpf->dwYUVAlphaBitMask = 0;
  222. pdpf->dwFourCC = 0;
  223. pdpf->dwFlags = DDPF_RGB;
  224. if( pmi->wFlags & DDMODEINFO_PALETTIZED )
  225. {
  226. pdpf->dwFlags |= DDPF_PALETTEINDEXED8;
  227. }
  228. pdpf->dwRGBBitCount = pmi->dwBPP;
  229. /*
  230. * This looks suspiciously like it was intended to run on 8 or 16 bpp
  231. * and nothing else. I changed it so we do this for 24 and 32 bpp
  232. * modes as well. jeffno 960610
  233. */
  234. if( pmi->dwBPP != 8 && hdc)
  235. {
  236. pbmi = (BITMAPINFO *)MemAlloc( sizeof( BITMAPINFOHEADER ) + 256 * 4 );
  237. if( pbmi )
  238. {
  239. hbm = CreateCompatibleBitmap(hdc, 1, 1);
  240. if (hbm == NULL)
  241. {
  242. DPF( 0, "CreateCompatibleBitmap failed; unable to build pixel format");
  243. }
  244. else
  245. {
  246. pbmi->bmiHeader.biSize = sizeof(BITMAPINFOHEADER);
  247. pbmi->bmiHeader.biBitCount = 0;
  248. GetDIBits(hdc, hbm, 0, 1, NULL, pbmi, DIB_RGB_COLORS);
  249. pbmi->bmiHeader.biClrUsed = 0;
  250. pbmi->bmiHeader.biCompression = BI_BITFIELDS;
  251. GetDIBits(hdc, hbm, 0, 1, NULL, pbmi, DIB_RGB_COLORS);
  252. pmi->dwRBitMask = *(long*)&(pbmi->bmiColors[0]);
  253. pmi->dwGBitMask = *(long*)&(pbmi->bmiColors[1]);
  254. pmi->dwBBitMask = *(long*)&(pbmi->bmiColors[2]);
  255. DeleteObject( hbm );
  256. }
  257. MemFree( pbmi );
  258. }
  259. }
  260. pdpf->dwRBitMask = pmi->dwRBitMask;
  261. pdpf->dwGBitMask = pmi->dwGBitMask;
  262. pdpf->dwBBitMask = pmi->dwBBitMask;
  263. pdpf->dwRGBAlphaBitMask = pmi->dwAlphaBitMask = 0;
  264. DPF(5, "Masks for current mode are: %08x %08x %08x", pdpf->dwRBitMask, pdpf->dwGBitMask, pdpf->dwBBitMask);
  265. } /* BuildPixelFormat */
  266. /*
  267. * FakeDDCreateDriverObject
  268. *
  269. * fake up that we are a driver that can't do anything...
  270. */
  271. LPDDRAWI_DIRECTDRAW_GBL FakeDDCreateDriverObject(
  272. HDC hdc_dd,
  273. LPSTR szDrvName,
  274. LPDDRAWI_DIRECTDRAW_GBL pdd_old,
  275. BOOL reset,
  276. HANDLE hDDVxd )
  277. {
  278. DDHALINFO ddhi;
  279. LPDDRAWI_DIRECTDRAW_GBL pdd;
  280. DDPIXELFORMAT dpf;
  281. LPDDHALMODEINFO pmi;
  282. DDHALMODEINFO cmodeinfo;
  283. DWORD freq;
  284. LPSTR szDevice;
  285. if( (szDrvName != NULL) && (_stricmp(szDrvName, "DISPLAY") != 0) )
  286. szDevice = szDrvName;
  287. else
  288. szDevice = NULL;
  289. /*
  290. * initialize the DDHALINFO struct
  291. */
  292. memset( &ddhi, 0, sizeof( ddhi ) );
  293. ddhi.dwSize = sizeof( ddhi );
  294. /*
  295. * capabilities supported (none)
  296. */
  297. ddhi.ddCaps.dwCaps = DDCAPS_NOHARDWARE;
  298. ddhi.ddCaps.dwCaps2 = 0;
  299. ddhi.ddCaps.dwFXCaps = 0;
  300. ddhi.ddCaps.dwCKeyCaps = 0;
  301. ddhi.ddCaps.ddsCaps.dwCaps = 0;
  302. /*
  303. * pointer to primary surface
  304. */
  305. ddhi.vmiData.fpPrimary = 0;
  306. /*
  307. * build mode and pixel format info
  308. */
  309. pmi = &cmodeinfo;
  310. if( !getDisplayMode( hdc_dd, pmi, &freq ) )
  311. {
  312. DPF( 0, "Could not get base mode" );
  313. return NULL;
  314. }
  315. #if WIN95
  316. {
  317. int i;
  318. ddhi.dwNumModes = BuildModes( szDevice, &ddhi.lpModeInfo );
  319. ddhi.dwModeIndex = (DWORD)-1;
  320. for( i=0;i<(int)ddhi.dwNumModes;i++ )
  321. {
  322. if( (ddhi.lpModeInfo[i].dwBPP == pmi->dwBPP) &&
  323. (ddhi.lpModeInfo[i].dwHeight == pmi->dwHeight) &&
  324. (ddhi.lpModeInfo[i].dwWidth == pmi->dwWidth) )
  325. {
  326. ddhi.dwModeIndex = i;
  327. DPF( 5, "dwModeIndex = %d", i );
  328. break;
  329. }
  330. }
  331. }
  332. #else
  333. {
  334. if (!GetCurrentMode(pdd_old, &ddhi, szDrvName))
  335. {
  336. DPF(0, "Could not get current mode information");
  337. return NULL;
  338. }
  339. }
  340. #endif
  341. ddhi.vmiData.dwDisplayHeight = pmi->dwHeight;
  342. ddhi.vmiData.dwDisplayWidth = pmi->dwWidth;
  343. ddhi.vmiData.lDisplayPitch = pmi->lPitch;
  344. /*
  345. * set up pixel format of primary surface
  346. */
  347. BuildPixelFormat( hdc_dd, pmi, &dpf );
  348. ddhi.vmiData.ddpfDisplay = dpf;
  349. /*
  350. * fourcc code information
  351. */
  352. ddhi.ddCaps.dwNumFourCCCodes = 0;
  353. ddhi.lpdwFourCC = NULL;
  354. /*
  355. * Fill in heap info
  356. */
  357. ddhi.vmiData.dwNumHeaps = 0;
  358. ddhi.vmiData.pvmList = NULL;
  359. /*
  360. * required alignments of the scanlines of each kind of memory
  361. * (DWORD is the MINIMUM)
  362. */
  363. ddhi.vmiData.dwOffscreenAlign = sizeof( DWORD );
  364. ddhi.vmiData.dwOverlayAlign = sizeof( DWORD );
  365. ddhi.vmiData.dwTextureAlign = sizeof( DWORD );
  366. ddhi.vmiData.dwAlphaAlign = sizeof( DWORD );
  367. ddhi.vmiData.dwZBufferAlign = sizeof( DWORD );
  368. /*
  369. * callback functions
  370. */
  371. ddhi.lpDDCallbacks = NULL;
  372. ddhi.lpDDSurfaceCallbacks = NULL;
  373. ddhi.lpDDPaletteCallbacks = NULL;
  374. /*
  375. * create the driver object
  376. */
  377. pdd = DirectDrawObjectCreate( &ddhi, reset, pdd_old, hDDVxd, szDrvName, 0, 0 /* ATTENTION: No lcl flags in emulation */ );
  378. if( pdd != NULL )
  379. {
  380. pdd->dwFlags |= DDRAWI_NOHARDWARE;
  381. pdd->dwFlags |= DDRAWI_DISPLAYDRV;
  382. pdd->dwFlags |= DDRAWI_GDIDRV;
  383. lstrcpy(pdd->cDriverName, szDrvName);
  384. /*
  385. * get mode info from HEL
  386. */
  387. {
  388. void UpdateDirectDrawMode( LPDDRAWI_DIRECTDRAW_GBL this );
  389. UpdateDirectDrawMode( pdd );
  390. }
  391. }
  392. MemFree( ddhi.lpModeInfo );
  393. return pdd;
  394. } /* FakeDDCreateDriverObject */