Nugget
Bare-metal libraries and examples for the original PlayStation
Loading...
Searching...
No Matches
bsdec.h
Go to the documentation of this file.
1/*
2
3MIT License
4
5Copyright (c) 2026 PCSX-Redux authors
6
7Permission is hereby granted, free of charge, to any person obtaining a copy
8of this software and associated documentation files (the "Software"), to deal
9in the Software without restriction, including without limitation the rights
10to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
11copies of the Software, and to permit persons to whom the Software is
12furnished to do so, subject to the following conditions:
13
14The above copyright notice and this permission notice shall be included in all
15copies or substantial portions of the Software.
16
17THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
18IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
19FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
20AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
21LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
22OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
23SOFTWARE.
24
25*/
26
27#pragma once
28
29/*
30 * A BS frame decoder. Takes the compressed frame a .STR video sector chain
31 * carries and produces the run-level halfwords the MDEC wants, which the caller
32 * then DMAs to MDEC0. Plain C, no dependencies beyond stdint, no allocation, no
33 * hardware access - it is pure bitstream work, so it builds and runs on a host
34 * as well as on the console.
35 *
36 * BS is Sony's own STR video format, described in FileFormat47 pp.1-20..1-21
37 * with the code book at pp.29-31. Three things about it that its documentation
38 * does not make easy, all measured against retail discs:
39 *
40 * - Versions 1 and 2 carry a raw 10-bit DC per block. ONLY version 3
41 * delta-codes it. Sony's own DecDCTvlc tests `type == 2` and sends version 1
42 * down the delta path, where it decodes 149 of 4416 halfwords and then fills
43 * the rest with end-of-block markers - while returning success. All three
44 * versions ship: Suikoden II's _KONAMIC.STR is v1, Castlevania SOTN's
45 * LOGO15XA.STR is v3, and everything else measured is v2.
46 *
47 * - Word 0 of the header is not a magic number, it is the MDEC(1) decode
48 * command, ready to write to MDEC0 before the DMA. mdecCommand below hands it
49 * back rather than making the caller rebuild it.
50 *
51 * - The header's length counts the DMA padding that the bitstream does not
52 * carry, because it describes what DMA0 will receive rather than what was
53 * encoded. bsdecRlHalfwords() returns that padded count, which is the buffer
54 * size to allocate; the decoder fills the tail with 0xfe00 itself.
55 *
56 * Bit order: codes are MSB-first inside little-endian halfwords. Sony's "coded
57 * bit sequences are ordered starting with low-order bits" is about the byte
58 * order, not the bits inside a code, and reading it the other way gives a
59 * well-formed stream that decodes to garbage.
60 */
61
62#include <stdint.h>
63
66 /* Refusals. Nothing is written to out. */
67 BSDEC_SHORT, /* fewer than 8 bytes, so not even a header */
68 BSDEC_NOT_BS, /* word 0 is not the MDEC decode command */
69 BSDEC_BAD_VERSION, /* version field outside 1..3 */
70 BSDEC_OUTPUT_TOO_SMALL, /* out holds fewer than bsdecRlHalfwords() entries */
71 /* Malformed bitstreams. out still holds a complete, DMA-able frame. */
72 BSDEC_TRUNCATED, /* ended more than a pad block early; rest padded */
73 BSDEC_OVERLONG, /* carried more than the header's length; excess dropped */
74};
75
84static inline int bsdecUsable(uint8_t error) {
85 return error == BSDEC_OK || error == BSDEC_TRUNCATED || error == BSDEC_OVERLONG;
86}
87
88/* Where a frame's decode time goes, for the console profile build. Ticks are
89 * counter 2 at system clock / 8, so one tick is 236 ns. Built only when
90 * BSDEC_PROFILE is defined; the symbols do not exist otherwise. */
91struct BsdecProf {
92 uint32_t tDc; /* ticks in the DC path, summed over blocks */
93 uint32_t tAc; /* ticks in the AC/VLC loop, summed over blocks */
94 uint32_t blocks; /* blocks decoded */
95 uint32_t acSymbols; /* VLC codes read in the AC loop */
96 uint32_t refillCalls; /* bsdecRefill entries */
97 uint32_t refillBytes; /* bytes the refill loop actually pulled */
98 uint32_t dcScanIters; /* iterations of the 9-deep DC code-length scan */
99};
100
101#ifdef BSDEC_PROFILE
102struct BsdecProf *bsdecProfile(void);
103void bsdecProfileReset(void);
104#endif
105
107 uint32_t mdecCommand; /* write this to MDEC0 before the DMA */
108 uint32_t halfwords; /* run-level halfwords written, padding included */
109 uint32_t blocks; /* blocks the bitstream actually carried; check this against
110 * the count the picture size implies, six per macroblock,
111 * which the caller knows and a BS header does not */
112 uint16_t qScale; /* the one quantization scale the whole frame uses */
113 uint8_t version; /* 1, 2 or 3 */
114 uint8_t error; /* enum BsdecError */
115};
116
124uint32_t bsdecRlHalfwords(const void *in, uint32_t inBytes);
125
struct BsdecResult bsdecFrame(const void *in, uint32_t inBytes, uint16_t *out, uint32_t outHalfwords);
struct BsdecResult bsdecFrame(const void *in, uint32_t inBytes, uint16_t *out, uint32_t outHalfwords)
Decode one BS frame into MDEC run-level halfwords.
Definition bsdec.c:181
uint32_t bsdecRlHalfwords(const void *in, uint32_t inBytes)
How many run-level halfwords a frame decodes to.
Definition bsdec.c:175
BsdecError
Definition bsdec.h:64
@ BSDEC_NOT_BS
Definition bsdec.h:68
@ BSDEC_OUTPUT_TOO_SMALL
Definition bsdec.h:70
@ BSDEC_OK
Definition bsdec.h:65
@ BSDEC_OVERLONG
Definition bsdec.h:73
@ BSDEC_SHORT
Definition bsdec.h:67
@ BSDEC_TRUNCATED
Definition bsdec.h:72
@ BSDEC_BAD_VERSION
Definition bsdec.h:69
uint32_t out
Definition cpu.c:62
char in[50]
Definition memcpy.c:79
Definition bsdec.h:91
uint32_t dcScanIters
Definition bsdec.h:98
uint32_t tDc
Definition bsdec.h:92
uint32_t blocks
Definition bsdec.h:94
uint32_t tAc
Definition bsdec.h:93
uint32_t refillBytes
Definition bsdec.h:97
uint32_t refillCalls
Definition bsdec.h:96
uint32_t acSymbols
Definition bsdec.h:95
Definition bsdec.h:106
uint8_t version
Definition bsdec.h:113
uint32_t mdecCommand
Definition bsdec.h:107
uint16_t qScale
Definition bsdec.h:112
uint32_t blocks
Definition bsdec.h:109
uint32_t halfwords
Definition bsdec.h:108
uint8_t error
Definition bsdec.h:114
void void(ptr, size)
void uint32_t(classId, spec)