From 90da3b27d939b3b7af1cf7fed10dfaaa7e271622 Mon Sep 17 00:00:00 2001 From: Andrew Opalach Date: Thu, 30 Oct 2025 14:40:08 -0400 Subject: Fixes from testing sink change, document things Signed-off-by: Andrew Opalach --- src/codec/codec.h | 46 ++++++++++++++----------------------------- src/codec/ffmpeg/demuxer.c | 31 ++++++++++++++++++----------- src/codec/ffmpeg/packet_ext.c | 2 +- src/codec/stb_image.c | 14 ++++++++++++- 4 files changed, 49 insertions(+), 44 deletions(-) (limited to 'src/codec') diff --git a/src/codec/codec.h b/src/codec/codec.h index 0829847..f32283e 100644 --- a/src/codec/codec.h +++ b/src/codec/codec.h @@ -18,12 +18,6 @@ enum { CAMU_LANG_JAPANESE }; -enum { - CAMU_MASK_AUDIO = 1, - CAMU_MASK_VIDEO = 1 << 1, - CAMU_MASK_SUBTITLE = 1 << 2 -}; - #ifdef CAMU_HAVE_FFMPEG enum { CAMU_OK = 0, @@ -36,33 +30,31 @@ enum { CAMU_SEEK_SIZE = AVSEEK_SIZE }; +// Stream types must be >= 0 and < 7 because we use them as shifts for a u8 mask and 7 +// is reserved for STREAM_UNKNOWN which is different than AVMEDIA_TYPE_UNKNOWN(-1). enum { - CAMU_STREAM_UNKNOWN = AVMEDIA_TYPE_UNKNOWN, CAMU_STREAM_VIDEO = AVMEDIA_TYPE_VIDEO, // 0 CAMU_STREAM_AUDIO = AVMEDIA_TYPE_AUDIO, // 1 CAMU_STREAM_SUBTITLE = AVMEDIA_TYPE_SUBTITLE, - CAMU_STREAM_ATTACHMENT = AVMEDIA_TYPE_ATTACHMENT + CAMU_STREAM_ATTACHMENT = AVMEDIA_TYPE_ATTACHMENT, + CAMU_STREAM_UNKNOWN = 7 }; +AL_STATIC_ASSERT(stream_type_count, AVMEDIA_TYPE_NB, <, 7); enum { - CAMU_SAMPLE_FORMAT_NONE = AV_SAMPLE_FMT_NONE, + CAMU_SAMPLE_FORMAT_NONE = AV_SAMPLE_FMT_NONE, // -1 CAMU_SAMPLE_FORMAT_U8 = AV_SAMPLE_FMT_U8, CAMU_SAMPLE_FORMAT_S16 = AV_SAMPLE_FMT_S16, CAMU_SAMPLE_FORMAT_S32 = AV_SAMPLE_FMT_S32, CAMU_SAMPLE_FORMAT_FLT = AV_SAMPLE_FMT_FLT, - CAMU_SAMPLE_FORMAT_DBL = AV_SAMPLE_FMT_DBL, CAMU_SAMPLE_FORMAT_U8P = AV_SAMPLE_FMT_U8P, CAMU_SAMPLE_FORMAT_S16P = AV_SAMPLE_FMT_S16P, CAMU_SAMPLE_FORMAT_S32P = AV_SAMPLE_FMT_S32P, - CAMU_SAMPLE_FORMAT_FLTP = AV_SAMPLE_FMT_FLTP, - CAMU_SAMPLE_FORMAT_DBLP = AV_SAMPLE_FMT_DBLP, -#ifndef CAMU_OLD_FFMPEG - CAMU_SAMPLE_FORMAT_S64 = AV_SAMPLE_FMT_S64, - CAMU_SAMPLE_FORMAT_S64P = AV_SAMPLE_FMT_S64P -#endif + CAMU_SAMPLE_FORMAT_FLTP = AV_SAMPLE_FMT_FLTP }; enum { + CAMU_PIXEL_FORMAT_NONE = AV_PIX_FMT_NONE, // -1 CAMU_PIXEL_FORMAT_RGBA = AV_PIX_FMT_RGBA, CAMU_PIXEL_FORMAT_RGB24 = AV_PIX_FMT_RGB24, CAMU_PIXEL_FORMAT_RGB32 = AV_PIX_FMT_RGB32, @@ -91,13 +83,13 @@ enum { CAMU_SEEK_SIZE = 0x10000 }; -// Using values from FFmpeg for potentially less confusing errors. +// Using values from FFmpeg for less confusing errors. enum { - CAMU_STREAM_UNKNOWN = -1, CAMU_STREAM_VIDEO = 0, CAMU_STREAM_AUDIO = 1, CAMU_STREAM_SUBTITLE = 3, - CAMU_STREAM_ATTACHMENT = 4 + CAMU_STREAM_ATTACHMENT = 4, + CAMU_STREAM_UNKNOWN = 7 }; enum { @@ -106,18 +98,15 @@ enum { CAMU_SAMPLE_FORMAT_S16, CAMU_SAMPLE_FORMAT_S32, CAMU_SAMPLE_FORMAT_FLT, - CAMU_SAMPLE_FORMAT_DBL, CAMU_SAMPLE_FORMAT_U8P, CAMU_SAMPLE_FORMAT_S16P, CAMU_SAMPLE_FORMAT_S32P, - CAMU_SAMPLE_FORMAT_FLTP, - CAMU_SAMPLE_FORMAT_DBLP, - CAMU_SAMPLE_FORMAT_S64, - CAMU_SAMPLE_FORMAT_S64P + CAMU_SAMPLE_FORMAT_FLTP }; enum { - CAMU_PIXEL_FORMAT_RGBA = 0, + CAMU_PIXEL_FORMAT_NONE = -1, + CAMU_PIXEL_FORMAT_RGBA, CAMU_PIXEL_FORMAT_RGB24, CAMU_PIXEL_FORMAT_RGB32, CAMU_PIXEL_FORMAT_GREYA, @@ -344,11 +333,6 @@ static inline size_t camu_audio_format_bytes_per_sample(struct camu_audio_format case CAMU_SAMPLE_FORMAT_FLT: case CAMU_SAMPLE_FORMAT_FLTP: return 4; - case CAMU_SAMPLE_FORMAT_S64: - case CAMU_SAMPLE_FORMAT_S64P: - case CAMU_SAMPLE_FORMAT_DBL: - case CAMU_SAMPLE_FORMAT_DBLP: - return 8; default: al_assert_and_return(0); } @@ -419,7 +403,7 @@ static inline s32 camu_pixel_format_from_channels(s32 channels) case 3: return CAMU_PIXEL_FORMAT_RGB24; case 2: return CAMU_PIXEL_FORMAT_GREYA; case 1: return CAMU_PIXEL_FORMAT_GREY; - default: al_assert_and_return(CAMU_PIXEL_FORMAT_GREY); + default: al_assert_and_return(CAMU_PIXEL_FORMAT_NONE); } } diff --git a/src/codec/ffmpeg/demuxer.c b/src/codec/ffmpeg/demuxer.c index e5aa2f6..32068f3 100644 --- a/src/codec/ffmpeg/demuxer.c +++ b/src/codec/ffmpeg/demuxer.c @@ -89,6 +89,7 @@ static bool ff_demuxer_init(struct camu_demuxer *demux, struct cch_handle *handl // @TODO: // - 1 frame .gif. // - No-duration video. (ex: data/test_resources/no_duration.mkv) + // - Incomplete video files with no duration. .temp.webm. #define GUESS_STREAM_IS_IMAGE(stream) \ ((stream->duration >= 0 && stream->nb_frames <= 1 && \ (stream->avg_frame_rate.den == 0 && stream->r_frame_rate.den > 0)) || \ @@ -105,6 +106,7 @@ static bool ff_demuxer_init(struct camu_demuxer *demux, struct cch_handle *handl #endif enum AVMediaType type = stream->codecpar->codec_type; u64 duration = 0; + u8 mapped_type; if (type == AVMEDIA_TYPE_AUDIO || type == AVMEDIA_TYPE_VIDEO || type == AVMEDIA_TYPE_SUBTITLE) { // Try to detect attached images. if (type == AVMEDIA_TYPE_VIDEO && GUESS_STREAM_IS_IMAGE(stream)) { @@ -117,15 +119,24 @@ static bool ff_demuxer_init(struct camu_demuxer *demux, struct cch_handle *handl i, stream->duration * av_q2d(stream->time_base)); } duration = (u64)av_rescale_q(stream->duration, stream->time_base, AV_TIME_BASE_Q); - if (duration > av->duration) av->duration = duration; + if (duration > av->duration) { + av->duration = duration; + } + } + if (stream->start_time == AV_NOPTS_VALUE) { + stream->start_time = 0; } - if (stream->start_time == AV_NOPTS_VALUE) stream->start_time = 0; - } else if (type != AVMEDIA_TYPE_ATTACHMENT) { - type = AVMEDIA_TYPE_UNKNOWN; // Mapped to CAMU_STREAM_UNKNOWN. + mapped_type = type; + } else if (type == AVMEDIA_TYPE_ATTACHMENT) { + mapped_type = CAMU_STREAM_ATTACHMENT; + } else { + // CAMU_STREAM_UNKNOWN(7) is a different value than AVMEDIA_TYPE_UNKNOWN(-1) because + // we don't support negative stream types. + mapped_type = CAMU_STREAM_UNKNOWN; } al_array_push(av->demux.streams, ((struct camu_codec_stream){ .mode = CAMU_FFMPEG_COMPAT, - .type = type, + .type = mapped_type, .duration = duration, .index = stream->index, .av.stream = stream @@ -184,12 +195,10 @@ static u64 ff_demuxer_get_duration(struct camu_demuxer *demux) static bool ff_demuxer_seek(struct camu_demuxer *demux, u64 pos, bool bytes) { struct camu_ff_demuxer *av = (struct camu_ff_demuxer *)demux; - if (av->eof) { - // avio_flush() here probably does nothing. - avio_flush(av->io_context); - avformat_flush(av->format_context); - av->eof = false; - } + // avio_flush() here probably does nothing. + avio_flush(av->io_context); + avformat_flush(av->format_context); + if (av->eof) av->eof = false; al_assert(pos <= INT64_MAX); al_assert(!(bytes && av->format_context->flags & AVFMT_NO_BYTE_SEEK)); if (!bytes && pos > av->duration) pos = av->duration; diff --git a/src/codec/ffmpeg/packet_ext.c b/src/codec/ffmpeg/packet_ext.c index 6b66dd1..68f1b4c 100644 --- a/src/codec/ffmpeg/packet_ext.c +++ b/src/codec/ffmpeg/packet_ext.c @@ -221,7 +221,7 @@ void nn_packet_read_av_packet(struct nn_packet *packet, AVPacket *pkt) enum AVPacketSideDataType type; s64 storage_for_size; NNWT_PACKET_READ_TYPE(packet, s64, storage_for_size); - al_assert((sizeof(size_t) > 4 || storage_for_size <= INT32_MAX)); + al_assert(sizeof(size_t) > 4 || storage_for_size <= INT32_MAX); size_t size = (size_t)storage_for_size; NNWT_PACKET_READ_DATA(packet, size, data); NNWT_PACKET_READ_TYPE(packet, enum AVPacketSideDataType, type); diff --git a/src/codec/stb_image.c b/src/codec/stb_image.c index b4fabc2..1d790dd 100644 --- a/src/codec/stb_image.c +++ b/src/codec/stb_image.c @@ -2,6 +2,7 @@ #define STBI_MALLOC camu_page_alloc #define STBI_FREE al_free #define STBI_REALLOC camu_page_realloc +#define STBI_ASSERT al_assert #define STBI_NO_STDIO #define STBI_NO_FAILURE_STRINGS #define STB_IMAGE_IMPLEMENTATION @@ -10,7 +11,7 @@ #include "stb_image.h" #ifdef LIANA_SERVER -#include "../../cache/entry.h" +#include "../cache/entry.h" static bool stbi_demuxer_init(struct camu_demuxer *demux, struct cch_handle *handle) { @@ -114,7 +115,14 @@ static s32 stbi_decoder_push(struct camu_decoder *dec, struct camu_codec_packet s32 w, h, channels; u8 *data = nn_buffer_get_ptr(packet->buffer, 0); +#ifdef NAUNET_ON_WINDOWS +#define STB_FORCE_RGBA +#endif +#ifdef STB_FORCE_RGBA + u8 *pixels = stbi_load_from_memory(data, packet->buffer->size, &w, &h, &channels, 4); +#else u8 *pixels = stbi_load_from_memory(data, packet->buffer->size, &w, &h, &channels, 0); +#endif if (!pixels) return CAMU_ERR_ERROR; struct camu_video_format *fmt = &stb->stream->video.fmt; @@ -126,8 +134,12 @@ static s32 stbi_decoder_push(struct camu_decoder *dec, struct camu_codec_packet frame->data = pixels; frame->video.width = (u32)w; frame->video.height = (u32)h; +#ifdef STB_FORCE_RGBA + frame->format = camu_pixel_format_from_channels(4); +#else frame->format = camu_pixel_format_from_channels(channels); al_assert(frame->format == fmt->format); +#endif frame->pts = 0.0; stb->callback(stb->userdata, frame); -- cgit v1.2.3-101-g0448