Source code of Windows XP (NT5)
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.

420 lines
10 KiB

  1. #include <windows.h>
  2. #define _INC_VFW
  3. #define VFWAPI FAR PASCAL _loadds
  4. #include "dva.h"
  5. #include "lockbm.h"
  6. /****************************************************************************
  7. ***************************************************************************/
  8. extern BOOL vga_get_surface(HDC, int, DVASURFACEINFO FAR *);
  9. extern BOOL ati_get_surface(HDC, int, DVASURFACEINFO FAR *);
  10. extern BOOL dib_get_surface(HDC, int, DVASURFACEINFO FAR *);
  11. extern BOOL thun_get_surface(HDC,int, DVASURFACEINFO FAR *);
  12. extern BOOL vlb_get_surface(HDC, int, DVASURFACEINFO FAR *);
  13. #define GetDS() SELECTOROF((LPVOID)&ScreenSel)
  14. static short ScreenSel;
  15. static BOOL InitSurface(DVASURFACEINFO FAR *pdva);
  16. static BOOL TestSurface(DVASURFACEINFO FAR *pdva);
  17. static void SetSelLimit(UINT sel, DWORD limit);
  18. /****************************************************************************
  19. ***************************************************************************/
  20. void FAR PASCAL DVAInit()
  21. {
  22. }
  23. /****************************************************************************
  24. ***************************************************************************/
  25. void FAR PASCAL DVATerm()
  26. {
  27. //
  28. // free screen alias
  29. //
  30. if (ScreenSel)
  31. {
  32. SetSelLimit(ScreenSel, 0);
  33. FreeSelector(ScreenSel);
  34. ScreenSel = 0;
  35. }
  36. }
  37. /****************************************************************************
  38. ***************************************************************************/
  39. BOOL FAR PASCAL _loadds DVAGetSurface(HDC hdc, int nSurface, DVASURFACEINFO FAR *pdva)
  40. {
  41. int i;
  42. #ifdef USESTUPIDESCAPE
  43. i = Escape(hdc, DVAGETSURFACE,sizeof(int),(LPCSTR)&nSurface,(LPVOID)pdva);
  44. #else
  45. i = 0;
  46. #endif
  47. //
  48. // should this be a function table? list?
  49. //
  50. if (i <= 0 &&
  51. #ifdef BADDIBENGINESTUFF
  52. !dib_get_surface(hdc, nSurface, pdva) &&
  53. #endif
  54. !ati_get_surface(hdc, nSurface, pdva) &&
  55. #ifdef DEBUG
  56. !vlb_get_surface(hdc, nSurface, pdva) &&
  57. !thun_get_surface(hdc, nSurface, pdva) &&
  58. #endif
  59. !vga_get_surface(hdc, nSurface, pdva))
  60. return FALSE;
  61. return InitSurface(pdva);
  62. }
  63. #if 0
  64. /****************************************************************************
  65. ***************************************************************************/
  66. HDVA FAR PASCAL DVAOpenSurface(HDC hdc, int nSurface)
  67. {
  68. PDVA pdva;
  69. pdva = (PDVA)GlobalAllocPtr(GHND|GMEM_SHARE, sizeof(DVASURFACEINFO));
  70. if (pdva == NULL)
  71. return NULL;
  72. if (!DVAGetSurface(hdc, nSurface, pdva) ||
  73. !pdva->OpenSurface(pdva->lpSurface))
  74. {
  75. GlobalFreePtr(pdva);
  76. return NULL;
  77. }
  78. return pdva;
  79. }
  80. /****************************************************************************
  81. ***************************************************************************/
  82. void FAR PASCAL DVACloseSurface(HDVA pdva)
  83. {
  84. if (pdva == NULL)
  85. return;
  86. pdva->CloseSurface(pdva->lpSurface);
  87. GlobalFreePtr(pdva);
  88. }
  89. #endif
  90. /****************************************************************************
  91. ***************************************************************************/
  92. BOOL CALLBACK default_open_surface(LPVOID pv)
  93. {
  94. return TRUE;
  95. }
  96. /****************************************************************************
  97. ***************************************************************************/
  98. void CALLBACK default_close_surface(LPVOID pv)
  99. {
  100. }
  101. /****************************************************************************
  102. ***************************************************************************/
  103. BOOL CALLBACK default_begin_access(LPVOID pv, int x, int y, int dx, int dy)
  104. {
  105. return TRUE;
  106. }
  107. /****************************************************************************
  108. ***************************************************************************/
  109. void CALLBACK default_end_access(LPVOID pv)
  110. {
  111. }
  112. /****************************************************************************
  113. ***************************************************************************/
  114. UINT CALLBACK default_show_surface(LPVOID pv, HWND hwnd, LPRECT src, LPRECT dst)
  115. {
  116. return 1;
  117. }
  118. /****************************************************************************
  119. ***************************************************************************/
  120. static BOOL InitSurface(DVASURFACEINFO FAR *pdva)
  121. {
  122. LPBITMAPINFOHEADER lpbi;
  123. if (pdva->Version != 0x0100)
  124. return FALSE;
  125. lpbi = &pdva->BitmapInfo;
  126. if (lpbi->biSize != sizeof(BITMAPINFOHEADER))
  127. return FALSE;
  128. if (lpbi->biPlanes != 1)
  129. return FALSE;
  130. //
  131. // make the pointer a 16:16 pointer
  132. //
  133. if (pdva->offSurface >= 0x10000 &&
  134. !(pdva->Flags & DVAF_1632_ACCESS))
  135. {
  136. if (ScreenSel == NULL)
  137. ScreenSel = AllocSelector(GetDS());
  138. if (pdva->selSurface != 0)
  139. pdva->offSurface += GetSelectorBase(pdva->selSurface);
  140. SetSelectorBase(ScreenSel,pdva->offSurface);
  141. SetSelLimit(ScreenSel,lpbi->biSizeImage-1);
  142. pdva->offSurface = 0;
  143. pdva->selSurface = ScreenSel;
  144. }
  145. //
  146. // fill in defaults.
  147. //
  148. if (pdva->OpenSurface == NULL)
  149. pdva->OpenSurface = default_open_surface;
  150. if (pdva->CloseSurface == NULL)
  151. pdva->CloseSurface = default_close_surface;
  152. if (pdva->ShowSurface == NULL)
  153. pdva->ShowSurface = default_show_surface;
  154. if (pdva->BeginAccess == NULL)
  155. {
  156. pdva->BeginAccess = default_begin_access;
  157. pdva->EndAccess = default_end_access;
  158. }
  159. //
  160. // only test RGB surfaces.
  161. //
  162. if (lpbi->biCompression == 0 ||
  163. lpbi->biCompression == BI_BITFIELDS ||
  164. lpbi->biCompression == BI_1632)
  165. {
  166. if (!TestSurface(pdva))
  167. return FALSE;
  168. }
  169. //
  170. // set BI_1632 if needed
  171. //
  172. if (pdva->Flags & DVAF_1632_ACCESS)
  173. {
  174. lpbi->biCompression = BI_1632;
  175. }
  176. return TRUE;
  177. }
  178. /****************************************************************************
  179. ***************************************************************************/
  180. #pragma optimize("", off)
  181. static void SetSelLimit(UINT sel, DWORD limit)
  182. {
  183. if (limit >= 1024*1024l)
  184. limit = ((limit+4096) & ~4095) - 1;
  185. _asm
  186. {
  187. mov ax,0008h ; DPMI set limit
  188. mov bx,sel
  189. mov dx,word ptr limit[0]
  190. mov cx,word ptr limit[2]
  191. int 31h
  192. }
  193. }
  194. #pragma optimize("", on)
  195. /****************************************************************************
  196. ***************************************************************************/
  197. #define ASM66 _asm _emit 0x66 _asm
  198. #define DB _asm _emit
  199. #pragma optimize("", off)
  200. static BYTE ReadByte(PDVA pdva, LPVOID lpBits, DWORD dw)
  201. {
  202. BYTE b=42;
  203. DVABeginAccess(pdva, 0, 0, 1024, 1024);
  204. _asm {
  205. ASM66 xor bx,bx
  206. les bx,lpBits
  207. ASM66 add bx,word ptr dw
  208. mov ax,es
  209. ASM66 lsl ax,ax
  210. ASM66 cmp bx,ax
  211. ja exit
  212. DB 26h ;mov al,es:[ebx]
  213. DB 67h
  214. DB 8Ah
  215. DB 03h
  216. mov b,al
  217. exit:
  218. }
  219. DVAEndAccess(pdva);
  220. return b;
  221. }
  222. #pragma optimize("", on)
  223. /////////////////////////////////////////////////////////////////////////////
  224. //
  225. // SetPixel
  226. //
  227. // some cards cant't seam to do SetPixel right it is amazing they work at all
  228. //
  229. /////////////////////////////////////////////////////////////////////////////
  230. static void SetPixelX(HDC hdc, int x, int y, COLORREF rgb)
  231. {
  232. RECT rc;
  233. rc.left = x;
  234. rc.top = y;
  235. rc.right = x+1;
  236. rc.bottom = y+1;
  237. SetBkColor(hdc, rgb);
  238. ExtTextOut(hdc, 0, 0, ETO_OPAQUE, &rc, NULL, 0, NULL);
  239. }
  240. #define SetPixel SetPixelX
  241. /****************************************************************************
  242. ***************************************************************************/
  243. static BOOL TestSurface(DVASURFACEINFO FAR *pdva)
  244. {
  245. HDC hdc;
  246. int x,y,h,w,wb;
  247. COLORREF rgb,rgb0,rgb1,rgb2,rgb3,rgb4;
  248. DWORD dw;
  249. BYTE b0,b1;
  250. UINT uType=0;
  251. LPBITMAPINFOHEADER lpbi;
  252. LPVOID lpBits;
  253. HCURSOR hcur;
  254. if (!pdva->OpenSurface(pdva->lpSurface))
  255. return FALSE;
  256. lpbi = DVAGetSurfaceFmt(pdva);
  257. lpBits = DVAGetSurfacePtr(pdva);
  258. h = abs((int)lpbi->biHeight);
  259. w = (int)lpbi->biWidth;
  260. wb = (w * ((UINT)lpbi->biBitCount/8) + 3) & ~3;
  261. dw = (DWORD)(UINT)(h-1) * (DWORD)(UINT)wb;
  262. if ((int)lpbi->biHeight < 0)
  263. y = 0;
  264. else
  265. y = h-1;
  266. #ifdef XDEBUG
  267. x = (int)lpbi->biWidth - 5;
  268. ((LPBYTE)lpBits) += x * (UINT)lpbi->biBitCount/8;
  269. #else
  270. x = 0;
  271. #endif
  272. hcur = SetCursor(NULL);
  273. hdc = GetDC(NULL);
  274. rgb = GetPixel(hdc, x, h-1-y);
  275. SetPixel(hdc, x, h-1-y, RGB(0,0,0)); GetPixel(hdc, x, h-1-y); b0 = ReadByte(pdva, lpBits, dw);
  276. SetPixel(hdc, x, h-1-y, RGB(255,255,255)); GetPixel(hdc, x, h-1-y); b1 = ReadByte(pdva, lpBits, dw);
  277. SetPixel(hdc, x, h-1-y,rgb);
  278. if (b0 != 0x00 || b1 == 0x00)
  279. goto done;
  280. rgb0 = GetPixel(hdc, x+0, y);
  281. rgb1 = GetPixel(hdc, x+1, y);
  282. rgb2 = GetPixel(hdc, x+2, y);
  283. rgb3 = GetPixel(hdc, x+3, y);
  284. rgb4 = GetPixel(hdc, x+4, y);
  285. TestSurfaceType(hdc, x, y);
  286. DVABeginAccess(pdva, x, y, 5, 1);
  287. uType = GetSurfaceType(lpBits);
  288. DVAEndAccess(pdva);
  289. SetPixel(hdc, x+0, y,rgb0);
  290. SetPixel(hdc, x+1, y,rgb1);
  291. SetPixel(hdc, x+2, y,rgb2);
  292. SetPixel(hdc, x+3, y,rgb3);
  293. SetPixel(hdc, x+4, y,rgb4);
  294. done:
  295. ReleaseDC(NULL, hdc);
  296. SetCursor(hcur);
  297. pdva->CloseSurface(pdva->lpSurface);
  298. switch (uType)
  299. {
  300. case BM_8BIT:
  301. break;
  302. case BM_16555:
  303. ((LPDWORD)(lpbi+1))[0] = 0x007C00;
  304. ((LPDWORD)(lpbi+1))[1] = 0x0003E0;
  305. ((LPDWORD)(lpbi+1))[2] = 0x00001F;
  306. break;
  307. case BM_24BGR:
  308. case BM_32BGR:
  309. ((LPDWORD)(lpbi+1))[0] = 0xFF0000;
  310. ((LPDWORD)(lpbi+1))[1] = 0x00FF00;
  311. ((LPDWORD)(lpbi+1))[2] = 0x0000FF;
  312. break;
  313. case BM_16565:
  314. lpbi->biCompression = BI_BITFIELDS;
  315. ((LPDWORD)(lpbi+1))[0] = 0x00F800;
  316. ((LPDWORD)(lpbi+1))[1] = 0x0007E0;
  317. ((LPDWORD)(lpbi+1))[2] = 0x00001F;
  318. break;
  319. case BM_24RGB:
  320. case BM_32RGB:
  321. lpbi->biCompression = BI_BITFIELDS;
  322. ((LPDWORD)(lpbi+1))[0] = 0x0000FF;
  323. ((LPDWORD)(lpbi+1))[1] = 0x00FF00;
  324. ((LPDWORD)(lpbi+1))[2] = 0xFF0000;
  325. break;
  326. }
  327. return uType != 0;
  328. }