1 /* 2 * Copyright (c) 2023, Alliance for Open Media. All rights reserved 3 * 4 * This source code is subject to the terms of the BSD 3-Clause Clear License 5 * and the Alliance for Open Media Patent License 1.0. If the BSD 3-Clause Clear 6 * License was not distributed with this source code in the LICENSE file, you 7 * can obtain it at www.aomedia.org/license/software-license/bsd-3-c-c. If the 8 * Alliance for Open Media Patent License 1.0 was not distributed with this 9 * source code in the PATENTS file, you can obtain it at 10 * www.aomedia.org/license/patent. 11 */ 12 13 #ifndef CLI_CLI_UTIL_H_ 14 #define CLI_CLI_UTIL_H_ 15 16 #include <cstdint> 17 #include <list> 18 #include <string> 19 #include <vector> 20 21 #include "absl/container/flat_hash_map.h" 22 #include "absl/container/flat_hash_set.h" 23 #include "absl/status/status.h" 24 #include "absl/strings/string_view.h" 25 #include "iamf/cli/audio_element_with_data.h" 26 #include "iamf/obu/codec_config.h" 27 #include "iamf/obu/mix_presentation.h" 28 #include "iamf/obu/param_definition_variant.h" 29 #include "iamf/obu/param_definitions.h" 30 #include "iamf/obu/types.h" 31 32 namespace iamf_tools { 33 34 /*!\brief Determines if the layout is a stereo layout. 35 * 36 * \param layout Layout to check. 37 * \return True if the layout is a stereo layout. False otherwise. 38 */ 39 bool IsStereoLayout(const Layout& layout); 40 41 /*!\brief Gets indices for the target Layout in the mix presentation. 42 * 43 * This function grabs the submix index and layout index of the desired layout 44 * in the mix presentation. 45 * 46 * \param mix_presentation_sub_mixes List of mix presentation submixes where we 47 * search for the target_layout. 48 * \param target_layout Layout to get the indices for. 49 * \param output_submix_index Index of the submix to use. 50 * \param output_layout_index Index of the layout to use. 51 * \return `absl::OkStatus()` on success. A specific status on failure. 52 */ 53 absl::Status GetIndicesForLayout( 54 const std::vector<MixPresentationSubMix>& mix_presentation_sub_mixes, 55 const Layout& target_layout, int& output_submix_index, 56 int& output_layout_index); 57 58 /*!\brief Collects and validates the parameter definitions against the spec. 59 * 60 * When `param_definition_mode = 0`, `duration`, `num_subblocks`, 61 * `constant_subblock_duration` and `subblock_duration` shall be same in all 62 * parameter definitions, respectively. 63 * 64 * \param audio_elements List of Audio Element OBUs with data. 65 * \param mix_presentation_obus List of Mix Presentation OBUs. 66 * \param param_definition_variants Output map from parameter IDs to parameter 67 * definitions. 68 * \return `absl::OkStatus()` on success. A specific status on failure. 69 */ 70 absl::Status CollectAndValidateParamDefinitions( 71 const absl::flat_hash_map<DecodedUleb128, AudioElementWithData>& 72 audio_elements, 73 const std::list<MixPresentationObu>& mix_presentation_obus, 74 absl::flat_hash_map<DecodedUleb128, ParamDefinitionVariant>& 75 param_definition_variants); 76 77 /*!\brief Validates that two timestamps are equal. 78 * 79 * \param expected_timestamp Expected timestamp. 80 * \param actual_timestamp Actual timestamp. 81 * \param prompt Prompt message to be included in the error status when the 82 * timestamps do not match. Defaulted to be empty. 83 * \return `absl::OkStatus()` if the timestamps are equal. 84 * `absl::InvalidArgumentError()` with a custom message otherwise. 85 */ 86 absl::Status CompareTimestamps(InternalTimestamp expected_timestamp, 87 InternalTimestamp actual_timestamp, 88 absl::string_view prompt = ""); 89 90 /*!\brief Writes interlaced PCM samples into the output buffer. 91 * 92 * \param frame Input frames arranged in (time, channel) axes. 93 * \param bit_depth Sample size in bits. 94 * \param big_endian Whether the sample should be written as big or little 95 * endian. 96 * \param buffer Buffer to resize and write to. 97 * \return `absl::OkStatus()` on success. A specific status on failure. 98 */ 99 absl::Status WritePcmFrameToBuffer( 100 const std::vector<std::vector<int32_t>>& frame, uint8_t bit_depth, 101 bool big_endian, std::vector<uint8_t>& buffer); 102 103 /*!\brief Gets the common output sample rate and bit-deph of the input sets. 104 * 105 * \param sample_rates Sample rates to find the common output sample rate of. 106 * \param bit_depths Bit-depths to find the common output bit-depth rate of. 107 * \param common_sample_rate The output sample rate of the Codec Config OBUs or 108 * 48000 if no common output sample rate is found. 109 * \param common_bit_depth The output bit-depth rate of the Codec Config OBUs or 110 * 16 if no common output bit depth is found. 111 * \param requires_resampling False if all output sample rates and bit-depths 112 * were the same. True otherwise. 113 * \return `absl::OkStatus()` on success. `absl::InvalidArgumentError()` if 114 * either of the input hash sets are empty. 115 */ 116 absl::Status GetCommonSampleRateAndBitDepth( 117 const absl::flat_hash_set<uint32_t>& sample_rates, 118 const absl::flat_hash_set<uint8_t>& bit_depths, 119 uint32_t& common_sample_rate, uint8_t& common_bit_depth, 120 bool& requires_resampling); 121 122 /*!\brief Gets the common samples per frame from all Codec Config OBUs 123 * 124 * \param codec_config_obus Codec Config OBUs to get the common frame size of. 125 * \param common_samples_per_frame The frame size of all Codec Config OBUs. 126 * \return `absl::OkStatus()` on success. `absl::UnknownError()` if there is no 127 * common frame size. 128 */ 129 absl::Status GetCommonSamplesPerFrame( 130 const absl::flat_hash_map<uint32_t, CodecConfigObu>& codec_config_obus, 131 uint32_t& common_samples_per_frame); 132 133 /*!\brief Logs the channel numbers. 134 * 135 * \param name Name of the channel to log. 136 * \param channel_numbers `ChannelNumbers` of the channel to log. 137 */ 138 void LogChannelNumbers(const std::string& name, 139 const ChannelNumbers& channel_numbers); 140 141 } // namespace iamf_tools 142 143 #endif // CLI_CLI_UTIL_H_ 144