scanning help

Discussions Related to Game Hacking and Memory Hacking Software

Moderators: g3nuin3, SpeedWing, WhiteHat, mezzo

Postby Torero » Thu Apr 19, 2007 4:01 am

When is MHS dbg going to live, and should I learn another dbg before you release yours ?


if so can you recomment one for me, as I am trying to learn as much as I can as fast as possible.


Will it be ok if I rely on MHS completely when everything is done?


When do you expect new MHS to reach 1.0 ?
Torero
NULL
 
Posts: 191
Joined: Thu Jan 04, 2007 10:14 am

Postby Torero » Thu Apr 19, 2007 4:03 am

How do I learn which module of which process is where?
Torero
NULL
 
Posts: 191
Joined: Thu Jan 04, 2007 10:14 am

Postby esco » Thu Apr 19, 2007 5:24 pm

Wussup dawg. I have 3 questions for you today bro:

1)Why is it that when I use \n (newline) in my code, in a PrintF statement instead of going down one line, it just prints a square character?

2)I declared a var called count to be of type int... then wrote this code:

void printstats()
{
extern SHORT timerseconds = { "", 0x0064ea78 };
int count;

if ((timerseconds == 0 || timerseconds == 30) && count == 0)
{
{count = 1;}
PrintF("Richter:\n Level: %d\n HP: %d/%d\n HEARTS: %d/%d\n", level, hp, maxhp, hearts, maxheartstag);
}
if (timerseconds != 0 && timerseconds != 30 && count != 0) {count = 0;}
}

3)What can I use to clear the entire text box, before the info is printed to the screen each time?

Yet the code doesn't work. SO I put in a PrintF statement that prints out the value of count... and it turned out to be some VERY large value in the 2 millions. Yet even though the code above is very clear, and timerseconds does NOT equal 0 or 30, it still doesn't change back to 0. Why is this?

........ LASTLY, something I wanted to point out.... Are you aware that printf must be used as PrintF (capital P and F) to work or it gives a script error?
Esco.... the name says it all. New Yorikan for life.
User avatar
esco
NULL
 
Posts: 148
Joined: Mon Sep 18, 2006 2:25 am
Location: Florida, a.k.a. the US's version of hell!

Postby L. Spiro » Thu Apr 19, 2007 9:01 pm

Torero wrote:When is MHS dbg going to live, and should I learn another dbg before you release yours ?


if so can you recomment one for me, as I am trying to learn as much as I can as fast as possible.


Will it be ok if I rely on MHS completely when everything is done?


When do you expect new MHS to reach 1.0 ?

The debugger will be functionally “useful” in only a few releases.
If you need a more useful debugger, I would recommend OllyDbg.
Yes, it will be okay (even better) to rely on MHS for all debugging needs in the future, as I plan to literally match every function in OllyDbg and better, plus a lot from IDA as well.


Torero wrote:How do I learn which module of which process is where?

Open the Hex Editor on the process and click the Info tab in the Helper.






esco wrote:Why is it that when I use \n (newline) in my code, in a PrintF statement instead of going down one line, it just prints a square character?

Because edit controls require the full “\r\n” combination to move text to a new line. Since an edit control is used to display the text, you have to use \r\n instead of \n.


esco wrote:What can I use to clear the entire text box, before the info is printed to the screen each time?

Clear().



esco wrote:Yet the code doesn't work. SO I put in a PrintF statement that prints out the value of count

count is not initialized.
int count = 0; might work better, but it depends on how and when you are calling this function, since count will always be 0 when you call this function (and use this code), which is probably not what you want.
You probably wanted count to be a global so its value is not reset each time the function is called.



esco wrote:LASTLY, something I wanted to point out.... Are you aware that printf must be used as PrintF (capital P and F) to work or it gives a script error?

Because if I named it “printf” it would look dorky, since all the other functions (except the new WinSocks functions) start with capital letters as per the modern standard.
The ONLY reason I left the WinSocks functions in the same lower-case format as the originals is because WinSocks are complicated enough for most people that they really would be better off being able to directly copy/paste examples they find on the Internet. If I changed their formats to capital letters, people would have to paste examples from online, then modify all the functions to get it to work.

