[Autogenerated] here's my local current debugger open on this
system that has eight logical processors.
We can look at any process that we choose.
So for example,
if I look at some process that we have on the system
such as some explorer process, for example with using 00,
just get some basic information about the process.
But if you use other flags we can see information
about threats within this process.
So hopefully the debugger is able to locate and explore process for us.
Here we go.
Let's just grab one of those who might have more than one and
I'm going to use the process command again.
But this time I'm going to focus on this particular process
and I'm going to add the flag three here to get some basic
information about threats.
Let's see.
So here what we get is some summary about the
threats in this process and explore, we know it has many threats.
So this is going to be pretty big for each thread.
We get this address and this is the address for the the threat data structure.
Let me break that up.
That's uh enough.
We can see here the thread object, that's the thread object point.
That's the the thread.
You can see there's a command called bank thread which allows us to see the
thread information for this particular thread in details.
If you just click that we get particular information
about this threat including its priority,
its creation time.
The time is spent in user mode in kernel mode,
which process it is part of pointing to the process object and even a
call stack for that threat at this point in time.
At least the point where where I clicked that particular button.
So this address represents the threat information for this thread.
And of course we can always go to the actual data
structure behind the scenes which is the thread and look
at that using something like the D.
T command.
So if I just copy this address I can do something like a thread
just grab this address and provided to a thread.
So now we see the threat data structure and its entire glory here and
the values as they pertain to this particular threat.
And as usual as we've seen already multiple times with the DT
command we can continue clicking to see more details about each of
each of these internal data structures,
some of which we can definitely guess as to their meaning,
some of them that probably not because most of these things are undocumented.
So you can probably guess this is the creation time and
exit time for the thread and there is a start address for
the threat and some other stuff.
But some other things here might not be easily guessed because they're not
really documented in any case going back here to this output.
We can see that the threat is waiting on this object,
notice the state of the thread is weight,
so it's in a waiting state and what we have here is the list of objects it
is waiting on in this case it's waiting on cue object,
something that we're not going to discuss in this course.
But let's see if we can use the primes example to to see what happens with
these thread objects once the operation is in plain.
So I want to put a breakpoint here just before starting to perform the waiting
here um and I want to see what happens to all these threats and what they look
like in the kernel debugger In order to do that,
I'm going to go to the properties here.
I can use release, I can use the bug, it doesn't really matter here.
Let me switch to release for this example.
Just provide a number to the command line.
Otherwise we'll have a single thread and I want to have a bit more.
So let's go with four threats and run this.
So once around this,
I expected the ______ to land in the breakpoint very quickly.
Of course there are some symbols being downloaded now,
so it might take a few more seconds for these symbols to be
downloaded from the Microsoft symbol server.
And I hope that breakpoint will hit.
So it doesn't because of optimizations provided by by the compiler.
Let me switch to the bug build because really have
to for this uh political example, unless I disable optimizations,
which I don't want to do at this point.
So let's just switch to the bug and do exactly the same thing.
Just put four threads here as an example and run this again.
So again it might take a few seconds, but here we go, we get to that breakpoint.
So at this point we can go back to our current
debugger and see what's going on there.
So first we're going to look up our process and we know
the process ID really it's a 5564.
We can see that in the debugger so we can go ahead and use that um using
the process I did is something that the process command expect except as
well and the zero and just a reminder indicating that decimal number
rather than hexadecimal And again, let's use three here to see what's going on.
Just to see the state of all the threats here in the
process in a very summarized kind of form.
So we expect the first threat to be um well let's see, let's see what we get.
So we see we have a bunch of threats waiting on various events objects.
You can also see the freeze count here being one and that's
because the threats are frozen as they are now frozen by the
debugger So they're not going to go anywhere.
So let's look at these threats a little bit more detailed by pressing
these links to see the call stack of these threats.
I'm going to start with the first one and the first one is the main
threat essentially the one that's supposed to be very soon waiting
for all these threats to complete.
But at this point it's not waiting just yet.
It's just frozen by the debugger And we can see the kernel stack here but
we don't see using mode stack and that has the reason is the same as the
ones that we've seen in the previous course.
We're looking at process,
we have to switch to this thread first before we can get to the
symbols or to be more precise to switch this process.
So the process subject is this one.
So you can just grab it and use the dot process command to switch to
this process and also have the symbols loaded already the user mode
symbols as as part of this movement here.
And then we can look at the thread once again,
hopefully see some user mode stuck here.
It should be pointing to our code and indeed it does.
You can see we have the main function here that's calling cal crimes
and this is where the threat is currently waiting.
It hasn't yet started to do much work in the cult primes function
although we can even switch to that frame if you so desire and see
exactly where that threat is if we switch to it.
But in general we can look at any thread that we want
and see what that threat is doing.
So that thread was one of the what that was the main thread.
What about some other worker thread?
Let's try this one.
Let's see what that threat is actually doing.
So this threat, in fact, is not one of the threats we created.
This is a threat which is part of the thread pool,
something we'll discuss in the next slide.
Um And this is just a worker thread that is waiting for something to do,
and it's going to be destroyed very quickly if there's no work to do.
But for now it doesn't really know that just yet, and it's waiting for work.
So let's try one of the other threats.
Perhaps that might be the ones that we have actually created,
the four threats we created.
So here is something that is closer to what we're trying to show here.
And the thing is that the threat hasn't started just yet.
You can see there's an internal threat function that is preparing things to run,
but it's not running just yet.
That's because we broke very quickly before the thread got a chance to
kind of wind up its stuff and start doing some work.
So maybe we need to let the process run a little bit more before we recheck.
Let's go back to visual studio and press F 10 and then quickly try to break.
So we can do something like press F 10,
and then break as quickly as as perhaps we can if we get a chance to do that.
Well, at this point, the threats are all done.
I didn't get a chance to break quickly enough.
Um and uh and that's it, the threats are done.
So all the threats should essentially go away at
least most of them from the process.
So let's see that here's our process again.
Let's see the state of the threats.
You might have some thread pool threads still existing in the process,
but all the other threats should be there should be gone really.
So you see number of threats has been significantly reduced.
We have destroyed the four threats we created.
They are no longer running and we just have a few threats that remain.
The main threat is always there, of course.
But then we have these two other threats which belong to the thread pool.
So, as you can see,
we can analyze the state of threats in several ways and didn't
look at the actual event objects and other synchronization
primitives that these threats were waiting on.
This is something you might say for a for a future course