diff options
Diffstat (limited to 'spec.md')
| -rw-r--r-- | spec.md | 51 |
1 files changed, 32 insertions, 19 deletions
@@ -19,21 +19,9 @@ Packets are made up of four parts: `[key] [length exponent] [payload length] [pa Because a payload could be as small as a few bytes, or much larger than a 16-bit number could convey, a _**length exponent**_ is used to define how many bytes make up the _**payload length**_. Whereas the _**payload length**_ defines how many bytes are in the _**payload**_ itself.
-### Examples
-Below is the hexadecimal representation of a package, with some 2-byte key, and a payload that is 5 bytes wide:
-```
- A8 2F 01 05 00 11 22 33 44
-└─key─┘ └──┘ └──┘ └───payload────┘
-```
-Here is another example of a different key, with a payload that is 260 bytes wide:
-```
- A8 2F 02 01 04 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F
-└─key─┘ └──┘ └─────┘ 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F
- ......
- F0 F1 F2 F3 F4 F5 F6 F7 F8 F9 FA FB FC FD FE FF
- 00 01 02 03 04 ┌────payload────────────────────┘
- └───────────────┘
-```
+The **length exponent** or just **exponent** for short, is named this way given that the number of bytes that make up the _**payload length**_, is determined based on (256^exponent - 1).
+
+Packet examples can be found later in this document.
## Key Definitions
Packets will often have an intended size depending on the key, however, they will still follow the packet format. Some keys will have a list of type specifiers with defined ID values.
@@ -44,7 +32,7 @@ _Reminder that every key is optional, and can appear across multiple packets as ```
Key | Payload Size | Name | Description
-0001 | 1 + p byte | ConsoleType | The console this TAS is made for.
+0001 | 1 + p bytes | ConsoleType | The console this TAS is made for. p = 0 for all except custom types.
-> 01 = NES
-> 02 = SNES
-> 03 = N64
@@ -54,7 +42,7 @@ Key | Payload Size | Name | Description -> 07 = GBA
-> 08 = Genesis
-> 09 = A2600 (Atari 2600)
- -> FF = Custom (p = custom name string)
+ -> FF = Custom (p = custom name string, no string length bytes needed)
0002 | 1 byte | ConsoleRegion | Console region required to play this TAS.
-> 01 = NTSC
@@ -75,7 +63,7 @@ Key | Payload Size | Name | Description 000D | 2 bytes | BlankFrames | Signed 16-bit number of blank frames to prepend to the TAS inputs (positive number), or frames to ignore from the start of the TAS (negative number).
000E | 1 byte | Verified | Whether or not this TAS has been verified by someone. (boolean, value of either 00 or 01)
-000F | 1 + v + k + n + p bytes | MemoryInit | Initialization of named memory space. (1 byte type, v = 1 byte exponent for k, k = length of n, n = name string, p = memory payload)
+000F | 1 + 1 + v + k + n + p bytes | MemoryInit | Initialization of named memory space. First byte is the kind of initialization. Second byte is whether or not this is required for verifications (0 = optional, 1 = required). Then the name of the space. And an optional custom payload. (1 byte type, 1 byte verification requirement, v = 1 byte exponent for k, k = length of n, n = name string, p = memory payload)
-> 01 = No intialization required (p = 0)
-> 02 = All 0x00 (p = 0)
-> 03 = All 0xFF (p = 0)
@@ -104,6 +92,12 @@ Key | Payload Size | Name | Description -> xx 04 01 = GC Standard
-> xx 04 02 = GC Keyboard
+ -> xx 05 01 = GB Gamepad
+
+ -> xx 06 01 = GBC Gamepad
+
+ -> xx 07 01 = GBA(SP) Gamepad
+
-> xx 08 01 = Genesis 3-Button
-> xx 08 02 = Genesis 6-Button
@@ -121,7 +115,7 @@ Key | Payload Size | Name | Description 0101 | 1 byte | LatchFilter | Latch Filter time span. (value multiplied by 0.1ms; inclusive range of 0.0ms to 25.5ms)
0102 | 1 byte | ClockFilter | Clock Filter time span. (value multiplied by 0.25us; inclusive range of 0.0us to 63.75us)
0103 | 1 byte | Overread | The data value to use when overread clock pulses occur. (active-low: 0 = HIGH, 1 = LOW)
-0105 | 6 or 8 bytes | GameGenieCode | (string) 6 or 8 character game genie code.
+0104 | 6 or 8 bytes | GameGenieCode | (string) 6 or 8 character game genie code.
```
#### SNES Keys:
@@ -166,6 +160,7 @@ FE01 | 1 + n bytes | InputChunks | Port number (1-indexed) + a variable n Refer to transitions to know if any controller types change mid-playback.
These packets, and the input chunks therein, are in sequential order!
Therefore, any following input packets are appended to the inputs contained in this one.
+ Input values are usually in native format (usually active-low), refer to `inputmaps.txt` for details.
FE02 | 4 + 1 + n bytes | Transition | Defines a transition at a specific point in the TAS. First 4 bytes is the frame/index number (0-indexed) based on all inputs contained in all FE01 packets. Then 1 byte specifying the transition type. Followed by a variable number of bytes if applicable.
-> 01 = "Soft" Reset (n = 0)
@@ -183,6 +178,24 @@ FE04 | 4 + 1 + n bytes | MovieTransition | Defines a transition based on the ori ## Controller Input Maps
Each controller from each console has defined data needed for each frame (or frame equivalent), which is stored in a specific number of bytes. This data is what is stored in InputChunks packets. These maps are designed to match the real hardware as much as possible, to make decoding easier. If you need to write an emulator/movie dump script, be aware that emulators may format these inputs in a different order. Refer to the `inputmaps.txt` file for specific details.
+## Examples
+These examples should cover most use cases of this file format. If something is still unclear, feel free to ask questions on Discord. All examples use hexadecimal values unless otherwise specified.
+
+A madeup packet, with some 2-byte key, and a payload that is 5 bytes wide:
+```
+ A8 2F 01 05 00 11 22 33 44
+└─key─┘ └──┘ └──┘ └───payload────┘
+```
+Another made up packet, with a payload that is 260 bytes wide:
+```
+ A8 2F 02 01 04 00 01 02 03 04 05 06 07 08 09 0A 0B 0C 0D 0E 0F
+└─key─┘ └──┘ └─────┘ 10 11 12 13 14 15 16 17 18 19 1A 1B 1C 1D 1E 1F
+ ......
+ F0 F1 F2 F3 F4 F5 F6 F7 F8 F9 FA FB FC FD FE FF
+ 00 01 02 03 04 ┌────payload────────────────────┘
+ └───────────────┘
+```
+
## Format Goals/Reasoning
The primary goal of this format is to provided a single comprehensive, replay-device-agnostic, TAS dump format, usable for any console. Additional goals include: no intermediate formats, forward-compatibility, high extensibility, and the ability to easily generate using lua scripting available in emulators. Consideration was also given to how usable the format would be to the software that interacts with replay devices (e.g. methods of ingestion/parsing, and the ease of doing so given various languages).
|
