Secret Agent Level Format
The map file contains all the levels for the game. Each episode has its own map file called SAMx03.GFX where x is the episode number (1-3). The entire map file is encrypted with Secret Agent encryption, with the encryption key resetting to the beginning every 42 bytes. The decryption key is also truncated to 42 bytes in length, including the terminating null, so the last byte used for actual decoding (before the key reset) should be 0x00.
The file consists of a number of levels, one after the other. Each level is fixed as 2016 bytes in length.
Each 2016-byte level is made up of 48 rows of 42 bytes. The first row contains a decimal number which controls the background tile used in the empty spaces of the map. It is padded with spaces up to 40-bytes in length, with a CRLF (0x0D 0x0A) making up the last two bytes. Effectively the format is a text file with MS-DOS line endings, and using full 8-bit characters.
If the first character in each line/row is an asterisk ("*") then that row is overlaid on top of the previous one. This is used to place point items in front of other elements such as furniture.
The first row in the map contains a decimal number which controls the background tile used in the level. How this maps to a tile is currently unknown, but there are about 15 possible values so the mapping can be hard coded. Some map codes represent 1, 2 or 3 tiles past the default background tile (used to cast shadows from lights) so if these are in use the possible background tiles are even smaller.
The second row in the map is never displayed and contains control values, as follows:
|0||Unknown, often set to 0xC3 or 0xE5.|
|1||Background overlay. This is a standard map code (the same as used in the rest of the map) however this tile is drawn over the top of the background tile, and this combined image is then used as the default background. So for example, if the first row in the map contains the number for red bricks, and the second character in the second row contains the character "S" used for ceiling lights, then anywhere in the level where there is no tile (map code 0x20) the game will draw red bricks with a ceiling light on them.|
|2||Unknown, often set to 0xC3 or 0xE5.|
|3||Unknown, but something to do with background tile offsets. Often set to 0x33.|
|4||Tile offset for map code 0x35. Normally set to 0x35.|
|5||Tile offset for map code 0x36. Normally set to 0x36.|
|6||Tile offset for map code 0x37. Normally set to 0x37.|
|7-40||Unused? Often set to 0x32 or 0x20. Maybe these affect other map codes like 0x38+?|
|41-42||0x0D, 0x0A (CRLF) per normal line endings.|
Mapping codes to images
Like Crystal Caves, there is no algorithm to map images to tiles and this must be done with a list. Furthermore, the overhead map uses a different set of tile mappings to the rest of the level. The map files themselves do not store which mapping is used, so it is up to the programmer to ensure the first level in the .gfx file uses the world-level mappings, while the rest of the levels use the normal-level mappings.