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.

2586 lines
77 KiB

  1. /*++
  2. *
  3. * WOW v1.0
  4. *
  5. * Copyright (c) 1991, Microsoft Corporation
  6. *
  7. * WUSER.C
  8. * WOW32 16-bit User API support
  9. *
  10. * History:
  11. * Created 07-Mar-1991 by Jeff Parsons (jeffpar)
  12. --*/
  13. #define OEMRESOURCE
  14. #include "precomp.h"
  15. #pragma hdrstop
  16. MODNAME(wuser.c);
  17. extern HANDLE hmodWOW32;
  18. /*++
  19. HDC BeginPaint(<hwnd>, <lpPaint>)
  20. HWND <hwnd>;
  21. LPPAINTSTRUCT <lpPaint>;
  22. The %BeginPaint% function prepares the given window for painting and fills
  23. the paint structure pointed to by the <lpPaint> parameter with information
  24. about the painting.
  25. The paint structure contains a handle to the device context for the window,
  26. a %RECT% structure that contains the smallest rectangle that completely
  27. encloses the update region, and a flag that specifies whether or not the
  28. background has been erased.
  29. The %BeginPaint% function automatically sets the clipping region of the
  30. device context to exclude any area outside the update region. The update
  31. region is set by the %InvalidateRect% or %InvalidateRgn% functions and by
  32. the system after sizing, moving, creating, scrolling, or any other operation
  33. that affects the client area. If the update region is marked for erasing,
  34. %BeginPaint% sends a WM_ERASEBKGND message to the window.
  35. An application should not call the %BeginPaint% function except in response
  36. to a WM_PAINT message. Each %BeginPaint% call must have a matching call to
  37. the %EndPaint% function.
  38. <hwnd>
  39. Identifies the window to be repainted.
  40. <lpPaint>
  41. Points to the %PAINTSTRUCT% structure that is to receive painting
  42. information, such as the device context for the window and the update
  43. rectangle.
  44. The return value identifies the device context for the specified window.
  45. If the caret is in the area to be painted, the %BeginPaint% function
  46. automatically hides the caret to prevent it from being erased.
  47. --*/
  48. ULONG FASTCALL WU32BeginPaint(PVDMFRAME pFrame)
  49. {
  50. ULONG ul;
  51. PAINTSTRUCT t2;
  52. register PBEGINPAINT16 parg16;
  53. VPVOID vpPaint;
  54. GETARGPTR(pFrame, sizeof(BEGINPAINT16), parg16);
  55. vpPaint = parg16->vpPaint;
  56. ul = GETHDC16(BeginPaint(
  57. HWND32(parg16->hwnd),
  58. &t2
  59. ));
  60. putpaintstruct16(vpPaint, &t2);
  61. W32FixPaintRect (vpPaint, &t2);
  62. FREEARGPTR(parg16);
  63. RETURN(ul);
  64. }
  65. /*++
  66. HICON CreateIcon(<hInstance>, <nWidth>, <nHeight>, <nPlanes>,
  67. <nBitsPixel>, <lpANDbits>, <lpXORbits>)
  68. HANDLE <hInstance>;
  69. int <nWidth>;
  70. int <nHeight>;
  71. BYTE <nPlanes>;
  72. BYTE <nBitsPixel>;
  73. LPSTR <lpANDbits>;
  74. LPSTR <lpXORbits>;
  75. This function creates an icon that has specified width, height, colors, and
  76. bit patterns.
  77. <hInstance>
  78. Identifies an instance of the module creating the icon.
  79. <nWidth>
  80. Specifies the width in pixels of the icon.
  81. <nHeight>
  82. Specifies the height in pixels of the icon.
  83. <nPlanes>
  84. Specifies the number of planes in the XOR mask of the icon.
  85. <nBitsPixel>
  86. Specifies the number of bits per pixel in the XOR mask of the icon.
  87. <lpANDbits>
  88. Points to an array of bytes that contains the bit values for the AND
  89. mask of the icon. This array must specify a monochrome mask.
  90. <lpXORbits>
  91. Points to an array of bytes that contains the bit values for the XOR
  92. mask of the icon. This can be the bits of a monochrome or
  93. device-dependent color bitmap.
  94. The return value identifies an icon if the function is successful.
  95. Otherwise, it is NULL.
  96. --*/
  97. ULONG FASTCALL WU32CreateIcon(PVDMFRAME pFrame)
  98. {
  99. ULONG ul;
  100. register PCREATEICON16 parg16;
  101. int nWidth;
  102. int nHeight;
  103. BYTE nPlanes;
  104. BYTE nBitsPixel;
  105. DWORD nBytesAND;
  106. DWORD nBytesXOR;
  107. LPBYTE lpBitsAND;
  108. LPBYTE lpBitsXOR;
  109. int ScanLen16;
  110. HANDLE h32;
  111. HAND16 h16;
  112. HAND16 hInst16;
  113. GETARGPTR(pFrame, sizeof(CREATEICON16), parg16);
  114. hInst16 = parg16->f1;
  115. nWidth = INT32(parg16->f2);
  116. nHeight = INT32(parg16->f3);
  117. /*
  118. ** Convert the AND mask bits
  119. */
  120. nPlanes = 1; /* MONOCHROME BITMAP */
  121. nBitsPixel = 1; /* MONOCHROME BITMAP */
  122. ScanLen16 = (((nWidth*nBitsPixel)+15)/16) * 2 ; // bytes/scan in 16 bit world
  123. nBytesAND = ScanLen16*nHeight*nPlanes;
  124. GETVDMPTR(parg16->f6, nBytesAND, lpBitsAND);
  125. /*
  126. ** Convert the XOR mask bits
  127. */
  128. nPlanes = BYTE32(parg16->f4);
  129. nBitsPixel = BYTE32(parg16->f5);
  130. ScanLen16 = (((nWidth*nBitsPixel)+15)/16) * 2 ; // bytes/scan in 16 bit world
  131. nBytesXOR = ScanLen16*nHeight*nPlanes;
  132. GETVDMPTR(parg16->f7, nBytesXOR, lpBitsXOR);
  133. h32 = (HANDLE)CreateIcon(HMODINST32(hInst16),
  134. nWidth,
  135. nHeight,
  136. nPlanes,
  137. nBitsPixel,
  138. lpBitsAND,
  139. lpBitsXOR);
  140. if (h32) {
  141. h16 = (HAND16)W32Create16BitCursorIcon(hInst16,
  142. nWidth/2, nHeight/2,
  143. nWidth, nHeight, nPlanes, nBitsPixel,
  144. lpBitsAND, lpBitsXOR,
  145. nBytesAND, nBytesXOR);
  146. ul = SetupCursorIconAlias(hInst16, h32, h16,
  147. HANDLE_TYPE_ICON, NULL, (WORD)NULL);
  148. } else {
  149. ul = 0;
  150. }
  151. FREEPSZPTR(lpBitsAND);
  152. FREEPSZPTR(lpBitsXOR);
  153. FREEARGPTR(parg16);
  154. RETURN(ul);
  155. }
  156. /*++
  157. BOOL DestroyIcon(<hIcon>)
  158. HICON <hIcon>;
  159. This function destroys an icon that was previously created by the
  160. %CreateIcon% function and frees any memory that the icon occupied. It should
  161. not be used to destroy any icon that was not created with the %CreateIcon%
  162. function.
  163. <hIcon>
  164. Identifies the icon to be destroyed. The icon must not be in current
  165. use.
  166. The return value is TRUE if the function was successful. It is FALSE if
  167. the function failed.
  168. --*/
  169. ULONG FASTCALL WU32DestroyIcon(PVDMFRAME pFrame)
  170. {
  171. ULONG ul;
  172. register PDESTROYICON16 parg16;
  173. GETARGPTR(pFrame, sizeof(DESTROYICON16), parg16);
  174. if (ul = GETBOOL16(DestroyIcon(HICON32(parg16->f1))))
  175. FREEHICON16(parg16->f1);
  176. FREEARGPTR(parg16);
  177. RETURN(ul);
  178. }
  179. ULONG FASTCALL WU32DragDetect(PVDMFRAME pFrame)
  180. {
  181. ULONG ul;
  182. POINT pt;
  183. register PDRAGDETECT16 parg16;
  184. GETARGPTR(pFrame, sizeof(*parg16), parg16);
  185. COPYPOINT16(parg16->pt, pt);
  186. ul = (ULONG) DragDetect(
  187. HWND32(parg16->hwnd),
  188. pt
  189. );
  190. FREEARGPTR(parg16);
  191. RETURN(ul);
  192. }
  193. /*++
  194. void DrawFocusRect(<hDC>, <lpRect>)
  195. HDC <hDC>;
  196. LPRECT <lpRect>;
  197. The %DrawFocusRect% function draws a rectangle in the style used to indicate
  198. focus.
  199. <hDC>
  200. Identifies the device context.
  201. <lpRect>
  202. Points to a %RECT% structure that specifies the
  203. coordinates of the rectangle to be drawn.
  204. This function does not return a value.
  205. Since this is an XOR function, calling this function a second time with the
  206. same rectangle removes the rectangle from the display.
  207. The rectangle drawn by this function cannot be scrolled. To scroll an area
  208. containing a rectangle drawn by this function, call %DrawFocusRect% to
  209. remove the rectangle from the display, scroll the area, and then call
  210. %DrawFocusRect% to draw the rectangle in the new position.
  211. --*/
  212. ULONG FASTCALL WU32DrawFocusRect(PVDMFRAME pFrame)
  213. {
  214. RECT t2;
  215. register PDRAWFOCUSRECT16 parg16;
  216. GETARGPTR(pFrame, sizeof(DRAWFOCUSRECT16), parg16);
  217. WOW32VERIFY(GETRECT16(parg16->f2, &t2));
  218. DrawFocusRect(
  219. HDC32(parg16->f1),
  220. &t2
  221. );
  222. FREEARGPTR(parg16);
  223. RETURN(0);
  224. }
  225. /*++
  226. int DrawText(<hDC>, <lpString>, <nCount>, <lpRect>, <wFormat>)
  227. HDC <hDC>;
  228. LPSTR <lpString>;
  229. int <nCount>;
  230. LPRECT <lpRect>;
  231. WORD <wFormat>;
  232. The %DrawText% function draws formatted text in the rectangle specified by
  233. the <lpRect> parameter. It formats text by expanding tabs into appropriate
  234. spaces, justifying text to the left, right, or center of the given
  235. rectangle, and breaking text into lines that fit within the given
  236. rectangle. The type of formatting is specified by the <wFormat> parameter.
  237. The %DrawText% function uses the device context's selected font, text color,
  238. and background color to draw the text. Unless the DT_NOCLIP format is used,
  239. %DrawText% clips the text so that the text does not appear outside the given
  240. rectangle. All formatting is assumed to have multiple lines unless the
  241. DT_SINGLELINE format is given.
  242. <hDC>
  243. Identifies the device context.
  244. <lpString>
  245. Points to the string to be drawn. If the <nCount> parameter is -1, the
  246. string must be null-terminated.
  247. <nCount>
  248. Specifies the number of bytes in the string. If <nCount> is -1,
  249. then <lpString> is assumed to be a long pointer to a null-terminated
  250. string and %DrawText% computes the character count automatically.
  251. <lpRect>
  252. Points to a %RECT% structure that contains the rectangle
  253. (in logical coordinates) in which the text is to be formatted.
  254. <wFormat>
  255. Specifies the method of formatting the text. It can be any
  256. combination of the following values:
  257. DT_BOTTOM
  258. Specifies bottom-justified text. This value must be combined with
  259. DT_SINGLELINE.
  260. DT_CALCRECT
  261. Determines the width and height of the rectangle. If there are multiple
  262. lines of text, %DrawText% will use the width of the rectangle pointed to
  263. by the <lpRect> parameter and extend the base of the rectangle to bound
  264. the last line of text. If there is only one line of text, %DrawText%
  265. will modify the right side of the rectangle so that it bounds the last
  266. character in the line. In either case, %DrawText% returns the height of
  267. the formatted text but does not draw the text.
  268. DT_CENTER
  269. Centers text horizontally.
  270. DT_EXPANDTABS
  271. Expands tab characters. The default number of characters per tab is
  272. eight.
  273. DT_EXTERNALLEADING
  274. Includes the font external leading in line height. Normally, external
  275. leading is not included in the height of a line of text.
  276. DT_LEFT
  277. Aligns text flush-left.
  278. DT_NOCLIP
  279. Draws without clipping. %DrawText% is somewhat faster when DT_NOCLIP is
  280. used.
  281. DT_NOPREFIX
  282. Turns off processing of prefix characters. Normally, %DrawText%
  283. interprets the mnemonic-prefix character & as a directive to
  284. underscore the character that follows, and the mnemonic-prefix
  285. characters && as a directive to print a single &. By specifying
  286. DT_NOPREFIX, this processing is turned off.
  287. DT_RIGHT
  288. Aligns text flush-right.
  289. DT_SINGLELINE
  290. Specifies single line only. Carriage returns and linefeeds do not break
  291. the line.
  292. DT_TABSTOP
  293. Sets tab stops. The high-order byte of the <wFormat> parameter is the
  294. number of characters for each tab. The default number of characters per
  295. tab is eight.
  296. DT_TOP
  297. Specifies top-justified text (single line only).
  298. DT_VCENTER
  299. Specifies vertically centered text (single line only).
  300. DT_WORDBREAK
  301. Specifies word breaking. Lines are automatically broken between words if
  302. a word would extend past the edge of the rectangle specified by the
  303. <lpRect> parameter. A carriage return/line sequence will also break the
  304. line.
  305. Note that the DT_CALCRECT, DT_EXTERNALLEADING, DT_INTERNAL, DT_NOCLIP,
  306. and DT_NOPREFIX values cannot be used with the DT_TABSTOP value:
  307. The return value specifies the height of the text.
  308. If the selected font is too large for the specified rectangle, the
  309. %DrawText% function does not attempt to substitute a smaller font.
  310. --*/
  311. ULONG FASTCALL WU32DrawText(PVDMFRAME pFrame)
  312. {
  313. ULONG ul;
  314. PSTR pstr2;
  315. RECT t4;
  316. register PDRAWTEXT16 parg16;
  317. GETARGPTR(pFrame, sizeof(DRAWTEXT16), parg16);
  318. GETVARSTRPTR(parg16->vpString, INT32(parg16->nCount), pstr2);
  319. WOW32VERIFY(GETRECT16(parg16->vpRect, &t4));
  320. ul = GETINT16(DrawText(
  321. HDC32(parg16->hdc),
  322. pstr2,
  323. INT32(parg16->nCount),
  324. &t4,
  325. WORD32(parg16->wFormat)
  326. ));
  327. PUTRECT16(parg16->vpRect, &t4);
  328. FREESTRPTR(pstr2);
  329. FREEARGPTR(parg16);
  330. RETURN(ul);
  331. }
  332. /*++
  333. void EndPaint(<hwnd>, <lpPaint>)
  334. HWND <hwnd>;
  335. LPPAINTSTRUCT <lpPaint>;
  336. The %EndPaint% function marks the end of painting in the given window. The
  337. %EndPaint% function is required for each call to the %BeginPaint% function,
  338. but only after painting is complete.
  339. <hwnd>
  340. Identifies the window that is repainted.
  341. <lpPaint>
  342. Points to a %PAINTSTRUCT% structure that contains the painting
  343. information retrieved by the %BeginPaint% function.
  344. This function does not return a value.
  345. If the caret was hidden by the %BeginPaint% function, %EndPaint% restores
  346. the caret to the screen.
  347. --*/
  348. ULONG FASTCALL WU32EndPaint(PVDMFRAME pFrame)
  349. {
  350. PAINTSTRUCT t2;
  351. register PENDPAINT16 parg16;
  352. GETARGPTR(pFrame, sizeof(ENDPAINT16), parg16);
  353. getpaintstruct16(parg16->vpPaint, &t2);
  354. EndPaint(
  355. HWND32(parg16->hwnd),
  356. &t2
  357. );
  358. FREEARGPTR(parg16);
  359. RETURN(0);
  360. }
  361. #define MAX_WIN16_PROP_TEXT 256 /* Taken from Win 3.1 - winprops.c */
  362. static VPVOID vpEnumPropsProc;
  363. static VPVOID vpString;
  364. INT W32EnumPropsFunc( HWND hwnd, LPSTR lpString, HANDLE hData )
  365. {
  366. PARM16 Parm16;
  367. LONG lReturn;
  368. VPVOID vp;
  369. if ( HIWORD(lpString) == 0 ) {
  370. vp = (DWORD)lpString;
  371. } else {
  372. INT cb;
  373. vp = vpString;
  374. cb = strlen(lpString)+1;
  375. if ( cb > MAX_WIN16_PROP_TEXT-1 ) {
  376. cb = MAX_WIN16_PROP_TEXT-1;
  377. }
  378. putstr16(vpString, lpString, cb);
  379. }
  380. Parm16.EnumPropsProc.hwnd = GETHWND16(hwnd);
  381. Parm16.EnumPropsProc.vpString = vp;
  382. Parm16.EnumPropsProc.hData = GETHANDLE16(hData);
  383. CallBack16(RET_ENUMPROPSPROC, &Parm16, vpEnumPropsProc, (PVPVOID)&lReturn);
  384. return (SHORT)lReturn;
  385. }
  386. /*++
  387. int EnumProps(<hwnd>, <lpEnumFunc>)
  388. HWND <hwnd>;
  389. FARPROC <lpEnumFunc>;
  390. The %EnumProps% function enumerates all entries in the property list of the
  391. specified window. It enumerates the entries by passing them, one by one, to
  392. the callback function specified by <lpEnumFunc>. %EnumProps% continues until
  393. the last entry is enumerated or the callback function returns zero.
  394. <hwnd>
  395. Identifies the window whose property list is to be enumerated.
  396. <lpEnumFunc>
  397. Specifies the procedure-instance address of the callback function.
  398. See the following Comments section for details.
  399. The return value specifies the last value returned by the callback function.
  400. It is -1 if the function did not find a property for enumeration.
  401. An application can remove only those properties which it has added. It
  402. should not remove properties added by other applications or by Windows
  403. itself.
  404. The following restrictions apply to the callback function:
  405. 1 The callback function must not yield control or do anything that might
  406. yield control to other tasks.
  407. 2 The callback function can call the %RemoveProp% function. However, the
  408. %RemoveProp% function can remove only the property passed to the
  409. callback function through the callback function's parameters.
  410. 3 A callback function should not attempt to add properties.
  411. The address passed in the <lpEnumFunc> parameter must be created by using
  412. the %MakeProcInstance% function.
  413. Fixed Data Segments:
  414. The callback function must use the Pascal calling convention and must be
  415. declared %FAR%. In applications and dynamic libraries with fixed data
  416. segments and in dynamic libraries with moveable data segments that do not
  417. contain a stack, the callback function must have the form shown below.
  418. Callback Function:
  419. int FAR PASCAL <EnumFunc>(<hwnd>, <lpString>, <hData>)
  420. HWND <hwnd>;
  421. LPSTR <lpString>;
  422. HANDLE <hData>;
  423. <EnumFunc> is a placeholder for the application-supplied function name. The
  424. actual name must be exported by including it in an %EXPORTS% statement in
  425. the application's module-definition file.
  426. <hwnd>
  427. Identifies a handle to the window that contains the property list.
  428. <lpString>
  429. Points to the null-terminated string associated with the data handle
  430. when the application called the%SetProp% function to set the property.
  431. If the application passed an atom instead of a string to the %SetProp%
  432. function, the<lpString> parameter contains the atom in its low-order
  433. word, and the high-order word is zero.
  434. <hData>
  435. Identifies the data handle.
  436. The callback function can carry out any desired task. It must return a
  437. nonzero value to continue enumeration, or a zero value to stop it.
  438. Moveable Data Segments:
  439. The callback function must use the Pascal calling convention and must be
  440. declared %FAR%. In applications with moveable data segments and in dynamic
  441. libraries whose moveable data segments also contain a stack, the callback
  442. function must have the form shown below.
  443. Callback Function:
  444. int FAR PASCAL <EnumFunc>(<hwnd>, <nDummy>, <pString>, <hData>)
  445. HWND <hwnd>;
  446. WORD <nDummy>;
  447. PSTR <pString>;
  448. HANDLE <hData>;
  449. <EnumFunc> is a placeholder for the application-supplied function name. The
  450. actual name must be exported by including it in an %EXPORTS% statement in
  451. the application's module-definition file.
  452. <hwnd>
  453. Identifies a handle to the window that contains the property list.
  454. <nDummy>
  455. Specifies a dummy parameter.
  456. <pString>
  457. Points to the null-terminated string associated with the data handle
  458. when the application called the %SetProp% function to set the property.
  459. If the application passed an atom instead of a string to the %SetProp%
  460. function, the <pString> parameter contains the atom.
  461. <hData>
  462. Identifies the data handle.
  463. The callback function can carry out any desired task. It should return a
  464. nonzero value to continue enumeration, or a zero value to stop it.
  465. The alternate form above is required since movement of the data will
  466. invalidate any long pointer to a variable on the stack, such as the
  467. <lpString> parameter. The data segment typically moves if the callback
  468. function allocates more space in the local heap than is currently
  469. available.
  470. --*/
  471. ULONG FASTCALL WU32EnumProps(PVDMFRAME pFrame)
  472. {
  473. ULONG ul;
  474. HWND hwnd;
  475. register PENUMPROPS16 parg16;
  476. GETARGPTR(pFrame, sizeof(ENUMPROPS16), parg16);
  477. hwnd = HWND32(parg16->f1);
  478. vpEnumPropsProc = parg16->f2;
  479. vpString = malloc16(MAX_WIN16_PROP_TEXT);
  480. // 16-bit memory may have moved - invalidate flat pointers
  481. FREEARGPTR(parg16);
  482. FREEVDMPTR(pFrame);
  483. if (vpString) {
  484. ul = GETINT16(EnumProps(hwnd,(PROPENUMPROC)W32EnumPropsFunc));
  485. free16(vpString);
  486. } else {
  487. ul = (ULONG)-1;
  488. }
  489. RETURN(ul);
  490. }
  491. /*++
  492. int FillWindow(<hWndParent>, <hWnd>, <hDC>, <hBrush>)
  493. HWND <hWndParent>;
  494. HWND <hWnd>;
  495. HDC <hDC>;
  496. HBRUSH <hBrush>;
  497. The %FillWindow% function paints a given window by using the specified
  498. brush.
  499. <hWndParent>
  500. Identifies the parent of the window to be painted.
  501. <hWnd>
  502. Identifies the window to be painted.
  503. <hDC>
  504. Identifies the device context.
  505. <hBrush>
  506. Identifies the brush used to fill the rectangle.
  507. --*/
  508. ULONG FASTCALL WU32FillWindow(PVDMFRAME pFrame)
  509. {
  510. register PFILLWINDOW16 parg16;
  511. GETARGPTR(pFrame, sizeof(FILLWINDOW16), parg16);
  512. (pfnOut.pfnFillWindow)(
  513. HWND32(parg16->f1),
  514. HWND32(parg16->f2),
  515. HDC32(parg16->f3),
  516. HBRUSH32(parg16->f4)
  517. );
  518. FREEARGPTR(parg16);
  519. RETURN(0);
  520. }
  521. /*++
  522. int FillRect(<hDC>, <lpRect>, <hBrush>)
  523. HDC <hDC>;
  524. LPRECT <lpRect>;
  525. HBRUSH <hBrush>;
  526. The %FillRect% function fills a given rectangle by using the specified
  527. brush. The %FillRect% function fills the complete rectangle, including the
  528. left and top borders, but does not fill the right and bottom borders.
  529. <hDC>
  530. Identifies the device context.
  531. <lpRect>
  532. Points to a %RECT% structure that contains the logical
  533. coordinates of the rectangle to be filled.
  534. <hBrush>
  535. Identifies the brush used to fill the rectangle.
  536. Although the %FillRect% function return type is an integer, the return value
  537. is not used and has no meaning.
  538. The brush must have been created previously by using either the
  539. %CreateHatchBrush%, %CreatePatternBrush%, or %CreateSolidBrush% function, or
  540. retrieved using the %GetStockObject% function.
  541. When filling the specified rectangle, the %FillRect% function does not
  542. include the rectangle's right and bottom sides. GDI fills a rectangle up to,
  543. but does not include, the right column and bottom row, regardless of the
  544. current mapping mode.
  545. %FillRect% compares the values of the %top%, %bottom%, %left%, and %right%
  546. members of the specified rectangle. If %bottom% is less than or equal to
  547. %top%, or if %right% is less than or equal to %left%, the rectangle is not
  548. drawn.
  549. --*/
  550. ULONG FASTCALL WU32FillRect(PVDMFRAME pFrame)
  551. {
  552. ULONG ul;
  553. RECT t2;
  554. register PFILLRECT16 parg16;
  555. GETARGPTR(pFrame, sizeof(FILLRECT16), parg16);
  556. WOW32VERIFY(GETRECT16(parg16->f2, &t2));
  557. ul = GETINT16(FillRect(
  558. HDC32(parg16->f1),
  559. &t2,
  560. HBRUSH32(parg16->f3)
  561. ));
  562. FREEARGPTR(parg16);
  563. RETURN(ul);
  564. }
  565. /*++
  566. int FrameRect(<hDC>, <lpRect>, <hBrush>)
  567. HDC <hDC>;
  568. LPRECT <lpRect>;
  569. HBRUSH <hBrush>;
  570. The %FrameRect% function draws a border around the rectangle specified by
  571. the <lpRect> parameter. The %FrameRect% function uses the given brush to
  572. draw the border. The width and height of the border is always one logical
  573. unit.
  574. <hDC>
  575. Identifies the device context of the window.
  576. <lpRect>
  577. Points to a %RECT% structure that contains the logical
  578. coordinates of the upper-left and lower-right corners of the rectangle.
  579. <hBrush>
  580. Identifies the brush to be used for framing the rectangle.
  581. Although the return value type is integer, its contents should be ignored.
  582. The brush identified by the <hBrush> parameter must have been created
  583. previously by using the %CreateHatchBrush%, %CreatePatternBrush%, or
  584. %CreateSolidBrush% function.
  585. If the %bottom% member is less than or equal to the %top% member, or if the
  586. %right% member is less than or equal to the %left% member, the rectangle is
  587. not drawn.
  588. --*/
  589. ULONG FASTCALL WU32FrameRect(PVDMFRAME pFrame)
  590. {
  591. ULONG ul;
  592. RECT t2;
  593. register PFRAMERECT16 parg16;
  594. GETARGPTR(pFrame, sizeof(FRAMERECT16), parg16);
  595. WOW32VERIFY(GETRECT16(parg16->f2, &t2));
  596. ul = GETINT16(FrameRect(
  597. HDC32(parg16->f1),
  598. &t2,
  599. HBRUSH32(parg16->f3)
  600. ));
  601. FREEARGPTR(parg16);
  602. RETURN(ul);
  603. }
  604. /*++
  605. HDC GetDC(<hwnd>)
  606. HWND <hwnd>;
  607. The %GetDC% function retrieves a handle to a display context for the client
  608. area of the given window. The display context can be used in subsequent GDI
  609. functions to draw in the client area.
  610. The %GetDC% function retrieves a common, class, or private display context
  611. depending on the class style specified for the given window. For common
  612. display contexts, %GetDC% assigns default attributes to the context each
  613. time it is retrieved. For class and private contexts, %GetDC% leaves the
  614. previously assigned attributes unchanged.
  615. <hwnd>
  616. Identifies the window whose display context is to be retrieved.
  617. The return value identifies the display context for the given window's
  618. client area if the function is successful. Otherwise, it is NULL.
  619. After painting with a common display context, the %ReleaseDC% function must
  620. be called to release the context. Class and private display contexts do not
  621. have to be released. Since only five common display contexts are available
  622. at any given time, failure to release a display context can prevent other
  623. applications from accessing a display context.
  624. --*/
  625. ULONG FASTCALL WU32GetDC(PVDMFRAME pFrame)
  626. {
  627. ULONG ul;
  628. register PGETDC16 parg16;
  629. HAND16 htask16 = pFrame->wTDB;
  630. GETARGPTR(pFrame, sizeof(GETDC16), parg16);
  631. if (CACHENOTEMPTY()) {
  632. ReleaseCachedDCs(htask16, parg16->f1, 0, 0, SRCHDC_TASK16_HWND16);
  633. }
  634. CURRENTPTD()->ulLastDesktophDC = 0;
  635. ul = GETHDC16(GetDC(
  636. HWND32(parg16->f1)
  637. ));
  638. if (ul) {
  639. // Some apps such as MSWORKS and MS PUBLISHER use some wizard code that accepts
  640. // a hDC or a hWnd as a parameter and attempt to figure out what type of handle
  641. // it is by using the IsWindow() call. Since both handles come from different
  642. // handle spaces they may end up the same value and this wizard code will end
  643. // up writing to the DC for a random window. By ORing in a 1 we ensure that the
  644. // handle types will never share the same value since all hWnds are even. Note
  645. // that this hack is also made in WG32CreateCompatibleDC()
  646. //
  647. // Note that there are some apps that use the lower 2 bits of the hDC for their
  648. // own purposes.
  649. if (CURRENTPTD()->dwWOWCompatFlags & WOWCF_UNIQUEHDCHWND) {
  650. ul = ul | 1;
  651. } else if ((CURRENTPTD()->dwWOWCompatFlagsEx & WOWCFEX_FIXDCFONT4MENUSIZE) &&
  652. (parg16->f1 == 0)) {
  653. // WP tutorial assumes that the font selected in the hDC for desktop window
  654. // (ie, result of GetDC(NULL)) is the same font as the font selected for
  655. // drawing the menu. Unfortunetly in SUR this is not true as the user can
  656. // select any font for the menu. So we remember the hDC returned for GetDC(0)
  657. // and check for it in GetTextExtentPoint. If the app does try to use it we
  658. // find the hDC for the current menu window and substitute that. When the app
  659. // does another GetDC or ReleaseDC we forget the hDC returned for the original
  660. // GetDC(0).
  661. CURRENTPTD()->ulLastDesktophDC = ul;
  662. }
  663. StoreDC(htask16, parg16->f1, (HAND16)ul);
  664. }
  665. FREEARGPTR(parg16);
  666. RETURN(ul);
  667. }
  668. /*++
  669. void GetScrollRange(<hwnd>, <nBar>, <lpMinPos>, <lpMaxPos>)
  670. HWND <hwnd>;
  671. int <nBar>;
  672. LPINT <lpMinPos>;
  673. LPINT <lpMaxPos>;
  674. The %GetScrollRange% function copies the current minimum and maximum
  675. scroll-bar positions for the given scroll bar to the locations specified by
  676. the <lpMinPos> and <lpMaxPos> parameters. If the given window does not have
  677. standard scroll bars or is not a scroll-bar control, then the
  678. %GetScrollRange% function copies zero to <lpMinPos> and <lpMaxPos>.
  679. <hwnd>
  680. Identifies a window that has standard scroll bars or a scroll-bar
  681. control, depending on the value of the nBar parameter.
  682. <nBar>
  683. Specifies an integer value that identifies which scroll bar to
  684. retrieve. It can be one of the following values:
  685. SB_CTL
  686. Retrieves the position of a scroll-bar control; in this case, the hwnd
  687. parameter must be the handle of a scroll-bar control.
  688. SB_HORZ
  689. Retrieves the position of a window's horizontal scroll bar.
  690. SB_VERT
  691. Retrieves the position of a window's vertical scroll bar.
  692. <lpMinPos>
  693. Points to the integer variable that is to receive the minimum
  694. position.
  695. <lpMaxPos>
  696. Points to the integer variable that is to receive the maximum
  697. position.
  698. This function does not return a value.
  699. The default range for a standard scroll bar is 0 to 100. The default range
  700. for a scroll-bar control is empty (both values are zero).
  701. --*/
  702. ULONG FASTCALL WU32GetScrollRange(PVDMFRAME pFrame)
  703. {
  704. INT t3;
  705. INT t4;
  706. register PGETSCROLLRANGE16 parg16;
  707. GETARGPTR(pFrame, sizeof(GETSCROLLRANGE16), parg16);
  708. GetScrollRange(
  709. HWND32(parg16->f1),
  710. INT32(parg16->f2),
  711. &t3,
  712. &t4
  713. );
  714. PUTINT16(parg16->f3, t3);
  715. PUTINT16(parg16->f4, t4);
  716. FREEARGPTR(parg16);
  717. RETURN(0);
  718. }
  719. /*++
  720. ULONG GetTimerResolution(VOID)
  721. This function has no parameters.
  722. The Win 3.0 & 3.1 code just return 1000.
  723. Contacts on this: NeilK DarrinM
  724. The return value is always 1000.
  725. --*/
  726. ULONG FASTCALL WU32GetTimerResolution(PVDMFRAME pFrame)
  727. {
  728. UNREFERENCED_PARAMETER(pFrame);
  729. RETURN(1000L);
  730. }
  731. /*++
  732. BOOL GetUpdateRect(<hwnd>, <lpRect>, <bErase>)
  733. HWND <hwnd>;
  734. LPRECT <lpRect>;
  735. BOOL <bErase>;
  736. The %GetUpdateRect% function retrieves the coordinates of the smallest
  737. rectangle that completely encloses the update region of the given window. If
  738. the window was created with the CS_OWNDC style and the mapping mode is not
  739. MM_TEXT, the %GetUpdateRect% function gives the rectangle in logical
  740. coordinates. Otherwise, %GetUpdateRect% gives the rectangle in client
  741. coordinates. If there is no update region, %GetUpdateRect% makes the
  742. rectangle empty (sets all coordinates to zero).
  743. The <bErase> parameter specifies whether %GetUpdateRect% should erase the
  744. background of the update region. If <bErase> is TRUE and the update region
  745. is not empty, the background is erased. To erase the background,
  746. %GetUpdateRect% sends a WM_ERASEBKGND message to the given window.
  747. <hwnd>
  748. Identifies the window whose update region is to be retrieved.
  749. <lpRect>
  750. Points to the %RECT% structure that is to receive the
  751. client coordinates of the enclosing rectangle.
  752. <bErase>
  753. Specifies whether the background in the update region is to be
  754. erased.
  755. The return value specifies the status of the update region of the given
  756. window. It is TRUE if the update region is not empty. Otherwise, it is
  757. FALSE.
  758. The update rectangle retrieved by the %BeginPaint% function is identical to
  759. that retrieved by the %GetUpdateRect% function.
  760. %BeginPaint% automatically validates the update region, so any call to
  761. %GetUpdateRect% made immediately after the %BeginPaint% call retrieves an
  762. empty update region.
  763. --*/
  764. ULONG FASTCALL WU32GetUpdateRect(PVDMFRAME pFrame)
  765. {
  766. ULONG ul;
  767. RECT t2;
  768. register PGETUPDATERECT16 parg16;
  769. GETARGPTR(pFrame, sizeof(GETUPDATERECT16), parg16);
  770. ul = GETBOOL16(GetUpdateRect(
  771. HWND32(parg16->f1),
  772. &t2,
  773. BOOL32(parg16->f3)
  774. ));
  775. PUTRECT16(parg16->f2, &t2);
  776. FREEARGPTR(parg16);
  777. RETURN(ul);
  778. }
  779. ULONG FASTCALL WU32GlobalAddAtom(PVDMFRAME pFrame)
  780. {
  781. ULONG ul;
  782. PSZ psz1;
  783. UINT dw1;
  784. register PGLOBALADDATOM16 parg16;
  785. GETARGPTR(pFrame, sizeof(GLOBALADDATOM16), parg16);
  786. dw1 = UINT32(parg16->f1);
  787. if (!HIWORD(dw1)) {
  788. //
  789. // If the hiword is zero, it's not a pointer.
  790. // Instead, it's an integer and we either return
  791. // the integer passed (if it's not a valid atom
  792. // value), or zero (if it is a valid atom value).
  793. //
  794. if (!dw1 || dw1 >= 0xc000) {
  795. ul = 0;
  796. } else {
  797. ul = dw1;
  798. }
  799. } else {
  800. GETPSZPTR(parg16->f1, psz1);
  801. ul = GETATOM16(GlobalAddAtom(
  802. psz1
  803. ));
  804. FREEPSZPTR(psz1);
  805. }
  806. FREEARGPTR(parg16);
  807. RETURN(ul);
  808. }
  809. ULONG FASTCALL WU32GlobalDeleteAtom(PVDMFRAME pFrame)
  810. {
  811. // Envoy viewer (part of PerfectOffice) has a bug in GlobalDeleteAtom
  812. // where it expects the wrong return value (the app thought 0 was
  813. // failure while its for success). This causes the app to go in an
  814. // infinite loop trying to delete a global object. This app works on
  815. // Win3.1 because Win3.1 returns some garbage in AX if the atom is
  816. // already deleted which takes this app out of the loop. On Win95 and
  817. // NT3.51 that is not the case and 0 is always returned. The following
  818. // comaptibility fix mimics the win3.1 behavior for this app.
  819. ULONG ul;
  820. static USHORT envoyHandle16=0;
  821. static BOOL fFoundEnvoyAtom = FALSE;
  822. BOOL IsEnvoy;
  823. CHAR envoyString [32];
  824. register PGLOBALDELETEATOM16 parg16;
  825. GETARGPTR(pFrame, sizeof(GLOBALDELETEATOM16), parg16);
  826. IsEnvoy = (CURRENTPTD()->dwWOWCompatFlagsEx & WOWCFEX_GLOBALDELETEATOM);
  827. if (IsEnvoy){
  828. if (!fFoundEnvoyAtom && GlobalGetAtomName (ATOM32(parg16->f1),
  829. envoyString,
  830. 32) &&
  831. !WOW32_stricmp (envoyString, "SomeEnvoyViewerIsRunning")) {
  832. envoyHandle16 = parg16->f1;
  833. }
  834. }
  835. ul = GETATOM16(GlobalDeleteAtom(
  836. ATOM32(parg16->f1)
  837. ));
  838. if (IsEnvoy){
  839. if (envoyHandle16 && !fFoundEnvoyAtom) {
  840. fFoundEnvoyAtom = TRUE;
  841. }
  842. else if (fFoundEnvoyAtom) {
  843. if (envoyHandle16 == parg16->f1) {
  844. envoyHandle16 = 0;
  845. fFoundEnvoyAtom = FALSE;
  846. ul = parg16->f1;
  847. }
  848. }
  849. }
  850. FREEARGPTR(parg16);
  851. RETURN(ul);
  852. }
  853. ULONG FASTCALL WU32GlobalGetAtomName(PVDMFRAME pFrame)
  854. {
  855. ULONG ul = 0;
  856. PSZ psz2;
  857. register PGLOBALGETATOMNAME16 parg16;
  858. GETARGPTR(pFrame, sizeof(GLOBALGETATOMNAME16), parg16);
  859. ALLOCVDMPTR(parg16->f2, parg16->f3, psz2);
  860. if (parg16->f1) {
  861. ul = GETWORD16(GlobalGetAtomName(ATOM32(parg16->f1),
  862. psz2,
  863. INT32(parg16->f3)));
  864. FLUSHVDMPTR(parg16->f2, strlen(psz2)+1, psz2);
  865. }
  866. else {
  867. *psz2 = '\0';
  868. }
  869. FREEVDMPTR(psz2);
  870. FREEARGPTR(parg16);
  871. RETURN(ul);
  872. }
  873. /*++
  874. BOOL GrayString(<hDC>, <hBrush>, <lpOutputFunc>, <lpData>, <nCount>, <X>,
  875. <Y>, <nWidth>, <nHeight>)
  876. HDC <hDC>;
  877. HBRUSH <hBrush>;
  878. FARPROC <lpOutputFunc>;
  879. DWORD <lpData>;
  880. int <nCount>;
  881. int <X>;
  882. int <Y>;
  883. int <nWidth>;
  884. int <nHeight>;
  885. The %GrayString% function draws gray text at the given location. The
  886. %GrayString% function draws gray text by writing the text in a memory
  887. bitmap, graying the bitmap, and then copying the bitmap to the display. The
  888. function grays the text regardless of the selected brush and
  889. background. %GrayString% uses the font currently selected for the device
  890. context specified by the <hDC> parameter.
  891. If the <lpOutputFunc> parameter is NULL, GDI uses the %TextOut% function,
  892. and the <lpData> parameter is assumed to be a long pointer to the character
  893. string to be output. If the characters to be output cannot be handled by
  894. %TextOut% (for example, the string is stored as a bitmap), the application
  895. must supply its own output function.
  896. <hDC>
  897. Identifies the device context.
  898. <hBrush>
  899. Identifies the brush to be used for graying.
  900. <lpOutputFunc>
  901. Is the procedure-instance address of the application-supplied
  902. function that will draw the string, or, if the %TextOut% function is to
  903. be used to draw the string, it is a NULL pointer. See the following
  904. Comments section for details.
  905. <lpData>
  906. Specifies a long pointer to data to be passed to the output
  907. function. If the <lpOutputFunc> parameter is NULL, <lpData> must be a
  908. long pointer to the string to be output.
  909. <nCount>
  910. Specifies the number of characters to be output. If the <nCount>
  911. parameter is zero, %GrayString% calculates the length of the string
  912. (assuming that <lpData> is a pointer to the string). If <nCount> is -1
  913. and the function pointed to by <lpOutputFunc> returns zero, the image is
  914. shown but not grayed.
  915. <X>
  916. Specifies the logical <x>-coordinate of the starting position of
  917. the rectangle that encloses the string.
  918. <Y>
  919. Specifies the logical <y>-coordinate of the starting position of
  920. the rectangle that encloses the string.
  921. <nWidth>
  922. Specifies the width (in logical units) of the rectangle that
  923. encloses the string. If the <nWidth> parameter is zero, %GrayString%
  924. calculates the width of the area, assuming <lpData> is a pointer to the
  925. string.
  926. <nHeight>
  927. Specifies the height (in logical units) of the rectangle that
  928. encloses the string. If the <nHeight> parameter is zero, %GrayString%
  929. calculates the height of the area, assuming <lpData> is a pointer to the
  930. string.
  931. The return value specifies the outcome of the function. It is TRUE if the
  932. string is drawn. A return value of FALSE means that either the %TextOut%
  933. function or the application-supplied output function returned FALSE, or
  934. there was insufficient memory to create a memory bitmap for graying.
  935. An application can draw grayed strings on devices that support a solid gray
  936. color, without calling the %GrayString% function. The system color
  937. COLOR_GRAYTEXT is the solid-gray system color used to draw disabled text.
  938. The application can call the %GetSysColor% function to retrieve the color
  939. value of COLOR_GRAYTEXT. If the color is other than zero (black), the
  940. application can call the %SetTextColor% to set the text color to the color
  941. value and then draw the string directly. If the retrieved color is black,
  942. the application must call %GrayString% to gray the text.
  943. The callback function must use the Pascal calling convention and must be
  944. declared %FAR%.
  945. Callback Function:
  946. BOOL FAR PASCAL <OutputFunc>(<hDC>, <lpData>, <nCount>)
  947. HDC <hDC>;
  948. DWORD <lpData>;
  949. int <nCount>;
  950. <OutputFunc> is a placeholder for the application-supplied callback function
  951. name. The actual name must be exported by including it in an %EXPORTS%
  952. statement in the application's module-definition file.
  953. <hDC>
  954. Identifies a memory device context with a bitmap of at least the width
  955. and height specified by the nWidth and nHeight parameters,
  956. respectively.
  957. <lpData>
  958. Points to the character string to be drawn.
  959. <nCount>
  960. Specifies the number of characters to be output.
  961. The return value must be TRUE to indicate success. Otherwise, it is FALSE.
  962. This output function (<OutputFunc>) must draw an image relative to the
  963. coordinates (0,0) rather than (<X,Y>). The address passed as the
  964. <lpOutputFunc> parameter must be created by using the %MakeProcInstance%
  965. function, and the output function name must be exported; it must be
  966. explicitly defined in an %EXPORTS% statement of the application's
  967. module-definition file.
  968. The MM_TEXT mapping mode must be selected before using this function.
  969. --*/
  970. BOOL W32GrayStringProc(HDC hDC,PGRAYSTRINGDATA pGray, int n) {
  971. INT iReturn;
  972. PARM16 Parm16;
  973. WOW32ASSERT(pGray);
  974. if (pGray->fResetLengthToZero)
  975. n = 0;
  976. LOGDEBUG(12,(" Graystring callback function, n = %d, hdc = %lx, %lx\n",n,hDC,pGray->dwUserParam));
  977. Parm16.GrayStringProc.n = (SHORT)n;
  978. Parm16.GrayStringProc.data = pGray->dwUserParam;
  979. pGray->hdc=Parm16.GrayStringProc.hdc = GETHDC16(hDC);
  980. CallBack16(RET_GRAYSTRINGPROC, &Parm16, pGray->vpfnGrayStringProc, (PVPVOID)&iReturn);
  981. LOGDEBUG(12,(" Graystring callback function returns %x\n",iReturn));
  982. return (BOOL)((SHORT)iReturn);
  983. }
  984. ULONG FASTCALL WU32GrayString(PVDMFRAME pFrame)
  985. {
  986. ULONG ul=0;
  987. PSZ psz2;
  988. HDC hdc;
  989. INT n,wid,hgt;
  990. VPVOID vpfn;
  991. VPVOID vpstr;
  992. GRAYSTRINGDATA Gray;
  993. register PGRAYSTRING16 parg16;
  994. GETARGPTR(pFrame, sizeof(GRAYSTRING16), parg16);
  995. hdc=HDC32(parg16->f1);
  996. vpfn = DWORD32(parg16->f3);
  997. vpstr = DWORD32(parg16->f4);
  998. n=INT32(parg16->f5);
  999. wid=INT32(parg16->f8);
  1000. hgt=INT32(parg16->f9);
  1001. if ( HIWORD(vpfn) ) { // SQLWin/repowin passes junk in low word
  1002. Gray.fResetLengthToZero = FALSE;
  1003. if( n==0 ) {
  1004. n = 1; // Prevent USER from doing strlen on &Gray below
  1005. if ( HIWORD(vpstr) != 0 ) { // Blow off small integers right away
  1006. GETVDMPTR(vpstr, 0, psz2); // This might assert on mips, ignore it!
  1007. if ( psz2 ) {
  1008. try {
  1009. n = strlen(psz2);
  1010. if (!n) {
  1011. n = 1;
  1012. Gray.fResetLengthToZero = TRUE;
  1013. }
  1014. } except( EXCEPTION_EXECUTE_HANDLER ) {
  1015. }
  1016. }
  1017. FREEVDMPTR( psz2 );
  1018. }
  1019. }
  1020. if ( wid == 0 || hgt == 0) {
  1021. if ( HIWORD(vpstr) != 0 ) {
  1022. GETVDMPTR(vpstr, 0, psz2); // This might assert on mips, ignore it!
  1023. if (psz2) {
  1024. SIZE size;
  1025. try {
  1026. GetTextExtentPointA(hdc, (LPCSTR)psz2, n, &size);
  1027. wid = size.cx;
  1028. hgt = size.cy;
  1029. } except (EXCEPTION_EXECUTE_HANDLER) {
  1030. }
  1031. }
  1032. FREEVDMPTR( psz2 );
  1033. }
  1034. }
  1035. Gray.vpfnGrayStringProc = DWORD32(parg16->f3);
  1036. Gray.dwUserParam = vpstr;
  1037. Gray.hdc = 0;
  1038. LOGDEBUG(12,(" Graystring with callback %lx n,w,h = %d,%d,%d\n",
  1039. vpstr,n,wid,hgt));
  1040. ul = GETBOOL16(GrayString(hdc,
  1041. HBRUSH32(parg16->f2),
  1042. (GRAYSTRINGPROC)W32GrayStringProc,
  1043. (DWORD)&Gray,
  1044. n,
  1045. INT32(parg16->f6),
  1046. INT32(parg16->f7),
  1047. wid,
  1048. hgt));
  1049. } else {
  1050. GETPSZPTR(vpstr, psz2);
  1051. #ifdef DOESNT_USER_DO_THIS
  1052. if( n==0 ) {
  1053. n=strlen(psz2);
  1054. }
  1055. if( ((wid == 0) || (hgt == 0)) ) {
  1056. GetTextExtentPoint(hdc,psz2,n,&sz);
  1057. wid=sz.cx;
  1058. hgt=sz.cy;
  1059. }
  1060. #endif
  1061. ul = GETBOOL16(GrayString(hdc,
  1062. HBRUSH32(parg16->f2),
  1063. NULL,
  1064. (DWORD)psz2,
  1065. n,
  1066. INT32(parg16->f6),
  1067. INT32(parg16->f7),
  1068. wid,
  1069. hgt));
  1070. FREEPSZPTR(psz2);
  1071. }
  1072. FREEARGPTR(parg16);
  1073. RETURN(ul);
  1074. }
  1075. /*++
  1076. void InvalidateRect(<hwnd>, <lpRect>, <bErase>)
  1077. HWND <hwnd>;
  1078. LPRECT <lpRect>;
  1079. BOOL <bErase>;
  1080. The %InvalidateRect% function invalidates the client area within the given
  1081. rectangle by adding that rectangle to the window's update region. The
  1082. invalidated rectangle, along with all other areas in the update region, is
  1083. marked for painting when the next WM_PAINT message occurs. The invalidated
  1084. areas accumulate in the update region until the region is processed when the
  1085. next WM_PAINT message occurs, or the region is validated by using the
  1086. %ValidateRect% or %ValidateRgn% function.
  1087. The <bErase> parameter specifies whether the background within the update
  1088. area is to be erased when the update region is processed. If <bErase> is
  1089. TRUE, the background is erased when the %BeginPaint% function is called;
  1090. if <bErase> is FALSE, the background remains unchanged. If <bErase> is
  1091. TRUE for any part of the update region, the background in the entire
  1092. region is erased, not just in the given part.
  1093. <hwnd>
  1094. Identifies the window whose update region is to be modified.
  1095. <lpRect>
  1096. Points to a %RECT% structure that contains the rectangle
  1097. (in client coordinates) to be added to the update region. If the
  1098. <lpRect> parameter is NULL, the entire client area is added to the
  1099. region.
  1100. <bErase>
  1101. Specifies whether the background within the update region is to
  1102. be erased.
  1103. This function does not return a value.
  1104. Windows sends a WM_PAINT message to a window whenever its update region is
  1105. not empty and there are no other messages in the application queue for that
  1106. window.
  1107. --*/
  1108. ULONG FASTCALL WU32InvalidateRect(PVDMFRAME pFrame)
  1109. {
  1110. RECT t2, *p2;
  1111. register PINVALIDATERECT16 parg16;
  1112. GETARGPTR(pFrame, sizeof(INVALIDATERECT16), parg16);
  1113. p2 = GETRECT16(parg16->f2, &t2);
  1114. InvalidateRect(
  1115. HWND32(parg16->f1),
  1116. p2,
  1117. BOOL32(parg16->f3)
  1118. );
  1119. FREEARGPTR(parg16);
  1120. RETURN(1); // Win 3.x always returned 1 as a side-effect of jmping to
  1121. // IRedrawWindow [core\user\wmupdate.c] - MarkRi 5/93
  1122. }
  1123. /*++
  1124. void InvalidateRgn(<hwnd>, <hRgn>, <bErase>)
  1125. HWND <hwnd>;
  1126. HRGN <hRgn>;
  1127. BOOL <bErase>;
  1128. The %InvalidateRgn% function invalidates the client area within the given
  1129. region by adding it to the current update region of the given window. The
  1130. invalidated region, along with all other areas in the update region, is
  1131. marked for painting when the next WM_PAINT message occurs. The invalidated
  1132. areas accumulate in the update region until the region is processed when the
  1133. next WM_PAINT message occurs, or the region is validated by using the
  1134. %ValidateRect% or %ValidateRgn% function.
  1135. The <bErase> parameter specifies whether the background within the update
  1136. area is to be erased when the update region is processed. If <bErase> is
  1137. TRUE, the background is erased when the %BeginPaint% function is called; if
  1138. <bErase> is FALSE, the background remains unchanged. If <bErase> is TRUE for
  1139. any part of the update region, the background in the entire region is
  1140. erased, not just in the given part.
  1141. <hwnd>
  1142. Identifies the window whose update region is to be modified.
  1143. <hRgn>
  1144. Identifies the region to be added to the update region. The
  1145. region is assumed to have client coordinates.
  1146. <bErase>
  1147. Specifies whether the background within the update region is to
  1148. be erased.
  1149. This function does not return a value.
  1150. Windows sends a WM_PAINT message to a window whenever its update region is
  1151. not empty and there are no other messages in the application queue for that
  1152. window.
  1153. The given region must have been previously created by using one of the
  1154. region functions (for more information, see Chapter 1, Window Manager
  1155. Interface Functions).
  1156. --*/
  1157. ULONG FASTCALL WU32InvalidateRgn(PVDMFRAME pFrame)
  1158. {
  1159. register PINVALIDATERGN16 parg16;
  1160. GETARGPTR(pFrame, sizeof(INVALIDATERGN16), parg16);
  1161. InvalidateRgn(
  1162. HWND32(parg16->f1),
  1163. HRGN32(parg16->f2),
  1164. BOOL32(parg16->f3)
  1165. );
  1166. FREEARGPTR(parg16);
  1167. RETURN(1); // Win 3.x always returned 1 as a side-effect of jmping to
  1168. // IRedrawWindow [core\user\wmupdate.c] - MarkRi 5/93
  1169. }
  1170. /*++
  1171. void InvertRect(<hDC>, <lpRect>)
  1172. HDC <hDC>;
  1173. LPRECT <lpRect>;
  1174. The %InvertRect% function inverts the contents of the given rectangle. On
  1175. monochrome displays, the %InvertRect% function makes white pixels black, and
  1176. black pixels white. On color displays, the inversion depends on how colors
  1177. are generated for the display. Calling %InvertRect% twice with the same
  1178. rectangle restores the display to its previous colors.
  1179. <hDC>
  1180. Identifies the device context.
  1181. <lpRect>
  1182. Points to a %RECT% structure that contains the logical coordinates of
  1183. the rectangle to be inverted.
  1184. This function does not return a value.
  1185. The %InvertRect% function compares the values of the %top%, %bottom%,
  1186. %left%, and %right% members of the specified rectangle. If %bottom% is less
  1187. than or equal to %top%, or if %right% is less than or equal to %left%, the
  1188. rectangle is not drawn.
  1189. --*/
  1190. ULONG FASTCALL WU32InvertRect(PVDMFRAME pFrame)
  1191. {
  1192. RECT t2;
  1193. register PINVERTRECT16 parg16;
  1194. GETARGPTR(pFrame, sizeof(INVERTRECT16), parg16);
  1195. WOW32VERIFY(GETRECT16(parg16->f2, &t2));
  1196. InvertRect(
  1197. HDC32(parg16->f1),
  1198. &t2
  1199. );
  1200. FREEARGPTR(parg16);
  1201. RETURN(0);
  1202. }
  1203. ULONG FASTCALL WU32LoadBitmap(PVDMFRAME pFrame)
  1204. {
  1205. ULONG ul = 0;
  1206. PSZ psz2;
  1207. register PLOADBITMAP16 parg16;
  1208. LPBYTE pResData = NULL;
  1209. GETARGPTR(pFrame, sizeof(LOADBITMAP16), parg16);
  1210. GETPSZIDPTR(parg16->f2, psz2);
  1211. GETMISCPTR(parg16->f3, pResData);
  1212. ul = GETHBITMAP16((pfnOut.pfnWOWLoadBitmapA)(HINSTRES32(parg16->f1),
  1213. psz2,
  1214. pResData,
  1215. parg16->f4));
  1216. FREEMISCPTR(pResData);
  1217. FREEPSZIDPTR(psz2);
  1218. FREEARGPTR(parg16);
  1219. RETURN(ul);
  1220. }
  1221. /*++
  1222. int ReleaseDC(<hwnd>, <hDC>)
  1223. HWND <hwnd>;
  1224. HDC <hDC>;
  1225. The %ReleaseDC% function releases a device context, freeing it for use by
  1226. other applications. The effect of the %ReleaseDC% function depends on the
  1227. device-context type. It only frees common and window device contexts. It has
  1228. no effect on class or private device contexts.
  1229. <hwnd>
  1230. Identifies the window whose device context is to be released.
  1231. <hDC>
  1232. Identifies the device context to be released.
  1233. The return value specifies whether the device context is released. It is 1
  1234. if the device context is released. Otherwise, it is zero.
  1235. The application must call the %ReleaseDC% function for each call to the
  1236. %GetWindowDC% function and for each call to the %GetDC% function that
  1237. retrieves a common device context.
  1238. --*/
  1239. ULONG FASTCALL WU32ReleaseDC(PVDMFRAME pFrame)
  1240. {
  1241. ULONG ul;
  1242. register PRELEASEDC16 parg16;
  1243. HAND16 htask16 = CURRENTPTD()->htask16;
  1244. GETARGPTR(pFrame, sizeof(RELEASEDC16), parg16);
  1245. CURRENTPTD()->ulLastDesktophDC = 0;
  1246. CacheReleasedDC(htask16, parg16->f1, parg16->f2);
  1247. ul = TRUE;
  1248. FREEARGPTR(parg16);
  1249. RETURN(ul);
  1250. }
  1251. /*++
  1252. BOOL ScrollDC(<hDC>, <dx>, <dy>, <lprcScroll>, <lprcClip>, <hrgnUpdate>,
  1253. <lprcUpdate>)
  1254. HDC <hDC>;
  1255. int <dx>;
  1256. int <dy>;
  1257. LPRECT <lprcScroll>;
  1258. LPRECT <lprcClip>;
  1259. HRGN <hrgnUpdate>;
  1260. LPRECT <lprcUpdate>;
  1261. The %ScrollDC% function scrolls a rectangle of bits horizontally and
  1262. vertically. The <lprcScroll> parameter points to the rectangle to be
  1263. scrolled, the <dx> parameter specifies the number of units to be scrolled
  1264. horizontally, and the <dy> parameter specifies the number of units to be
  1265. scrolled vertically.
  1266. <hDC>
  1267. Identifies the device context that contains the bits to be scrolled.
  1268. <dx>
  1269. Specifies the number of horizontal scroll units.
  1270. <dy>
  1271. Specifies the number of vertical scroll units.
  1272. <lprcScroll>
  1273. Points to the %RECT% structure that contains the
  1274. coordinates of the scrolling rectangle.
  1275. <lprcClip>
  1276. Points to the %RECT% structure that contains the
  1277. coordinates of the clipping rectangle. When this rectangle is smaller
  1278. than the original pointed to by <lprcScroll>, scrolling occurs only in
  1279. the smaller rectangle.
  1280. <hrgnUpdate>
  1281. Identifies the region uncovered by the scrolling process. The
  1282. %ScrollDC% function defines this region; it is not necessarily a
  1283. rectangle.
  1284. <lprcUpdate>
  1285. Points to the %RECT% structure that, upon return, contains
  1286. the coordinates of the rectangle that bounds the scrolling update
  1287. region. This is the largest rectangular area that requires repainting.
  1288. This value specifies the outcome of the function. It is TRUE if scrolling is
  1289. executed. Otherwise, it is FALSE.
  1290. If the <lprcUpdate> parameter is NULL, Windows does not compute the update
  1291. rectangle. If both the <hrgnUpdate> and <lprcUpdate> parameters are NULL,
  1292. Windows does not compute the update region. If <hrgnUpdate> is not NULL,
  1293. Windows assumes that it contains a valid region handle to the region
  1294. uncovered by the scrolling process (defined by the %ScrollDC% function).
  1295. An application should use the %ScrollWindow% function when it is necessary
  1296. to scroll the entire client area of a window. Otherwise, it should use
  1297. %ScrollDC%.
  1298. --*/
  1299. ULONG FASTCALL WU32ScrollDC(PVDMFRAME pFrame)
  1300. {
  1301. ULONG ul;
  1302. RECT t4;
  1303. RECT t5;
  1304. RECT t7;
  1305. register PSCROLLDC16 parg16;
  1306. GETARGPTR(pFrame, sizeof(SCROLLDC16), parg16);
  1307. ul = GETBOOL16(ScrollDC(
  1308. HDC32(parg16->f1),
  1309. INT32(parg16->f2),
  1310. INT32(parg16->f3),
  1311. GETRECT16(parg16->f4, &t4),
  1312. GETRECT16(parg16->f5, &t5),
  1313. HRGN32(parg16->f6),
  1314. &t7
  1315. ));
  1316. PUTRECT16(parg16->f7, &t7);
  1317. FREEARGPTR(parg16);
  1318. RETURN(ul);
  1319. }
  1320. /*++
  1321. HWND SetCapture(<hwnd>)
  1322. HWND <hwnd>;
  1323. The %SetCapture% function causes all subsequent mouse input to be sent to
  1324. the window specified by the <hwnd> parameter, regardless of the position of
  1325. the cursor.
  1326. <hwnd>
  1327. Identifies the window that is to receive the mouse input.
  1328. The return value identifies the window that previously received all mouse
  1329. input. It is NULL if there is no such window.
  1330. When the window no longer requires all mouse input, the application should
  1331. call the %ReleaseCapture% function so that other windows can receive mouse
  1332. input.
  1333. --*/
  1334. ULONG FASTCALL WU32SetCapture(PVDMFRAME pFrame)
  1335. {
  1336. ULONG ul;
  1337. register PSETCAPTURE16 parg16;
  1338. GETARGPTR(pFrame, sizeof(SETCAPTURE16), parg16);
  1339. // MS Works Ver 3.0B has an unintialized local variable. We need to make
  1340. // sure it see's a positive int value in the location on the stack where we
  1341. // write the 32-bit thunk address for fast dispatching to this thunk.
  1342. if (CURRENTPTD()->dwWOWCompatFlagsEx & WOWCFEX_SETCAPSTACK) {
  1343. // wCallID has already been used for dispatch so we can overwrite it.
  1344. // Note: This will cause the logging on checked builds show ISCHILD()
  1345. // as the return API instead of SetCapture().
  1346. // For folks grepping for this: SetCapture() : IsChild()
  1347. pFrame->wCallID = 0x100;
  1348. }
  1349. ul = GETHWND16(SetCapture(HWND32(parg16->f1)));
  1350. FREEARGPTR(parg16);
  1351. RETURN(ul);
  1352. }
  1353. ULONG FASTCALL WU32SetEventHook(PVDMFRAME pFrame)
  1354. {
  1355. PTD ptd;
  1356. PTDB pTDB;
  1357. DWORD dwButtonPushed;
  1358. #ifdef FE_SB
  1359. CHAR szErrorMessage[256];
  1360. #else // !FE_SB
  1361. CHAR szErrorMessage[200];
  1362. #endif // !FE_SB
  1363. char szModName[9];
  1364. char szTitle[100];
  1365. register PSETEVENTHOOK16 parg16;
  1366. GETARGPTR(pFrame, sizeof(SETEVENTHOOK16), parg16);
  1367. // Retail Build
  1368. ptd = CURRENTPTD();
  1369. if (ptd->dwFlags & TDF_FORCETASKEXIT) {
  1370. goto SetEventHookExit;
  1371. }
  1372. pTDB = (PVOID)SEGPTR(ptd->htask16,0);
  1373. RtlCopyMemory(szModName, pTDB->TDB_ModName, sizeof(szModName)-1);
  1374. szModName[sizeof(szModName)-1] = 0;
  1375. if (!LoadString(hmodWOW32, iszEventHook,
  1376. szErrorMessage, sizeof(szErrorMessage)/sizeof(CHAR)))
  1377. {
  1378. szErrorMessage[0] = 0;
  1379. }
  1380. if (!LoadString(hmodWOW32, iszApplication,
  1381. szTitle, sizeof(szTitle)/sizeof(CHAR)))
  1382. {
  1383. szTitle[0] = 0;
  1384. }
  1385. strcat(szTitle, szModName);
  1386. dwButtonPushed = WOWSysErrorBox(
  1387. szTitle,
  1388. szErrorMessage,
  1389. SEB_CLOSE | SEB_DEFBUTTON,
  1390. 0,
  1391. SEB_IGNORE
  1392. );
  1393. if (dwButtonPushed != 3) {
  1394. //
  1395. // If user typed Cancel or Any of the above fail,
  1396. // force the task to die.
  1397. //
  1398. GETFRAMEPTR(ptd->vpStack, pFrame);
  1399. pFrame->wRetID = RET_FORCETASKEXIT;
  1400. ptd->dwFlags |= TDF_FORCETASKEXIT;
  1401. }
  1402. SetEventHookExit:
  1403. FREEARGPTR(parg16);
  1404. RETURN(0);
  1405. }
  1406. /*++
  1407. void SetKeyboardState(<lpKeyState>)
  1408. LPBYTE <lpKeyState>;
  1409. The %SetKeyboardState% function copies the 256 bytes pointed to by the
  1410. <lpKeyState> parameter into the Windows keyboard-state table.
  1411. <lpKeyState>
  1412. Points to an array of 256 bytes that contains keyboard key states.
  1413. This function does not return a value.
  1414. In many cases, an application should call the %GetKeyboardState% function
  1415. first to initialize the 256-byte array. The application should then change
  1416. the desired bytes.
  1417. %SetKeyboardState% sets the LEDs and BIOS flags for the ^NUMLOCK^,
  1418. ^CAPSLOCK^, and ^SCROLL LOCK^ keys according to the toggle state of the
  1419. VK_NUMLOCK, VK_CAPITAL, and VK_OEM_SCROLL entries of the array.
  1420. For more information, see the description of %GetKeyboardState%, earlier in
  1421. this chapter.
  1422. --*/
  1423. ULONG FASTCALL WU32SetKeyboardState(PVDMFRAME pFrame)
  1424. {
  1425. PBYTE p1;
  1426. register PSETKEYBOARDSTATE16 parg16;
  1427. GETARGPTR(pFrame, sizeof(SETKEYBOARDSTATE16), parg16);
  1428. GETVDMPTR(parg16->f1, 256, p1);
  1429. SetKeyboardState(
  1430. p1
  1431. );
  1432. FREEVDMPTR(p1);
  1433. FREEARGPTR(parg16);
  1434. RETURN(0);
  1435. }
  1436. /*++
  1437. void SetSysColors(<cDspElements>, <aiDspElements>, <aRgbValues>)
  1438. int <cDspElements>;
  1439. LPINT <aiDspElements>;
  1440. LPDWORD <aRgbValues>;
  1441. The %SetSysColors% function sets the system colors for one or more display
  1442. elements. Display elements are the various parts of a window and the Windows
  1443. display that appear on the system display screen.
  1444. The %SetSysColors% function sends a WM_SYSCOLORCHANGE message to all windows
  1445. to inform them of the change in color. It also directs Windows to repaint
  1446. the affected portions of all currently visible windows.
  1447. <cDspElements>
  1448. Specifies the number of display elements in the <aiDspElements> array.
  1449. <aiDspElements>
  1450. Points to an array of integers that specify the display elements
  1451. to be changed. For a list of possible display elements, see the following
  1452. "Comments" section.
  1453. <aRgbValues>
  1454. Points to an array of unsigned long integers that contains the new RGB
  1455. color value for each display element in the <aiDspElements> array.
  1456. This function does not return a value.
  1457. The %SetSysColors% function changes the current Windows session only. The
  1458. new colors are not saved when Windows terminates.
  1459. The following is the list of display elements that may be used in the array
  1460. of display elements pointed to by the <aiDspElements> parameter:
  1461. COLOR_ACTIVEBORDER
  1462. Active window border.
  1463. COLOR_ACTIVECAPTION
  1464. Active window caption.
  1465. COLOR_APPWORKSPACE
  1466. Background color of multiple document interface (MDI) applications.
  1467. COLOR_BACKGROUND
  1468. Desktop.
  1469. COLOR_BTNFACE
  1470. Face shading on push buttons.
  1471. COLOR_BTNSHADOW
  1472. Edge shading on push buttons.
  1473. COLOR_BTNTEXT
  1474. Text on push buttons.
  1475. COLOR_CAPTIONTEXT
  1476. Text in caption, size box, scroll-bar arrow box.
  1477. COLOR_GRAYTEXT
  1478. Grayed (disabled) text. This color is set to 0 if the current display
  1479. driver does not support a solid gray color.
  1480. COLOR_HIGHLIGHT
  1481. Items selected item in a control.
  1482. COLOR_HIGHLIGHTTEXT
  1483. Text of item selected in a control.
  1484. COLOR_INACTIVEBORDER
  1485. Inactive window border.
  1486. COLOR_INACTIVECAPTION
  1487. Inactive window caption.
  1488. COLOR_INACTIVECAPTIONTEXT
  1489. Color of text in an inactive caption.
  1490. COLOR_MENU
  1491. Menu background.
  1492. COLOR_MENUTEXT
  1493. Text in menus.
  1494. COLOR_SCROLLBAR
  1495. Scroll-bar gray area.
  1496. COLOR_WINDOW
  1497. Window background.
  1498. COLOR_WINDOWFRAME
  1499. Window frame.
  1500. COLOR_WINDOWTEXT
  1501. Text in windows.
  1502. --*/
  1503. #define SSC_BUF_SIZE 256
  1504. ULONG FASTCALL WU32SetSysColors(PVDMFRAME pFrame)
  1505. {
  1506. PINT p2;
  1507. PDWORD p3;
  1508. register PSETSYSCOLORS16 parg16;
  1509. INT BufElements[SSC_BUF_SIZE];
  1510. GETARGPTR(pFrame, sizeof(SETSYSCOLORS16), parg16);
  1511. p2 = STACKORHEAPALLOC(INT32(parg16->f1) * sizeof(INT), sizeof(BufElements), BufElements);
  1512. getintarray16(parg16->f2, INT32(parg16->f1), p2);
  1513. GETDWORDARRAY16(parg16->f3, INT32(parg16->f1), p3);
  1514. if (SetSysColors(
  1515. INT32(parg16->f1),
  1516. p2,
  1517. p3
  1518. ) == FALSE) {
  1519. #ifndef i386
  1520. PDWORD p4;
  1521. ULONG BufRGB [SSC_BUF_SIZE];
  1522. // On RISC platforms, SetSysColors could fail if the third parameter
  1523. // is unaligned. We need to check that and copy it to an aligned
  1524. // buffer before making this call. Win16 SetSysColor never fails
  1525. // so on x86 if this ever fails under NT, it will just pass through.
  1526. if ((ULONG)p3 & 3) {
  1527. p4 = STACKORHEAPALLOC(INT32(parg16->f1) * sizeof(INT), sizeof(BufRGB), BufRGB);
  1528. RtlMoveMemory ((PVOID)p4, (CONST VOID *)p3,
  1529. INT32(parg16->f1) * sizeof(ULONG));
  1530. SetSysColors(
  1531. INT32(parg16->f1),
  1532. p2,
  1533. p4
  1534. );
  1535. STACKORHEAPFREE(p4, BufRGB);
  1536. }
  1537. #endif
  1538. }
  1539. FREEDWORDARRAY16(p3);
  1540. STACKORHEAPFREE(p2, BufElements);
  1541. FREEARGPTR(parg16);
  1542. RETURN(0);
  1543. }
  1544. /*++
  1545. void InvalidateRect(<hwnd>, <lpRect>, <bErase>)
  1546. HWND <hwnd>;
  1547. LPRECT <lpRect>;
  1548. BOOL <bErase>;
  1549. The %InvalidateRect% function invalidates the client area within the given
  1550. rectangle by adding that rectangle to the window's update region. The
  1551. invalidated rectangle, along with all other areas in the update region, is
  1552. marked for painting when the next WM_PAINT message occurs. The invalidated
  1553. areas accumulate in the update region until the region is processed when the
  1554. next WM_PAINT message occurs, or the region is validated by using the
  1555. %ValidateRect% or %ValidateRgn% function.
  1556. The <bErase> parameter specifies whether the background within the update
  1557. area is to be erased when the update region is processed. If <bErase> is
  1558. TRUE, the background is erased when the %BeginPaint% function is called;
  1559. if <bErase> is FALSE, the background remains unchanged. If <bErase> is
  1560. TRUE for any part of the update region, the background in the entire
  1561. region is erased, not just in the given part.
  1562. <hwnd>
  1563. Identifies the window whose update region is to be modified.
  1564. <lpRect>
  1565. Points to a %RECT% structure that contains the rectangle
  1566. (in client coordinates) to be added to the update region. If the
  1567. <lpRect> parameter is NULL, the entire client area is added to the
  1568. region.
  1569. <bErase>
  1570. Specifies whether the background within the update region is to
  1571. be erased.
  1572. This function does not return a value.
  1573. Windows sends a WM_PAINT message to a window whenever its update region is
  1574. not empty and there are no other messages in the application queue for that
  1575. window.
  1576. --*/
  1577. ULONG FASTCALL WU32ValidateRect(PVDMFRAME pFrame)
  1578. {
  1579. RECT t2, *p2;
  1580. register PVALIDATERECT16 parg16;
  1581. GETARGPTR(pFrame, sizeof(VALIDATERECT16), parg16);
  1582. p2 = GETRECT16(parg16->f2, &t2);
  1583. ValidateRect(
  1584. HWND32(parg16->f1),
  1585. p2
  1586. );
  1587. FREEARGPTR(parg16);
  1588. RETURN(1); // Win 3.x always returned 1 as a side-effect of jmping to
  1589. // IRedrawWindow [core\user\wmupdate.c] - MarkRi 5/93
  1590. }
  1591. /*++
  1592. void InvalidateRgn(<hwnd>, <hRgn>, <bErase>)
  1593. HWND <hwnd>;
  1594. HRGN <hRgn>;
  1595. BOOL <bErase>;
  1596. The %InvalidateRgn% function invalidates the client area within the given
  1597. region by adding it to the current update region of the given window. The
  1598. invalidated region, along with all other areas in the update region, is
  1599. marked for painting when the next WM_PAINT message occurs. The invalidated
  1600. areas accumulate in the update region until the region is processed when the
  1601. next WM_PAINT message occurs, or the region is validated by using the
  1602. %ValidateRect% or %ValidateRgn% function.
  1603. The <bErase> parameter specifies whether the background within the update
  1604. area is to be erased when the update region is processed. If <bErase> is
  1605. TRUE, the background is erased when the %BeginPaint% function is called; if
  1606. <bErase> is FALSE, the background remains unchanged. If <bErase> is TRUE for
  1607. any part of the update region, the background in the entire region is
  1608. erased, not just in the given part.
  1609. <hwnd>
  1610. Identifies the window whose update region is to be modified.
  1611. <hRgn>
  1612. Identifies the region to be added to the update region. The
  1613. region is assumed to have client coordinates.
  1614. <bErase>
  1615. Specifies whether the background within the update region is to
  1616. be erased.
  1617. This function does not return a value.
  1618. Windows sends a WM_PAINT message to a window whenever its update region is
  1619. not empty and there are no other messages in the application queue for that
  1620. window.
  1621. The given region must have been previously created by using one of the
  1622. region functions (for more information, see Chapter 1, Window Manager
  1623. Interface Functions).
  1624. --*/
  1625. ULONG FASTCALL WU32ValidateRgn(PVDMFRAME pFrame)
  1626. {
  1627. register PVALIDATERGN16 parg16;
  1628. GETARGPTR(pFrame, sizeof(VALIDATERGN16), parg16);
  1629. ValidateRgn(
  1630. HWND32(parg16->f1),
  1631. HRGN32(parg16->f2)
  1632. );
  1633. FREEARGPTR(parg16);
  1634. RETURN(1); // Win 3.x always returned 1 as a side-effect of jmping to
  1635. // IRedrawWindow [core\user\wmupdate.c] - MarkRi 5/93
  1636. }
  1637. /*++
  1638. BOOL WinHelp(<hwnd>, <lpHelpFile>, <wCommand>, <dwData>)
  1639. HWND <hwnd>;
  1640. LPSTR <lpHelpFile>;
  1641. WORD <wCommand>;
  1642. DWORD <dwData>;
  1643. This function invokes the Windows Help application and passes optional data
  1644. indicating the nature of the help requested by the application. The
  1645. application specifies the name and, where required, the directory path of
  1646. the help file which the Help application is to display.
  1647. <hwnd>
  1648. Identifies the window requesting help.
  1649. <lpHelpFile>
  1650. Points to a null-terminated string containing the directory
  1651. path, if needed, and the name of the help file which the Help
  1652. application is to display.
  1653. <wCommand>
  1654. Specifies the type of help requested. It may be any one of the
  1655. following values:
  1656. HELP_CONTEXT
  1657. Displays help for a particular context identified by a 32-bit unsigned
  1658. integer value in dwData.
  1659. HELP_HELPONHELP
  1660. Displays help for using the help application itself. If the <wCommand>
  1661. parameter is set to HELP_HELPONHELP, %WinHelp% ignores the
  1662. <lpHelpFile> and <dwData> parameters.
  1663. HELP_INDEX
  1664. Displays the index of the specified help file. An application should use
  1665. this value only for help files with a single index. It should not use
  1666. this value with HELP_SETINDEX.
  1667. HELP_MULTIKEY
  1668. Displays help for a key word in an alternate keyword table.
  1669. HELP_QUIT
  1670. Notifies the help application that the specified help file is no longer
  1671. in use.
  1672. HELP_SETINDEX
  1673. Sets the context specified by the <dwData> parameter as the current
  1674. index for the help file specified by the <lpHelpFile> parameter. This
  1675. index remains current until the user accesses a different help file. To
  1676. help ensure that the correct index remains set, the application should
  1677. call %WinHelp% with <wCommand> set to HELP_SETINDEX (with <dwData>
  1678. specifying the corresponding context identifier) following each call to
  1679. %WinHelp% with <wCommand> set to HELP_CONTEXT. An application should use
  1680. this value only for help files with more than one index. It should not
  1681. use this value with HELP_INDEX.
  1682. <dwData>
  1683. %DWORD% Specifies the context or key word of the help requested. If
  1684. <wCommand> is HELP_CONTEXT, <dwData> is a 32-bit unsigned integer
  1685. containing a context-identifier number. If <wCommand> is HELP_KEY,
  1686. <dwData> is a long pointer to a null-terminated string that contains a
  1687. key word identifying the help topic. If <wCommand> is HELP_MULTIKEY,
  1688. <dwData> is a long pointer to a %MULTIKEYHELP% structure.
  1689. Otherwise, <dwData> is ignored and should be set to NULL.
  1690. The return value specifies the outcome of the function. It is TRUE if the
  1691. function was successful. Otherwise it is FALSE.
  1692. The application must call %WinHelp% with <wCommand> set to HELP_QUIT before
  1693. closing the window that requested the help. The Help application will not
  1694. actually terminate until all applications that have requested help have
  1695. called %WinHelp% with <wCommand> set to HELP_QUIT.
  1696. --*/
  1697. /*++
  1698. RAID bug # 394455
  1699. 05/19/2001 alexsm
  1700. Some applications were having problems finding and displaying their helpfiles
  1701. via the 16 bit winhelp. These issues can be fixed by redirecting the calls to
  1702. winhlp32.
  1703. This redirection is activitated by the WOWCFEX_USEWINHELP32 compat flag. The flag
  1704. is checked in the IWinHelp() function in user.exe. It redirects the call, along with
  1705. its parameters, to this 32 bit thunk.
  1706. --*/
  1707. ULONG FASTCALL WU32WinHelp(PVDMFRAME pFrame)
  1708. {
  1709. ULONG ul;
  1710. PSZ psz2;
  1711. register PWIN32WINHELP16 parg16;
  1712. DWORD dwCommand;
  1713. DWORD dwData;
  1714. UINT cb;
  1715. MULTIKEYHELP *lpmkey;
  1716. PMULTIKEYHELP16 pmkey16;
  1717. HELPWININFO hwinfo;
  1718. PHELPWININFO16 phwinfo16;
  1719. UpdateDosCurrentDirectory(DIR_DOS_TO_NT);
  1720. GETARGPTR(pFrame, sizeof(WIN32WINHELP16), parg16);
  1721. GETPSZPTR(parg16->f2, psz2);
  1722. dwCommand = WORD32(parg16->f3);
  1723. switch (dwCommand) {
  1724. case HELP_KEY:
  1725. case HELP_COMMAND:
  1726. case HELP_PARTIALKEY:
  1727. GETPSZPTR(parg16->f4, (PSZ)dwData);
  1728. break;
  1729. case HELP_HELPONHELP:
  1730. //
  1731. // some apps (eg multimedia raid#) pass along a help file name which confuses winhlp32.exe
  1732. // by definition the help gfile name parameter is meaningless.
  1733. //
  1734. psz2 = NULL;
  1735. dwData = 0;
  1736. break;
  1737. case HELP_MULTIKEY:
  1738. GETVDMPTR(parg16->f4, sizeof(MULTIKEYHELP16), pmkey16);
  1739. cb = FETCHWORD(pmkey16->mkSize);
  1740. FREEVDMPTR(pmkey16);
  1741. GETVDMPTR(parg16->f4, cb, pmkey16);
  1742. //
  1743. // It is my understanding that 'mkSize' is the total
  1744. // data length and NOT just sizeof(MULTIKEYHELP)
  1745. //
  1746. cb += sizeof(MULTIKEYHELP) - sizeof(MULTIKEYHELP16);
  1747. lpmkey = (MULTIKEYHELP *)malloc_w(cb);
  1748. if (lpmkey) {
  1749. lpmkey->mkSize = cb;
  1750. lpmkey->mkKeylist = pmkey16->mkKeylist;
  1751. strcpy(lpmkey->szKeyphrase, pmkey16->szKeyphrase);
  1752. }
  1753. FREEVDMPTR(pmkey16);
  1754. dwData = (DWORD)lpmkey;
  1755. break;
  1756. case HELP_SETWINPOS:
  1757. GETVDMPTR(parg16->f4, sizeof(HELPWININFO16), phwinfo16);
  1758. hwinfo.wStructSize = (int)(FETCHWORD(phwinfo16->wStructSize) +
  1759. (sizeof(HELPWININFO) - sizeof(HELPWININFO16)));
  1760. hwinfo.x = (int)FETCHSHORT(phwinfo16->x);
  1761. hwinfo.y = (int)FETCHSHORT(phwinfo16->y);
  1762. hwinfo.dx = (int)FETCHSHORT(phwinfo16->dx);
  1763. hwinfo.dy = (int)FETCHSHORT(phwinfo16->dy);
  1764. hwinfo.wMax = (int)FETCHSHORT(phwinfo16->wMax);
  1765. hwinfo.rgchMember[0] = (CHAR)phwinfo16->rgchMember[0];
  1766. hwinfo.rgchMember[1] = (CHAR)phwinfo16->rgchMember[1];
  1767. FREEVDMPTR(phwinfo16);
  1768. dwData = (DWORD)&hwinfo;
  1769. break;
  1770. default:
  1771. dwData = DWORD32(parg16->f4);
  1772. break;
  1773. }
  1774. LOGDEBUG(LOG_WARNING,
  1775. ("WU32Winhelp: Paramaters passed to WinHelp():/nHwnd=%x psz2=%x dwCommand=%x dwData=%x",
  1776. parg16->f1, psz2, dwCommand, dwData));
  1777. ul = GETBOOL16(WinHelp(HWND32(parg16->f1), psz2, dwCommand, dwData));
  1778. switch (dwCommand) {
  1779. case HELP_KEY:
  1780. case HELP_COMMAND:
  1781. case HELP_PARTIALKEY:
  1782. FREEPSZPTR((PSZ)dwData);
  1783. break;
  1784. case HELP_MULTIKEY:
  1785. if (lpmkey)
  1786. free_w(lpmkey);
  1787. break;
  1788. case HELP_SETWINPOS:
  1789. break;
  1790. default:
  1791. break;
  1792. }
  1793. FREEPSZPTR(psz2);
  1794. FREEARGPTR(parg16);
  1795. RETURN(ul);
  1796. }
  1797. #pragma pack(1)
  1798. //
  1799. // win16 Module Table structure (based off of ne header)
  1800. // see wow16\inc\newexe.inc
  1801. //
  1802. typedef struct _NE_MODULE {
  1803. USHORT ne_magic; // Magic number
  1804. USHORT ne_usage; // usage count of module
  1805. USHORT ne_enttab; // Offset of Entry Table
  1806. USHORT ne_pnextexe; // sel next module table
  1807. USHORT ne_pautodata; // offset autodata seg table
  1808. USHORT ne_pfileinfo; // offset load file info
  1809. USHORT ne_flags; // Flag word
  1810. USHORT ne_autodata; // Automatic data segment number
  1811. USHORT ne_heap; // Initial heap allocation
  1812. USHORT ne_stack; // Initial stack allocation
  1813. ULONG ne_csip; // Initial CS:IP setting
  1814. ULONG ne_sssp; // Initial SS:SP setting
  1815. USHORT ne_cseg; // Count of file segments
  1816. USHORT ne_cmod; // Entries in Module Reference Table
  1817. USHORT ne_cbnrestab; // Size of non-resident name table
  1818. USHORT ne_segtab; // Offset of Segment Table
  1819. USHORT ne_rsrctab; // Offset of Resource Table
  1820. USHORT ne_restab; // Offset of resident name table
  1821. USHORT ne_modtab; // Offset of Module Reference Table
  1822. USHORT ne_imptab; // Offset of Imported Names Table
  1823. ULONG ne_nrestab; // Offset of Non-resident Names Table
  1824. USHORT ne_cmovent; // Count of movable entries
  1825. USHORT ne_align; // Segment alignment shift count
  1826. USHORT ne_cres; // Count of resource segments
  1827. UCHAR ne_exetyp; // Target Operating system
  1828. UCHAR ne_flagsothers; // Other .EXE flags
  1829. USHORT ne_pretthunks; // offset to return thunks
  1830. USHORT ne_psegrefbytes; // offset to segment ref. bytes
  1831. USHORT ne_swaparea; // Minimum code swap area size
  1832. USHORT ne_expver; // Expected Windows version number
  1833. } NEMODULE;
  1834. typedef NEMODULE UNALIGNED *PNEMODULE;
  1835. #pragma pack()
  1836. #ifdef FE_IME
  1837. VOID WN32WINNLSSImeNotifyTaskExit(); // wnman.c
  1838. #endif // FE_IME
  1839. //
  1840. // Performs Module cleanup (win31:tmdstroy.c\ModuleUnload())
  1841. //
  1842. void
  1843. ModuleUnload(
  1844. HAND16 hModule16,
  1845. BOOL fTaskExit
  1846. )
  1847. {
  1848. PNEMODULE pNeModule = SEGPTR(hModule16, 0);
  1849. PTD ptd = CURRENTPTD();
  1850. if (pNeModule->ne_usage == 1 || fTaskExit) {
  1851. W32UnhookHooks(hModule16,FALSE);
  1852. }
  1853. if (fTaskExit) {
  1854. ptd->dwFlags |= TDF_TASKCLEANUPDONE;
  1855. (pfnOut.pfnWOWCleanup)(HINSTRES32(ptd->hInst16), (DWORD) ptd->htask16);
  1856. }
  1857. if (pNeModule->ne_usage > 1) {
  1858. return;
  1859. }
  1860. #ifdef FE_IME
  1861. /*
  1862. * We need to notify IMM that this WOW task is quiting before
  1863. * calling WowCleanup or IME windows can not receive WM_DESTROY
  1864. * and will fail to clean up their 32bit resource.
  1865. */
  1866. if ( fTaskExit ) {
  1867. WN32WINNLSSImeNotifyTaskExit();
  1868. }
  1869. #endif // FE_IME
  1870. /* WowCleanup, UserSrv private api
  1871. * It cleans up any USER objects created by this hModule, most notably
  1872. * classes, and subclassed windows.
  1873. */
  1874. (pfnOut.pfnWOWModuleUnload)((HANDLE)hModule16);
  1875. RemoveHmodFromCache(hModule16);
  1876. }
  1877. WORD
  1878. FASTCALL
  1879. WOWGetProcModule16(
  1880. DWORD vpfn
  1881. )
  1882. {
  1883. WOW32ASSERTMSG(gpfn16GetProcModule, "WOWGetProcModule16 called before gpfn16GetProcModule initialized.\n");
  1884. return (WORD) WOWCallback16(
  1885. gpfn16GetProcModule,
  1886. vpfn
  1887. );
  1888. }
  1889. /*++
  1890. BOOL SignalProc(<hwnd>, <lpHelpFile>, <wCommand>, <dwData>)
  1891. HWND <hwnd>;
  1892. LPSTR <lpHelpFile>;
  1893. WORD <wCommand>;
  1894. DWORD <dwData>;
  1895. This function provides the communication link between KERNEL and USER.
  1896. --*/
  1897. #define SG_EXIT 0x0020
  1898. #define SG_LOAD_DLL 0x0040
  1899. #define SG_EXIT_DLL 0x0080
  1900. #define SG_GP_FAULT 0x0666
  1901. ULONG FASTCALL WU32SignalProc(PVDMFRAME pFrame)
  1902. {
  1903. WORD message;
  1904. LONG lparam;
  1905. register PSIGNALPROC16 parg16;
  1906. HAND16 hModule16;
  1907. PTD ptd;
  1908. GETARGPTR(pFrame, sizeof(SIGNALPROC16), parg16);
  1909. message = FETCHWORD(parg16->f2);
  1910. switch( message ) {
  1911. case SG_EXIT:
  1912. case SG_GP_FAULT:
  1913. lparam = FETCHDWORD(parg16->f4);
  1914. ptd = CURRENTPTD();
  1915. ptd->dwFlags |= TDF_IGNOREINPUT;
  1916. ptd->cStackAlloc16 = 0;
  1917. ModuleUnload(GetExePtr16((HAND16)HIWORD(lparam)), TRUE);
  1918. FreeCursorIconAlias(ptd->htask16, CIALIAS_HTASK);
  1919. break;
  1920. case SG_LOAD_DLL:
  1921. break;
  1922. case SG_EXIT_DLL:
  1923. hModule16 = FETCHWORD(parg16->f1);
  1924. ModuleUnload(hModule16, FALSE);
  1925. FreeCursorIconAlias(hModule16, CIALIAS_HMOD);
  1926. break;
  1927. }
  1928. FREEARGPTR(parg16);
  1929. RETURN(0);
  1930. }
  1931. // This routine checks the RECT structure (in PAINTSTRUCT) on BeginPaint
  1932. // call and updates its fields for maximum positive and minimum negative
  1933. // numbers for 16 bit apps to be compatible with win 3.1.
  1934. //
  1935. void W32FixPaintRect (VPVOID vpPaint, LPPAINTSTRUCT ps)
  1936. {
  1937. SHORT i;
  1938. PPAINTSTRUCT16 pps16;
  1939. GETVDMPTR(vpPaint, sizeof(PAINTSTRUCT16), pps16);
  1940. if (i = ConvertInt16 (ps->rcPaint.left)) {
  1941. STORESHORT(pps16->rcPaint.left, i);
  1942. }
  1943. if (i = ConvertInt16 (ps->rcPaint.top)) {
  1944. STORESHORT(pps16->rcPaint.top, i);
  1945. }
  1946. if (i = ConvertInt16 (ps->rcPaint.right)) {
  1947. STORESHORT(pps16->rcPaint.right, i);
  1948. }
  1949. if (i = ConvertInt16 (ps->rcPaint.bottom)) {
  1950. STORESHORT(pps16->rcPaint.bottom, i);
  1951. }
  1952. FLUSHVDMPTR(vpPaint, sizeof(PAINTSTRUCT16), pps16);
  1953. FREEVDMPTR(pps16);
  1954. }
  1955. SHORT ConvertInt16 (LONG x)
  1956. {
  1957. if (x > (LONG)0x7fff)
  1958. return((SHORT)0x7fff);
  1959. if (x < (LONG)0xffff8000)
  1960. return((SHORT)0x8000);
  1961. return ((SHORT)0);
  1962. }