BOOL FASTCALL UserSetProcessWindowStation(HWINSTA hWindowStation) { PPROCESSINFO ppi; NTSTATUS Status; HWINSTA hwinstaOld; PWINSTATION_OBJECT NewWinSta = NULL, OldWinSta; ppi = PsGetCurrentProcessWin32Process(); /* Reference the new window station */ if(hWindowStation !=NULL) { Status = IntValidateWindowStationHandle( hWindowStation, KernelMode, 0, &NewWinSta); if (!NT_SUCCESS(Status)) { TRACE("Validation of window station handle (0x%X) failed\n", hWindowStation); SetLastNtError(Status); return FALSE; } } OldWinSta = ppi->prpwinsta; hwinstaOld = PsGetProcessWin32WindowStation(ppi->peProcess); /* Dereference the previous window station */ if(OldWinSta != NULL) { ObDereferenceObject(OldWinSta); } /* Check if we have a stale handle (it should happen for console apps) */ if(hwinstaOld != ppi->hwinsta) { ObCloseHandle(hwinstaOld, UserMode); } /* * FIXME: Don't allow changing the window station if there are threads that are attached to desktops and own GUI objects. */ PsSetProcessWindowStation(ppi->peProcess, hWindowStation); ppi->prpwinsta = NewWinSta; ppi->hwinsta = hWindowStation; return TRUE; }
BOOL FASTCALL UserSetProcessWindowStation(HWINSTA hWindowStation) { PPROCESSINFO ppi; NTSTATUS Status; HWINSTA hwinstaOld; OBJECT_HANDLE_INFORMATION ObjectHandleInfo; PWINSTATION_OBJECT NewWinSta = NULL, OldWinSta; ppi = PsGetCurrentProcessWin32Process(); /* Reference the new window station */ if(hWindowStation !=NULL) { Status = IntValidateWindowStationHandle(hWindowStation, UserMode, 0, &NewWinSta, &ObjectHandleInfo); if (!NT_SUCCESS(Status)) { TRACE("Validation of window station handle (%p) failed\n", hWindowStation); SetLastNtError(Status); return FALSE; } } OldWinSta = ppi->prpwinsta; hwinstaOld = PsGetProcessWin32WindowStation(ppi->peProcess); /* Dereference the previous window station */ if(OldWinSta != NULL) { ObDereferenceObject(OldWinSta); } /* Check if we have a stale handle (it should happen for console apps) */ if(hwinstaOld != ppi->hwinsta) { ObCloseHandle(hwinstaOld, UserMode); } /* * FIXME: Don't allow changing the window station if there are threads that are attached to desktops and own GUI objects. */ PsSetProcessWindowStation(ppi->peProcess, hWindowStation); ppi->prpwinsta = NewWinSta; ppi->hwinsta = hWindowStation; ppi->amwinsta = hWindowStation != NULL ? ObjectHandleInfo.GrantedAccess : 0; TRACE("WS : Granted Access 0x%08lx\n",ppi->amwinsta); if (RtlAreAllAccessesGranted(ppi->amwinsta, WINSTA_READSCREEN)) { ppi->W32PF_flags |= W32PF_READSCREENACCESSGRANTED; } else { ppi->W32PF_flags &= ~W32PF_READSCREENACCESSGRANTED; } if (NewWinSta && !(NewWinSta->Flags & WSS_NOIO) ) { ppi->W32PF_flags |= W32PF_IOWINSTA; } else // Might be closed if the handle is null. { ppi->W32PF_flags &= ~W32PF_IOWINSTA; } return TRUE; }