Process Termination with Antirootkit gives BSOD

Hi All,

I am working in Quick Heal Techonologies Pvt. Ltd., which is a security company. We have developed a AntiRootkit product which is capable of finding processes hidden by system call hooking or Direct Kernel Object Manipulation.

But the problem is when we terminate the process kernel gives BSOD if the process is hidden by Direct Kernel Object Manipulation technique.

I found that this is due to following reason…
Rootkit alters linklist of active processes to remove the node(EPROCESS) of the process to be hidden. It adjust the pointers in link list to make it consistent but leave the pointers in EPROCESS of the process to be hidden as it is. That means pointers in EPROCESS are invalid, but when we terminate the process the system call trys to remove the process from active link list, which is not there. Thus, these manupulations creates inconsistency in link list and result in BSOD.

Is there any solution to this problem?

Thanks & Regards,
Amit.

If people are corrupting the kernel there is nothing you can do to
un-corrupt it. Anything you try to do to fix the corruption will have as
good of a chance of BSOD-ing the system as the rootkit does. Kernel
corruption cannot be healed in the Windows architecture. Out of curiosity -
are you running in kernel mode or user mode?

wrote in message news:xxxxx@ntdev…
> Hi All,
>
> I am working in Quick Heal Techonologies Pvt. Ltd., which is a security
> company. We have developed a AntiRootkit product which is capable of
> finding processes hidden by system call hooking or Direct Kernel Object
> Manipulation.
>
> But the problem is when we terminate the process kernel gives BSOD if the
> process is hidden by Direct Kernel Object Manipulation technique.
>
> I found that this is due to following reason…
> Rootkit alters linklist of active processes to remove the node(EPROCESS)
> of the process to be hidden. It adjust the pointers in link list to make
> it consistent but leave the pointers in EPROCESS of the process to be
> hidden as it is. That means pointers in EPROCESS are invalid, but when we
> terminate the process the system call trys to remove the process from
> active link list, which is not there. Thus, these manupulations creates
> inconsistency in link list and result in BSOD.
>
> Is there any solution to this problem?
>
> Thanks & Regards,
> Amit.
>

Kernel or link list does not get corrupted untill we terminate such process. If we terminate such hidden process then only inconsistency in link list occures.

If we initialise that proces’s EPROCESS list pointer in such a way that all become consistent, then BSOD will not be there. E.g. If I put that EPROCESS structure in active link list by some way(in reverse order that of rootkit) then problem will be solved.

But I do not want to touch consistent link list of the OS. Because I dont know the side effects of doing so.

That’s why I want some other way.

Right - you can’t do it. The process lists are modified under a system owned
lock. You can’t safely modify the list outside of that lock. Plus - you
can’t even touch the memory that contains the EPROCESS block safely - you
don’t own it and you might screw up some other owner reading or writing.
Once the system is corrupted - you can’t trust or safely do anything. I know
this is a frustrating reality - but it is the truth - honest. :slight_smile:

wrote in message news:xxxxx@ntdev…
> Kernel or link list does not get corrupted untill we terminate such
> process. If we terminate such hidden process then only inconsistency in
> link list occures.
>
> If we initialise that proces’s EPROCESS list pointer in such a way that
> all become consistent, then BSOD will not be there. E.g. If I put that
> EPROCESS structure in active link list by some way(in reverse order that
> of rootkit) then problem will be solved.
>
> But I do not want to touch consistent link list of the OS. Because I dont
> know the side effects of doing so.
>
> That’s why I want some other way.
>

> The process lists are modified under a system owned lock. You can’t safely modify the list outside

of that lock.

What you can do is just to acquire it. All dispatcher objects in the system are protected by a single spinlock, and you can acquire it by KeSetEvent() - all you have to do is to supply ‘Wait’ parameter, telling the system that KeSetEvent() call is followed by the one to KeWaitXXX(). In such case KeSetEvent() returns at DPC level with dispatcher spinlock being held…

Anton Bassov

No, this is another list. There is no processes on KeXxx lists, only
threads.


Maxim Shatskih, Windows DDK MVP
StorageCraft Corporation
xxxxx@storagecraft.com
http://www.storagecraft.com

wrote in message news:xxxxx@ntdev…
> > The process lists are modified under a system owned lock. You can’t safely
modify the list outside
> > of that lock.
>
> What you can do is just to acquire it. All dispatcher objects in the system
are protected by a single spinlock, and you can acquire it by KeSetEvent() -
all you have to do is to supply ‘Wait’ parameter, telling the system that
KeSetEvent() call is followed by the one to KeWaitXXX(). In such case
KeSetEvent() returns at DPC level with dispatcher spinlock being held…
>
> Anton Bassov
>

