[NTOS:PS] Rewrite NtQueryInformationThread to match NtQueryInformationProcess

The information length must always be checked before referencing the thread object. This fixes the remaining test failure.
This commit is contained in:
Eric Kohl 2021-05-02 12:46:19 +02:00
parent 249f2388bd
commit 5585767460

View file

@ -2538,15 +2538,6 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
/* Check what class this is */
Access = THREAD_QUERY_INFORMATION;
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status)) return Status;
/* Check what kind of information class this is */
switch (ThreadInformationClass)
{
@ -2561,6 +2552,17 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = STATUS_INFO_LENGTH_MISMATCH;
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
/* Protect writes with SEH */
_SEH2_TRY
{
@ -2578,6 +2580,9 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = _SEH2_GetExceptionCode();
}
_SEH2_END;
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
/* Thread time information */
@ -2591,6 +2596,17 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = STATUS_INFO_LENGTH_MISMATCH;
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
/* Protect writes with SEH */
_SEH2_TRY
{
@ -2615,6 +2631,9 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = _SEH2_GetExceptionCode();
}
_SEH2_END;
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
case ThreadQuerySetWin32StartAddress:
@ -2627,6 +2646,17 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = STATUS_INFO_LENGTH_MISMATCH;
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
/* Protect write with SEH */
_SEH2_TRY
{
@ -2639,6 +2669,9 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = _SEH2_GetExceptionCode();
}
_SEH2_END;
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
case ThreadPerformanceCount:
@ -2651,6 +2684,17 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = STATUS_INFO_LENGTH_MISMATCH;
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
/* Protect write with SEH */
_SEH2_TRY
{
@ -2663,6 +2707,9 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = _SEH2_GetExceptionCode();
}
_SEH2_END;
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
case ThreadAmILastThread:
@ -2675,6 +2722,17 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = STATUS_INFO_LENGTH_MISMATCH;
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
/* Protect write with SEH */
_SEH2_TRY
{
@ -2691,6 +2749,9 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = _SEH2_GetExceptionCode();
}
_SEH2_END;
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
case ThreadIsIoPending:
@ -2703,6 +2764,17 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = STATUS_INFO_LENGTH_MISMATCH;
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
/* Raise the IRQL to protect the IRP list */
KeRaiseIrql(APC_LEVEL, &OldIrql);
@ -2721,17 +2793,33 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
/* Lower IRQL back */
KeLowerIrql(OldIrql);
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
/* LDT and GDT information */
case ThreadDescriptorTableEntry:
#if defined(_X86_)
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
/* Call the worker routine */
Status = PspQueryDescriptorThread(Thread,
ThreadInformation,
ThreadInformationLength,
ReturnLength);
/* Dereference the thread */
ObDereferenceObject(Thread);
#else
/* Only implemented on x86 */
Status = STATUS_NOT_IMPLEMENTED;
@ -2749,6 +2837,16 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
_SEH2_TRY
{
*(PULONG)ThreadInformation = Thread->Tcb.DisableBoost ? 1 : 0;
@ -2758,6 +2856,9 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
Status = _SEH2_GetExceptionCode();
}
_SEH2_END;
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
case ThreadIsTerminated:
@ -2771,6 +2872,16 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
break;
}
/* Reference the process */
Status = ObReferenceObjectByHandle(ThreadHandle,
Access,
PsThreadType,
PreviousMode,
(PVOID*)&Thread,
NULL);
if (!NT_SUCCESS(Status))
break;
ThreadTerminated = PsIsThreadTerminating(Thread);
_SEH2_TRY
@ -2783,6 +2894,8 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
}
_SEH2_END;
/* Dereference the thread */
ObDereferenceObject(Thread);
break;
/* Anything else */
@ -2806,8 +2919,6 @@ NtQueryInformationThread(IN HANDLE ThreadHandle,
}
_SEH2_END;
/* Dereference the thread, and return */
ObDereferenceObject(Thread);
return Status;
}