As of now, you have to do that with the standard functions, but people already know how to use those functions and it does not cause confusion.

When I make the preprocessor I will add macros that allow you to write “printf” and it will be changed to “PrintF” to work with my compiler.


L. Spiro
User avatar
L. Spiro
L. Spiro
 
Posts: 3129
Joined: Mon Jul 17, 2006 10:14 pm
Location: Tokyo, Japan

Postby esco » Sun Apr 22, 2007 4:53 am

Okay dawg, I got it. Thanks for all the help it works fine now.

I was also wondering, since you said it supports some C++ features, are you ever planning on making it support most (if not all) c++ syntax as well? I'm just asking because I was trying to use cout and cin (easier than printf statements to me) and of course I quickly figured out that your program did NOT recognize the syntax.
Esco.... the name says it all. New Yorikan for life.
User avatar
esco
NULL
 
Posts: 148
Joined: Mon Sep 18, 2006 2:25 am
Location: Florida, a.k.a. the US's version of hell!

Postby L. Spiro » Sun Apr 22, 2007 10:25 am

I was also wondering, since you said it supports some C++ features, are you ever planning on making it support most (if not all) c++ syntax as well?

No.
People underestimate how much of an addition over C C++ is.
C++ adds classes over C. So people imagine C, with a bit of C++ added on top.

In fact, simply by adding classes, templates, and operator overloading (required for your cout and cin), C++ becomes an addition 5 times the size of the original C, making the language altogether 6 times larger.
Had I decided to implement C++ into the language, I would simply never be able to finish.


Besides, I really hate cout and cin. The syntax is ugly.


L. Spiro
User avatar
L. Spiro
L. Spiro
 
Posts: 3129
Joined: Mon Jul 17, 2006 10:14 pm
Location: Tokyo, Japan

Postby esco » Mon Apr 23, 2007 2:13 pm

L. Spiro wrote:
I was also wondering, since you said it supports some C++ features, are you ever planning on making it support most (if not all) c++ syntax as well?

No.
People underestimate how much of an addition over C C++ is.
C++ adds classes over C. So people imagine C, with a bit of C++ added on top.

In fact, simply by adding classes, templates, and operator overloading (required for your cout and cin), C++ becomes an addition 5 times the size of the original C, making the language altogether 6 times larger.
Had I decided to implement C++ into the language, I would simply never be able to finish.


Besides, I really hate cout and cin. The syntax is ugly.

L. Spiro


HA HAAAA! Yeah it sure is. :P

Anyways, I've run into a bit of a dilemma... I decided to switch emulators today, since epsxe seems VERY archaic compared to psx emulator.

Of course this means that in my code, I had to update the memory addresses that the variables pointed to... which I did. I in fact ran my code MANY times today while at work and added new stuff.... and everything worked GREAT! So I figured all was well.

.......... WRONG! I get home, download the emulator and try my code, and guess what..... for some reason... the memory addresses for everything are DIFFERENT NOW!

So alright then... I reboot and try it several times... same addresses come up as last time. I reboot and retry several times... addresses stay the same. So it's not DMA, since it doesn't change every time.

I was wondering, do you have any idea why this is, or how I can get the addresses to stay constant between 2 or more computers? I don't have a 3rd to try it on or I would. But I want to make sure that this thing will work on everyone's computer.

I never had this problem with epsxe so imagined how surprised I was. The only thing I did different when installing it at HOME was that a direct x dll file I needed was already in my windows/system32 folder (d3dx9_26.dll) so I didn't have to install it into the emulator directory instead. I also had newer ones in the system32 directory (up to d3dx9_32.dll).

I even tried puting all these files in the recycle bin, and putting the d3dx9_26.dll file in the same directory as the emu so it's setup just like at work. Address STILL don't change to the same as the work one, they don't change at all in fact.

DO you have any advice? This emulator is still being updated constantly so if I know what the issue is I MAY be able to get the creator if the program to make an adjustment to the code of the emulator itself for me if it's not a HUGE one or something. Or better yet... I could get around it myself. Which I would prefer to do. :)
Esco.... the name says it all. New Yorikan for life.
User avatar
esco
NULL
 
