1 /* 2 * COPYRIGHT: See COPYING in the top level directory 3 * PROJECT: ReactOS Win32k subsystem 4 * PURPOSE: Native User stubs 5 * FILE: win32ss/user/ntuser/ntstubs.c 6 * PROGRAMER: Casper S. Hornstrup (chorns@users.sourceforge.net) 7 */ 8 9 #include <win32k.h> 10 DBG_DEFAULT_CHANNEL(UserMisc); 11 12 DWORD 13 APIENTRY 14 NtUserAssociateInputContext( 15 DWORD dwUnknown1, 16 DWORD dwUnknown2, 17 DWORD dwUnknown3) 18 { 19 STUB 20 return 0; 21 } 22 23 // 24 // Works like BitBlt, http://msdn.microsoft.com/en-us/library/ms532278(VS.85).aspx 25 // 26 BOOL 27 APIENTRY 28 NtUserBitBltSysBmp( 29 HDC hdc, 30 INT nXDest, 31 INT nYDest, 32 INT nWidth, 33 INT nHeight, 34 INT nXSrc, 35 INT nYSrc, 36 DWORD dwRop ) 37 { 38 BOOL Ret = FALSE; 39 UserEnterExclusive(); 40 41 Ret = NtGdiBitBlt( hdc, 42 nXDest, 43 nYDest, 44 nWidth, 45 nHeight, 46 hSystemBM, 47 nXSrc, 48 nYSrc, 49 dwRop, 50 0, 51 0); 52 53 UserLeave(); 54 return Ret; 55 } 56 57 DWORD 58 APIENTRY 59 NtUserBuildHimcList( 60 DWORD dwUnknown1, 61 DWORD dwUnknown2, 62 DWORD dwUnknown3, 63 DWORD dwUnknown4) 64 { 65 STUB; 66 return 0; 67 } 68 69 DWORD 70 APIENTRY 71 NtUserDragObject( 72 HWND hwnd1, 73 HWND hwnd2, 74 UINT u1, 75 DWORD dw1, 76 HCURSOR hc1 77 ) 78 { 79 STUB 80 81 return 0; 82 } 83 84 BOOL 85 APIENTRY 86 NtUserDrawAnimatedRects( 87 HWND hwnd, 88 INT idAni, 89 RECT *lprcFrom, 90 RECT *lprcTo) 91 { 92 STUB 93 94 return 0; 95 } 96 97 DWORD 98 APIENTRY 99 NtUserEvent( 100 DWORD Unknown0) 101 { 102 STUB 103 104 return 0; 105 } 106 107 BOOL 108 APIENTRY 109 NtUserGetAltTabInfo( 110 HWND hwnd, 111 INT iItem, 112 PALTTABINFO pati, 113 LPWSTR pszItemText, 114 UINT cchItemText, 115 BOOL Ansi) 116 { 117 STUB 118 119 return 0; 120 } 121 122 NTSTATUS 123 APIENTRY 124 NtUserInitializeClientPfnArrays( 125 PPFNCLIENT pfnClientA, 126 PPFNCLIENT pfnClientW, 127 PPFNCLIENTWORKER pfnClientWorker, 128 HINSTANCE hmodUser) 129 { 130 NTSTATUS Status = STATUS_SUCCESS; 131 TRACE("Enter NtUserInitializeClientPfnArrays User32 0x%p\n", hmodUser); 132 133 if (ClientPfnInit) return Status; 134 135 UserEnterExclusive(); 136 137 _SEH2_TRY 138 { 139 ProbeForRead( pfnClientA, sizeof(PFNCLIENT), 1); 140 ProbeForRead( pfnClientW, sizeof(PFNCLIENT), 1); 141 ProbeForRead( pfnClientWorker, sizeof(PFNCLIENTWORKER), 1); 142 RtlCopyMemory(&gpsi->apfnClientA, pfnClientA, sizeof(PFNCLIENT)); 143 RtlCopyMemory(&gpsi->apfnClientW, pfnClientW, sizeof(PFNCLIENT)); 144 RtlCopyMemory(&gpsi->apfnClientWorker, pfnClientWorker, sizeof(PFNCLIENTWORKER)); 145 146 //// FIXME: HAX! Temporary until server side is finished. 147 //// Copy the client side procs for now. 148 RtlCopyMemory(&gpsi->aStoCidPfn, pfnClientW, sizeof(gpsi->aStoCidPfn)); 149 150 hModClient = hmodUser; 151 ClientPfnInit = TRUE; 152 } 153 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 154 { 155 Status =_SEH2_GetExceptionCode(); 156 } 157 _SEH2_END 158 159 if (!NT_SUCCESS(Status)) 160 { 161 ERR("Failed reading Client Pfns from user space.\n"); 162 SetLastNtError(Status); 163 } 164 165 UserLeave(); 166 return Status; 167 } 168 169 DWORD 170 APIENTRY 171 NtUserInitTask( 172 DWORD Unknown0, 173 DWORD Unknown1, 174 DWORD Unknown2, 175 DWORD Unknown3, 176 DWORD Unknown4, 177 DWORD Unknown5, 178 DWORD Unknown6, 179 DWORD Unknown7, 180 DWORD Unknown8, 181 DWORD Unknown9, 182 DWORD Unknown10, 183 DWORD Unknown11) 184 { 185 STUB 186 187 return 0; 188 } 189 190 DWORD 191 APIENTRY 192 NtUserMNDragLeave(VOID) 193 { 194 STUB 195 196 return 0; 197 } 198 199 DWORD 200 APIENTRY 201 NtUserMNDragOver( 202 DWORD Unknown0, 203 DWORD Unknown1) 204 { 205 STUB 206 207 return 0; 208 } 209 210 DWORD 211 APIENTRY 212 NtUserModifyUserStartupInfoFlags( 213 DWORD Unknown0, 214 DWORD Unknown1) 215 { 216 STUB 217 218 return 0; 219 } 220 221 DWORD 222 APIENTRY 223 NtUserQueryUserCounters( 224 DWORD Unknown0, 225 DWORD Unknown1, 226 DWORD Unknown2, 227 DWORD Unknown3, 228 DWORD Unknown4) 229 { 230 STUB 231 232 return 0; 233 } 234 235 DWORD 236 APIENTRY 237 NtUserRegisterTasklist( 238 DWORD Unknown0) 239 { 240 STUB 241 242 return 0; 243 } 244 245 DWORD 246 APIENTRY 247 NtUserSetConsoleReserveKeys( 248 DWORD Unknown0, 249 DWORD Unknown1) 250 { 251 STUB 252 253 return 0; 254 } 255 256 DWORD 257 APIENTRY 258 NtUserSetDbgTag( 259 DWORD Unknown0, 260 DWORD Unknown1) 261 { 262 STUB; 263 264 return 0; 265 } 266 267 DWORD 268 APIENTRY 269 NtUserSetDbgTagCount( 270 DWORD Unknown0) 271 { 272 STUB; 273 274 return 0; 275 } 276 277 DWORD 278 APIENTRY 279 NtUserSetRipFlags( 280 DWORD Unknown0) 281 { 282 STUB; 283 284 return 0; 285 } 286 287 DWORD 288 APIENTRY 289 NtUserDbgWin32HeapFail( 290 DWORD Unknown0, 291 DWORD Unknown1) 292 { 293 STUB 294 295 return 0; 296 } 297 298 DWORD 299 APIENTRY 300 NtUserDbgWin32HeapStat( 301 DWORD Unknown0, 302 DWORD Unknown1) 303 { 304 STUB 305 306 return 0; 307 } 308 309 BOOL 310 APIENTRY 311 NtUserSetSysColors( 312 int cElements, 313 IN CONST INT *lpaElements, 314 IN CONST COLORREF *lpaRgbValues, 315 FLONG Flags) 316 { 317 DWORD Ret = TRUE; 318 319 if (cElements == 0) 320 return TRUE; 321 322 /* We need this check to prevent overflow later */ 323 if ((ULONG)cElements >= 0x40000000) 324 { 325 EngSetLastError(ERROR_NOACCESS); 326 return FALSE; 327 } 328 329 UserEnterExclusive(); 330 331 _SEH2_TRY 332 { 333 ProbeForRead(lpaElements, cElements * sizeof(INT), 1); 334 ProbeForRead(lpaRgbValues, cElements * sizeof(COLORREF), 1); 335 336 IntSetSysColors(cElements, lpaElements, lpaRgbValues); 337 } 338 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 339 { 340 SetLastNtError(_SEH2_GetExceptionCode()); 341 Ret = FALSE; 342 } 343 _SEH2_END; 344 345 if (Ret) 346 { 347 UserSendNotifyMessage(HWND_BROADCAST, WM_SYSCOLORCHANGE, 0, 0); 348 349 UserRedrawDesktop(); 350 } 351 352 UserLeave(); 353 return Ret; 354 } 355 356 DWORD 357 APIENTRY 358 NtUserUpdateInputContext( 359 DWORD Unknown0, 360 DWORD Unknown1, 361 DWORD Unknown2) 362 { 363 STUB 364 365 return 0; 366 } 367 368 DWORD 369 APIENTRY 370 NtUserUpdateInstance( 371 DWORD Unknown0, 372 DWORD Unknown1, 373 DWORD Unknown2) 374 { 375 STUB 376 377 return 0; 378 } 379 380 BOOL 381 APIENTRY 382 NtUserUserHandleGrantAccess( 383 IN HANDLE hUserHandle, 384 IN HANDLE hJob, 385 IN BOOL bGrant) 386 { 387 STUB 388 389 return 0; 390 } 391 392 DWORD 393 APIENTRY 394 NtUserWaitForMsgAndEvent( 395 DWORD Unknown0) 396 { 397 STUB 398 399 return 0; 400 } 401 402 DWORD 403 APIENTRY 404 NtUserWin32PoolAllocationStats( 405 DWORD Unknown0, 406 DWORD Unknown1, 407 DWORD Unknown2, 408 DWORD Unknown3, 409 DWORD Unknown4, 410 DWORD Unknown5) 411 { 412 STUB 413 414 return 0; 415 } 416 417 DWORD 418 APIENTRY 419 NtUserYieldTask(VOID) 420 { 421 STUB 422 423 return 0; 424 } 425 426 DWORD 427 APIENTRY 428 NtUserCreateInputContext( 429 DWORD dwUnknown1) 430 { 431 STUB; 432 return 0; 433 } 434 435 DWORD 436 APIENTRY 437 NtUserDestroyInputContext( 438 DWORD dwUnknown1) 439 { 440 STUB; 441 return 0; 442 } 443 444 DWORD 445 APIENTRY 446 NtUserGetRawInputBuffer( 447 PRAWINPUT pData, 448 PUINT pcbSize, 449 UINT cbSizeHeader) 450 { 451 STUB; 452 return 0; 453 } 454 455 DWORD 456 APIENTRY 457 NtUserGetRawInputData( 458 HRAWINPUT hRawInput, 459 UINT uiCommand, 460 LPVOID pData, 461 PUINT pcbSize, 462 UINT cbSizeHeader) 463 { 464 STUB; 465 return 0; 466 } 467 468 DWORD 469 APIENTRY 470 NtUserGetRawInputDeviceInfo( 471 HANDLE hDevice, 472 UINT uiCommand, 473 LPVOID pData, 474 PUINT pcbSize 475 ) 476 { 477 STUB; 478 return 0; 479 } 480 481 DWORD 482 APIENTRY 483 NtUserGetRawInputDeviceList( 484 PRAWINPUTDEVICELIST pRawInputDeviceList, 485 PUINT puiNumDevices, 486 UINT cbSize) 487 { 488 STUB; 489 return 0; 490 } 491 492 DWORD 493 APIENTRY 494 NtUserGetRegisteredRawInputDevices( 495 PRAWINPUTDEVICE pRawInputDevices, 496 PUINT puiNumDevices, 497 UINT cbSize) 498 { 499 STUB; 500 return 0; 501 } 502 503 DWORD 504 APIENTRY 505 NtUserHardErrorControl( 506 DWORD dwUnknown1, 507 DWORD dwUnknown2, 508 DWORD dwUnknown3) 509 { 510 STUB; 511 return 0; 512 } 513 514 BOOL 515 NTAPI 516 NtUserNotifyProcessCreate( 517 HANDLE NewProcessId, 518 HANDLE ParentThreadId, 519 ULONG dwUnknown, 520 ULONG CreateFlags) 521 { 522 // STUB; 523 TRACE("NtUserNotifyProcessCreate is UNIMPLEMENTED\n"); 524 return FALSE; 525 } 526 527 NTSTATUS 528 APIENTRY 529 NtUserProcessConnect( 530 IN HANDLE ProcessHandle, 531 OUT PUSERCONNECT pUserConnect, 532 IN ULONG Size) 533 { 534 NTSTATUS Status; 535 PEPROCESS Process = NULL; 536 PPROCESSINFO W32Process; 537 538 TRACE("NtUserProcessConnect\n"); 539 540 if ( pUserConnect == NULL || 541 Size != sizeof(*pUserConnect) ) 542 { 543 return STATUS_UNSUCCESSFUL; 544 } 545 546 /* Get the process object the user handle was referencing */ 547 Status = ObReferenceObjectByHandle(ProcessHandle, 548 PROCESS_VM_OPERATION, 549 *PsProcessType, 550 UserMode, 551 (PVOID*)&Process, 552 NULL); 553 if (!NT_SUCCESS(Status)) return Status; 554 555 UserEnterShared(); 556 557 /* Get Win32 process information */ 558 W32Process = PsGetProcessWin32Process(Process); 559 560 _SEH2_TRY 561 { 562 // FIXME: Check that pUserConnect->ulVersion == USER_VERSION; 563 564 ProbeForWrite(pUserConnect, sizeof(*pUserConnect), sizeof(PVOID)); 565 pUserConnect->siClient.psi = gpsi; 566 pUserConnect->siClient.aheList = gHandleTable; 567 pUserConnect->siClient.ulSharedDelta = 568 (ULONG_PTR)W32Process->HeapMappings.KernelMapping - 569 (ULONG_PTR)W32Process->HeapMappings.UserMapping; 570 } 571 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 572 { 573 Status = _SEH2_GetExceptionCode(); 574 } 575 _SEH2_END; 576 577 if (!NT_SUCCESS(Status)) 578 SetLastNtError(Status); 579 580 UserLeave(); 581 582 /* Dereference the process object */ 583 ObDereferenceObject(Process); 584 585 return Status; 586 } 587 588 NTSTATUS 589 APIENTRY 590 NtUserQueryInformationThread(IN HANDLE ThreadHandle, 591 IN USERTHREADINFOCLASS ThreadInformationClass, 592 OUT PVOID ThreadInformation, 593 IN ULONG ThreadInformationLength) 594 { 595 NTSTATUS Status = STATUS_SUCCESS; 596 PETHREAD Thread; 597 598 /* Allow only CSRSS to perform this operation */ 599 if (PsGetCurrentProcess() != gpepCSRSS) 600 return STATUS_ACCESS_DENIED; 601 602 UserEnterExclusive(); 603 604 /* Get the Thread */ 605 Status = ObReferenceObjectByHandle(ThreadHandle, 606 THREAD_QUERY_INFORMATION, 607 *PsThreadType, 608 UserMode, 609 (PVOID)&Thread, 610 NULL); 611 if (!NT_SUCCESS(Status)) goto Quit; 612 613 switch (ThreadInformationClass) 614 { 615 default: 616 { 617 STUB; 618 Status = STATUS_NOT_IMPLEMENTED; 619 break; 620 } 621 } 622 623 ObDereferenceObject(Thread); 624 625 Quit: 626 UserLeave(); 627 return Status; 628 } 629 630 DWORD 631 APIENTRY 632 NtUserQueryInputContext( 633 DWORD dwUnknown1, 634 DWORD dwUnknown2) 635 { 636 STUB; 637 return 0; 638 } 639 640 BOOL 641 APIENTRY 642 NtUserRealInternalGetMessage( 643 LPMSG lpMsg, 644 HWND hWnd, 645 UINT wMsgFilterMin, 646 UINT wMsgFilterMax, 647 UINT wRemoveMsg, 648 BOOL bGMSG) 649 { 650 STUB; 651 return 0; 652 } 653 654 BOOL 655 APIENTRY 656 NtUserRealWaitMessageEx( 657 DWORD dwWakeMask, 658 UINT uTimeout) 659 { 660 STUB; 661 return 0; 662 } 663 664 BOOL 665 APIENTRY 666 NtUserRegisterRawInputDevices( 667 IN PCRAWINPUTDEVICE pRawInputDevices, 668 IN UINT uiNumDevices, 669 IN UINT cbSize) 670 { 671 STUB; 672 return 0; 673 } 674 675 DWORD APIENTRY 676 NtUserResolveDesktopForWOW(DWORD Unknown0) 677 { 678 STUB 679 return 0; 680 } 681 682 DWORD 683 APIENTRY 684 NtUserSetInformationProcess( 685 DWORD dwUnknown1, 686 DWORD dwUnknown2, 687 DWORD dwUnknown3, 688 DWORD dwUnknown4) 689 { 690 STUB; 691 return 0; 692 } 693 694 NTSTATUS 695 APIENTRY 696 NtUserSetInformationThread(IN HANDLE ThreadHandle, 697 IN USERTHREADINFOCLASS ThreadInformationClass, 698 IN PVOID ThreadInformation, 699 IN ULONG ThreadInformationLength) 700 { 701 NTSTATUS Status = STATUS_SUCCESS; 702 PETHREAD Thread; 703 704 /* Allow only CSRSS to perform this operation */ 705 if (PsGetCurrentProcess() != gpepCSRSS) 706 return STATUS_ACCESS_DENIED; 707 708 UserEnterExclusive(); 709 710 /* Get the Thread */ 711 Status = ObReferenceObjectByHandle(ThreadHandle, 712 THREAD_SET_INFORMATION, 713 *PsThreadType, 714 UserMode, 715 (PVOID)&Thread, 716 NULL); 717 if (!NT_SUCCESS(Status)) goto Quit; 718 719 switch (ThreadInformationClass) 720 { 721 case UserThreadInitiateShutdown: 722 { 723 ULONG CapturedFlags = 0; 724 725 TRACE("Shutdown initiated\n"); 726 727 if (ThreadInformationLength != sizeof(ULONG)) 728 { 729 Status = STATUS_INFO_LENGTH_MISMATCH; 730 break; 731 } 732 733 /* Capture the caller value */ 734 Status = STATUS_SUCCESS; 735 _SEH2_TRY 736 { 737 ProbeForWrite(ThreadInformation, sizeof(CapturedFlags), sizeof(PVOID)); 738 CapturedFlags = *(PULONG)ThreadInformation; 739 } 740 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 741 { 742 Status = _SEH2_GetExceptionCode(); 743 _SEH2_YIELD(break); 744 } 745 _SEH2_END; 746 747 Status = UserInitiateShutdown(Thread, &CapturedFlags); 748 749 /* Return the modified value to the caller */ 750 _SEH2_TRY 751 { 752 *(PULONG)ThreadInformation = CapturedFlags; 753 } 754 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 755 { 756 Status = _SEH2_GetExceptionCode(); 757 } 758 _SEH2_END; 759 760 break; 761 } 762 763 case UserThreadEndShutdown: 764 { 765 NTSTATUS ShutdownStatus; 766 767 TRACE("Shutdown ended\n"); 768 769 if (ThreadInformationLength != sizeof(ShutdownStatus)) 770 { 771 Status = STATUS_INFO_LENGTH_MISMATCH; 772 break; 773 } 774 775 /* Capture the caller value */ 776 Status = STATUS_SUCCESS; 777 _SEH2_TRY 778 { 779 ProbeForRead(ThreadInformation, sizeof(ShutdownStatus), sizeof(PVOID)); 780 ShutdownStatus = *(NTSTATUS*)ThreadInformation; 781 } 782 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 783 { 784 Status = _SEH2_GetExceptionCode(); 785 _SEH2_YIELD(break); 786 } 787 _SEH2_END; 788 789 Status = UserEndShutdown(Thread, ShutdownStatus); 790 break; 791 } 792 793 case UserThreadCsrApiPort: 794 { 795 HANDLE CsrPortHandle; 796 797 ERR("Set CSR API Port for Win32k\n"); 798 799 if (ThreadInformationLength != sizeof(CsrPortHandle)) 800 { 801 Status = STATUS_INFO_LENGTH_MISMATCH; 802 break; 803 } 804 805 /* Capture the caller value */ 806 Status = STATUS_SUCCESS; 807 _SEH2_TRY 808 { 809 ProbeForRead(ThreadInformation, sizeof(CsrPortHandle), sizeof(PVOID)); 810 CsrPortHandle = *(PHANDLE)ThreadInformation; 811 } 812 _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER) 813 { 814 Status = _SEH2_GetExceptionCode(); 815 _SEH2_YIELD(break); 816 } 817 _SEH2_END; 818 819 Status = InitCsrApiPort(CsrPortHandle); 820 break; 821 } 822 823 default: 824 { 825 STUB; 826 Status = STATUS_NOT_IMPLEMENTED; 827 break; 828 } 829 } 830 831 ObDereferenceObject(Thread); 832 833 Quit: 834 UserLeave(); 835 return Status; 836 } 837 838 DWORD 839 APIENTRY 840 NtUserSetThreadLayoutHandles( 841 DWORD dwUnknown1, 842 DWORD dwUnknown2) 843 { 844 STUB; 845 return 0; 846 } 847 848 BOOL 849 APIENTRY 850 NtUserSoundSentry(VOID) 851 { 852 STUB; 853 return 0; 854 } 855 856 DWORD 857 APIENTRY 858 NtUserTestForInteractiveUser( 859 DWORD dwUnknown1) 860 { 861 STUB; 862 return 0; 863 } 864 865 DWORD 866 APIENTRY 867 NtUserRemoteConnect( 868 DWORD dwUnknown1, 869 DWORD dwUnknown2, 870 DWORD dwUnknown3) 871 { 872 STUB; 873 return 0; 874 } 875 876 DWORD 877 APIENTRY 878 NtUserRemoteRedrawRectangle( 879 DWORD dwUnknown1, 880 DWORD dwUnknown2, 881 DWORD dwUnknown3, 882 DWORD dwUnknown4) 883 { 884 STUB; 885 return 0; 886 } 887 888 DWORD 889 APIENTRY 890 NtUserRemoteRedrawScreen(VOID) 891 { 892 STUB; 893 return 0; 894 } 895 896 DWORD 897 APIENTRY 898 NtUserRemoteStopScreenUpdates(VOID) 899 { 900 STUB; 901 return 0; 902 } 903 904 DWORD 905 APIENTRY 906 NtUserCtxDisplayIOCtl( 907 DWORD dwUnknown1, 908 DWORD dwUnknown2, 909 DWORD dwUnknown3) 910 { 911 STUB; 912 return 0; 913 } 914 915 /* 916 * @unimplemented 917 */ 918 BOOL APIENTRY 919 NtUserLockWindowUpdate(HWND hWnd) 920 { 921 STUB 922 923 return 0; 924 } 925 926 DWORD APIENTRY 927 NtUserQuerySendMessage(DWORD Unknown0) 928 { 929 STUB; 930 931 return 0; 932 } 933 934 BOOL APIENTRY NtUserAddClipboardFormatListener( 935 HWND hwnd 936 ) 937 { 938 STUB; 939 return FALSE; 940 } 941 942 BOOL APIENTRY NtUserRemoveClipboardFormatListener( 943 HWND hwnd 944 ) 945 { 946 STUB; 947 return FALSE; 948 } 949 950 BOOL APIENTRY NtUserGetUpdatedClipboardFormats( 951 PUINT lpuiFormats, 952 UINT cFormats, 953 PUINT pcFormatsOut 954 ) 955 { 956 STUB; 957 return FALSE; 958 } 959 960 // Yes, I know, these do not belong here, just tell me where to put them 961 BOOL 962 APIENTRY 963 NtGdiMakeObjectXferable( 964 _In_ HANDLE hHandle, 965 _In_ DWORD dwProcessId) 966 { 967 STUB; 968 return 0; 969 } 970 971 DWORD 972 APIENTRY 973 NtDxEngGetRedirectionBitmap( 974 DWORD Unknown0) 975 { 976 STUB; 977 return 0; 978 } 979 980 981 /* EOF */ 982