Cheat Engine Forum Index Cheat Engine
The Official Site of Cheat Engine
 
 FAQFAQ   SearchSearch   MemberlistMemberlist   UsergroupsUsergroups   RegisterRegister 
 ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 


API for "modify register at address"?
Goto page 1, 2, 3  Next
 
Post new topic   Reply to topic    Cheat Engine Forum Index -> Cheat Engine Source
View previous topic :: View next topic  
Author Message
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Fri Oct 07, 2005 12:59 pm    Post subject: API for "modify register at address"? Reply with quote

I noticed that CE is able to modify a register (any of them) at a given address. I was wondering if there is a Windows API that would do this?

I have the address, the value, and I know which register I want put the value in but I just don't know how to do it.

I know that the API "WriteProcessMemory" does something similar to this by writing a value to a given address. Is there a way to use it to write a value to a register at a given address?

If you know other ways to go at this, please explain. BTW, I'm trying to write this in C++ (VB or C# ways is fine as well).

Thanks
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 470

Joined: 09 May 2003
Posts: 25785
Location: The netherlands

PostPosted: Fri Oct 07, 2005 1:40 pm    Post subject: Reply with quote

You need to use debugger mechanics to do that.

first start a debug session with the process (debugactiveprocess or createprocess with debug parameters, in a seperate thread preferably)

then in the waitfordebugevent/continuedebugevent loop you watch for thread creations. When a tread gets created you set one or more debug registers so it'll break at one of the positions you want.

Then when you get a breakpoint exception on one of the addresses use GeThreadContext followed by SetThreaContext and set the registers you want.

------------------------
Another method of setting breakpoints is replacing the first byte of a instruction with a int3 instruction, and on break replace the int3 with the old code and put back when continueing. But if you want to do this for a certain game that disconnects when the code gets changed (different crc) this wont work.

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping
Back to top
View user's profile Send private message MSN Messenger
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Fri Oct 07, 2005 4:18 pm    Post subject: Reply with quote

I just have some more questions reguarding your reply. BTW, thanks a lot Wink and your CE kick ass!!!

Quote:
"When a tread gets created you set one or more debug registers so it'll break at one of the positions you want."


Each time a thread is created, I would create a break point at the address that I am interested in, correct?

1) What function (or I guess API) allow me to create a break point at a desire address?
2) If 3 threads are created, it would create 3 break points at the same address, correct?

Code:
BOOL SetThreadContext(
  HANDLE hThread,
  const CONTEXT* lpContext
);


What would the "lpContext" be if I want register EAX to hold the value 0034C45?

Thanks Dark Byte
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 470

Joined: 09 May 2003
Posts: 25785
Location: The netherlands

PostPosted: Sat Oct 08, 2005 2:18 am    Post subject: Reply with quote

No, thread creation isn't a real breakpoint, but the process will break. I use that debug event to store a list of running threads (because the only way to get the threadhandle is by linking the threadid and threadhandle together)

In that event use setthreadcontext and set the debugregisters so they break at the position you want. (Check the intel instruction manual on the exact bits to set in dr7)

then continue debugging untill a breakpoint causes the debugger to be called and then if you've checked if it's your breakpoint use setthreadcontext to change the registers to what you want)


1: yes, every thread has it's own debug registers so every thread can have up to 4 breakpoints. It's easiest to set the debugregs of all threads to the same.

2: lpContext is a pointer to a CONTEXT structure and the context.EAX=0x34C45

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping
Back to top
View user's profile Send private message MSN Messenger
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Sun Oct 09, 2005 2:33 am    Post subject: Reply with quote

I encounted some problems while doing this.

Code:
// attached to process
// enter loop (loop forever)
WaitForDebugEvent(out debug_event, INFINITE);