As Max pointed out these are seperate lists, not only that but there is an
effort in the Windows kernel to segregate more things out of these locks to
improve performance. Sorry, such a design is not going to work, and even if
you get away with it now, it will fail in the future.


Don Burn (MVP, Windows DDK)
Windows 2k/XP/2k3 Filesystem and Driver Consulting
Website: http://www.windrvr.com
Blog: http://msmvps.com/blogs/WinDrvr
Remove StopSpam to reply

wrote in message news:xxxxx@ntdev…
>> The process lists are modified under a system owned lock. You can’t
>> safely modify the list outside
>> of that lock.
>
> What you can do is just to acquire it. All dispatcher objects in the
> system are protected by a single spinlock, and you can acquire it by
> KeSetEvent() - all you have to do is to supply ‘Wait’ parameter, telling
> the system that KeSetEvent() call is followed by the one to KeWaitXXX().
> In such case KeSetEvent() returns at DPC level with dispatcher spinlock
> being held…
>
> Anton Bassov
>

The process list lock is not exposed nor are any of the routines required to
acquire or release it. There is no way to safely modify the process list
outside of the process management code that is compiled into the kernel.
Even if you could figure out a way to acquire the lock - you would have no
way of knowing the internal lock ordering, which is required to prevent your
code from deadlocking the system. I have seen lots of people attempt this
feat and it always ends in pain and misery. :slight_smile:

wrote in message news:xxxxx@ntdev…
>> The process lists are modified under a system owned lock. You can’t
>> safely modify the list outside
>> of that lock.
>
> What you can do is just to acquire it. All dispatcher objects in the
> system are protected by a single spinlock, and you can acquire it by
> KeSetEvent() - all you have to do is to supply ‘Wait’ parameter, telling
> the system that KeSetEvent() call is followed by the one to KeWaitXXX().
> In such case KeSetEvent() returns at DPC level with dispatcher spinlock
> being held…
>
> Anton Bassov
>

> No, this is another list. There is no processes on KeXxx lists, only threads.

I am not speaking about process and thread lists that are, indeed, different. I am speaking about *dispatcher spinlock*, and, AFAIK, it is the same for all dispatcher objects in the system, be it thread, process, event or anything else that start with DISPATCHER_HEADER, and, hence, can be in either signaled or unsignaled state.

Anton Bassov

The process list is not a dispatcher object and is not protected in any way
by the dispatcher lock.

wrote in message news:xxxxx@ntdev…
>> No, this is another list. There is no processes on KeXxx lists, only
>> threads.
>
>
> I am not speaking about process and thread lists that are, indeed,
> different. I am speaking about dispatcher spinlock, and, AFAIK, it is
> the same for all dispatcher objects in the system, be it thread, process,
> event or anything else that start with DISPATCHER_HEADER, and, hence, can
> be in either signaled or unsignaled state.
>
> Anton Bassov
>

> The process list is not a dispatcher object and is not protected in any way by the dispatcher lock.

Hold on - what makes KPROCESS different from, say, KEVENT or any other waitable object?After all, it can appear on a given thread’s wait list exactly like any other waitable object, and, AFAIK, as far as dispatcher spinlock is concerned, this is the only thing that matters. Am I wrong?

Anton Bassov

> Hold on - what makes KPROCESS different from, say, KEVENT or any other

waitable object?
Nothing. But the process list is not a KPROCESS or KEVENT - it is just a
linked data structure.

wrote in message news:xxxxx@ntdev…
>> The process list is not a dispatcher object and is not protected in any
>> way by the dispatcher lock.
>
> Hold on - what makes KPROCESS different from, say, KEVENT or any other
> waitable object?After all, it can appear on a given thread’s wait list
> exactly like any other waitable object, and, AFAIK, as far as dispatcher
> spinlock is concerned, this is the only thing that matters. Am I wrong?
>
> Anton Bassov
>

>objects in the system, be it thread, process, event or anything else that
start with

DISPATCHER_HEADER

There is no such list.

Dispatcher has:
a) several lists (one per priority) of all ready threads in system, only
ready
c) a list of threads currently waiting on the given DISPATCHER_HEADER

Nothing else. The list of all processes in system belongs to Ps and is not
documented.