Posts: 148
Joined: Mon Sep 18, 2006 2:25 am
Location: Florida, a.k.a. the US's version of hell!

Postby L. Spiro » Mon Apr 23, 2007 7:00 pm

.......... WRONG! I get home, download the emulator and try my code, and guess what..... for some reason... the memory addresses for everything are DIFFERENT NOW!

So alright then... I reboot and try it several times... same addresses come up as last time. I reboot and retry several times... addresses stay the same. So it's not DMA, since it doesn't change every time.

Actually this is the exact nature of DMA, and guaranteed your addresses on one computer will be the same for 2 weeks, then suddenly change for no reason, yet always be different on each new computer you use to test.


The addresses can stay the same for days, weeks, and even months.
It simply means your RAM is fragmented similarly each time.
Sometimes it will be the same for 2 weeks, change once, and go back to the way it was for 2 weeks after a single restart (*cough* Doom® 3 *cough*).

No two computers will have the same RAM fragmentation, however a single computer might have a single fragmentation pattern for a long time, depending on what is running and the order in which things are loaded.


Your answer is quite simple. It is basic DMA, and you have to use standard anti-DMA tactics.


This emulator is still being updated constantly

Then be cautious before using it.
Every time he updates you will have to reverify your base pointers and you will have to keep a careful release log explaining which versions are compatible and which aren’t.
And no, the author of the emulator can not help you; DMA is a fundamental design choice that can not be altered once chosen on such a low-level area of the system.
And the fact is, all emulators should be DMA, since every ROM is a different size.
I was really surprised your old emulator wasn’t DMA. In fact it shouldn’t even be possible.


L. Spiro
User avatar
L. Spiro
L. Spiro
 
Posts: 3129
Joined: Mon Jul 17, 2006 10:14 pm
Location: Tokyo, Japan

Postby esco » Tue Apr 24, 2007 2:26 am

Well, alright then, now that I know this I went and looked thru the help file for memhack and learned how to use pointer search (though it seemed like the go to closest button mentioned was NOWHERE to be found, lol)... and I found 4 possible addresses... 1 of which I eliminated on my own since I restarted the emulator and it then said unobtainable in memhack. So alright then, I figured I would just change the addresses that it points to on each one, and see which one has an effect so I know which one is the correct one to use.

But when I changed the address they point to, nothing happens. So maybe I'm finding the wrong ones?

I basically read thru your help file, and it said what I thought I should do... search for a pointer that points to an address NEAR the one I'm searching for (in this case I'll use 1d67bc0 for my example). And I picked the ones that were less than 10000 from the address. But how do I know when I have the right address?

Also I'm assuming that once I have one of these addresses (which should be all I need right), I then have to declare all my variables like this:

example: 7750000 has value 1d67bc0, and I want to declare a variable also for 1d67bca

extern WORD paused = {value at 7750000 + a };

Of course, this is INCORRECT syntax, but that is the basic concept how I get around DMA, right? Since all the addresses are relative to each other from what I've seen. :?:
Esco.... the name says it all. New Yorikan for life.
User avatar
esco
NULL
 
Posts: 148
Joined: Mon Sep 18, 2006 2:25 am
Location: Florida, a.k.a. the US's version of hell!

Postby esco » Tue Apr 24, 2007 3:21 am

Alright... someone here gave me some advice...

He told me to find 1 single static pointer.... it didn't matter which one... and of course just make the rest of the declarations for vars relative to it.

Ex. let's say I choose 7750000 which holds the address 1cd0510.

so I do this

extern LONG base = { "", 0x7750000 };
//assigns subchoice mem address 1cd051a
extern SHORT subchoice = { "", base + 10 };

This of course requires me to convert every address to long and then do some subtraction. Where as if I could just do this DIRECTLY with the memory address in hex format, it would make things quicker.

So how can i declare a variable to return the value in hex format. Using HEX or Void/void/VOID (like it says for value type in the memhack screen), doesn't work. So how do I do it?
Esco.... the name says it all. New Yorikan for life.
User avatar
esco
NULL
 
