133 lines
3.9 KiB
C
133 lines
3.9 KiB
C
/* ************************************************************************** */
|
|
/* _____ _ */
|
|
/* libg1m/format/main.h |_ _|__ _ _| |__ ___ _ _ */
|
|
/* | Project: libg1m | |/ _ \| | | | '_ \ / _ \ | | | */
|
|
/* | | (_) | |_| | | | | __/ |_| | */
|
|
/* By: thomas <thomas@touhey.fr> |_|\___/ \__,_|_| |_|\___|\__, |.fr */
|
|
/* Last updated: 2016/11/02 14:15:46 |___/ */
|
|
/* */
|
|
/* ************************************************************************** */
|
|
#ifndef LIBG1M_FORMAT_H
|
|
# define LIBG1M_FORMAT_H
|
|
# include <stdint.h>
|
|
# pragma pack(1)
|
|
|
|
/* Welcome on this new episode of Monster Circus! Today we'll present to you
|
|
* something that you might not be able to forget: the G1M format.
|
|
*
|
|
* This format is used by CASIO with its calculator for storing things
|
|
* like add-ins (compiled programs), MCS (main memory saves), and others.
|
|
* In fact, there is no name for the general format, only names for the
|
|
* "subformats" based on this one.
|
|
*
|
|
* It all starts with a header, called Standard Header by Simon Lothar.
|
|
* This Standard Header contains the total filesize, the G1M type (add-in,
|
|
* MCS, e-acts), some data that will be useful for the MCS type, and some
|
|
* magic and control bytes.
|
|
*
|
|
* For some reason, this StandardHeader is INVERTED on every file it's on,
|
|
* you will have to apply a NOT operation on its bytes for it to make sense.
|
|
*
|
|
* Keep in mind that, everywhere in the header, multi-bytes integers
|
|
* are BIG ENDIAN.
|
|
*
|
|
* The LSB is the Least Significant Byte: once adapted to the host endianness,
|
|
* it can simply be obtained by bitwise-AND-ing with 0xff. */
|
|
|
|
struct standard_header {
|
|
/* the file identifier - see below */
|
|
uint8_t main_id[8];
|
|
|
|
/* our filetype! */
|
|
uint8_t type;
|
|
|
|
/* magic numbers, not always the same:
|
|
* - for fx-CG formats: {0x00, 0x01, 0x00, 0x01, 0x00}
|
|
* - otherwise: {0x00, 0x10, 0x00, 0x10, 0x00} */
|
|
uint8_t magic[5];
|
|
|
|
/* first control byte: filesize LSB + 0x41 */
|
|
uint8_t control;
|
|
|
|
/* said to be 0x01, but doesn't need to */
|
|
uint8_t align_one;
|
|
|
|
/* total filesize */
|
|
uint32_t filesize;
|
|
|
|
/* second control byte: filesize LSB + 0xb8 */
|
|
uint8_t control2;
|
|
|
|
/* alignment */
|
|
uint8_t align[8];
|
|
|
|
/* is obfuscated - useful for G3P */
|
|
uint8_t obfuscated;
|
|
|
|
/* number of objects contained (useful for MCS filetype) */
|
|
uint16_t number;
|
|
};
|
|
|
|
/* At the beginning, we thought "USBPower" was some magic sequence we would
|
|
* systematically find in the "main_id" field. But a counter example came:
|
|
* the G3L, where the main ID was "Ly755 ".
|
|
*
|
|
* So here are the known main IDs: */
|
|
|
|
enum g1m_main_id {
|
|
/* "USBPower": the most common one */
|
|
g1m_mid_usbpower,
|
|
|
|
/* "Ly755 ": fx-CG specific types */
|
|
g1m_mid_ly755,
|
|
};
|
|
|
|
/* Each main ID have their own types. Here are the USBPower types: */
|
|
|
|
enum g1m_usbpower_type {
|
|
/* fx language file */
|
|
g1m_usbpower_type_lang = 0x12,
|
|
|
|
/* fx-CG add-in */
|
|
g1m_usbpower_type_addin_cg = 0x2c,
|
|
|
|
/* mcs (main memory) save */
|
|
g1m_usbpower_type_mcs = 0x31,
|
|
|
|
/* e-activity (document) */
|
|
g1m_usbpower_type_eact = 0x49,
|
|
|
|
/* g1r equivalent */
|
|
g1m_usbpower_type_g2r = 0x62,
|
|
|
|
/* g3m (fx-CG program) */
|
|
g1m_usbpower_type_g3m = 0x75,
|
|
|
|
/* g3p (fx-CG picture) */
|
|
g1m_usbpower_type_g3p = 0x7d,
|
|
|
|
/* add-in (compiled program) */
|
|
g1m_usbpower_type_addin = 0xf3,
|
|
};
|
|
|
|
/* And here are Ly755 types: */
|
|
|
|
enum g1m_ly755_type {
|
|
/* language file */
|
|
g1m_ly755_type_lang = 0x2c
|
|
};
|
|
|
|
# pragma pack()
|
|
|
|
/* After the Standard Header is read and the G1M type is read, we have parts,
|
|
* each with their own subheaders and their own subtilities.
|
|
*
|
|
* Where do you want to start? Pick your poison. */
|
|
|
|
# include <libg1m/format/addin.h>
|
|
# include <libg1m/format/eact.h>
|
|
# include <libg1m/format/mcs.h>
|
|
# include <libg1m/format/picture.h>
|
|
# include <libg1m/format/lang.h>
|
|
#endif /* LIBG1M_FORMAT_H */
|