Maxim Shatskih, Windows DDK MVP
StorageCraft Corporation
xxxxx@storagecraft.com
http://www.storagecraft.com

xxxxx@hotmail.com wrote:

I am not speaking about process and thread lists that are, indeed, different. I am speaking about *dispatcher spinlock*, and, AFAIK, it is the same for all dispatcher objects in the system, be it thread, process, event or anything else that start with DISPATCHER_HEADER, and, hence, can be in either signaled or unsignaled state.

Well yes, and … it’s extremely likely that the dispatcher spinlock
only protects _EPROCESS->Pcb->Header which is of type
_DISPATCHER_HEADER. Given the number of different things in _EPROCESS
and _KPROCESS, it’s *extremely* unlikely that they’re all protected
under the same spinlock:

Incidentally, there’s also _EPROCESS->ProcessLock, which is an
_EX_PUSH_LOCK, and also _EPROCESS->Pcb->ProcessLock, which is a
spinlock. I wouldn’t be surprised if they were used to protect the
various bits of state hanging off the two structures.

MH.

xxxxx@hotmail.com wrote:

Hold on - what makes KPROCESS different from, say, KEVENT or any other waitable object?After all, it can appear on a given thread’s wait list exactly like any other waitable object, and, AFAIK, as far as dispatcher spinlock is concerned, this is the only thing that matters. Am I wrong?

Unfortunately, yes, because locks do not necessarily protect entire
structures. The locking is more fine grained than that, and you end up
with a heirarchy of locks that in some way corresponds to the possible
lifetimes and use cases of the various parts of those structures.

MH.

> But the process list is not a KPROCESS or KEVENT - it is just a linked data structure.

Now I see your point - indeed,there is no need to protect the *whole* list with a dispatcher spinlock (in fact, it can be not even a spinlock but some construct that allows preemption)…

Anton Bassov

The discussion on the process list, synchronization thereto, etc, while
somewhat interesting is pretty irrelevant. While I wholeheartedly agree
with those that say you shouldn’t do what you’re doing, I’m sure you’re
going to do it anyway.

So, have you tried the painfully simple what-the-hell-are-you-thinking
obvious? If process termination is doing a RemoveEntryList on the EPROCESS,
why don’t you put it in a damn list before you kill it? Any list should do;
try a locally declared LIST_ENTRY.

  • Dan.

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of
xxxxx@yahoo.com
Sent: Friday, March 14, 2008 12:35 AM
To: Windows System Software Devs Interest List
Subject: [ntdev] Process Termination with Antirootkit gives BSOD

Hi All,

I am working in Quick Heal Techonologies Pvt. Ltd., which is a security
company. We have developed a AntiRootkit product which is capable of finding
processes hidden by system call hooking or Direct Kernel Object
Manipulation.

But the problem is when we terminate the process kernel gives BSOD if the
process is hidden by Direct Kernel Object Manipulation technique.

I found that this is due to following reason…
Rootkit alters linklist of active processes to remove the node(EPROCESS) of
the process to be hidden. It adjust the pointers in link list to make it
consistent but leave the pointers in EPROCESS of the process to be hidden as
it is. That means pointers in EPROCESS are invalid, but when we terminate
the process the system call trys to remove the process from active link
list, which is not there. Thus, these manupulations creates inconsistency in
link list and result in BSOD.

Is there any solution to this problem?

Thanks & Regards,
Amit.


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer

The whole mechanism on how to traverse the process list and deal with the synchronization issues is described by the book “Rootkits: Subverting the Windows Kernel” from Greg Hoglund and James Butler.

I haven’t tried the suggestions from that book, so I don’t know how well they work, however according to the book:

  1. In order to prevent the “hidden” process (i.e. a process that was removed from the operating system’s process list) from crashing, when you terminate it, you need to change the Flink and the Blink to point to its own Flink.
  2. In order to traverse the list without causing any synchronization issues, you need to prevent context switching by setting all CPUs to DISPATCH_LEVEL. This can be done by raising the current processor’s IRQL to DISPATCH_LEVEL and then sending DPCs to the rest of the processors.

The book has way more details on that and I suggest reading it, unless somebody else from the list thinks that this solution won’t work (as I said, I just point out what I read in the book, since I haven’t tried it, so I don’t know how well it works).

Ilias


From: xxxxx@lists.osr.com [xxxxx@lists.osr.com] On Behalf Of Dan Kyler [xxxxx@privtek.com]
Sent: Sunday, March 16, 2008 6:58 PM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] Process Termination with Antirootkit gives BSOD