Posts: 148
Joined: Mon Sep 18, 2006 2:25 am
Location: Florida, a.k.a. the US's version of hell!

Postby L. Spiro » Tue Apr 24, 2007 9:56 am

Ex. let's say I choose 7750000 which holds the address 1cd0510.

so I do this

extern LONG base = { "", 0x7750000 };
//assigns subchoice mem address 1cd051a
extern SHORT subchoice = { "", base + 10 };

No, you do this:

extern struct MYOBJECT {
BYTE bBuffer[0x0A];
SHORT sSubChoice;
} * e_lpObject = { "", 0x7750000 };

e_lpObject->sSubChoice = 3;




This of course requires me to convert every address to long and then do some subtraction. Where as if I could just do this DIRECTLY with the memory address in hex format, it would make things quicker.

So how can i declare a variable to return the value in hex format.

There is no such thing as a value stored in hex format.
Hex is just a way of printing values. The values are already stored in every way possible: binary, octal, decimal, and hexadecimal. the data is all the same.

And using the method above you don’t need to do it at all anyway since you just write the buffer size in hexadecimal.


L. Spiro
User avatar
L. Spiro
L. Spiro
 
Posts: 3129
Joined: Mon Jul 17, 2006 10:14 pm
Location: Tokyo, Japan

Postby esco » Tue Apr 24, 2007 11:00 am

I meant hexadecimal dawg. Not HEX, sorry. :)

Your probably gonna want to slap me with a trout for asking this... but wtf does this all mean? lol

//I know this is declaring a structure//
extern struct MYOBJECT {

//declaring 2 variables... and it looks like the top one is for adding A, but... why is the address it's pointing to just A? How does this add anything at all? And what is this variable supposed to stand for, I can't tell by the// name (buffer)
BYTE bBuffer[0x0A];
SHORT sSubChoice;

//why is this thing multiplying? And what is it? It doesn't look like a var declaration?//
} * e_lpObject = { "", 0x7750000 };


//?????? I have no clue what this does.. why would 3 be assigned to sub choice?//
e_lpObject->sSubChoice = 3;

So ummm.. yeah. I'm just a little lost here. Sorry.Image
Esco.... the name says it all. New Yorikan for life.
User avatar
esco
NULL
 
Posts: 148
Joined: Mon Sep 18, 2006 2:25 am
Location: Florida, a.k.a. the US's version of hell!

Postby L. Spiro » Tue Apr 24, 2007 12:05 pm

I know this is declaring a structure

It is.

declaring 2 variables... and it looks like the top one is for adding A, but... why is the address it's pointing to just A? How does this add anything at all? And what is this variable supposed to stand for, I can't tell by the// name (buffer)

BYTE bBuffer[0x0A]; declares an array of 10 bytes, thereby making sSubChoice 10 bytes from the start of this structure.

It is not pointing to any address. It is an array. You knew that already.


why is this thing multiplying? And what is it? It doesn't look like a var declaration?//

It is not multiplying. This is a declaration line, and in declarations * means pointer.

The easier-to-read way to write this is:

Code: Select all
struct MYOBJECT {
    BYTE bBuffer[0x0A];
    SHORT sSubChoice;
};
extern MYOBJECT * e_lpObject = { "", 0x7750000 };

This is the exact same thing; in my first example we just declare the structure and a variable of that structure type at the same time, in one line of code.



?????? I have no clue what this does.. why would 3 be assigned to sub choice?

It assigns 3 to sSubChoice. Why? To demonstrate how to use sSubChoice.

The point is, don’t declare two external variables. Declare a single external variable as a pointer and use -> to access its members (instead of .)

Code: Select all
e_lpObject->sSubChoice = e_lpObject->sSubChoice + 2;
e_lpObject->sSubChoice -= 34;
SHORT sNewThing = e_lpObject->sSubChoice;



L. Spiro
User avatar
L. Spiro
L. Spiro
 
Posts: 3129
Joined: Mon Jul 17, 2006 10:14 pm
Location: Tokyo, Japan

Postby esco » Tue Apr 24, 2007 2:42 pm

