Esempio n. 1
0
NTSTATUS
APIENTRY
Win32kThreadCallback(struct _ETHREAD *Thread,
                     PSW32THREADCALLOUTTYPE Type)
{
    NTSTATUS Status;

    UserEnterExclusive();

    ASSERT(NtCurrentTeb());

    if (Type == PsW32ThreadCalloutInitialize)
    {
        ASSERT(PsGetThreadWin32Thread(Thread) == NULL);
        Status = UserCreateThreadInfo(Thread);
    }
    else
    {
        ASSERT(PsGetThreadWin32Thread(Thread) != NULL);
        Status = UserDestroyThreadInfo(Thread);
    }

    UserLeave();

    return Status;
}
Esempio n. 2
0
/*
 * UserGetKeyboardLayout
 *
 * Returns hkl of given thread keyboard layout
 */
HKL FASTCALL
UserGetKeyboardLayout(
    DWORD dwThreadId)
{
    NTSTATUS Status;
    PETHREAD pThread;
    PTHREADINFO pti;
    PKL pKl;
    HKL hKl;

    if (!dwThreadId)
    {
        pti = PsGetCurrentThreadWin32Thread();
        pKl = pti->KeyboardLayout;
        return pKl ? pKl->hkl : NULL;
    }

    Status = PsLookupThreadByThreadId((HANDLE)(DWORD_PTR)dwThreadId, &pThread);
    if (!NT_SUCCESS(Status))
    {
        EngSetLastError(ERROR_INVALID_PARAMETER);
        return NULL;
    }

    pti = PsGetThreadWin32Thread(pThread);
    pKl = pti->KeyboardLayout;
    hKl = pKl ? pKl->hkl : NULL;;
    ObDereferenceObject(pThread);
    return hKl;
}
Esempio n. 3
0
/*
 * Test the Thread to verify and validate it. Hard to the core tests are required.
 */
