@TheComet
I'm not sure how the debug console works, but here's how debugging works in most languages (and how I did it when I was writing a debugger for DBPro):
When the program is compiled, the compiler knows which lines of code were translated into which assembly instructions, and it saves this information to a file. The debugger can see which instruction is executing at runtime, and do a reverse lookup using the debug information generated by the compiler to find out which line that assembly instruction belongs to.
The names and addresses of program level variables are saved as part of the debug info, so the debugger can convert a variable name to the correct address and then read the memory at that address.
For function level variables, the debug info stores the variables for each function, and an address relative to the stack frame of that function. At runtime, the debugger can look at which function the current assembly instruction belongs to because it knows the addresses of all the functions, and it knows the stack frame address because that is stored in a register. All it has to do is add on the relative address from the debug info for a particular local variable and read the value at that memory location.
All of this requires no cooperation from the program being debugged, as the facilities to pause and access another process's registers and memory are built into windows as a debugging api.
However, I'm fairly sure the debug console works in a much more cooperative way. I know for a fact that the line number is stored in a hidden global variable at all times, so it may use that. To access variables it would have to do something similar to a normal debugger though.
[b]