..... k. Other than the structure though for setting up memory addresses to get around the DMA.... what is the point of these other things? Do they help my code run better? :?:

Also since I'm gonna have SO many variables that I'm gonna have to do this for, wouldn't eat be easier to read and take less effort just to use my above idea with longs? Or am I missing something here?

EDIT:

The address for ROOMS is: 1afc780

Code: Select all
struct GAMEDATA {
    BYTE bBuffer[0x10299b4];
    SHORT rooms;
};
extern GAMEDATA * address = { "", 0xad2dcc };

VOID lock ()
{
PrintF("Rooms= %d", address->rooms);
}


When I try this I get an error: Array too large. So I guess that idea is going out the window, unless you have some kind of suggestion? And that is the CLOSEST static address I could find to the area I will be editing.

And when I try my technique (which probably sucks, lol):

Code: Select all
extern LONG address = { "", 0xad2dcc }; //190000
extern SHORT rooms = {"", address+26658688};

VOID lock ()
{

}


I get this error IF I use rooms as a global....

ERROR: Pos: 93 Code emition failed! File: (null)
ERROR: Pos: 93 Unable to set the initialization data for “extern” global “rooms” (error evaluating second initializer). File: (null)

....but if I declare rooms it under lock it works fine. Of course then it's not global and I have to declare it in each function it is used in. Which means of course that I am screwing up AGAIN somehow. [/code]
Esco.... the name says it all. New Yorikan for life.
User avatar
esco
NULL
 
Posts: 148
Joined: Mon Sep 18, 2006 2:25 am
Location: Florida, a.k.a. the US's version of hell!

Postby L. Spiro » Tue Apr 24, 2007 5:01 pm

what is the point of these other things? Do they help my code run better?

Organization and speed. Your code will be faster if it only has to initialize one external variable.


Also since I'm gonna have SO many variables that I'm gonna have to do this for, wouldn't eat be easier to read and take less effort just to use my above idea with longs? Or am I missing something here?

It isn’t easier to make twice as many external variables for each one than to make a single structure that is easy to edit for each.
It is correct to make a structure to make this type of data structure in the game.




When I try this I get an error: Array too large. So I guess that idea is going out the window, unless you have some kind of suggestion? And that is the CLOSEST static address I could find to the area I will be editing.

And when I try my technique (which probably sucks, lol):



I get this error IF I use rooms as a global....

ERROR: Pos: 93 Code emition failed! File: (null)
ERROR: Pos: 93 Unable to set the initialization data for “extern” global “rooms” (error evaluating second initializer). File: (null)

....but if I declare rooms it under lock it works fine. Of course then it's not global and I have to declare it in each function it is used in. Which means of course that I am screwing up AGAIN somehow.


There is no such thing as a structure that large (0x10299B4 bytes).
You are taking a pointer to the ROM base and using that as if it was a huge structure.

The preimise is technically workable, except that such large number, when used this way, cause other problems (as you noticed).
To keep stack sizes sane, I force a maximum limit on the length of pre-defined arrays.
This is standard in C as well.

But you aren’t actually using a pointer to the rooms.
Your pointer points to the start of the ROM image (hopefully, since that is what you should be using on emulated games), and all the ROM-static data in the game is an offset from there, though usually a very huge offset, not actyally part of a structure.

In this situation, you need to use your second example.
Create a single global at address 0xAD2DCC as type DWORD.
Then for each static location inside the ROM based off this pointer, make a new local external variable using that value + the offset.

And yes, the second external has to be local. It can’t possibly work if both are global. Global = precalculated when compiled. And obviously the address of an external value can't be precalculated if it depends on another value that could change at any time.

When externals are declared as local, the address is recalculated each time the function is called, and only then, so it is not precalculated.

The same behavior would appear in C/C++ if C/C++ had external variables.


L. Spiro
User avatar
L. Spiro
L. Spiro
 
Posts: 3129
Joined: Mon Jul 17, 2006 10:14 pm
Location: Tokyo, Japan

PreviousNext

Return to General Related Discussions

Who is online

Users browsing this forum: No registered users and 0 guests