switch (debug_event.dwDebugEventCode)
.
.
.
case CREATE_THREAD_DEBUG_EVENT:
  CREATE_THREAD_DEBUG_INFO ctdi = debug_event.CreateThread;
  this.threads.Add(debug_event.dwThreadId,ctdi.hThread);     // threads heap table
  CONTEXT context;     // an empty context
  GetThreadContext( ctdi.hThread, out context);     // get the context

  // note: at this point, context is still empty after calling GetThreadContext, don't know if this is correct

  context.Dr0 = 0x4C039;    // set debug register 0 to address to break
  context.Dr7 = 0x3;     // set debug register 7 first 2 bits to 11 (L0 and G0)
  SetThreadContext(ctdi.hThread, ref context);    // create break point at that address
  break;


I took the thread id and thread handle and add it to a hash table to keep track of the threads. Created a CONTEXT and called GetThreadContext to fill up the values (registers) in it. Turn out it is still empty after setting it. Changed Dr0 to the address I wanted to put a breakpoint on and set Dr7 R/W to 00 and LEN to 00, also the L is 1 and G is 1. (got this info from http://pdos.csail.mit.edu/6.828/2005/readings/i386/s12_02.htm)

Now, waiting for debug event to hit the exception breakpoint.

Code:
case EXCEPTION_DEBUG_EVENT:
  EXCEPTION_DEBUG_INFO edi = debug_event.Exception;
 
  // new switch to see the different exceptions
  switch (edi.ExceptionRecord.ExceptionCode)
  {
     case EXCEPTION_BREAKPOINT:
       // check to see if it is the correct breakpoint 
       if (edi.ExceptionRecord.ExceptionAddress == 0x4C039)
       { // check to see if hash table has that thread id
         if(threads.ContainsKey(debug_event.dwThreadId))
         {
            int handle = threads[debug_event.dwThreadId];     // get handle
            CONTEXT context;     // create empty context
            GetThreadContext(handle, out context);  // get context
            context.Eax = 0x6254A;     // change one of the register to something else
            SetThreadContext(handle, ref context);     // set the modified context back
          }
        }
        break;

      case EXCEPTION_ACCESS_VIOLATION:
      . . .


After setting some breakpoint when a new thread is created, somehow it keeps going into EXCEPTION_ACCESS_VIOLATION. After a couple of loops and keep going into EXCEPTION_ACCESS_VIOLATION, the debugger crash along with the process.

Do I need to setup any security to attach a debugger to a process? It seems like it is not getting to the breakpoint that I had set (or if I set it correctly?).

Thanks
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 470

Joined: 09 May 2003
Posts: 25785
Location: The netherlands

PostPosted: Sun Oct 09, 2005 4:35 am    Post subject: Reply with quote

before calling setthreadcontext or getthreadcontext set the ContextFlags accordingly. (set them for CONTEXT_DEBUG_REGISTERS, also note that CONTEXT_FULL doesn't include the debug registers)

I also recommend removing a threadid-threadhandle link on a terminate thread event.

Also, debug registers don't cause a EXCEPTION_BREAKPOINT event. Only int3 instructions do that. Debug registers cause a EXCEPTION_SINGLE_STEP

and if the exceptions still arnt solved keep in mind that EXCEPTION_DEBUG_EVENT is one of the cases where you DEFAULT return DBG_EXCEPTION_NOT_HANDLED instead of DBG_CONTINUE

Only return DBG_CONTINUE when it is a debug event you caused and not the game itself

e.g: a simple method used in some games to crash debuggers:
Code:

__try
{
__asm {int 3}
ReallyLargeFunctionWithOnlyCrapThatWillCrashTheGame(); //never gets called unless a debugger handled the int3
}
__except(1)
{
  ContinueWithNormalGame();
}





Oh yes, one more thing you might want to know:
When a debug event fired and you want to continue, remove the debug registers, do a single step (set the singe step flag in the eflags register) and reset the debug registers. (else when you go back it the debug event fires again on the same instruction)
There is supposed to be a resume flag in the eflags registers so you dont have to do that, but I never got it to work. (I gues filtered out by windows)

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping
Back to top
View user's profile Send private message MSN Messenger
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Sun Oct 09, 2005 5:41 pm    Post subject: Reply with quote

I tried what you told me and I still get the same problem. CONTEXT is still empty after setting the ContextFlag to CONTEXT_DEBUG_REGISTERS. Then I tried to set it to CONTEXT_FULL and CONTEXT is also empty. I don't know if this is correct or not maybe because a new thread is created so the context for that thread is new (empty)?

Well, I got an ExceptoinCode = 0xE06D7363, which does not match anything in the Win32 Debug API. After doing a DBG_CONTINUE on that exception, I get the EXCEPTION_ACCESS_VIOLATION. If I do a DBG_EXCEPTION_NOT_HANDLED on this exception, the debugger dies automatically. If I do a DBG_CONTINUE, it would loop and keep going into EXCEPTION_ACCESS_VIOLATION.

After that, I took a step back and comment out all the Get/SetThreadContext and so on. This time I just wanted to see how many threads are created and what kind of exceptions there were.

Code:
New thread created: thread id = 4516, thread handle = 564, start address 0x7C810856
New thread created: thread id = 2576, thread handle = 540, start address 0x7C810856
New thread created: thread id = 4288, thread handle = 556, start address 0x7C810856
New thread created: thread id = 5996, thread handle = 628, start address 0x7C810856
New thread created: thread id = 6028, thread handle = 600, start address 0x7C810856
New thread created: thread id = 5248, thread handle = 892, start address 0x7C810856
New thread created: thread id = 4432, thread handle = 1100, start address 0x7C95077B      // thread created at different address
Debug Exception: thread id = 4432, exception address = 0x7C901230, exception code = EXCEPTION_BREAKPOINT     // this exception always happen
// do DBG_CONTINUE
Debug Exception: thread id = 4628, exception address = 0x7C81EB33, exception code = 0xE06D7363     // no clue what wtf this code is
// do DBG_EXCEPTION_NOT_HANDLE
Debug Exception: thread id = 4628, exception address = 0x7C81EB33, exception code = 0xE06D7363     // do DBG_EXCEPTION_NOT_HANDLE
Debug Exception: thread id = 4628, exception address = 0x7C81EB33, exception code = 0xE06D7363     // do DBG_EXCEPTION_NOT_HANDLE
// debugger dies after this


Here is another one that loops on and on with different DBG_CONTINUE and DBG_EXCEPTION_NOT_HANLE...
Code:
New thread created: thread id = 1952, thread handle = 856, start address = 0x7C810856
New thread created: thread id = 4976, thread handle = 860, start address = 0x7C810856
New thread created: thread id = 4612, thread handle = 864, start address = 0x7C810856
New thread created: thread id = 5668, thread handle = 868, start address = 0x7C810856
New thread created: thread id = 2520, thread handle = 872, start address = 0x7C810856
New thread created: thread id = 5424, thread handle = 876, start address = 0x7C810856
New thread created: thread id = 4872, thread handle = 1088, start address = 0x7C95077B     // thread created at different address
Debug Exception: thread id = 4872, exception address = 0x7C901230, exception code = EXCEPTION_BREAKPOINT     // this exception always happens
// do DBG_CONTINUE
Debug Exception: thread id = 4140, exception address = 0x7C81EB33, exception code = 0xE06D7363     // no clue wtf this exception code is
///////////////////////////// do DBG_CONTINUE (different from top code) ////////////////////////
Debug Exception: thread id = 4140, exception address = 0x43C9EA, exception code = EXCEPTION_ACCESS_VIOLATION     // do DBG_CONTINUE
// loops forever and same thread keep getting this same exception

// if I do DBG_EXCEPTION_NOT_HANDLE on EXCEPTION_ACCESS_VIOLATION, debugger dies after this


So, even not messing with the debuggee at all, the debugger dies a few moment after attaching to the debuggee due to those exceptions that are encounted. I think I'm going to give up on this, unless you know my problem to why those exceptions cause things to break.

Thanks
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 470

Joined: 09 May 2003
Posts: 25785
Location: The netherlands

PostPosted: Mon Oct 10, 2005 3:03 am    Post subject: Reply with quote

Did you try it on a simple process like the cheat engine tutorial ?

Perhaps there's a bug inside your own app that crashes , like writing beyond the space of a array. (and when a debugger dies the debugged process also dies)

Or otherwhise you're not handling all exceptions as you should have.
No idea where though, but when just testing and not doing anything with your debugger you should always return DBG_EXCEPTION_NOT_HANDLED for the EXCEPTION_DEBUG_EVENT)
Sure, exceptions will still show up in the debugger, but with luck the game handles those exceptions itself.

Oh yes, you might want to handle the breakpoint exceptions from 7f000000 and above

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping
Back to top
View user's profile Send private message MSN Messenger
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Mon Oct 10, 2005 12:19 pm    Post subject: Reply with quote

Probably the game I'm debugging on is killing the debugger. I'll try it on minesweeper or something when I get home from work.

Let say that minesweeper doesn't kill the debugger, than that mean the game I'm debugging on does, how will I over come this? Is there an API for hiding the assembler from the debugger? I think you have this "check box" function in the "Settings->Assembler tab" within CE.
Back to top
View user's profile Send private message
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Tue Oct 11, 2005 12:20 am    Post subject: Reply with quote

Tested it out with Minesweeper, Freecell, and Pinball (all Microsoft's Windows games).

Minesweeper = create only 1 thread, break point exception after that thread is created (like I said before, this break point exception always happen after you attach the debugger to a process).

Freecell = same like Minesweeper.

Pinball = a lot of threads are created due to the ball rolling around hitting all kinds of things. Even flipping the flipper create new threads. But only that one exception after the dubugger attach itself to the process occur. No other exception happens.

So all 3 games works fine, that mean the previous process I tried to attach crash my dubugger on purpose. Would you know how to deal with this? Your CE attach to it fine and debug and everything fine.
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 470

Joined: 09 May 2003
Posts: 25785
Location: The netherlands

PostPosted: Tue Oct 11, 2005 2:13 am    Post subject: Reply with quote

I've made a quick test app that may help you with your debugger.
See if you can get through all 4 stages without a error

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping
Back to top
View user's profile Send private message MSN Messenger
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Tue Oct 11, 2005 6:51 am    Post subject: Reply with quote

I ran the process, then attach to it with the debugger. Ran your tool, and ran through all 4 stages. It say it found no errors.

But the debugger dies after like 15 seconds attaching to the process. It exception with the code 0xE06D7363 (doesn't match any thing I know). AfFter doing the DBG_EXCEPTION_NOT_HANDLE, it dies.
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 470

Joined: 09 May 2003
Posts: 25785
Location: The netherlands

PostPosted: Tue Oct 11, 2005 7:21 am    Post subject: Reply with quote

It even didn't say it found the debugger in step 4 ?
(I take it you havn't patched isdebuggerpresent yet, so it should have given a message about that)

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping
Back to top
View user's profile Send private message MSN Messenger
ducspam
Expert Cheater
Reputation: 0

Joined: 07 Oct 2005
Posts: 171

PostPosted: Tue Oct 11, 2005 11:38 am    Post subject: Reply with quote

It say something like "no error found, or do you not have a dubugger running?" on step 4.
Back to top
View user's profile Send private message
Dark Byte
Site Admin
Reputation: 470

Joined: 09 May 2003
Posts: 25785
Location: The netherlands

PostPosted: Tue Oct 11, 2005 12:49 pm    Post subject: Reply with quote

did you attach your debugger to it at least before clicking the last button?
Because it looks like you're not debugging the debugger, and step 4 should have told you it detected a debugger unless you messed up the isdebugger present api

_________________
Do not ask me about online cheats. I don't know any and wont help finding them.

Like my help? Join me on Patreon so i can keep helping
Back to top
View user's profile Send private message MSN Messenger
Display posts from previous:   
Post new topic   Reply to topic    Cheat Engine Forum Index -> Cheat Engine Source All times are GMT - 6 Hours
Goto page 1, 2, 3  Next
Page 1 of 3

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum
You cannot attach files in this forum
You can download files in this forum


Powered by phpBB © 2001, 2005 phpBB Group

CE Wiki   IRC (#CEF)   Twitter
Third party websites