146 lines
4.5 KiB
C
146 lines
4.5 KiB
C
/* *****************************************************************************
|
|
* libg1m/format/std/picture.h -- the picture formats description.
|
|
* Copyright (C) 2017 Thomas "Cakeisalie5" Touhey <thomas@touhey.fr>
|
|
*
|
|
* This file is part of libg1m.
|
|
* libg1m is free software; you can redistribute it and/or modify it
|
|
* under the terms of the GNU Lesser General Public License as published by
|
|
* the Free Software Foundation; either version 3.0 of the License,
|
|
* or (at your option) any later version.
|
|
*
|
|
* libg1m is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.
|
|
* See the GNU Lesser General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU Lesser General Public License
|
|
* along with libg1m; if not, see <http://www.gnu.org/licenses/>.
|
|
* ************************************************************************** */
|
|
#ifndef LIBG1M_FORMAT_STD_PICTURE_H
|
|
# define LIBG1M_FORMAT_STD_PICTURE_H
|
|
# include <stdint.h>
|
|
# pragma pack(1)
|
|
|
|
/* ************************************************************************** */
|
|
/* G3P: pictures for Prizm */
|
|
/* ************************************************************************** */
|
|
/* G3P are pictures for fx-CG. They start with a Standard Header, and
|
|
* a Standard Picture Header.
|
|
*
|
|
* This mysteries over this format have been unraveled by many, but I'm using
|
|
* Simon Lothar's documentation and Kerm Martian's articles.
|
|
*
|
|
* Prizm pictures (G3P) support several image depths (encodings): */
|
|
|
|
# define g3p_color_4bit 0x03
|
|
# define g3p_color_16bit 0x10
|
|
|
|
/* After the standard headers, comes the specific header: */
|
|
|
|
struct g3p_subheader {
|
|
/* magic sequence? is: 0x00, 0x01, 0x00, 0x00 */
|
|
uint8_t magic[4];
|
|
|
|
/* size of the image data + footer */
|
|
uint32_t df_size;
|
|
|
|
/* w0t */
|
|
uint8_t _unknown0[2];
|
|
|
|
/* width */
|
|
uint16_t width;
|
|
|
|
/* height */
|
|
uint16_t height;
|
|
|
|
/* color depth - see `g3p_colorsize` */
|
|
uint16_t color_depth;
|
|
|
|
/* undocumented, again */
|
|
uint8_t _unknown1[4];
|
|
|
|
/* length of the image data + 6
|
|
* the 6 bytes are:
|
|
* - the 16-bit generator ID at the beginning;
|
|
* - the 32-bit checksum at the end of the data. */
|
|
uint32_t data_size;
|
|
|
|
/* Generator ID */
|
|
uint16_t generator_id;
|
|
};
|
|
|
|
/* The generator ID is a 16-bit ID giving information about the picture
|
|
* generator. The known IDs are the following: */
|
|
|
|
# define g3p_id_casio 0x3C1B
|
|
# define g3p_id_unknown0 0x388D
|
|
# define g3p_id_unknown1 0x789C
|
|
# define g3p_id_unknown2 0x3E93
|
|
|
|
/* Then we have the deflated image data, which is `data_size - 6` sized
|
|
* (see the `data_size` comment above for more explanation).
|
|
*
|
|
* Before inflating, you should check if the image is obfuscated (Simon Lothar
|
|
* says 'encrypted', I suppose that's more polite). It is if:
|
|
*
|
|
* (std.obfuscated + 8) & 0xFF != (std.filesize & 0xff00) >> 8
|
|
*
|
|
* If it is, then in order to de-obfuscate, you should do the following
|
|
* operation:
|
|
*
|
|
* byte = ~((byte << 5) | (byte >> 3)) & 0xFF;
|
|
*
|
|
* Then you can inflate.
|
|
* Once this is done, you can get the next four bytes, also considered as
|
|
* part of the data: the 32-bit adler32 checksum. It is a checksum over the
|
|
* raw, uncompressed data (and is appended to it before deflating/obfuscating).
|
|
*
|
|
* TODO: footers */
|
|
/* ************************************************************************** */
|
|
/* C2P: Images for Classpads */
|
|
/* ************************************************************************** */
|
|
/* C2P are pictures for CASIO Classpad calculators (fx-CP*). They start with
|
|
* a Standard Header, followed by a Standard Picture Header.
|
|
*
|
|
* Then comes the specific subheader: */
|
|
|
|
struct c2p_subheader {
|
|
/* "0100" */
|
|
uint8_t magic[4];
|
|
|
|
/* footer offset? `filesize - 0x254` */
|
|
uint32_t footer_offset;
|
|
|
|
/* unknown */
|
|
uint16_t unknown2;
|
|
|
|
/* width (max for screen: 0x136 */
|
|
uint16_t width;
|
|
|
|
/* height (max for screen: 0x191) */
|
|
uint16_t height;
|
|
|
|
/* undocumented, again */
|
|
uint8_t undocumented2[18];
|
|
|
|
/* filesize - 0x258 */
|
|
uint32_t unknown_size3;
|
|
};
|
|
|
|
/* Then there is the zlib header with default compression.
|
|
* The pixels format is R5G6B5.
|
|
*
|
|
* After the image, there is a footer, which is mainly undocumented, but
|
|
* here is what we've got: */
|
|
|
|
struct c2p_footer {
|
|
/* "0100", again */
|
|
uint8_t magic[4];
|
|
|
|
/* and some undocumented stuff */
|
|
uint8_t undocumented[0xE4];
|
|
};
|
|
|
|
# pragma pack()
|
|
#endif /* LIBG1M_FORMAT_STD_PICTURE_H */
|