PTHREADINFO
FASTCALL
IntTID2PTI(HANDLE id)
{
   NTSTATUS Status;
   PETHREAD Thread;
   PTHREADINFO pti;
   Status = PsLookupThreadByThreadId(id, &Thread);
   if (!NT_SUCCESS(Status))
   {
      return NULL;
   }
   if (PsIsThreadTerminating(Thread))
   {
      ObDereferenceObject(Thread);
      return NULL;
   }
   pti = PsGetThreadWin32Thread(Thread);
   if (!pti)
   {
      ObDereferenceObject(Thread);
      return NULL;
   }
   // Validate and verify!
   _SEH2_TRY
   {
      if (pti->TIF_flags & TIF_INCLEANUP) pti = NULL;
      if (pti && !(pti->TIF_flags & TIF_GUITHREADINITIALIZED)) pti = NULL;
      if (PsGetThreadId(Thread) != id) pti = NULL;
   }
   _SEH2_EXCEPT(EXCEPTION_EXECUTE_HANDLER)
   {
      pti = NULL;
   }
   _SEH2_END
   ObDereferenceObject(Thread);
   return pti;
}
Esempio n. 4
0
NTSTATUS DispatchIoctl(IN PDEVICE_OBJECT DeviceObject, IN PIRP Irp){
    NTSTATUS  ntStatus = STATUS_UNSUCCESSFUL;
    PIO_STACK_LOCATION irpStack = IoGetCurrentIrpStackLocation(Irp);
    PDEVICE_EXTENSION extension = DeviceObject->DeviceExtension;
    switch(irpStack->Parameters.DeviceIoControl.IoControlCode){
        case IOCTL_GET_HOOKS:
            {
                unsigned int i,j;
                PETHREAD pethread;
                PTHREADINFO ptiCurrent;
                PDESKTOPINFO pdesktopinfo;
                PPROCESSINFO ppi;
                PARAMS_GET_HOOKS *params;
                DATA_GET_HOOKS *data;
                PHOOK* aphkStart;

                if (irpStack->Parameters.DeviceIoControl.OutputBufferLength < sizeof(DATA_GET_HOOKS)) {
                    ntStatus = STATUS_BUFFER_TOO_SMALL;
                    break;
                }
                if (irpStack->Parameters.DeviceIoControl.InputBufferLength < sizeof(PARAMS_GET_HOOKS)) {
                    ntStatus = STATUS_BUFFER_TOO_SMALL;
                    break;
                }

                params = ExAllocatePoolWithTag(PagedPool, sizeof(PARAMS_GET_HOOKS), 'tdkh');
                if (!params) {
                    break;
                }

                memcpy(params, Irp->AssociatedIrp.SystemBuffer, sizeof(PARAMS_GET_HOOKS));

                pethread = PsGetCurrentThread();
                ptiCurrent = PsGetThreadWin32Thread(pethread);
                if (g_win7) {
                    pdesktopinfo = (PDESKTOPINFO)((unsigned int*)ptiCurrent)[0xCC/4];
                    ppi = (PPROCESSINFO)&((char*)ptiCurrent)[0xB8];
                    aphkStart = (PHOOK*)&((char*)pdesktopinfo)[0x10];
                } else {
                    pdesktopinfo = ptiCurrent->pDeskInfo;
                    ppi = ptiCurrent->ppi;
                    aphkStart = pdesktopinfo->aphkStart;
                }

                data = (DATA_GET_HOOKS*)Irp->AssociatedIrp.SystemBuffer;
                memset(data, 0, sizeof(DATA_GET_HOOKS));

                retrieve_hooks(aphkStart, ppi, data->global_hook);

                data->threads=0;
                j=0;
                for (i=0;i<params->threads;i++) {
                    if (PsLookupThreadByThreadId((HANDLE)params->thread_id[i], &pethread) != STATUS_SUCCESS) {
                        continue;
                    }
                    if (g_win7) {
                        if (PsGetThreadSessionId(pethread) != PsGetCurrentProcessSessionId()) {
                            ObDereferenceObject(pethread);
                            continue;
                        }
                    }
                    ptiCurrent = PsGetThreadWin32Thread(pethread);
                    if (ptiCurrent) {
                        if (g_win7) {
                            aphkStart = (PHOOK*)&((char*)ptiCurrent)[0x198];
                            ppi = (PPROCESSINFO)&((char*)ptiCurrent)[0xB8];
                        } else {
                            aphkStart = (PHOOK*)&((char*)ptiCurrent)[0xf4];
                            ppi = ptiCurrent->ppi;
                        }
                        if (has_hooks(aphkStart)) {
                            data->threads++;
                            if (j<MAX_OUT_THREADS) {
                                retrieve_hooks(aphkStart, ppi, data->thread[j].hook);
                                data->thread[j].thread_id = params->thread_id[i];
                                j++;
                            }
                        }
                    }
                    ObDereferenceObject(pethread);
                }

                ExFreePool(params);

                ntStatus = STATUS_SUCCESS;
                break;
            }
        case IOCTL_HMOD_TBL_INX_TO_MOD_NAME:
            {
                DATA_HMOD_TBL_INX_TO_MOD_NAME *data;
                PARAMS_HMOD_TBL_INX_TO_MOD_NAME *params;
                WCHAR tmp;
                int hmod_table_index;

                if (irpStack->Parameters.DeviceIoControl.OutputBufferLength < sizeof(DATA_HMOD_TBL_INX_TO_MOD_NAME)) {
                    ntStatus = STATUS_BUFFER_TOO_SMALL;
                    break;
                }
                if (irpStack->Parameters.DeviceIoControl.InputBufferLength < sizeof(PARAMS_HMOD_TBL_INX_TO_MOD_NAME)) {
                    ntStatus = STATUS_BUFFER_TOO_SMALL;
                    break;
                }

                params = Irp->AssociatedIrp.SystemBuffer;

                UserGetAtomName = (UserGetAtomName_ptr)params->UserGetAtomName_address;
                aatomSysLoaded = (ATOM*)params->aatomSysLoaded_address;
                hmod_table_index = params->hmod_table_index;

                if (UserGetAtomName && aatomSysLoaded) {
                    __try {
                        (*UserGetAtomName)(aatomSysLoaded[0], &tmp, 1);
                    } __except (EXCEPTION_EXECUTE_HANDLER) {
                        UserGetAtomName = 0;
                    }
                }

                data = Irp->AssociatedIrp.SystemBuffer;

                if (UserGetAtomName) {
                    (*UserGetAtomName)(aatomSysLoaded[hmod_table_index], data->module_name, MAX_PATH);
                } else {
                    data->module_name[0] = 0;
                }

                ntStatus = STATUS_SUCCESS;
                break;
            }
    }
Esempio n. 5
0
NTSTATUS
NTAPI
UserDestroyThreadInfo(struct _ETHREAD *Thread)
{
    PTHREADINFO *ppti;
    PSINGLE_LIST_ENTRY psle;
    PPROCESSINFO ppiCurrent;
    struct _EPROCESS *Process;
    PTHREADINFO ptiCurrent;

    Process = Thread->ThreadsProcess;

    /* Get the Win32 Thread */
    ptiCurrent = PsGetThreadWin32Thread(Thread);

    ASSERT(ptiCurrent);

    TRACE_CH(UserThread,"Destroying pti 0x%p eThread 0x%p\n", ptiCurrent, Thread);

    ptiCurrent->TIF_flags |= TIF_INCLEANUP;
    ptiCurrent->pClientInfo->dwTIFlags = ptiCurrent->TIF_flags;

    ppiCurrent = ptiCurrent->ppi;
    ASSERT(ppiCurrent);

    IsRemoveAttachThread(ptiCurrent);

    ptiCurrent->TIF_flags |= TIF_DONTATTACHQUEUE;
    ptiCurrent->pClientInfo->dwTIFlags = ptiCurrent->TIF_flags;

    /* Decrement thread count and check if its 0 */
    ppiCurrent->cThreads--;

    if(ptiCurrent->TIF_flags & TIF_GUITHREADINITIALIZED)
    {
        /* Do now some process cleanup that requires a valid win32 thread */
        if(ptiCurrent->ppi->cThreads == 0)
        {
            /* Check if we have registered the user api hook */
            if(ptiCurrent->ppi == ppiUahServer)
            {
                /* Unregister the api hook */
                UserUnregisterUserApiHook();
            }

            /* Notify logon application to restart shell if needed */
            if(ptiCurrent->pDeskInfo)
            {
                if(ptiCurrent->pDeskInfo->ppiShellProcess == ppiCurrent)
                {
                    DWORD ExitCode = PsGetProcessExitStatus(Process);

                    TRACE_CH(UserProcess, "Shell process is exiting (%lu)\n", ExitCode);

                    UserPostMessage(hwndSAS,
                                    WM_LOGONNOTIFY,
                                    LN_SHELL_EXITED,
                                    ExitCode);

                    ptiCurrent->pDeskInfo->ppiShellProcess = NULL;
                }
            }
        }

        DceFreeThreadDCE(ptiCurrent);
        HOOK_DestroyThreadHooks(Thread);
        EVENT_DestroyThreadEvents(Thread);
        DestroyTimersForThread(ptiCurrent);
        KeSetEvent(ptiCurrent->pEventQueueServer, IO_NO_INCREMENT, FALSE);
        UnregisterThreadHotKeys(ptiCurrent);
        /*
                if (IsListEmpty(&ptiCurrent->WindowListHead))
                {
                   ERR_CH(UserThread,"Thread Window List is Empty!\n");
                }
        */
        co_DestroyThreadWindows(Thread);

        if (ppiCurrent && ppiCurrent->ptiList == ptiCurrent && !ptiCurrent->ptiSibling &&
                ppiCurrent->W32PF_flags & W32PF_CLASSESREGISTERED)
        {
            TRACE_CH(UserThread,"DestroyProcessClasses\n");
            /* no process windows should exist at this point, or the function will assert! */
            DestroyProcessClasses(ppiCurrent);
            ppiCurrent->W32PF_flags &= ~W32PF_CLASSESREGISTERED;
        }

        IntBlockInput(ptiCurrent, FALSE);
        IntCleanupThreadCallbacks(ptiCurrent);

        /* cleanup user object references stack */
        psle = PopEntryList(&ptiCurrent->ReferencesList);
        while (psle)
        {
            PUSER_REFERENCE_ENTRY ref = CONTAINING_RECORD(psle, USER_REFERENCE_ENTRY, Entry);
            TRACE_CH(UserThread,"thread clean: remove reference obj 0x%p\n",ref->obj);
            UserDereferenceObject(ref->obj);

            psle = PopEntryList(&ptiCurrent->ReferencesList);
        }
    }

    /* Find the THREADINFO in the PROCESSINFO's list */
    ppti = &ppiCurrent->ptiList;
    while (*ppti != NULL && *ppti != ptiCurrent)
    {
        ppti = &((*ppti)->ptiSibling);
    }

    /* we must have found it */
    ASSERT(*ppti == ptiCurrent);

    /* Remove it from the list */
    *ppti = ptiCurrent->ptiSibling;

    if (ptiCurrent->KeyboardLayout)
        UserDereferenceObject(ptiCurrent->KeyboardLayout);

    if (gptiForeground == ptiCurrent)
    {
//       IntNotifyWinEvent(EVENT_OBJECT_FOCUS, NULL, OBJID_CLIENT, CHILDID_SELF, 0);
//       IntNotifyWinEvent(EVENT_SYSTEM_FOREGROUND, NULL, OBJID_WINDOW, CHILDID_SELF, 0);

        gptiForeground = NULL;
    }

    // Fixes CORE-6384 & CORE-7030.
    /*    if (ptiLastInput == ptiCurrent)
        {
           if (!ppiCurrent->ptiList)
              ptiLastInput = gptiForeground;
           else
              ptiLastInput = ppiCurrent->ptiList;
           ERR_CH(UserThread,"DTI: ptiLastInput is Cleared!!\n");
        }
    */
    TRACE_CH(UserThread,"Freeing pti 0x%p\n", ptiCurrent);

    /* Free the THREADINFO */
    IntDereferenceThreadInfo(ptiCurrent);

    return STATUS_SUCCESS;
}