The discussion on the process list, synchronization thereto, etc, while
somewhat interesting is pretty irrelevant. While I wholeheartedly agree
with those that say you shouldn’t do what you’re doing, I’m sure you’re
going to do it anyway.

So, have you tried the painfully simple what-the-hell-are-you-thinking
obvious? If process termination is doing a RemoveEntryList on the EPROCESS,
why don’t you put it in a damn list before you kill it? Any list should do;
try a locally declared LIST_ENTRY.

  • Dan.

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of
xxxxx@yahoo.com
Sent: Friday, March 14, 2008 12:35 AM
To: Windows System Software Devs Interest List
Subject: [ntdev] Process Termination with Antirootkit gives BSOD

Hi All,

I am working in Quick Heal Techonologies Pvt. Ltd., which is a security
company. We have developed a AntiRootkit product which is capable of finding
processes hidden by system call hooking or Direct Kernel Object
Manipulation.

But the problem is when we terminate the process kernel gives BSOD if the
process is hidden by Direct Kernel Object Manipulation technique.

I found that this is due to following reason…
Rootkit alters linklist of active processes to remove the node(EPROCESS) of
the process to be hidden. It adjust the pointers in link list to make it
consistent but leave the pointers in EPROCESS of the process to be hidden as
it is. That means pointers in EPROCESS are invalid, but when we terminate
the process the system call trys to remove the process from active link
list, which is not there. Thus, these manupulations creates inconsistency in
link list and result in BSOD.

Is there any solution to this problem?

Thanks & Regards,
Amit.


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer

I think that book is pretty good as well - however, the problem with 2) is
that the process lock is sometimes acquired at passive level so you may send
a DPC and interrupt the processor that is currently modifying the list
legally (while holding the process lock) - and screw up the list up nicely
when the interrupting thread removes the process from the list. There really
is no way to do this correctly. It will always have a really high
probability of crashing the system. :slight_smile:

“Ilias Tsigkogiannis” wrote in message
news:xxxxx@ntdev…
The whole mechanism on how to traverse the process list and deal with the
synchronization issues is described by the book “Rootkits: Subverting the
Windows Kernel” from Greg Hoglund and James Butler.

I haven’t tried the suggestions from that book, so I don’t know how well
they work, however according to the book:
1) In order to prevent the “hidden” process (i.e. a process that was removed
from the operating system’s process list) from crashing, when you terminate
it, you need to change the Flink and the Blink to point to its own Flink.
2) In order to traverse the list without causing any synchronization issues,
you need to prevent context switching by setting all CPUs to
DISPATCH_LEVEL. This can be done by raising the current processor’s IRQL to
DISPATCH_LEVEL and then sending DPCs to the rest of the processors.

The book has way more details on that and I suggest reading it, unless
somebody else from the list thinks that this solution won’t work (as I said,
I just point out what I read in the book, since I haven’t tried it, so I
don’t know how well it works).

Ilias

________________________________________
From: xxxxx@lists.osr.com [xxxxx@lists.osr.com]
On Behalf Of Dan Kyler [xxxxx@privtek.com]
Sent: Sunday, March 16, 2008 6:58 PM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] Process Termination with Antirootkit gives BSOD

The discussion on the process list, synchronization thereto, etc, while
somewhat interesting is pretty irrelevant. While I wholeheartedly agree
with those that say you shouldn’t do what you’re doing, I’m sure you’re
going to do it anyway.

So, have you tried the painfully simple what-the-hell-are-you-thinking
obvious? If process termination is doing a RemoveEntryList on the EPROCESS,
why don’t you put it in a damn list before you kill it? Any list should do;
try a locally declared LIST_ENTRY.

- Dan.

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of
xxxxx@yahoo.com
Sent: Friday, March 14, 2008 12:35 AM
To: Windows System Software Devs Interest List
Subject: [ntdev] Process Termination with Antirootkit gives BSOD

Hi All,

I am working in Quick Heal Techonologies Pvt. Ltd., which is a security
company. We have developed a AntiRootkit product which is capable of finding
processes hidden by system call hooking or Direct Kernel Object
Manipulation.

But the problem is when we terminate the process kernel gives BSOD if the
process is hidden by Direct Kernel Object Manipulation technique.

I found that this is due to following reason…
Rootkit alters linklist of active processes to remove the node(EPROCESS) of
the process to be hidden. It adjust the pointers in link list to make it
consistent but leave the pointers in EPROCESS of the process to be hidden as
it is. That means pointers in EPROCESS are invalid, but when we terminate
the process the system call trys to remove the process from active link
list, which is not there. Thus, these manupulations creates inconsistency in
link list and result in BSOD.

