MEDIA_FORMAT_RGBA = (MEDIA_FORMAT_VIDEO | MEDIA_FORMAT_RAW | 0x25c0), /**< media format mime type is RGBA, VIDEO */
MEDIA_FORMAT_ARGB = (MEDIA_FORMAT_VIDEO | MEDIA_FORMAT_RAW | 0x25d0), /**< media format mime type is ARGB, VIDEO */
MEDIA_FORMAT_BGRA = (MEDIA_FORMAT_VIDEO | MEDIA_FORMAT_RAW | 0x25e0), /**< media format mime type is BGRA, VIDEO, (Since 3.0) */
+ MEDIA_FORMAT_Y8 = (MEDIA_FORMAT_VIDEO | MEDIA_FORMAT_RAW | 0x25f0), /**< media format mime type is Y8, VIDEO, (Since 5.5) */
/* CONTAINER VIDEO */
MEDIA_FORMAT_CONTAINER_MP4 = (MEDIA_FORMAT_CONTAINER | 0x3010), /**< media format mime type is MP4 container, VIDEO, (Since 3.0) */
MEDIA_FORMAT_TEXT_TYPE_UNKNOWN, /**< media format text type is unknown */
} media_format_text_type_e;
+/**
+ * @brief Enumeration for audio channel positions.
+ * @since_tizen 5.5
+ */
+typedef enum {
+ MEDIA_FORMAT_CHANNEL_POSITION_NONE = -3, /**< Used for position-less channels (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_MONO = -2, /**< Used for mono without direction (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID = -1, /**< Used for invalid position (Since 5.5) */
+
+ /* Normal cases */
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_LEFT = 0, /**< Front left (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_RIGHT, /**< Front Right (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_CENTER, /**< Front Center (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_LFE1, /**< Low-frequency effects 1 (subwoofer) (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_REAR_LEFT, /**< Rear left (Since 5.5)*/
+ MEDIA_FORMAT_CHANNEL_POSITION_REAR_RIGHT, /**< Rear right (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_LEFT_OF_CENTER, /**< Front left of center (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_RIGHT_OF_CENTER, /**< Front right of center (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_REAR_CENTER, /**< Rear center (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_LFE2, /**< Low-frequency effects 2 (subwoofer) (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_SIDE_LEFT, /**< Side left (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_SIDE_RIGHT, /**< Side Right (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_FRONT_LEFT, /**< Top front left (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_FRONT_RIGHT, /**< Top front right (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_FRONT_CENTER, /**< Top front center (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_CENTER, /**< Top center (Since 5.5)*/
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_REAR_LEFT, /**< Top rear left (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_REAR_RIGHT, /**< Top rear right (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_SIDE_LEFT, /**< Top side left (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_SIDE_RIGHT, /**< Top side right (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_REAR_CENTER, /**< Top rear center (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_BOTTOM_FRONT_CENTER, /**< Bottom front center (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_BOTTOM_FRONT_LEFT, /**< Bottom front left (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_BOTTOM_FRONT_RIGHT, /**< Bottom front right (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_WIDE_LEFT, /**< Wide left (between front left and side left) (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_WIDE_RIGHT, /**< Wide right (between front right and side right) (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_SURROUND_LEFT, /**< Surround left (between rear left and side left) (Since 5.5) */
+ MEDIA_FORMAT_CHANNEL_POSITION_SURROUND_RIGHT /**< Surround right (between rear right and side right) (Since 5.5) */
+} media_format_channel_position_e;
+
/**
* @brief Creates a media format.
* @since_tizen @if MOBILE 2.3 @elseif WEARABLE 2.3.1 @endif
* @see media_format_set_extra()
*/
int media_format_get_extra(media_format_h fmt, void **extra_data);
+
+/**
+ * @brief Sets audio channel mask of media format.
+ * @since_tizen 5.5
+ * @param[in] fmt The media format handle
+ * @param[in] channel_mask The input channel mask
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ * @retval #MEDIA_FORMAT_ERROR_NONE Successful
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_PACKET_ERROR_INVALID_OPERATION Invalid operation
+ * @see media_format_get_audio_channel_mask()
+ * @see media_format_channel_positions_to_mask()
+ * @par Example
+ * @code
+ uint64_t channel_mask;
+ media_format_channel_position_e position[2];
+
+ position[0] = MEDIA_FORMAT_CHANNEL_POSITION_FRONT_LEFT;
+ position[1] = MEDIA_FORMAT_CHANNEL_POSITION_FRONT_RIGHT;
+
+ media_format_channel_positions_to_mask(fmt, position, &channel_mask);
+ media_format_set_audio_channel_mask(fmt, channel_mask);
+ * @endcode
+ */
+int media_format_set_audio_channel_mask(media_format_h fmt, uint64_t channel_mask);
+
+/**
+ * @brief Gets audio channel mask of media format.
+ * @since_tizen 5.5
+ * @param[in] fmt The media format handle
+ * @param[out] channel_mask The output channel mask
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ * @retval #MEDIA_FORMAT_ERROR_NONE Successful
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_PACKET_ERROR_INVALID_OPERATION Invalid operation
+ * @see media_format_set_audio_channel_mask()
+ * @see media_format_channel_positions_from_mask()
+ * @par Example
+ * @code
+ int channels;
+ uint64_t channel_mask;
+ media_format_channel_position_e *positions;
+
+ media_format_get_audio_info(fmt, NULL, &channels, NULL, NULL, NULL);
+ positions = malloc(channels * sizeof(media_format_channel_position_e));
+ media_format_get_audio_channel_mask(fmt, &channel_mask);
+ media_format_channel_positions_from_mask(fmt, channel_mask, &positions);
+ ...
+ free(positions);
+ * @endcode
+ */
+int media_format_get_audio_channel_mask(media_format_h fmt, uint64_t *channel_mask);
+
+/**
+ * @brief Checks whether the given media format is little endian.
+ * @since_tizen 5.5
+ * @param[in] fmt The media format handle
+ * @param[out] is_little_endian @c true if the given media format is little endian,
+ * @c false if the given media format is big endian
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ * @retval #MEDIA_PACKET_ERROR_NONE Successful
+ * @retval #MEDIA_PACKET_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_PACKET_ERROR_INVALID_OPERATION Invalid operation
+ * @see media_format_mimetype_e
+ * @see media_format_type_e
+ */
+int media_format_is_little_endian(media_format_h fmt, bool *is_little_endian);
+
+/**
+ * @brief Gets the number of bits of information in digital audio using pulse-code modulation (PCM).
+ * @since_tizen 5.5
+ * @param[in] fmt The media format handle
+ * @param[out] bit_depth The number of bits of information in each sample
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ * @retval #MEDIA_FORMAT_ERROR_NONE Successful
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_OPERATION Invalid operation
+ * @see media_format_set_audio_aac_header_type()
+ */
+int media_format_get_audio_bit_depth(media_format_h fmt, int *bit_depth);
+
+/**
+ * @brief Converts the channels in the @a channel_mask to a positions array.
+ * @detail The size of the position array is equal to the number of channels,
+ * that can be obtained with media_format_get_audio_info().
+ * @since_tizen 5.5
+ * @remarks A @channel_mask with fewer bits set than the number of channels is considered valid.
+ * The @a positions should be released with free().
+ * @param[in] fmt The media format handle
+ * @param[in] channel_mask The input channel_mask
+ * @param[out] positions The channel positions array, its length is equal to the number of channels
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ * @retval #MEDIA_FORMAT_ERROR_NONE Successful
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_OPERATION Invalid operation
+ * @pre The number of channels must be set with media_format_set_audio_channel().
+ * @pre The @channel should be set before calling media_format_channel_positions_from_mask().
+ * @see media_format_set_audio_channel()
+ * @see media_format_get_audio_info()
+ * @par Example
+ * @code
+ int channels;
+ uint64_t channel_mask;
+ media_format_channel_position_e *positions;
+
+ media_format_get_audio_info(fmt, NULL, &channels, NULL, NULL, NULL);
+ positions = malloc(channels * sizeof(media_format_channel_position_e));
+ media_format_channel_positions_from_mask(fmt, channel_mask, &positions);
+ ...
+ free(positions);
+ * @endcode
+ */
+int media_format_channel_positions_from_mask(media_format_h fmt, uint64_t channel_mask, media_format_channel_position_e **positions);
+
+/**
+ * @brief Converts the @a positions array to a bitmask.
+ * @since_tizen 5.5
+ * @remarks A @channel_mask with fewer bits set than the number of channels is considered valid.
+ * @param[in] fmt The media format handle
+ * @param[in] positions The channel positions array, its lengh is equal to the number of channels
+ * @param[out] channel_mask_out the output channel mask
+ * @return @c 0 on success,
+ * otherwise a negative error value
+ * @retval #MEDIA_FORMAT_ERROR_NONE Successful
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_PARAMETER Invalid parameter
+ * @retval #MEDIA_FORMAT_ERROR_INVALID_OPERATION Invalid operation
+ * @pre The number of channels must be set with media_format_set_audio_channel().
+ * @pre The @channel should be set before calling media_format_channel_positions_to_mask().
+ * @see media_format_set_audio_channel()
+ */
+int media_format_channel_positions_to_mask(media_format_h fmt, const media_format_channel_position_e *positions, uint64_t *channel_mask_out);
/**
* @}
*/
static void _media_format_destroy(media_format_s *fmt);
+static const media_format_channel_position_e default_channel_order[64] = {
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_LFE1,
+ MEDIA_FORMAT_CHANNEL_POSITION_REAR_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_REAR_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_LEFT_OF_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_FRONT_RIGHT_OF_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_REAR_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_LFE2,
+ MEDIA_FORMAT_CHANNEL_POSITION_SIDE_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_SIDE_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_FRONT_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_FRONT_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_FRONT_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_REAR_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_REAR_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_SIDE_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_SIDE_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_TOP_REAR_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_BOTTOM_FRONT_CENTER,
+ MEDIA_FORMAT_CHANNEL_POSITION_BOTTOM_FRONT_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_BOTTOM_FRONT_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_WIDE_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_WIDE_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_SURROUND_LEFT,
+ MEDIA_FORMAT_CHANNEL_POSITION_SURROUND_RIGHT,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID,
+ MEDIA_FORMAT_CHANNEL_POSITION_INVALID
+};
+
int media_format_create(media_format_h *fmt)
{
MEDIA_FORMAT_NULL_ARG_CHECK(fmt);
return MEDIA_FORMAT_ERROR_NONE;
}
+
+int media_format_set_audio_channel_mask(media_format_h fmt, uint64_t channel_mask)
+{
+ MEDIA_FORMAT_INSTANCE_CHECK(fmt);
+
+ media_format_s *fmt_handle;
+ fmt_handle = (media_format_s *)fmt;
+
+ if (MEDIA_FORMAT_GET_REFCOUNT(fmt) <= 0) {
+ LOGE("The format ref_count is less than 0..\n");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ if (!CHECK_IS_AUDIO(fmt_handle->mimetype)) {
+ LOGE("The format handle is not for MEDIA_FORMAT_AUDIO..\n");
+ return MEDIA_FORMAT_ERROR_INVALID_PARAMETER;
+ }
+
+ fmt_handle->detail.audio.channel_mask = channel_mask;
+
+ return MEDIA_FORMAT_ERROR_NONE;
+}
+
+int media_format_get_audio_channel_mask(media_format_h fmt, uint64_t *channel_mask)
+{
+ MEDIA_FORMAT_INSTANCE_CHECK(fmt);
+
+ media_format_s *fmt_handle;
+ fmt_handle = (media_format_s *)fmt;
+
+ if (MEDIA_FORMAT_GET_REFCOUNT(fmt) <= 0) {
+ LOGE("The format ref_count is less than 0..\n");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ if (!CHECK_IS_AUDIO(fmt_handle->mimetype)) {
+ LOGE("The format handle is not for MEDIA_FORMAT_AUDIO..\n");
+ return MEDIA_FORMAT_ERROR_INVALID_PARAMETER;
+ }
+
+ if (!fmt_handle->detail.audio.channel_mask) {
+ LOGE("The channel mask is not set");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ if (fmt_handle->detail.audio.channel < 0 || fmt_handle->detail.audio.channel > 8)
+ *channel_mask = 0;
+ else
+ *channel_mask = fmt_handle->detail.audio.channel_mask;
+
+ return MEDIA_FORMAT_ERROR_NONE;
+}
+
+int media_format_is_little_endian(media_format_h fmt, bool *is_little_endian)
+{
+ MEDIA_FORMAT_INSTANCE_CHECK(fmt);
+
+ media_format_s *fmt_handle;
+ fmt_handle = (media_format_s *)fmt;
+
+ if (MEDIA_FORMAT_GET_REFCOUNT(fmt) <= 0) {
+ LOGE("The format ref_count is less than 0..\n");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ if (!CHECK_IS_AUDIO(fmt_handle->mimetype) || !CHECK_IS_RAW(fmt_handle->mimetype)) {
+ LOGE("The format handle is not for PCM\n");
+ return MEDIA_FORMAT_ERROR_INVALID_PARAMETER;
+ }
+
+ switch (fmt_handle->mimetype) {
+ case MEDIA_FORMAT_PCM_S16LE:
+ case MEDIA_FORMAT_PCM_S24LE:
+ case MEDIA_FORMAT_PCM_S32LE:
+ case MEDIA_FORMAT_PCM_F32LE:
+ case MEDIA_FORMAT_PCM_U16LE:
+ case MEDIA_FORMAT_PCM_U24LE:
+ case MEDIA_FORMAT_PCM_U32LE:
+ *is_little_endian = true;
+ break;
+ case MEDIA_FORMAT_PCM_S16BE:
+ case MEDIA_FORMAT_PCM_S24BE:
+ case MEDIA_FORMAT_PCM_S32BE:
+ case MEDIA_FORMAT_PCM_F32BE:
+ case MEDIA_FORMAT_PCM_U16BE:
+ case MEDIA_FORMAT_PCM_U24BE:
+ case MEDIA_FORMAT_PCM_U32BE:
+ *is_little_endian = false;
+ break;
+ deault:
+ LOGE("The format handle is not for PCM\n");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ return MEDIA_FORMAT_ERROR_NONE;
+}
+
+int media_format_get_audio_bit_depth(media_format_h fmt, int *bit_depth)
+{
+ MEDIA_FORMAT_INSTANCE_CHECK(fmt);
+
+ media_format_s *fmt_handle;
+ fmt_handle = (media_format_s *)fmt;
+
+ if (MEDIA_FORMAT_GET_REFCOUNT(fmt) <= 0) {
+ LOGE("The format ref_count is less than 0..\n");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ if (!CHECK_IS_AUDIO(fmt_handle->mimetype) || !CHECK_IS_RAW(fmt_handle->mimetype)) {
+ LOGE("The format handle is not for AUDIO");
+ return MEDIA_FORMAT_ERROR_INVALID_PARAMETER;
+ }
+
+ switch (fmt_handle->mimetype) {
+ case MEDIA_FORMAT_PCM_S16LE:
+ case MEDIA_FORMAT_PCM_S16BE:
+ case MEDIA_FORMAT_PCM_U16LE:
+ case MEDIA_FORMAT_PCM_U16BE:
+ *bit_depth = 16;
+ break;
+ case MEDIA_FORMAT_PCM_S24LE:
+ case MEDIA_FORMAT_PCM_S24BE:
+ case MEDIA_FORMAT_PCM_U24LE:
+ case MEDIA_FORMAT_PCM_U24BE:
+ *bit_depth = 24;
+ break;
+ case MEDIA_FORMAT_PCM_S32LE:
+ case MEDIA_FORMAT_PCM_F32LE:
+ case MEDIA_FORMAT_PCM_U32LE:
+ case MEDIA_FORMAT_PCM_S32BE:
+ case MEDIA_FORMAT_PCM_F32BE:
+ case MEDIA_FORMAT_PCM_U32BE:
+ *bit_depth = 32;
+ break;
+ deault:
+ LOGE("The format handle is not for PCM\n");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ return MEDIA_FORMAT_ERROR_NONE;
+}
+
+int media_format_channel_positions_from_mask(media_format_h fmt, uint64_t channel_mask, media_format_channel_position_e **position)
+{
+ MEDIA_FORMAT_INSTANCE_CHECK(fmt);
+ MEDIA_FORMAT_INSTANCE_CHECK(*position);
+
+ media_format_s *fmt_handle;
+ fmt_handle = (media_format_s *)fmt;
+
+ if (MEDIA_FORMAT_GET_REFCOUNT(fmt) <= 0) {
+ LOGE("The format ref_count is less than 0..\n");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ }
+
+ if (!channel_mask) {
+ if (fmt_handle->detail.audio.channel == 1) {
+ (*position)[0] = MEDIA_FORMAT_CHANNEL_POSITION_MONO;
+ } else if (fmt_handle->detail.audio.channel == 2) {
+ (*position)[0] = MEDIA_FORMAT_CHANNEL_POSITION_FRONT_LEFT;
+ (*position)[1] = MEDIA_FORMAT_CHANNEL_POSITION_FRONT_RIGHT;
+ } else {
+ goto no_channel_mask;
+ }
+ } else {
+ int i, j;
+
+ j = 0;
+ for (i = 0; i < 64; i++) {
+ if ((channel_mask & (G_GUINT64_CONSTANT(1) << i))) {
+ if (j < fmt_handle->detail.audio.channel)
+ (*position)[j] = default_channel_order[i];
+ j++;
+ }
+ }
+ if (j != fmt_handle->detail.audio.channel)
+ LOGE("Only partially valid channel mask 0x%016" G_GINT64_MODIFIER
+ "x for %d channels", channel_mask,
+ fmt_handle->detail.audio.channel);
+ }
+
+ return MEDIA_FORMAT_ERROR_NONE;
+
+/* ERROR */
+no_channel_mask:
+ LOGE("no channel-mask property given");
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+}
+
+int media_format_channel_positions_to_mask(media_format_h fmt, const media_format_channel_position_e* position, uint64_t* channel_mask_out)
+{
+ MEDIA_FORMAT_INSTANCE_CHECK(fmt);
+ MEDIA_FORMAT_INSTANCE_CHECK(position);
+
+ int i, j;
+ uint64_t channel_mask = 0;
+ media_format_s *fmt_handle;
+ fmt_handle = (media_format_s *)fmt;
+
+ if (!fmt_handle->detail.audio.channel)
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+
+ if (fmt_handle->detail.audio.channel == 1 && position[0] == MEDIA_FORMAT_CHANNEL_POSITION_MONO) {
+ if (channel_mask_out)
+ *channel_mask_out = 0;
+ return MEDIA_FORMAT_ERROR_NONE;
+ }
+
+ if (fmt_handle->detail.audio.channel > 0 && position[0] == MEDIA_FORMAT_CHANNEL_POSITION_NONE) {
+ if (channel_mask_out)
+ *channel_mask_out = 0;
+ return MEDIA_FORMAT_ERROR_NONE;
+ }
+
+ j = 0;
+ for (i = 0; i < fmt_handle->detail.audio.channel; i++) {
+ while (j < G_N_ELEMENTS(default_channel_order)
+ && default_channel_order[j] != position[i])
+ j++;
+
+ if (position[i] == MEDIA_FORMAT_CHANNEL_POSITION_INVALID ||
+ position[i] == MEDIA_FORMAT_CHANNEL_POSITION_MONO ||
+ position[i] == MEDIA_FORMAT_CHANNEL_POSITION_NONE)
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+
+ /* Is this in valid channel order? */
+ if (j == G_N_ELEMENTS(default_channel_order))
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+ j++;
+
+ if ((channel_mask & (G_GUINT64_CONSTANT(1) << position[i])))
+ return MEDIA_FORMAT_ERROR_INVALID_OPERATION;
+
+ channel_mask |= (G_GUINT64_CONSTANT(1) << position[i]);
+ }
+
+ if (channel_mask_out)
+ *channel_mask_out = channel_mask;
+
+ return MEDIA_FORMAT_ERROR_NONE;
+}