Skip to content

Commit

Permalink
Fix playback of atrac3+ when block align not specified
Browse files Browse the repository at this point in the history
  • Loading branch information
hrydgard committed Apr 11, 2024
1 parent d4023fb commit 58cb2ba
Show file tree
Hide file tree
Showing 4 changed files with 31 additions and 18 deletions.
12 changes: 8 additions & 4 deletions Core/HW/Atrac3Standalone.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -18,11 +18,11 @@ class Atrac3Audio : public AudioDecoder {
Atrac3Audio(PSPAudioType audioType, int channels, size_t blockAlign, const uint8_t *extraData, size_t extraDataSize) : audioType_(audioType) {
blockAlign_ = blockAlign;
if (audioType == PSP_CODEC_AT3PLUS) {
at3pCtx_ = atrac3p_alloc(channels, blockAlign);
at3pCtx_ = atrac3p_alloc(channels, &blockAlign_);
if (at3pCtx_)
codecOpen_ = true;
} else if (audioType_ == PSP_CODEC_AT3) {
at3Ctx_ = atrac3_alloc(channels, blockAlign, extraData, extraDataSize);
at3Ctx_ = atrac3_alloc(channels, &blockAlign_, extraData, extraDataSize);
if (at3Ctx_)
codecOpen_ = true;
}
Expand All @@ -42,13 +42,18 @@ class Atrac3Audio : public AudioDecoder {
}
}

bool IsOK() const override {
return codecOpen_;
}

bool Decode(const uint8_t *inbuf, int inbytes, uint8_t *outbuf, int *outbytes) override {
if (!codecOpen_) {
_dbg_assert_(false);
}
if (inbytes != blockAlign_) {
if (inbytes != blockAlign_ && blockAlign_ != 0) {
WARN_LOG(ME, "Atrac3Audio::Decode: Unexpected block align %d (expected %d)", inbytes, blockAlign_);
}
blockAlign_ = inbytes;
// We just call the decode function directly without going through the whole packet machinery.
int got_frame = 0;
int result;
Expand Down Expand Up @@ -82,7 +87,6 @@ class Atrac3Audio : public AudioDecoder {
return true;
}

bool IsOK() const override { return true; }
int GetOutSamples() const override {
return outSamples_;
}
Expand Down
6 changes: 4 additions & 2 deletions ext/at3_standalone/at3_decoders.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,10 +7,12 @@
struct ATRAC3Context;
struct ATRAC3PContext;

ATRAC3Context *atrac3_alloc(int channels, int block_align, const uint8_t *extra_data, int extra_data_size);
// If the block_align passed in is 0, tries to audio detect.

ATRAC3Context *atrac3_alloc(int channels, int *block_align, const uint8_t *extra_data, int extra_data_size);
void atrac3_free(ATRAC3Context *ctx);
int atrac3_decode_frame(ATRAC3Context *ctx, float *out_data[2], int *nb_samples, int *got_frame_ptr, const uint8_t *buf, int buf_size);

ATRAC3PContext *atrac3p_alloc(int channels, int block_align);
ATRAC3PContext *atrac3p_alloc(int channels, int *block_align);
void atrac3p_free(ATRAC3PContext *ctx);
int atrac3p_decode_frame(ATRAC3PContext *ctx, float *out_data[2], int *nb_samples, int *got_frame_ptr, const uint8_t *buf, int buf_size);
18 changes: 12 additions & 6 deletions ext/at3_standalone/atrac3.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -785,7 +785,7 @@ static void atrac3_init_static_data(void)

static int static_init_done;

ATRAC3Context *atrac3_alloc(int channels, int block_align, const uint8_t *extra_data, int extra_data_size) {
ATRAC3Context *atrac3_alloc(int channels, int *block_align, const uint8_t *extra_data, int extra_data_size) {
int i, ret;
int version, delay, samples_per_frame, frame_factor;

Expand All @@ -798,7 +798,13 @@ ATRAC3Context *atrac3_alloc(int channels, int block_align, const uint8_t *extra_

ATRAC3Context *q = (ATRAC3Context *)av_mallocz(sizeof(ATRAC3Context));
q->channels = channels;
q->block_align = block_align;
if (*block_align) {
q->block_align = *block_align;
} else {
// Atrac3 (unlike Atrac3+) requires a specified block align.
atrac3_free(q);
return nullptr;
}

if (!static_init_done)
atrac3_init_static_data();
Expand All @@ -824,9 +830,9 @@ ATRAC3Context *atrac3_alloc(int channels, int block_align, const uint8_t *extra_
q->coding_mode = q->coding_mode ? JOINT_STEREO : STEREO;
q->scrambled_stream = 0;

if (block_align != 96 * channels * frame_factor &&
block_align != 152 * channels * frame_factor &&
block_align != 192 * channels * frame_factor) {
if (q->block_align != 96 * channels * frame_factor &&
q->block_align != 152 * channels * frame_factor &&
q->block_align != 192 * channels * frame_factor) {
av_log(AV_LOG_ERROR, "Unknown frame/channel/frame_factor "
"configuration %d/%d/%d\n", block_align,
channels, frame_factor);
Expand Down Expand Up @@ -887,7 +893,7 @@ ATRAC3Context *atrac3_alloc(int channels, int block_align, const uint8_t *extra_
return nullptr;
}

q->decoded_bytes_buffer = (uint8_t *)av_mallocz(FFALIGN(block_align, 4) + AV_INPUT_BUFFER_PADDING_SIZE);
q->decoded_bytes_buffer = (uint8_t *)av_mallocz(FFALIGN(q->block_align, 4) + AV_INPUT_BUFFER_PADDING_SIZE);

/* initialize the MDCT transform */
if ((ret = ff_mdct_init(&q->mdct_ctx, 9, 1, 1.0 / 32768)) < 0) {
Expand Down
13 changes: 7 additions & 6 deletions ext/at3_standalone/atrac3plusdec.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -125,15 +125,16 @@ static int set_channel_params(ATRAC3PContext *ctx, int channels) {
return 0;
}

ATRAC3PContext *atrac3p_alloc(int channels, int block_align) {
ATRAC3PContext *atrac3p_alloc(int channels, int *block_align) {
int i, ch, ret;
if (!block_align) {
av_log(AV_LOG_ERROR, "block_align is not set\n");
return nullptr;
}

ATRAC3PContext *ctx = (ATRAC3PContext *)av_mallocz(sizeof(ATRAC3PContext));
ctx->block_align = block_align;
ctx->block_align = *block_align;

if (!*block_align) {
// No block align was passed in, using the default.
*block_align = 0x000002e8;
}

ff_atrac3p_init_vlcs();

Expand Down

0 comments on commit 58cb2ba

Please sign in to comment.