Is there any solution to this problem?

Thanks & Regards,
Amit.


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer

So, what happens in the “normal” case, where the process lock is already acquired at passive level and at that moment the quantum ends, so the scheduler decides to do a context switch? Won’t there be a blue screen?

Ilias


From: xxxxx@lists.osr.com [xxxxx@lists.osr.com] On Behalf Of the_el_vez [xxxxx@microsoft.com]
Sent: Sunday, March 16, 2008 10:45 PM
To: Windows System Software Devs Interest List
Subject: Re:[ntdev] Process Termination with Antirootkit gives BSOD

I think that book is pretty good as well - however, the problem with 2) is
that the process lock is sometimes acquired at passive level so you may send
a DPC and interrupt the processor that is currently modifying the list
legally (while holding the process lock) - and screw up the list up nicely
when the interrupting thread removes the process from the list. There really
is no way to do this correctly. It will always have a really high
probability of crashing the system. :slight_smile:

“Ilias Tsigkogiannis” wrote in message
news:xxxxx@ntdev…
The whole mechanism on how to traverse the process list and deal with the
synchronization issues is described by the book “Rootkits: Subverting the
Windows Kernel” from Greg Hoglund and James Butler.

I haven’t tried the suggestions from that book, so I don’t know how well
they work, however according to the book:
1) In order to prevent the “hidden” process (i.e. a process that was removed
from the operating system’s process list) from crashing, when you terminate
it, you need to change the Flink and the Blink to point to its own Flink.
2) In order to traverse the list without causing any synchronization issues,
you need to prevent context switching by setting all CPUs to
DISPATCH_LEVEL. This can be done by raising the current processor’s IRQL to
DISPATCH_LEVEL and then sending DPCs to the rest of the processors.

The book has way more details on that and I suggest reading it, unless
somebody else from the list thinks that this solution won’t work (as I said,
I just point out what I read in the book, since I haven’t tried it, so I
don’t know how well it works).

Ilias

________________________________________
From: xxxxx@lists.osr.com [xxxxx@lists.osr.com]
On Behalf Of Dan Kyler [xxxxx@privtek.com]
Sent: Sunday, March 16, 2008 6:58 PM
To: Windows System Software Devs Interest List
Subject: RE: [ntdev] Process Termination with Antirootkit gives BSOD

The discussion on the process list, synchronization thereto, etc, while
somewhat interesting is pretty irrelevant. While I wholeheartedly agree
with those that say you shouldn’t do what you’re doing, I’m sure you’re
going to do it anyway.

So, have you tried the painfully simple what-the-hell-are-you-thinking
obvious? If process termination is doing a RemoveEntryList on the EPROCESS,
why don’t you put it in a damn list before you kill it? Any list should do;
try a locally declared LIST_ENTRY.

- Dan.

-----Original Message-----
From: xxxxx@lists.osr.com
[mailto:xxxxx@lists.osr.com] On Behalf Of
xxxxx@yahoo.com
Sent: Friday, March 14, 2008 12:35 AM
To: Windows System Software Devs Interest List
Subject: [ntdev] Process Termination with Antirootkit gives BSOD

Hi All,

I am working in Quick Heal Techonologies Pvt. Ltd., which is a security
company. We have developed a AntiRootkit product which is capable of finding
processes hidden by system call hooking or Direct Kernel Object
Manipulation.

But the problem is when we terminate the process kernel gives BSOD if the
process is hidden by Direct Kernel Object Manipulation technique.

I found that this is due to following reason…
Rootkit alters linklist of active processes to remove the node(EPROCESS) of
the process to be hidden. It adjust the pointers in link list to make it
consistent but leave the pointers in EPROCESS of the process to be hidden as
it is. That means pointers in EPROCESS are invalid, but when we terminate
the process the system call trys to remove the process from active link
list, which is not there. Thus, these manupulations creates inconsistency in
link list and result in BSOD.

Is there any solution to this problem?

Thanks & Regards,
Amit.


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at
http://www.osronline.com/page.cfm?name=ListServer


NTDEV is sponsored by OSR

For our schedule of WDF, WDM, debugging and other seminars visit:
http://www.osr.com/seminars

To unsubscribe, visit the List Server section of OSR Online at http://www.osronline.com/page.cfm?name=ListServer