diff options
author | Max Trussell <maxtrussell@gmail.com> | 2021-12-21 15:07:49 -0800 |
---|---|---|
committer | Andreas Kling <kling@serenityos.org> | 2022-03-26 11:04:25 +0100 |
commit | 346696ffbbee5e261e275ad4d31fbe611e8a8e7f (patch) | |
tree | 14a4ca30d0be6fb3201be5f2edf85025c491fe6e /Userland/Libraries/LibAudio | |
parent | d7c7e6e496594986ed52bb83be589e710d5f00da (diff) | |
download | serenity-346696ffbbee5e261e275ad4d31fbe611e8a8e7f.zip |
FlacLoader: Parse SEEKTABLE header
Populates m_seektable attribute with FlacSeekPoints.
For more information see:
https://datatracker.ietf.org/doc/html/draft-ietf-cellar-flac#section-11.13
Co-authored-by: kleines Filmröllchen <filmroellchen@serenityos.org>
Diffstat (limited to 'Userland/Libraries/LibAudio')
-rw-r--r-- | Userland/Libraries/LibAudio/FlacLoader.cpp | 26 | ||||
-rw-r--r-- | Userland/Libraries/LibAudio/FlacLoader.h | 2 | ||||
-rw-r--r-- | Userland/Libraries/LibAudio/FlacTypes.h | 6 |
3 files changed, 32 insertions, 2 deletions
diff --git a/Userland/Libraries/LibAudio/FlacLoader.cpp b/Userland/Libraries/LibAudio/FlacLoader.cpp index ab74865e27..baef59d7eb 100644 --- a/Userland/Libraries/LibAudio/FlacLoader.cpp +++ b/Userland/Libraries/LibAudio/FlacLoader.cpp @@ -118,13 +118,20 @@ MaybeLoaderError FlacLoaderPlugin::parse_header() md5_checksum.bytes().copy_to({ m_md5_checksum, sizeof(m_md5_checksum) }); // Parse other blocks - // TODO: For a simple first implementation, all other blocks are skipped as allowed by the FLAC specification. - // Especially the SEEKTABLE block may become useful in a more sophisticated version. [[maybe_unused]] u16 meta_blocks_parsed = 1; [[maybe_unused]] u16 total_meta_blocks = meta_blocks_parsed; FlacRawMetadataBlock block = streaminfo; while (!block.is_last_block) { block = TRY(next_meta_block(*bit_input)); + switch (block.type) { + case (FlacMetadataBlockType::SEEKTABLE): + TRY(load_seektable(block)); + break; + default: + // TODO: Parse the remaining metadata block types. + // Currently only STREAMINFO and SEEKTABLE are handled. + break; + } ++total_meta_blocks; } @@ -133,6 +140,21 @@ MaybeLoaderError FlacLoaderPlugin::parse_header() return {}; } +MaybeLoaderError FlacLoaderPlugin::load_seektable(FlacRawMetadataBlock& block) +{ + auto memory_stream = LOADER_TRY(Core::Stream::MemoryStream::construct(block.data.bytes())); + auto seektable_bytes = LOADER_TRY(BigEndianInputBitStream::construct(*memory_stream)); + for (size_t i = 0; i < block.length / 18; ++i) { + FlacSeekPoint seekpoint { + .sample_index = LOADER_TRY(seektable_bytes->read_bits<u64>(64)), + .byte_offset = LOADER_TRY(seektable_bytes->read_bits<u64>(64)), + .num_samples = LOADER_TRY(seektable_bytes->read_bits<u16>(16)) + }; + m_seektable.append(seekpoint); + } + return {}; +} + ErrorOr<FlacRawMetadataBlock, LoaderError> FlacLoaderPlugin::next_meta_block(BigEndianInputBitStream& bit_input) { diff --git a/Userland/Libraries/LibAudio/FlacLoader.h b/Userland/Libraries/LibAudio/FlacLoader.h index 9082b3901f..f78c2cf093 100644 --- a/Userland/Libraries/LibAudio/FlacLoader.h +++ b/Userland/Libraries/LibAudio/FlacLoader.h @@ -83,6 +83,7 @@ private: MaybeLoaderError decode_residual(Vector<i32>& decoded, FlacSubframeHeader& subframe, BigEndianInputBitStream& bit_input); // decode a single rice partition that has its own rice parameter ALWAYS_INLINE ErrorOr<Vector<i32>, LoaderError> decode_rice_partition(u8 partition_type, u32 partitions, u32 partition_index, FlacSubframeHeader& subframe, BigEndianInputBitStream& bit_input); + MaybeLoaderError load_seektable(FlacRawMetadataBlock&); // Converters for special coding used in frame headers ALWAYS_INLINE ErrorOr<u32, LoaderError> convert_sample_count_code(u8 sample_count_code); @@ -113,6 +114,7 @@ private: // Whatever the last get_more_samples() call couldn't return gets stored here. Vector<Sample, FLAC_BUFFER_SIZE> m_unread_data; u64 m_current_sample_or_frame { 0 }; + Vector<FlacSeekPoint> m_seektable; }; } diff --git a/Userland/Libraries/LibAudio/FlacTypes.h b/Userland/Libraries/LibAudio/FlacTypes.h index c5fb663b4e..0b1f6e5431 100644 --- a/Userland/Libraries/LibAudio/FlacTypes.h +++ b/Userland/Libraries/LibAudio/FlacTypes.h @@ -87,4 +87,10 @@ struct FlacSubframeHeader { u8 bits_per_sample; }; +struct FlacSeekPoint { + u64 sample_index; + u64 byte_offset; + u16 num_samples; +}; + } |