gbadev.org forum archive

This is a read-only mirror of the content originally found on forum.gbadev.org (now offline), salvaged from Wayback machine copies. A new forum can be found here.

Beginners > About GBA & Savegames & SuperCard SD

#177635 - sverx - Mon Oct 08, 2012 3:47 pm

I still haven't started coding a single line and I'm here already looking for help...

I got a GBA and a SuperCard SD. To test that everything is working as expected I downloaded genecyst's HolyHell and gauauu's Anguna. They both work, but I have problems with save/restore game.
I can't save on .sav file directly when in-game, but I can use the so called 'quick power cycle' trick to save (power off and on again very quickly, so selecting a .sav file you can save the SRAM contents into it).
After that, when I fire again HolyHell it works... the highscore and settings are retained. No luck with Anguna, instead. It always starts again from beginning.

It seems to me there's something I miss. Should I 'patch' the .gba files somehow before putting them into the SD card? Or...?
_________________
libXM7|NDS programming tutorial (Italiano)|Waimanu DS / GBA|A DS Homebrewer's Diary

#177636 - gauauu - Tue Oct 09, 2012 3:12 pm

Hmm, no clue. I assume you tried the L+R+A+Select trick that's supposed to do something on that card as far as saving?

On anguna, I'm just reading/writing data at 0x0E000000 which worked on the 2 different carts that I tested it on. I don't know what the supercard does differently.

#177637 - sverx - Wed Oct 10, 2012 9:08 am

SuperCard loads the .sav file into SRAM before starting the game, and it saves SRAM to .sav file if I quickly turn off/on the GBA and select the anguna .sav file (the so called QPC method).

Is there some particular string I can search in the .sav file to see if it's a valid Anguna save file? Or a particular pattern...

Thanks!
_________________
libXM7|NDS programming tutorial (Italiano)|Waimanu DS / GBA|A DS Homebrewer's Diary

#177639 - gauauu - Mon Oct 15, 2012 3:25 pm

Sorry I took so long to reply, I've been checking the forum, but didn't realize that I was no longer logged in, so I wasn't getting the orange "unread threads" icon :-/

Anyway, there's not a simple way to check like a magic string, but here's my save format if you want to try to compare:

Code:

typedef struct
{
   //positional info
   int roomX;
   int roomY;
   LevelData * room;

   int lastGoodRoomX;
   int lastGoodRoomY;
   LevelData * lastGoodRoom;

   //gameState info
   int gameState[GAME_STATE_SLOTS];
   int toggleState[TOGGLE_SLOTS];
   u32 minimapState[MINIMAP_ARRAY_SIZE];

   //enemy database
   EnemyType * enemyDatabase[ENEMY_DATABASE_SIZE];

   //mainChar info
   int hp;
   int hpMax;
   int mcPower;
   int mcArmor;
   int inventory[NUM_ITEMS];

   int mcGold;
   
   int checksum;
   LevelData * room1;  //for verifying rom status
   
} SaveGameData;


Yes, there are pointers saved in there. Which means it necessarily doesn't work across different builds. I know this is bad, but I was lazy :)

Oh, and I guess you need the values for the array lengths:
Code:

#define GAME_STATE_SLOTS 256
#define TOGGLE_SLOTS 32

#define MINIMAP_ARRAY_SIZE 35
#define ENEMY_DATABASE_SIZE 32
#define NUM_ITEMS 21



Anyway, the easiest way to check would probably be the hp, power, armor, gold values. Starting HP/maxHP should be 24, so you could look for that.

The last pointer in the struct (pointer to room 1) should be the same with each save, but I don't know what it should be in the build you are using.

The checksum is based on all the other save data combined, so it won't be useful to you.

#177640 - sverx - Tue Oct 16, 2012 12:41 pm

Thanks! I'll try to see if I can locate that HP/MaxHP (that should be 00 00 00 18 00 00 00 18, so kind of magic string ;) )

edit: is it the checksum that tells you if SRAM contains a valid save, when starting?
_________________
libXM7|NDS programming tutorial (Italiano)|Waimanu DS / GBA|A DS Homebrewer's Diary

#177641 - gauauu - Tue Oct 16, 2012 3:20 pm

sverx wrote:
Thanks! I'll try to see if I can locate that HP/MaxHP (that should be 00 00 00 18 00 00 00 18, so kind of magic string


Yup, that should work.

Quote:

edit: is it the checksum that tells you if SRAM contains a valid save, when starting?


Yeah, if you try to resume, it will load up the save state, and compare the checksum. If it doesn't match up, it will start at the beginning. If you need the checksum logic, let me know.

#177643 - sverx - Thu Oct 18, 2012 8:57 am

I found the "18 00 00 00 18 00 00 00" 'magic string' (I was wrong... it's little-endian, so the LSB is on the left) in the sav file, and it seems to me that the problem is in the 1st byte, because I guess the value of 'roomX' variable wasn't zero, but in the sav file it is.
So it might be a problem originating from the QPC trick... maybe when I turn down the GBA it writes ZERO in the first SRAM byte (or word) (why? don't know!).
I'll do some more testing btw.

Is there a way to have roomX to be exactly 0? Leaning to a wall on the left of the room, for instance? So that I can try if it works that way...
_________________
libXM7|NDS programming tutorial (Italiano)|Waimanu DS / GBA|A DS Homebrewer's Diary

#177644 - gauauu - Thu Oct 18, 2012 2:55 pm

It's possible, but it'd be hard to find the exact spot. It would only work on rooms that have a passage leading to the left -- if you put the left edge of your sprite exactly on the left edge of the screen, it should be 0.

#177645 - sverx - Wed Oct 24, 2012 12:25 pm

No luck, I didn't succeed.
Anyway I finally understood how to use the "real time save" feature of the card: I need to patch the gba rom file with a tool provided by the SuperCard vendor. So it copies the SRAM content into a .sav file on the SD card while you're playing the game, when you press the requested key combination. Problem solved. So bad the QPC system thrashes the 1st byte(s?), I wouldn't have to patch anything...

Thanks :)
_________________
libXM7|NDS programming tutorial (Italiano)|Waimanu DS / GBA|A DS Homebrewer's Diary