Leaked source code of windows server 2003
You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

861 lines
24 KiB

  1. /*++
  2. *
  3. * WOW v1.0
  4. *
  5. * Copyright (c) 1991, Microsoft Corporation
  6. *
  7. * WUSER31.C
  8. * WOW32 16-bit Win 3.1 User API support
  9. *
  10. * History:
  11. * Created 16-Mar-1992 by Chandan S. Chauhan (ChandanC)
  12. --*/
  13. #include "precomp.h"
  14. #pragma hdrstop
  15. MODNAME(wuser31.c);
  16. ULONG FASTCALL WU32DlgDirSelectComboBoxEx(PVDMFRAME pFrame)
  17. {
  18. ULONG ul;
  19. PSZ psz2;
  20. VPVOID vp;
  21. register PDLGDIRSELECTCOMBOBOXEX16 parg16;
  22. GETARGPTR(pFrame, sizeof(DLGDIRSELECTCOMBOBOXEX16), parg16);
  23. GETVDMPTR(parg16->f2, INT32(parg16->f3), psz2);
  24. vp = parg16->f2;
  25. // note: this calls back to 16-bit code and could invalidate the flat ptrs
  26. ul = GETBOOL16(DlgDirSelectComboBoxEx(
  27. HWND32(parg16->f1),
  28. psz2,
  29. INT32(parg16->f3),
  30. WORD32(parg16->f4) // we zero-extend window IDs everywhere
  31. ));
  32. // special case to keep common dialog structs in sync (see wcommdlg.c)
  33. Check_ComDlg_pszptr(CURRENTPTD()->CommDlgTd, vp);
  34. FLUSHVDMPTR(parg16->f2, INT32(parg16->f3), psz2);
  35. FREEVDMPTR(psz2);
  36. FREEARGPTR(parg16);
  37. RETURN (ul);
  38. }
  39. ULONG FASTCALL WU32DlgDirSelectEx(PVDMFRAME pFrame)
  40. {
  41. ULONG ul;
  42. PSZ psz2;
  43. VPVOID vp;
  44. register PDLGDIRSELECTEX16 parg16;
  45. GETARGPTR(pFrame, sizeof(DLGDIRSELECTEX16), parg16);
  46. GETVDMPTR(parg16->f2, INT32(parg16->f3), psz2);
  47. vp = parg16->f2;
  48. ul = GETBOOL16(DlgDirSelectEx(
  49. HWND32(parg16->f1),
  50. psz2,
  51. INT32(parg16->f3),
  52. WORD32(parg16->f4)
  53. ));
  54. // special case to keep common dialog structs in sync (see wcommdlg.c)
  55. Check_ComDlg_pszptr(CURRENTPTD()->CommDlgTd, vp);
  56. FLUSHVDMPTR(parg16->f2, INT32(parg16->f3), psz2);
  57. FREEVDMPTR(psz2);
  58. FREEARGPTR(parg16);
  59. RETURN (ul);
  60. }
  61. ULONG FASTCALL WU32GetClipCursor(PVDMFRAME pFrame)
  62. {
  63. RECT Rect;
  64. register PGETCLIPCURSOR16 parg16;
  65. GETARGPTR(pFrame, sizeof(GETCLIPCURSOR16), parg16);
  66. GetClipCursor(&Rect);
  67. PUTRECT16(parg16->f1, &Rect);
  68. FREEARGPTR(parg16);
  69. RETURN (0); // GetClipCursor has no return value
  70. }
  71. ULONG FASTCALL WU32GetDCEx(PVDMFRAME pFrame)
  72. {
  73. ULONG ul;
  74. register PGETDCEX16 parg16;
  75. HAND16 htask16 = pFrame->wTDB;
  76. GETARGPTR(pFrame, sizeof(GETDCEX16), parg16);
  77. // This may need the same logic as WU32GetDC() and WU32GetWindowDC() to
  78. // prevent a handle leak during the life of a given task (or at least until
  79. // the app calls GetDC() or GetWindowDC() which will empty the cache):
  80. //
  81. // if (CACHENOTEMPTY()) {
  82. // ReleaseCachedDCs(htask16, parg16->f1, 0, 0, SRCHDC_TASK16_HWND16);
  83. // }
  84. // CURRENTPTD()->ulLastDesktophDC = 0;
  85. //
  86. // We may not be removing cached DC's in this case because the cache code
  87. // has no concept of "clip regions" which are associated with this API. I
  88. // kind of doubt it because the SRCHDC_TASK16_HWND16 flag specified in the
  89. // other two cases wlll cause all cached DC's to be released
  90. // indiscriminantly.
  91. ul = GETHDC16(GetDCEx(HWND32(parg16->f1),
  92. HRGN32(parg16->f2),
  93. DWORD32(parg16->f3)));
  94. if (ul)
  95. StoreDC(htask16, parg16->f1, (HAND16)ul);
  96. FREEARGPTR(parg16);
  97. RETURN (ul);
  98. }
  99. ULONG FASTCALL WU32RedrawWindow(PVDMFRAME pFrame)
  100. {
  101. ULONG ul;
  102. RECT Rect, *p2;
  103. register PREDRAWWINDOW16 parg16;
  104. GETARGPTR(pFrame, sizeof(REDRAWWINDOW16), parg16);
  105. p2 = GETRECT16 (parg16->f2, &Rect);
  106. ul = GETBOOL16(RedrawWindow(HWND32(parg16->f1),
  107. p2,
  108. HRGN32(parg16->f3),
  109. WORD32(parg16->f4)));
  110. FREEARGPTR(parg16);
  111. RETURN (ul);
  112. }
  113. ULONG FASTCALL WU32ScrollWindowEx(PVDMFRAME pFrame)
  114. {
  115. ULONG ul;
  116. register PSCROLLWINDOWEX16 parg16;
  117. RECT RectScroll, *p4;
  118. RECT RectClip, *p5;
  119. RECT RectUpdate;
  120. GETARGPTR(pFrame, sizeof(SCROLLWINDOWEX16), parg16);
  121. p4 = GETRECT16 (parg16->f4, &RectScroll);
  122. p5 = GETRECT16 (parg16->f5, &RectClip);
  123. ul = GETINT16(ScrollWindowEx(HWND32(parg16->f1),
  124. INT32(parg16->f2),
  125. INT32(parg16->f3),
  126. p4,
  127. p5,
  128. HRGN32(parg16->f6),
  129. &RectUpdate,
  130. UINT32(parg16->f8)));
  131. PUTRECT16 (parg16->f7, &RectUpdate);
  132. FREEARGPTR(parg16);
  133. RETURN (ul);
  134. }
  135. ULONG FASTCALL WU32SystemParametersInfo(PVDMFRAME pFrame)
  136. {
  137. ULONG ul = 0;
  138. register PSYSTEMPARAMETERSINFO16 parg16;
  139. UINT wParam;
  140. LONG vParam;
  141. LOGFONT lf;
  142. INT iMouse[3];
  143. PVOID lpvParam;
  144. PWORD16 lpw;
  145. PDWORD16 lpdw;
  146. RECT rect;
  147. #ifndef _X86_
  148. DWORD dwSize;
  149. LPBYTE lpFree = NULL;
  150. #endif
  151. GETARGPTR(pFrame, sizeof(SYSTEMPARAMETERSINFO16), parg16);
  152. // Assume these parameters fly straight through; fix them up per option
  153. // if they don't
  154. wParam = parg16->f2;
  155. lpvParam = &vParam;
  156. switch (parg16->f1) {
  157. case SPI_GETICONTITLELOGFONT:
  158. wParam = sizeof(LOGFONT);
  159. lpvParam = &lf;
  160. break;
  161. case SPI_SETICONTITLELOGFONT:
  162. GETLOGFONT16(parg16->f3, &lf);
  163. wParam = sizeof(LOGFONT);
  164. lpvParam = &lf;
  165. break;
  166. case SPI_GETMOUSE:
  167. case SPI_SETMOUSE:
  168. lpvParam = iMouse;
  169. break;
  170. case SPI_SETDESKPATTERN:
  171. // For the pattern if wParam == -1 then no string for lpvParam copy as is
  172. if (parg16->f2 == 0xFFFF) {
  173. wParam = 0xFFFFFFFF;
  174. lpvParam = (PVOID)parg16->f3;
  175. break;
  176. }
  177. // Otherwise fall through and do a string check
  178. case SPI_SETDESKWALLPAPER:
  179. // lpvParam (f3) is may be 0,-1 or a string
  180. if (parg16->f3 == 0xFFFF) {
  181. lpvParam = (PVOID)0xFFFFFFFF;
  182. break;
  183. }
  184. if (parg16->f3 == 0) {
  185. lpvParam = (PVOID)NULL;
  186. break;
  187. }
  188. // Otherwise fall through and do a string copy
  189. case SPI_LANGDRIVER:
  190. GETPSZPTR(parg16->f3, lpvParam);
  191. break;
  192. //
  193. // SPI_GET structures pointed to by pvParam, size in first dword of struct.
  194. // Note all these assume the Win16 and Win32 structures are equal.
  195. // These are all new for Win95 and thankfully that's true. However unlike
  196. // Win95 we need to ensure the buffer passed to Win32 is aligned on RISC.
  197. // To have common code to thunk all these various structures, we align to
  198. // 16 bytes.
  199. //
  200. case SPI_GETACCESSTIMEOUT:
  201. case SPI_GETANIMATION:
  202. case SPI_GETNONCLIENTMETRICS:
  203. case SPI_GETMINIMIZEDMETRICS:
  204. case SPI_GETICONMETRICS:
  205. case SPI_GETFILTERKEYS:
  206. case SPI_GETSTICKYKEYS:
  207. case SPI_GETTOGGLEKEYS:
  208. case SPI_GETMOUSEKEYS:
  209. case SPI_GETSOUNDSENTRY:
  210. #ifndef _X86_
  211. GETMISCPTR(parg16->f3, lpdw);
  212. dwSize = *lpdw;
  213. lpFree = malloc_w(dwSize + 16);
  214. if(lpFree) {
  215. lpvParam = (LPVOID)(((DWORD)lpFree + 16) & ~(16 - 1));
  216. *(PDWORD16)lpvParam = dwSize;
  217. break;
  218. }
  219. else {
  220. lpvParam = NULL;
  221. }
  222. #endif // otherwise fall through to simple struct case
  223. //
  224. // SPI_SET structures pointed to by pvParam, size in first dword of struct.
  225. // Note all these assume the Win16 and Win32 structures are equal.
  226. // These are all new for Win95 and thankfully that's true. However unlike
  227. // Win95 we need to ensure the buffer passed to Win32 is aligned on RISC.
  228. // To have common code to thunk all these various structures, we align to
  229. // 16 bytes.
  230. //
  231. case SPI_SETANIMATION:
  232. case SPI_SETICONMETRICS:
  233. case SPI_SETMINIMIZEDMETRICS:
  234. case SPI_SETNONCLIENTMETRICS:
  235. case SPI_SETACCESSTIMEOUT:
  236. #ifndef _X86_
  237. GETMISCPTR(parg16->f3, lpdw);
  238. dwSize = *lpdw;
  239. lpFree = malloc_w(dwSize + 16);
  240. if(lpFree) {
  241. lpvParam = (LPVOID)(((DWORD)lpFree + 16) & ~(16 - 1));
  242. RtlCopyMemory(lpvParam, lpdw, dwSize);
  243. break;
  244. }
  245. else {
  246. lpvParam = NULL;
  247. }
  248. #endif // otherwise fall through to simple struct case
  249. //
  250. // structures pointed to by pvParam, size in uiParam or first dword.
  251. // Note all these assume the Win16 and Win32 structures are equal.
  252. // These are all new for Win95 and thankfully that's true.
  253. //
  254. case SPI_GETHIGHCONTRAST:
  255. case SPI_GETSERIALKEYS:
  256. case SPI_SETDEFAULTINPUTLANG:
  257. case SPI_SETFILTERKEYS:
  258. case SPI_SETHIGHCONTRAST:
  259. case SPI_SETMOUSEKEYS:
  260. case SPI_SETSERIALKEYS:
  261. case SPI_SETSHOWSOUNDS:
  262. case SPI_SETSOUNDSENTRY:
  263. case SPI_SETSTICKYKEYS:
  264. case SPI_SETTOGGLEKEYS:
  265. GETMISCPTR(parg16->f3, lpvParam);
  266. break;
  267. //
  268. // pvParam points to WORD or BOOL
  269. //
  270. case SPI_GETBEEP:
  271. case SPI_GETBORDER:
  272. case SPI_GETDRAGFULLWINDOWS:
  273. case SPI_GETFASTTASKSWITCH:
  274. case SPI_GETFONTSMOOTHING:
  275. case SPI_GETGRIDGRANULARITY:
  276. case SPI_GETICONTITLEWRAP:
  277. case SPI_GETKEYBOARDSPEED:
  278. case SPI_GETKEYBOARDDELAY:
  279. case SPI_GETKEYBOARDPREF:
  280. case SPI_GETLOWPOWERACTIVE:
  281. case SPI_GETLOWPOWERTIMEOUT:
  282. case SPI_GETMENUDROPALIGNMENT:
  283. case SPI_GETMOUSETRAILS:
  284. case SPI_GETPOWEROFFACTIVE:
  285. case SPI_GETPOWEROFFTIMEOUT:
  286. case SPI_GETSCREENREADER:
  287. case SPI_GETSCREENSAVEACTIVE:
  288. case SPI_GETSCREENSAVETIMEOUT:
  289. case SPI_GETSHOWSOUNDS:
  290. case SPI_SCREENSAVERRUNNING:
  291. break;
  292. //
  293. // pvParam points to DWORD
  294. //
  295. case SPI_GETDEFAULTINPUTLANG:
  296. break;
  297. //
  298. // pvParam not used
  299. //
  300. case SPI_GETWINDOWSEXTENSION:
  301. case SPI_ICONHORIZONTALSPACING:
  302. case SPI_ICONVERTICALSPACING:
  303. case SPI_SETBEEP:
  304. case SPI_SETBORDER:
  305. case SPI_SETDOUBLECLICKTIME:
  306. case SPI_SETDOUBLECLKHEIGHT:
  307. case SPI_SETDOUBLECLKWIDTH:
  308. case SPI_SETDRAGFULLWINDOWS:
  309. case SPI_SETDRAGHEIGHT:
  310. case SPI_SETDRAGWIDTH:
  311. case SPI_SETFASTTASKSWITCH:
  312. case SPI_SETFONTSMOOTHING:
  313. case SPI_SETGRIDGRANULARITY:
  314. case SPI_SETHANDHELD:
  315. case SPI_SETICONTITLEWRAP:
  316. case SPI_SETKEYBOARDDELAY:
  317. case SPI_SETKEYBOARDPREF:
  318. case SPI_SETKEYBOARDSPEED:
  319. case SPI_SETLANGTOGGLE:
  320. case SPI_SETLOWPOWERACTIVE:
  321. case SPI_SETLOWPOWERTIMEOUT:
  322. case SPI_SETMENUDROPALIGNMENT:
  323. case SPI_SETMOUSEBUTTONSWAP:
  324. case SPI_SETMOUSETRAILS:
  325. case SPI_SETPENWINDOWS:
  326. case SPI_SETPOWEROFFACTIVE:
  327. case SPI_SETPOWEROFFTIMEOUT:
  328. case SPI_SETSCREENREADER:
  329. case SPI_SETSCREENSAVEACTIVE:
  330. case SPI_SETSCREENSAVETIMEOUT:
  331. break;
  332. //
  333. // pvParam points to a RECT
  334. //
  335. case SPI_GETWORKAREA:
  336. case SPI_SETWORKAREA:
  337. GETRECT16(parg16->f3, &rect);
  338. lpvParam = ▭
  339. break;
  340. default:
  341. #ifdef DEBUG
  342. {
  343. DWORD dwSaveOptions = flOptions;
  344. flOptions |= OPT_DEBUG;
  345. LOGDEBUG(0, ("WARNING SystemParametersInfo case %d not pre-thunked in WOW!\n", parg16->f1));
  346. flOptions = dwSaveOptions;
  347. }
  348. #endif
  349. break;
  350. }
  351. ul = SystemParametersInfo(
  352. UINT32(parg16->f1),
  353. wParam,
  354. lpvParam,
  355. UINT32(parg16->f4)
  356. );
  357. switch (parg16->f1) {
  358. case SPI_GETICONTITLELOGFONT:
  359. PUTLOGFONT16(parg16->f3, sizeof(LOGFONT), lpvParam);
  360. break;
  361. case SPI_SETICONTITLELOGFONT:
  362. break;
  363. case SPI_GETMOUSE:
  364. case SPI_SETMOUSE:
  365. PUTINTARRAY16(parg16->f3, 3, lpvParam);
  366. break;
  367. case SPI_LANGDRIVER:
  368. case SPI_SETDESKWALLPAPER:
  369. FREEPSZPTR(lpvParam);
  370. break;
  371. case SPI_ICONHORIZONTALSPACING:
  372. case SPI_ICONVERTICALSPACING:
  373. // optional outee
  374. if (!parg16->f3)
  375. break;
  376. // fall through
  377. //
  378. // pvParam points to WORD or BOOL
  379. //
  380. case SPI_GETBEEP:
  381. case SPI_GETBORDER:
  382. case SPI_GETDRAGFULLWINDOWS:
  383. case SPI_GETFASTTASKSWITCH:
  384. case SPI_GETFONTSMOOTHING:
  385. case SPI_GETGRIDGRANULARITY:
  386. case SPI_GETICONTITLEWRAP:
  387. case SPI_GETKEYBOARDSPEED:
  388. case SPI_GETKEYBOARDDELAY:
  389. case SPI_GETKEYBOARDPREF:
  390. case SPI_GETLOWPOWERACTIVE:
  391. case SPI_GETLOWPOWERTIMEOUT:
  392. case SPI_GETMENUDROPALIGNMENT:
  393. case SPI_GETMOUSETRAILS:
  394. case SPI_GETPOWEROFFACTIVE:
  395. case SPI_GETPOWEROFFTIMEOUT:
  396. case SPI_GETSCREENREADER:
  397. case SPI_GETSCREENSAVEACTIVE:
  398. case SPI_GETSCREENSAVETIMEOUT:
  399. case SPI_GETSHOWSOUNDS:
  400. case SPI_SCREENSAVERRUNNING:
  401. GETVDMPTR(FETCHDWORD(parg16->f3), sizeof(*lpw), lpw);
  402. *lpw = (WORD)(*(LPLONG)lpvParam);
  403. FLUSHVDMPTR(FETCHDWORD(parg16->f3), sizeof(*lpw), lpw);
  404. FREEVDMPTR(lpw);
  405. break;
  406. //
  407. // pvParam points to DWORD
  408. //
  409. case SPI_GETDEFAULTINPUTLANG:
  410. GETVDMPTR(FETCHDWORD(parg16->f3), sizeof(*lpdw), lpdw);
  411. *lpdw = *(LPDWORD)lpvParam;
  412. FLUSHVDMPTR(FETCHDWORD(parg16->f3), sizeof(*lpdw), lpdw);
  413. FREEVDMPTR(lpdw);
  414. break;
  415. //
  416. // SPI_GET structures pointed to by pvParam, size in first dword of struct.
  417. // Note all these assume the Win16 and Win32 structures are equal.
  418. // These are all new for Win95 and thankfully that's true. However unlike
  419. // Win95 we need to ensure the buffer passed to Win32 is aligned. In order
  420. // to have common code to thunk all these various structures, we align to
  421. // 16 bytes.
  422. //
  423. case SPI_GETACCESSTIMEOUT:
  424. case SPI_GETANIMATION:
  425. case SPI_GETNONCLIENTMETRICS:
  426. case SPI_GETMINIMIZEDMETRICS:
  427. case SPI_GETICONMETRICS:
  428. case SPI_GETFILTERKEYS:
  429. case SPI_GETSTICKYKEYS:
  430. case SPI_GETTOGGLEKEYS:
  431. case SPI_GETMOUSEKEYS:
  432. case SPI_GETSOUNDSENTRY:
  433. #ifndef _X86_
  434. RtlCopyMemory(lpdw, lpvParam, dwSize);
  435. FREEMISCPTR(lpdw);
  436. break;
  437. #endif // otherwise fall through to simple struct case
  438. //
  439. // SPI_SET structures pointed to by pvParam, size in first dword of struct.
  440. // Note all these assume the Win16 and Win32 structures are equal.
  441. // These are all new for Win95 and thankfully that's true. However unlike
  442. // Win95 we need to ensure the buffer passed to Win32 is aligned. In order
  443. // to have common code to thunk all these various structures, we align to
  444. // 16 bytes.
  445. //
  446. case SPI_SETANIMATION:
  447. case SPI_SETICONMETRICS:
  448. case SPI_SETMINIMIZEDMETRICS:
  449. case SPI_SETNONCLIENTMETRICS:
  450. case SPI_SETACCESSTIMEOUT:
  451. #ifndef _X86_
  452. FREEMISCPTR(lpdw);
  453. break;
  454. #endif // otherwise fall through to simple struct case
  455. //
  456. // structures pointed to by pvParam, size in uiParam or first dword.
  457. // Note all these assume the Win16 and Win32 structures are equal.
  458. // These are all new for Win95 and thankfully that's true.
  459. //
  460. case SPI_GETHIGHCONTRAST:
  461. case SPI_GETSERIALKEYS:
  462. case SPI_SETDEFAULTINPUTLANG:
  463. case SPI_SETFILTERKEYS:
  464. case SPI_SETHIGHCONTRAST:
  465. case SPI_SETMOUSEKEYS:
  466. case SPI_SETSERIALKEYS:
  467. case SPI_SETSHOWSOUNDS:
  468. case SPI_SETSOUNDSENTRY:
  469. case SPI_SETSTICKYKEYS:
  470. case SPI_SETTOGGLEKEYS:
  471. FREEMISCPTR(lpvParam);
  472. break;
  473. //
  474. // pvParam not used
  475. //
  476. case SPI_GETWINDOWSEXTENSION:
  477. case SPI_SETBEEP:
  478. case SPI_SETBORDER:
  479. case SPI_SETDOUBLECLICKTIME:
  480. case SPI_SETDOUBLECLKHEIGHT:
  481. case SPI_SETDOUBLECLKWIDTH:
  482. case SPI_SETDRAGFULLWINDOWS:
  483. case SPI_SETDRAGHEIGHT:
  484. case SPI_SETDRAGWIDTH:
  485. case SPI_SETFASTTASKSWITCH:
  486. case SPI_SETFONTSMOOTHING:
  487. case SPI_SETGRIDGRANULARITY:
  488. case SPI_SETHANDHELD:
  489. case SPI_SETICONTITLEWRAP:
  490. case SPI_SETKEYBOARDDELAY:
  491. case SPI_SETKEYBOARDPREF:
  492. case SPI_SETKEYBOARDSPEED:
  493. case SPI_SETLANGTOGGLE:
  494. case SPI_SETLOWPOWERACTIVE:
  495. case SPI_SETLOWPOWERTIMEOUT:
  496. case SPI_SETMENUDROPALIGNMENT:
  497. case SPI_SETMOUSEBUTTONSWAP:
  498. case SPI_SETMOUSETRAILS:
  499. case SPI_SETPENWINDOWS:
  500. case SPI_SETPOWEROFFACTIVE:
  501. case SPI_SETPOWEROFFTIMEOUT:
  502. case SPI_SETSCREENREADER:
  503. case SPI_SETSCREENSAVEACTIVE:
  504. case SPI_SETSCREENSAVETIMEOUT:
  505. break;
  506. //
  507. // pvParam points to a RECT
  508. //
  509. case SPI_GETWORKAREA:
  510. case SPI_SETWORKAREA:
  511. PUTRECT16(parg16->f3, &rect);
  512. break;
  513. default:
  514. #ifdef DEBUG
  515. {
  516. DWORD dwSaveOptions = flOptions;
  517. flOptions |= OPT_DEBUG;
  518. LOGDEBUG(0, ("WARNING SystemParametersInfo case %d not post-thunked in WOW!\n", parg16->f1));
  519. flOptions = dwSaveOptions;
  520. }
  521. #endif
  522. break;
  523. }
  524. #ifndef _X86_
  525. if (lpFree) {
  526. free_w(lpFree);
  527. }
  528. #endif
  529. FREEARGPTR(parg16);
  530. RETURN (ul);
  531. }
  532. ULONG FASTCALL WU32SetWindowPlacement(PVDMFRAME pFrame)
  533. {
  534. ULONG ul = 0;
  535. register PSETWINDOWPLACEMENT16 parg16;
  536. WINDOWPLACEMENT wndpl;
  537. GETARGPTR(pFrame, sizeof(SETWINDOWPLACEMENT16), parg16);
  538. WINDOWPLACEMENT16TO32(parg16->f2, &wndpl);
  539. ul = GETBOOL16(SetWindowPlacement(HWND32(parg16->f1),
  540. &wndpl));
  541. FREEARGPTR(parg16);
  542. RETURN (ul);
  543. }
  544. ULONG FASTCALL WU32GetWindowPlacement(PVDMFRAME pFrame)
  545. {
  546. ULONG ul = 0;
  547. register PGETWINDOWPLACEMENT16 parg16;
  548. WINDOWPLACEMENT wndpl;
  549. GETARGPTR(pFrame, sizeof(GETWINDOWPLACEMENT16), parg16);
  550. wndpl.length = sizeof(WINDOWPLACEMENT);
  551. ul = GETBOOL16(GetWindowPlacement(HWND32(parg16->f1),
  552. &wndpl));
  553. WINDOWPLACEMENT32TO16(parg16->f2, &wndpl);
  554. FREEARGPTR(parg16);
  555. RETURN (ul);
  556. }
  557. ULONG FASTCALL WU32GetFreeSystemResources(PVDMFRAME pFrame)
  558. {
  559. ULONG ul = 90;
  560. UNREFERENCED_PARAMETER( pFrame );
  561. RETURN (ul);
  562. }
  563. ULONG FASTCALL WU32ExitWindowsExec(PVDMFRAME pFrame)
  564. {
  565. ULONG ul = 0;
  566. register PEXITWINDOWSEXEC16 parg16;
  567. LPSTR lpstrProgName;
  568. LPSTR lpstrCmdLine;
  569. UINT lengthProgName;
  570. UINT lengthCmdLine;
  571. BYTE abT[REGISTRY_BUFFER_SIZE];
  572. GETARGPTR(pFrame, sizeof(EXITWINDOWSEXEC16), parg16);
  573. GETPSZPTR(parg16->vpProgName, lpstrProgName);
  574. GETPSZPTR(parg16->vpCmdLine, lpstrCmdLine);
  575. lengthProgName = (lpstrProgName) ? strlen(lpstrProgName) : 0;
  576. lengthCmdLine = (lpstrCmdLine) ? strlen(lpstrCmdLine) : 0;
  577. WOW32ASSERT(sizeof(abT) > (lengthProgName+lengthCmdLine+2));
  578. abT[0] = '\0';
  579. // + space + NULL
  580. if(sizeof(abT) >= (lengthProgName + lengthCmdLine + 1 + 1)) {
  581. if ( lpstrProgName ) {
  582. strcpy(abT, lpstrProgName );
  583. }
  584. if ( lpstrCmdLine ) {
  585. strcat(abT, " " );
  586. strcat(abT, lpstrCmdLine );
  587. }
  588. }
  589. else {
  590. return ul;
  591. }
  592. //
  593. // We write the commandline to registry "WOW/EWExecCmdLine"
  594. // If the system logs off successfully, after reboot, we read
  595. // the registry and exec the specfied app before launching any
  596. // wow app in any wow vdm. We donot launch the app before logoff
  597. // because winlogon doesn't allow any app to be execed during
  598. // the logoff process.
  599. // - nanduri
  600. // only one exitwindowsexec call at a time.
  601. // if value/key exists, return error.
  602. if (!W32EWExecData(EWEXEC_QUERY, abT, sizeof(abT))) {
  603. HANDLE hevT;
  604. // only one exitwindowsexec call at a time.
  605. // if event exits, return error.
  606. if (hevT = CreateEvent(NULL, TRUE, FALSE, WOWSZ_EWEXECEVENT)) {
  607. if (GetLastError() == 0) {
  608. // wake up any waiting threads (in w32ewexecer)
  609. SetEvent(hevT);
  610. // Write the data to the registry
  611. if (W32EWExecData(EWEXEC_SET, abT, strlen(abT)+1)) {
  612. DWORD dwlevel;
  613. DWORD dwflags;
  614. if (!GetProcessShutdownParameters(&dwlevel, &dwflags)) {
  615. dwlevel = 0x280; // default level per docs
  616. dwflags = 0;
  617. }
  618. //
  619. // 0xff = last system reserved level Logically makes this last user
  620. // process to shutdown. This takes care of Multiple WOW VDMs
  621. //
  622. SetProcessShutdownParameters(0xff, 0);
  623. //
  624. // EWX_NOTIFY private bit for WOW. Generates queue message
  625. // WM_ENDSESSION, if any process cancels logoff/shutdown.
  626. if (ExitWindowsEx(EWX_LOGOFF | EWX_NOTIFY, 0)) {
  627. MSG msg;
  628. //
  629. // PeekMessage yields to other WOW tasks. We effectively
  630. // freeze the current task by removing all input messages.
  631. // Loop terminates only if WM_ENDSESSION message has been
  632. // received. This message is posted by winsrv if any process
  633. // in the system cancels logoff.
  634. //
  635. while (TRUE) {
  636. if (PeekMessage(&msg, 0, 0, 0, PM_REMOVE)) {
  637. if ((msg.message >= WM_MOUSEFIRST &&
  638. msg.message <= WM_MOUSELAST) ||
  639. (msg.message >= WM_KEYFIRST &&
  640. msg.message <= WM_KEYLAST) ||
  641. (msg.message >= WM_NCMOUSEMOVE &&
  642. msg.message <= WM_NCMBUTTONDBLCLK)) {
  643. // don't dispatch the message
  644. }
  645. else if (msg.message == WM_ENDSESSION) {
  646. WOW32ASSERT((msg.hwnd == 0) && (msg.wParam == 0));
  647. break;
  648. }
  649. else {
  650. TranslateMessage(&msg);
  651. DispatchMessage(&msg);
  652. }
  653. }
  654. }
  655. }
  656. //
  657. // Here if logoff was cancelled.
  658. // Set defaults and delete the associated value from registry.
  659. //
  660. SetProcessShutdownParameters(dwlevel, dwflags);
  661. if (!W32EWExecData(EWEXEC_DEL, (LPSTR)NULL, 0)) {
  662. WOW32ASSERT(FALSE);
  663. }
  664. }
  665. }
  666. CloseHandle(hevT);
  667. }
  668. }
  669. LOGDEBUG(0,("WOW: ExitWindowsExec failed\r\n"));
  670. FREEARGPTR(parg16);
  671. return 0;
  672. }
  673. ULONG FASTCALL WU32MapWindowPoints(PVDMFRAME pFrame)
  674. {
  675. LPPOINT p3;
  676. register PMAPWINDOWPOINTS16 parg16;
  677. POINT BufferT[128];
  678. GETARGPTR(pFrame, sizeof(MAPWINDOWPOINTS16), parg16);
  679. p3 = STACKORHEAPALLOC(parg16->f4 * sizeof(POINT), sizeof(BufferT), BufferT);
  680. if ( p3 ) {
  681. getpoint16(parg16->f3, parg16->f4, p3);
  682. MapWindowPoints(
  683. HWND32(parg16->f1),
  684. HWND32(parg16->f2),
  685. p3,
  686. INT32(parg16->f4)
  687. );
  688. PUTPOINTARRAY16(parg16->f3, parg16->f4, p3);
  689. STACKORHEAPFREE(p3, BufferT);
  690. }
  691. else {
  692. FREEARGPTR(parg16);
  693. RETURN(0);
  694. }
  695. FREEARGPTR(parg16);
  696. RETURN(1);
  697. }