Fire EmBot: Already made?

Hi everyone! I want to create a bot capable of playing FE7 automatically like a person would: reading the information from the screen and introducing the inputs on the emulator to beat every level.

I searched the internet and looked at some topics on the blog, but I couldn’t find anything related, so the first question i have is there already a topic or project like this that I can consult?

If the answer is “no” then I have some ideas on how to get started, and the main problem I want to tackle is how to get the map information. I thought on two alternatives: accessing the in-play map file each turn to read the terrain cost, accessibility, player/enemy positioning, events (like “seize” options, buy from stores, etc.) of each file if possible; or gathering the same information via screenshots (which I think will be way more difficult). I have no idea about reading game files or how can I extract the mentioned information, so I’d be very grateful if you could point me to some topic I can consult for documentation on file manipulation.

Also, if you have any suggestion on how can I gather the map information on each turn, that would be super useful to me. Thanks to everyone in advance!

The closest thing to that that I know is this AFK Romhack AI v2.1 - seize, villages, and more
But it’s essentially just giving control of the blue units to the AI while making that AI slightly smarter than red/green units and adding things like visiting villages.

If you open a game in FEbuilder’s debugger by pressing F5, you can see a lot of RAM data that is documented there which you can make your program read during play.

2 Likes

I want to try to run the bot’s script outside the game itself, but I’ll definitely look at the AFK Romhack you linked when I reach that stage of development.

As for the RAM data of FEbuilder, I think I found an interesting MapID value but still don’t know how to use it or how can I read the map information using an external script.

I’d also recommend checking out @StanH’s GBA Fire Emblem for Screen Readers (GitHub). It’s not for the same purpose as what you’re describing, but it demonstrates a method for reading various information from the game’s memory using Lua.

It’s currently hard-coded to support FE8U, but you can reference various community resources such as FEBuilder, the decompilations of the GBAFE games, and other documentation threads to locate important addresses for the other games/versions.

Good luck! This seems like a cool project!

3 Likes

I believe the procs lua script StanH made also writes to ram whenever the game reaches a certain line of code as a bugfix, so lua scripts could also write to ram as player inputs or to tell the game what to do. Vba-rr supports lua scripting iirc.

Fe8u has far more documentation than fe7, so be prepared to do a lot of digging in no$gba yourself if you must make this for fe7 and not fe8. Good luck

2 Likes

This is truly an interesting idea. Technically speaking, as long as you can dump the entire ROM file and also instantly refresh the data in IWRAM and EWRAM, you can obtain the complete information at any given moment. The subsequent work involves analyzing the data, making decisions, and guiding button inputs. Theoretically, if these tasks are handed over to a modern CPU, I believe it wouldn’t even cause any lag.

1 Like

Thank you all for your suggestions! :blush:

Since I have no idea of Lua, this is the approach I’m taking :point_up:.

So far I’ve discovered a few things:

  1. The ROM stores a pointer list to every level map at address 0xC9C9C8. Browsing through this list, we can see a pointer to each map (and other things I haven’t looked into yet) in a format like 0x8######. I’ve got this information by looking at FEBuilder, as you can see on the box next to the “Pointer” button on Advanced Editors → MAP PLIST Editor (I couldn’t upload an image, sorry :sweat_smile:).

  2. It seems that 0x08000000 is a common ROM base for GBA games, so substracting this base to the map pointers mentioned before gives us the map tileset information! For example, the first map for Lyn’s story is pointed at 0x0836AF00, therefore, the information of this map is located at 0x36AF00, which we can verify by looking at the map editor.

  3. Reading the information on that memory direction I’d found out that the 6th and 7th bytes on the returning string gives us information about the size of the map! In this case the string goes 0F 0A, which is equivalent to a 15x10 map. Once again, this can be seen on the map editor, and I’ve tested this for other maps as well and it seems to be correct!

This three conclusions are probably right for the other GBA games as well, but I haven’t tried it.

I’ve yet to figure out a way to read the properties of every individual tile & then try to read the IWRAM and EWRAM information at any given time to see the position of every unit (I have no idea how to do the latter hahaha).

Thanks again for all your comments!

Your first point is referring to the PTABLE, which is an indexed table of various things retaining to map data. Each entry in the PTABLE can be a pointer to one of the following:

  • Tileset Object
  • Tileset Palette
  • Tileset Config
  • Tileset Tile Animations 1 (Actual animation)
  • Tileset Tile Animations 2 (Palette shifting used in ch18)
  • Map Data
  • Tile Changes
  • Event Data

It’s probably useful to know that most of the time, only the application of the config to the object matters for tilesets, and hence then the map data/tile changes and events
So around 25-30% of the PTABLE is useless for a bot.

You can grab info about specific tiles by using the relevant maps.

############
MAPS:
Map size: 202D200 (FE6) 202E3D8 (FE7) 202E4D4 (FE8) 202E4D0 (FE8J): Has length and height as halfwords. Note: These are 1-aligned, not 0-aligned.

There's a table of pointers immediately afterwards:

FE6		FE7		FE8		Description
202D204 202E3DC	202E4D8	Unit map (allegiance byte)
202D208 202E3E0	202E4DC	Terrain map (tile id)
202D20C 202E3E4	202E4E0	Movement map (movement cost to move to a specific tile when selecting a character; 0xFF else)
202D210 202E3E8	202E4E4	Range map (nonzero if square can be reached/targeted)
202D214 202E3EC	202E4E8	Fog (nonzero if square can be seen)
202D218 202E3F0	202E4EC	Unknown (code at 18592 in FE8 suggests this is a bitfield, which isn't spectacularly helpful)
202D21C 202E3F4	202E4F0	Backup movement map (seems to be used when exiting the moveable tile zone and entering on another tile to calculate the new path, also used for enemy movement?) (also filled in with squares covered by magic seals prior to displaying red squares when selecting a unit in FE7) (AI stores potential target (str + weapon might)/2 for calcs)
202D220 202E3F8	202E4F4	Middle of the unit map? Seems unused
202D224 202E3FC	202E4F8	Middle of the unit map? Seems unused

Quote from Teq Doq
https://www.dropbox.com/scl/fo/otz4z799wu08jb5or937h/ANJpaKaLANAJnCs1SK9j8F4/Tequila/Teq%20Doq?e=1&preview=Better+Notes.txt&rlkey=1yywzhb79g9qiax0rdpawj925&dl=0

More recent documentation for the same thing:
https://github.com/FireEmblemUniverse/fireemblem8u/blob/1193deefdd322c261df42d561e21002957ccc08d/include/bmmap.h#L31

Addresses of decomp names for things:
https://fireemblemuniverse.github.io/fireemblem8u/symbols.txt

1 Like