Utils.cpp revision faf35c0c279114b11a36615dc6630c126e767da0
120111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber/* 220111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * Copyright (C) 2009 The Android Open Source Project 320111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * 420111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 520111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * you may not use this file except in compliance with the License. 620111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * You may obtain a copy of the License at 720111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * 820111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * http://www.apache.org/licenses/LICENSE-2.0 920111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * 1020111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * Unless required by applicable law or agreed to in writing, software 1120111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 1220111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1320111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * See the License for the specific language governing permissions and 1420111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber * limitations under the License. 1520111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber */ 1620111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 179806555d3930be43e11106281dee354820ac1c88Andreas Huber//#define LOG_NDEBUG 0 189806555d3930be43e11106281dee354820ac1c88Andreas Huber#define LOG_TAG "Utils" 199806555d3930be43e11106281dee354820ac1c88Andreas Huber#include <utils/Log.h> 20a1df816c0677185534babba6ffc29970b048e52eLajos Molnar#include <ctype.h> 2183b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen#include <stdio.h> 2283b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen#include <sys/stat.h> 239806555d3930be43e11106281dee354820ac1c88Andreas Huber 249806555d3930be43e11106281dee354820ac1c88Andreas Huber#include "include/ESDS.h" 259aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim#include "include/HevcUtils.h" 269806555d3930be43e11106281dee354820ac1c88Andreas Huber 2720111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber#include <arpa/inet.h> 28cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber#include <cutils/properties.h> 292829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad#include <media/openmax/OMX_Audio.h> 30caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu#include <media/stagefright/CodecBase.h> 319806555d3930be43e11106281dee354820ac1c88Andreas Huber#include <media/stagefright/foundation/ABuffer.h> 329806555d3930be43e11106281dee354820ac1c88Andreas Huber#include <media/stagefright/foundation/ADebug.h> 339806555d3930be43e11106281dee354820ac1c88Andreas Huber#include <media/stagefright/foundation/AMessage.h> 349806555d3930be43e11106281dee354820ac1c88Andreas Huber#include <media/stagefright/MetaData.h> 3594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald#include <media/stagefright/MediaDefs.h> 3694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald#include <media/AudioSystem.h> 3794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald#include <media/MediaPlayerInterface.h> 3894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald#include <hardware/audio.h> 3920111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber#include <media/stagefright/Utils.h> 4094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald#include <media/AudioParameter.h> 4120111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 4220111aa043c5f404472bc63b90bc5aad906b1101Andreas Hubernamespace android { 4320111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 4420111aa043c5f404472bc63b90bc5aad906b1101Andreas Huberuint16_t U16_AT(const uint8_t *ptr) { 4520111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber return ptr[0] << 8 | ptr[1]; 4620111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber} 4720111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 4820111aa043c5f404472bc63b90bc5aad906b1101Andreas Huberuint32_t U32_AT(const uint8_t *ptr) { 4920111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber return ptr[0] << 24 | ptr[1] << 16 | ptr[2] << 8 | ptr[3]; 5020111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber} 5120111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 5220111aa043c5f404472bc63b90bc5aad906b1101Andreas Huberuint64_t U64_AT(const uint8_t *ptr) { 5320111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber return ((uint64_t)U32_AT(ptr)) << 32 | U32_AT(ptr + 4); 5420111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber} 5520111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 56ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huberuint16_t U16LE_AT(const uint8_t *ptr) { 57ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber return ptr[0] | (ptr[1] << 8); 58ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber} 59ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber 60ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huberuint32_t U32LE_AT(const uint8_t *ptr) { 61ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber return ptr[3] << 24 | ptr[2] << 16 | ptr[1] << 8 | ptr[0]; 62ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber} 63ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber 64ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huberuint64_t U64LE_AT(const uint8_t *ptr) { 65ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber return ((uint64_t)U32LE_AT(ptr + 4)) << 32 | U32LE_AT(ptr); 66ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber} 67ee7ff20e69498ebd53dd9717a0f984188341a75eAndreas Huber 6820111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber// XXX warning: these won't work on big-endian host. 6920111aa043c5f404472bc63b90bc5aad906b1101Andreas Huberuint64_t ntoh64(uint64_t x) { 7020111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber return ((uint64_t)ntohl(x & 0xffffffff) << 32) | ntohl(x >> 32); 7120111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber} 7220111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 7320111aa043c5f404472bc63b90bc5aad906b1101Andreas Huberuint64_t hton64(uint64_t x) { 7420111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber return ((uint64_t)htonl(x & 0xffffffff) << 32) | htonl(x >> 32); 7520111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber} 7620111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 779c170c076382096b9e767da0e3f9f37dafa76546Wei Jiastatic status_t copyNALUToABuffer(sp<ABuffer> *buffer, const uint8_t *ptr, size_t length) { 789c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (((*buffer)->size() + 4 + length) > ((*buffer)->capacity() - (*buffer)->offset())) { 799c170c076382096b9e767da0e3f9f37dafa76546Wei Jia sp<ABuffer> tmpBuffer = new (std::nothrow) ABuffer((*buffer)->size() + 4 + length + 1024); 809c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (tmpBuffer.get() == NULL || tmpBuffer->base() == NULL) { 819c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 829c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 839c170c076382096b9e767da0e3f9f37dafa76546Wei Jia memcpy(tmpBuffer->data(), (*buffer)->data(), (*buffer)->size()); 849c170c076382096b9e767da0e3f9f37dafa76546Wei Jia tmpBuffer->setRange(0, (*buffer)->size()); 859c170c076382096b9e767da0e3f9f37dafa76546Wei Jia (*buffer) = tmpBuffer; 869c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 879c170c076382096b9e767da0e3f9f37dafa76546Wei Jia 889c170c076382096b9e767da0e3f9f37dafa76546Wei Jia memcpy((*buffer)->data() + (*buffer)->size(), "\x00\x00\x00\x01", 4); 899c170c076382096b9e767da0e3f9f37dafa76546Wei Jia memcpy((*buffer)->data() + (*buffer)->size() + 4, ptr, length); 909c170c076382096b9e767da0e3f9f37dafa76546Wei Jia (*buffer)->setRange((*buffer)->offset(), (*buffer)->size() + 4 + length); 919c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return OK; 929c170c076382096b9e767da0e3f9f37dafa76546Wei Jia} 939c170c076382096b9e767da0e3f9f37dafa76546Wei Jia 94caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wustatic void convertMetaDataToMessageInt32( 95caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu const sp<MetaData> &meta, sp<AMessage> &msg, uint32_t key, const char *name) { 96caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t value; 97caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (meta->findInt32(key, &value)) { 98caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu msg->setInt32(name, value); 99caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 100caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu} 101caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 102caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wustatic void convertMetaDataToMessageColorAspects(const sp<MetaData> &meta, sp<AMessage> &msg) { 103caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu // 0 values are unspecified 104caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t range = 0; 105caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t primaries = 0; 106caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t transferFunction = 0; 107caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t colorMatrix = 0; 108caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->findInt32(kKeyColorRange, &range); 109caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->findInt32(kKeyColorPrimaries, &primaries); 110caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->findInt32(kKeyTransferFunction, &transferFunction); 111caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->findInt32(kKeyColorMatrix, &colorMatrix); 112caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu ColorAspects colorAspects; 113caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu memset(&colorAspects, 0, sizeof(colorAspects)); 114caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu colorAspects.mRange = (ColorAspects::Range)range; 115caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu colorAspects.mPrimaries = (ColorAspects::Primaries)primaries; 116caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu colorAspects.mTransfer = (ColorAspects::Transfer)transferFunction; 117caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu colorAspects.mMatrixCoeffs = (ColorAspects::MatrixCoeffs)colorMatrix; 118caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 119caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t rangeMsg, standardMsg, transferMsg; 120caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (CodecBase::convertCodecColorAspectsToPlatformAspects( 121caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu colorAspects, &rangeMsg, &standardMsg, &transferMsg) != OK) { 122caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu return; 123caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 124caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 125caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu // save specified values to msg 126caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (rangeMsg != 0) { 127caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu msg->setInt32("color-range", rangeMsg); 128caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 129caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (standardMsg != 0) { 130caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu msg->setInt32("color-standard", standardMsg); 131caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 132caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (transferMsg != 0) { 133caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu msg->setInt32("color-transfer", transferMsg); 134caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 135caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu} 136caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 1379806555d3930be43e11106281dee354820ac1c88Andreas Huberstatus_t convertMetaDataToMessage( 1389806555d3930be43e11106281dee354820ac1c88Andreas Huber const sp<MetaData> &meta, sp<AMessage> *format) { 13959e469e0b0d95bba2aee3bbda003b7042fd1cdd9Marco Nelissen 1409806555d3930be43e11106281dee354820ac1c88Andreas Huber format->clear(); 1419806555d3930be43e11106281dee354820ac1c88Andreas Huber 14259e469e0b0d95bba2aee3bbda003b7042fd1cdd9Marco Nelissen if (meta == NULL) { 14359e469e0b0d95bba2aee3bbda003b7042fd1cdd9Marco Nelissen ALOGE("convertMetaDataToMessage: NULL input"); 14459e469e0b0d95bba2aee3bbda003b7042fd1cdd9Marco Nelissen return BAD_VALUE; 14559e469e0b0d95bba2aee3bbda003b7042fd1cdd9Marco Nelissen } 14659e469e0b0d95bba2aee3bbda003b7042fd1cdd9Marco Nelissen 1479806555d3930be43e11106281dee354820ac1c88Andreas Huber const char *mime; 148f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih if (!meta->findCString(kKeyMIMEType, &mime)) { 149f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih return BAD_VALUE; 150f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih } 1519806555d3930be43e11106281dee354820ac1c88Andreas Huber 1529806555d3930be43e11106281dee354820ac1c88Andreas Huber sp<AMessage> msg = new AMessage; 1539806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setString("mime", mime); 1549806555d3930be43e11106281dee354820ac1c88Andreas Huber 1559806555d3930be43e11106281dee354820ac1c88Andreas Huber int64_t durationUs; 1569806555d3930be43e11106281dee354820ac1c88Andreas Huber if (meta->findInt64(kKeyDuration, &durationUs)) { 1579806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt64("durationUs", durationUs); 1589806555d3930be43e11106281dee354820ac1c88Andreas Huber } 1599806555d3930be43e11106281dee354820ac1c88Andreas Huber 160bc2fb720bbd0acd122bacc67e844e982d068f6f9Wei Jia int avgBitRate; 161bc2fb720bbd0acd122bacc67e844e982d068f6f9Wei Jia if (meta->findInt32(kKeyBitRate, &avgBitRate)) { 162bc2fb720bbd0acd122bacc67e844e982d068f6f9Wei Jia msg->setInt32("bit-rate", avgBitRate); 163bc2fb720bbd0acd122bacc67e844e982d068f6f9Wei Jia } 164bc2fb720bbd0acd122bacc67e844e982d068f6f9Wei Jia 1658c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen int32_t isSync; 1668c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen if (meta->findInt32(kKeyIsSyncFrame, &isSync) && isSync != 0) { 1678c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen msg->setInt32("is-sync-frame", 1); 1688c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen } 1698c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen 170faf35c0c279114b11a36615dc6630c126e767da0Lajos Molnar // this only needs to be translated from meta to message as it is an extractor key 171faf35c0c279114b11a36615dc6630c126e767da0Lajos Molnar int32_t trackID; 172faf35c0c279114b11a36615dc6630c126e767da0Lajos Molnar if (meta->findInt32(kKeyTrackID, &trackID)) { 173faf35c0c279114b11a36615dc6630c126e767da0Lajos Molnar msg->setInt32("track-id", trackID); 174faf35c0c279114b11a36615dc6630c126e767da0Lajos Molnar } 175faf35c0c279114b11a36615dc6630c126e767da0Lajos Molnar 1769806555d3930be43e11106281dee354820ac1c88Andreas Huber if (!strncasecmp("video/", mime, 6)) { 1779806555d3930be43e11106281dee354820ac1c88Andreas Huber int32_t width, height; 178f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih if (!meta->findInt32(kKeyWidth, &width) 179f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih || !meta->findInt32(kKeyHeight, &height)) { 180f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih return BAD_VALUE; 181f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih } 1829806555d3930be43e11106281dee354820ac1c88Andreas Huber 1839806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("width", width); 1849806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("height", height); 185516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber 186516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber int32_t sarWidth, sarHeight; 187516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber if (meta->findInt32(kKeySARWidth, &sarWidth) 188516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber && meta->findInt32(kKeySARHeight, &sarHeight)) { 189516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber msg->setInt32("sar-width", sarWidth); 190516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber msg->setInt32("sar-height", sarHeight); 191516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber } 192475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu 193475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu int32_t colorFormat; 194475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (meta->findInt32(kKeyColorFormat, &colorFormat)) { 195475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu msg->setInt32("color-format", colorFormat); 196475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu } 197475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu 198475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu int32_t cropLeft, cropTop, cropRight, cropBottom; 199475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (meta->findRect(kKeyCropRect, 200475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropLeft, 201475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropTop, 202475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropRight, 203475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropBottom)) { 204475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu msg->setRect("crop", cropLeft, cropTop, cropRight, cropBottom); 205475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu } 206475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu 207475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu int32_t rotationDegrees; 208475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (meta->findInt32(kKeyRotation, &rotationDegrees)) { 209475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu msg->setInt32("rotation-degrees", rotationDegrees); 210475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu } 211caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 212caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu convertMetaDataToMessageInt32(meta, msg, kKeyMinLuminance, "min-luminance"); 213caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu convertMetaDataToMessageInt32(meta, msg, kKeyMaxLuminance, "max-luminance"); 214caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu convertMetaDataToMessageColorAspects(meta, msg); 2159806555d3930be43e11106281dee354820ac1c88Andreas Huber } else if (!strncasecmp("audio/", mime, 6)) { 2169806555d3930be43e11106281dee354820ac1c88Andreas Huber int32_t numChannels, sampleRate; 217f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih if (!meta->findInt32(kKeyChannelCount, &numChannels) 218f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih || !meta->findInt32(kKeySampleRate, &sampleRate)) { 219f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih return BAD_VALUE; 220f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih } 2219806555d3930be43e11106281dee354820ac1c88Andreas Huber 2229806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("channel-count", numChannels); 2239806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("sample-rate", sampleRate); 2249806555d3930be43e11106281dee354820ac1c88Andreas Huber 2259806555d3930be43e11106281dee354820ac1c88Andreas Huber int32_t channelMask; 2269806555d3930be43e11106281dee354820ac1c88Andreas Huber if (meta->findInt32(kKeyChannelMask, &channelMask)) { 2279806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("channel-mask", channelMask); 2289806555d3930be43e11106281dee354820ac1c88Andreas Huber } 2299806555d3930be43e11106281dee354820ac1c88Andreas Huber 2309806555d3930be43e11106281dee354820ac1c88Andreas Huber int32_t delay = 0; 2319806555d3930be43e11106281dee354820ac1c88Andreas Huber if (meta->findInt32(kKeyEncoderDelay, &delay)) { 2329806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("encoder-delay", delay); 2339806555d3930be43e11106281dee354820ac1c88Andreas Huber } 2349806555d3930be43e11106281dee354820ac1c88Andreas Huber int32_t padding = 0; 2359806555d3930be43e11106281dee354820ac1c88Andreas Huber if (meta->findInt32(kKeyEncoderPadding, &padding)) { 2369806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("encoder-padding", padding); 2379806555d3930be43e11106281dee354820ac1c88Andreas Huber } 2389806555d3930be43e11106281dee354820ac1c88Andreas Huber 2399806555d3930be43e11106281dee354820ac1c88Andreas Huber int32_t isADTS; 2409806555d3930be43e11106281dee354820ac1c88Andreas Huber if (meta->findInt32(kKeyIsADTS, &isADTS)) { 2412954bca7bdec618da2b94a7e8ac62595b56598a3Pawin Vongmasa msg->setInt32("is-adts", isADTS); 2429806555d3930be43e11106281dee354820ac1c88Andreas Huber } 243ccad786f3497f223cbc5af981b08b460433ee622aarti jadhav-gaikwad 244ccad786f3497f223cbc5af981b08b460433ee622aarti jadhav-gaikwad int32_t aacProfile = -1; 245ccad786f3497f223cbc5af981b08b460433ee622aarti jadhav-gaikwad if (meta->findInt32(kKeyAACAOT, &aacProfile)) { 246ccad786f3497f223cbc5af981b08b460433ee622aarti jadhav-gaikwad msg->setInt32("aac-profile", aacProfile); 247ccad786f3497f223cbc5af981b08b460433ee622aarti jadhav-gaikwad } 24878bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar 24978bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar int32_t pcmEncoding; 25078bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar if (meta->findInt32(kKeyPcmEncoding, &pcmEncoding)) { 25178bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar msg->setInt32("pcm-encoding", pcmEncoding); 25278bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar } 2539806555d3930be43e11106281dee354820ac1c88Andreas Huber } 2549806555d3930be43e11106281dee354820ac1c88Andreas Huber 2559806555d3930be43e11106281dee354820ac1c88Andreas Huber int32_t maxInputSize; 2569806555d3930be43e11106281dee354820ac1c88Andreas Huber if (meta->findInt32(kKeyMaxInputSize, &maxInputSize)) { 2579806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setInt32("max-input-size", maxInputSize); 2589806555d3930be43e11106281dee354820ac1c88Andreas Huber } 2599806555d3930be43e11106281dee354820ac1c88Andreas Huber 260a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang int32_t maxWidth; 261a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang if (meta->findInt32(kKeyMaxWidth, &maxWidth)) { 262a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang msg->setInt32("max-width", maxWidth); 263a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang } 264a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang 265a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang int32_t maxHeight; 266a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang if (meta->findInt32(kKeyMaxHeight, &maxHeight)) { 267a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang msg->setInt32("max-height", maxHeight); 268a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang } 269a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang 270e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang int32_t rotationDegrees; 271e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang if (meta->findInt32(kKeyRotation, &rotationDegrees)) { 272e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang msg->setInt32("rotation-degrees", rotationDegrees); 273e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang } 274e9e63bcf6c36351f1129b0bdc5e93f17f0f9f0b4Chong Zhang 2758f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang int32_t fps; 2762a886d196ae717adc353a9fb4371b6a5abbd89a5Lajos Molnar if (meta->findInt32(kKeyFrameRate, &fps) && fps > 0) { 2778f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang msg->setInt32("frame-rate", fps); 2788f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang } 2798f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang 2809806555d3930be43e11106281dee354820ac1c88Andreas Huber uint32_t type; 2819806555d3930be43e11106281dee354820ac1c88Andreas Huber const void *data; 2829806555d3930be43e11106281dee354820ac1c88Andreas Huber size_t size; 2839806555d3930be43e11106281dee354820ac1c88Andreas Huber if (meta->findData(kKeyAVCC, &type, &data, &size)) { 2849806555d3930be43e11106281dee354820ac1c88Andreas Huber // Parse the AVCDecoderConfigurationRecord 2859806555d3930be43e11106281dee354820ac1c88Andreas Huber 2869806555d3930be43e11106281dee354820ac1c88Andreas Huber const uint8_t *ptr = (const uint8_t *)data; 2879806555d3930be43e11106281dee354820ac1c88Andreas Huber 2887bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia if (size < 7 || ptr[0] != 1) { // configurationVersion == 1 2897bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia ALOGE("b/23680780"); 2907bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia return BAD_VALUE; 2917bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia } 292b3f9759c8c9437c45b9a34519ce2ea38a8314d4eAndreas Gampe uint8_t profile __unused = ptr[1]; 293b3f9759c8c9437c45b9a34519ce2ea38a8314d4eAndreas Gampe uint8_t level __unused = ptr[3]; 2949806555d3930be43e11106281dee354820ac1c88Andreas Huber 2959806555d3930be43e11106281dee354820ac1c88Andreas Huber // There is decodable content out there that fails the following 2969806555d3930be43e11106281dee354820ac1c88Andreas Huber // assertion, let's be lenient for now... 2979806555d3930be43e11106281dee354820ac1c88Andreas Huber // CHECK((ptr[4] >> 2) == 0x3f); // reserved 2989806555d3930be43e11106281dee354820ac1c88Andreas Huber 299b3f9759c8c9437c45b9a34519ce2ea38a8314d4eAndreas Gampe size_t lengthSize __unused = 1 + (ptr[4] & 3); 3009806555d3930be43e11106281dee354820ac1c88Andreas Huber 3019806555d3930be43e11106281dee354820ac1c88Andreas Huber // commented out check below as H264_QVGA_500_NO_AUDIO.3gp 3029806555d3930be43e11106281dee354820ac1c88Andreas Huber // violates it... 3039806555d3930be43e11106281dee354820ac1c88Andreas Huber // CHECK((ptr[5] >> 5) == 7); // reserved 3049806555d3930be43e11106281dee354820ac1c88Andreas Huber 3059806555d3930be43e11106281dee354820ac1c88Andreas Huber size_t numSeqParameterSets = ptr[5] & 31; 3069806555d3930be43e11106281dee354820ac1c88Andreas Huber 3079806555d3930be43e11106281dee354820ac1c88Andreas Huber ptr += 6; 3089806555d3930be43e11106281dee354820ac1c88Andreas Huber size -= 6; 3099806555d3930be43e11106281dee354820ac1c88Andreas Huber 3109c170c076382096b9e767da0e3f9f37dafa76546Wei Jia sp<ABuffer> buffer = new (std::nothrow) ABuffer(1024); 3119c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 3129c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 3139c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 3149806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->setRange(0, 0); 3159806555d3930be43e11106281dee354820ac1c88Andreas Huber 3169806555d3930be43e11106281dee354820ac1c88Andreas Huber for (size_t i = 0; i < numSeqParameterSets; ++i) { 3177bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia if (size < 2) { 3187bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia ALOGE("b/23680780"); 3197bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia return BAD_VALUE; 3207bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia } 3219806555d3930be43e11106281dee354820ac1c88Andreas Huber size_t length = U16_AT(ptr); 3229806555d3930be43e11106281dee354820ac1c88Andreas Huber 3239806555d3930be43e11106281dee354820ac1c88Andreas Huber ptr += 2; 3249806555d3930be43e11106281dee354820ac1c88Andreas Huber size -= 2; 3259806555d3930be43e11106281dee354820ac1c88Andreas Huber 3269c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (size < length) { 3279c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return BAD_VALUE; 3289c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 3299c170c076382096b9e767da0e3f9f37dafa76546Wei Jia status_t err = copyNALUToABuffer(&buffer, ptr, length); 3309c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (err != OK) { 3319c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return err; 3329c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 3339806555d3930be43e11106281dee354820ac1c88Andreas Huber 3349806555d3930be43e11106281dee354820ac1c88Andreas Huber ptr += length; 3359806555d3930be43e11106281dee354820ac1c88Andreas Huber size -= length; 3369806555d3930be43e11106281dee354820ac1c88Andreas Huber } 3379806555d3930be43e11106281dee354820ac1c88Andreas Huber 3389806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt32("csd", true); 3399806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt64("timeUs", 0); 3409806555d3930be43e11106281dee354820ac1c88Andreas Huber 3419806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setBuffer("csd-0", buffer); 3429806555d3930be43e11106281dee354820ac1c88Andreas Huber 3439c170c076382096b9e767da0e3f9f37dafa76546Wei Jia buffer = new (std::nothrow) ABuffer(1024); 3449c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 3459c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 3469c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 3479806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->setRange(0, 0); 3489806555d3930be43e11106281dee354820ac1c88Andreas Huber 3497bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia if (size < 1) { 3507bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia ALOGE("b/23680780"); 3517bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia return BAD_VALUE; 3527bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia } 3539806555d3930be43e11106281dee354820ac1c88Andreas Huber size_t numPictureParameterSets = *ptr; 3549806555d3930be43e11106281dee354820ac1c88Andreas Huber ++ptr; 3559806555d3930be43e11106281dee354820ac1c88Andreas Huber --size; 3569806555d3930be43e11106281dee354820ac1c88Andreas Huber 3579806555d3930be43e11106281dee354820ac1c88Andreas Huber for (size_t i = 0; i < numPictureParameterSets; ++i) { 3587bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia if (size < 2) { 3597bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia ALOGE("b/23680780"); 3607bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia return BAD_VALUE; 3617bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia } 3629806555d3930be43e11106281dee354820ac1c88Andreas Huber size_t length = U16_AT(ptr); 3639806555d3930be43e11106281dee354820ac1c88Andreas Huber 3649806555d3930be43e11106281dee354820ac1c88Andreas Huber ptr += 2; 3659806555d3930be43e11106281dee354820ac1c88Andreas Huber size -= 2; 3669806555d3930be43e11106281dee354820ac1c88Andreas Huber 3679c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (size < length) { 3689c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return BAD_VALUE; 3699c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 3709c170c076382096b9e767da0e3f9f37dafa76546Wei Jia status_t err = copyNALUToABuffer(&buffer, ptr, length); 3719c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (err != OK) { 3729c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return err; 3739c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 3749806555d3930be43e11106281dee354820ac1c88Andreas Huber 3759806555d3930be43e11106281dee354820ac1c88Andreas Huber ptr += length; 3769806555d3930be43e11106281dee354820ac1c88Andreas Huber size -= length; 3779806555d3930be43e11106281dee354820ac1c88Andreas Huber } 3789806555d3930be43e11106281dee354820ac1c88Andreas Huber 3799806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt32("csd", true); 3809806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt64("timeUs", 0); 3819806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setBuffer("csd-1", buffer); 3823b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar } else if (meta->findData(kKeyHVCC, &type, &data, &size)) { 3833b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar const uint8_t *ptr = (const uint8_t *)data; 3843b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 3857bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia if (size < 23 || ptr[0] != 1) { // configurationVersion == 1 3867bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia ALOGE("b/23680780"); 3877bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia return BAD_VALUE; 3887bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia } 389b3f9759c8c9437c45b9a34519ce2ea38a8314d4eAndreas Gampe uint8_t profile __unused = ptr[1] & 31; 390b3f9759c8c9437c45b9a34519ce2ea38a8314d4eAndreas Gampe uint8_t level __unused = ptr[12]; 3913b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar ptr += 22; 3923b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size -= 22; 3933b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 3943b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 3953b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size_t numofArrays = (char)ptr[0]; 3963b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar ptr += 1; 3973b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size -= 1; 3983b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size_t j = 0, i = 0; 3993b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4009c170c076382096b9e767da0e3f9f37dafa76546Wei Jia sp<ABuffer> buffer = new (std::nothrow) ABuffer(1024); 4019c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 4029c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 4039c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 4043b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar buffer->setRange(0, 0); 4053b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4063b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar for (i = 0; i < numofArrays; i++) { 4077bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia if (size < 3) { 4087bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia ALOGE("b/23680780"); 4097bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia return BAD_VALUE; 4107bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia } 4113b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar ptr += 1; 4123b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size -= 1; 4133b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4143b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar //Num of nals 4153b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size_t numofNals = U16_AT(ptr); 4163b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4173b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar ptr += 2; 4183b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size -= 2; 4193b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4203b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar for (j = 0; j < numofNals; j++) { 4217bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia if (size < 2) { 4227bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia ALOGE("b/23680780"); 4237bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia return BAD_VALUE; 4247bb772e0c643ff3292599cf485b9dbf232bf39a4Wei Jia } 4253b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size_t length = U16_AT(ptr); 4263b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4273b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar ptr += 2; 4283b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size -= 2; 4293b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4309c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (size < length) { 4319c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return BAD_VALUE; 4329c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 4339c170c076382096b9e767da0e3f9f37dafa76546Wei Jia status_t err = copyNALUToABuffer(&buffer, ptr, length); 4349c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (err != OK) { 4359c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return err; 4369c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 4373b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4383b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar ptr += length; 4393b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar size -= length; 4403b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar } 4413b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar } 4423b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar buffer->meta()->setInt32("csd", true); 4433b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar buffer->meta()->setInt64("timeUs", 0); 4443b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar msg->setBuffer("csd-0", buffer); 4453b5a6b9fa6c6825a1d0b441429e2bb365b259827Harish Mahendrakar 4469806555d3930be43e11106281dee354820ac1c88Andreas Huber } else if (meta->findData(kKeyESDS, &type, &data, &size)) { 4479806555d3930be43e11106281dee354820ac1c88Andreas Huber ESDS esds((const char *)data, size); 448f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih if (esds.InitCheck() != (status_t)OK) { 449f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih return BAD_VALUE; 450f4101f746a4a2c407a220dd61860a2b742eade51Robert Shih } 4519806555d3930be43e11106281dee354820ac1c88Andreas Huber 4529806555d3930be43e11106281dee354820ac1c88Andreas Huber const void *codec_specific_data; 4539806555d3930be43e11106281dee354820ac1c88Andreas Huber size_t codec_specific_data_size; 4549806555d3930be43e11106281dee354820ac1c88Andreas Huber esds.getCodecSpecificInfo( 4559806555d3930be43e11106281dee354820ac1c88Andreas Huber &codec_specific_data, &codec_specific_data_size); 4569806555d3930be43e11106281dee354820ac1c88Andreas Huber 4579c170c076382096b9e767da0e3f9f37dafa76546Wei Jia sp<ABuffer> buffer = new (std::nothrow) ABuffer(codec_specific_data_size); 4589c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 4599c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 4609c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 4619806555d3930be43e11106281dee354820ac1c88Andreas Huber 4629806555d3930be43e11106281dee354820ac1c88Andreas Huber memcpy(buffer->data(), codec_specific_data, 4639806555d3930be43e11106281dee354820ac1c88Andreas Huber codec_specific_data_size); 4649806555d3930be43e11106281dee354820ac1c88Andreas Huber 4659806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt32("csd", true); 4669806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt64("timeUs", 0); 4679806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setBuffer("csd-0", buffer); 4689806555d3930be43e11106281dee354820ac1c88Andreas Huber } else if (meta->findData(kKeyVorbisInfo, &type, &data, &size)) { 4699c170c076382096b9e767da0e3f9f37dafa76546Wei Jia sp<ABuffer> buffer = new (std::nothrow) ABuffer(size); 4709c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 4719c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 4729c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 4739806555d3930be43e11106281dee354820ac1c88Andreas Huber memcpy(buffer->data(), data, size); 4749806555d3930be43e11106281dee354820ac1c88Andreas Huber 4759806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt32("csd", true); 4769806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt64("timeUs", 0); 4779806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setBuffer("csd-0", buffer); 4789806555d3930be43e11106281dee354820ac1c88Andreas Huber 4799806555d3930be43e11106281dee354820ac1c88Andreas Huber if (!meta->findData(kKeyVorbisBooks, &type, &data, &size)) { 4809806555d3930be43e11106281dee354820ac1c88Andreas Huber return -EINVAL; 4819806555d3930be43e11106281dee354820ac1c88Andreas Huber } 4829806555d3930be43e11106281dee354820ac1c88Andreas Huber 4839c170c076382096b9e767da0e3f9f37dafa76546Wei Jia buffer = new (std::nothrow) ABuffer(size); 4849c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 4859c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 4869c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 4879806555d3930be43e11106281dee354820ac1c88Andreas Huber memcpy(buffer->data(), data, size); 4889806555d3930be43e11106281dee354820ac1c88Andreas Huber 4899806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt32("csd", true); 4909806555d3930be43e11106281dee354820ac1c88Andreas Huber buffer->meta()->setInt64("timeUs", 0); 4919806555d3930be43e11106281dee354820ac1c88Andreas Huber msg->setBuffer("csd-1", buffer); 492bf927f8ec7979f2b64331c2b2f12a6a5dba05bcaVignesh Venkatasubramanian } else if (meta->findData(kKeyOpusHeader, &type, &data, &size)) { 4939c170c076382096b9e767da0e3f9f37dafa76546Wei Jia sp<ABuffer> buffer = new (std::nothrow) ABuffer(size); 4949c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 4959c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 4969c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 497bf927f8ec7979f2b64331c2b2f12a6a5dba05bcaVignesh Venkatasubramanian memcpy(buffer->data(), data, size); 498bf927f8ec7979f2b64331c2b2f12a6a5dba05bcaVignesh Venkatasubramanian 499bf927f8ec7979f2b64331c2b2f12a6a5dba05bcaVignesh Venkatasubramanian buffer->meta()->setInt32("csd", true); 500bf927f8ec7979f2b64331c2b2f12a6a5dba05bcaVignesh Venkatasubramanian buffer->meta()->setInt64("timeUs", 0); 501bf927f8ec7979f2b64331c2b2f12a6a5dba05bcaVignesh Venkatasubramanian msg->setBuffer("csd-0", buffer); 5029b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian 5039b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian if (!meta->findData(kKeyOpusCodecDelay, &type, &data, &size)) { 5049b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian return -EINVAL; 5059b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian } 5069b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian 5079c170c076382096b9e767da0e3f9f37dafa76546Wei Jia buffer = new (std::nothrow) ABuffer(size); 5089c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 5099c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 5109c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 5119b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian memcpy(buffer->data(), data, size); 5129b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian 5139b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian buffer->meta()->setInt32("csd", true); 5149b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian buffer->meta()->setInt64("timeUs", 0); 5159b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian msg->setBuffer("csd-1", buffer); 5169b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian 5179b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian if (!meta->findData(kKeyOpusSeekPreRoll, &type, &data, &size)) { 5189b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian return -EINVAL; 5199b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian } 5209b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian 5219c170c076382096b9e767da0e3f9f37dafa76546Wei Jia buffer = new (std::nothrow) ABuffer(size); 5229c170c076382096b9e767da0e3f9f37dafa76546Wei Jia if (buffer.get() == NULL || buffer->base() == NULL) { 5239c170c076382096b9e767da0e3f9f37dafa76546Wei Jia return NO_MEMORY; 5249c170c076382096b9e767da0e3f9f37dafa76546Wei Jia } 5259b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian memcpy(buffer->data(), data, size); 5269b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian 5279b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian buffer->meta()->setInt32("csd", true); 5289b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian buffer->meta()->setInt64("timeUs", 0); 5299b4b24a46f3f76ebb186df8bc01c58848af02108Vignesh Venkatasubramanian msg->setBuffer("csd-2", buffer); 5309806555d3930be43e11106281dee354820ac1c88Andreas Huber } 5319806555d3930be43e11106281dee354820ac1c88Andreas Huber 532793c9fb11114c7be4636b8cae5477995aadeb71dRobert Shih // TODO expose "crypto-key"/kKeyCryptoKey through public api 533793c9fb11114c7be4636b8cae5477995aadeb71dRobert Shih if (meta->findData(kKeyCryptoKey, &type, &data, &size)) { 534793c9fb11114c7be4636b8cae5477995aadeb71dRobert Shih sp<ABuffer> buffer = new (std::nothrow) ABuffer(size); 535793c9fb11114c7be4636b8cae5477995aadeb71dRobert Shih msg->setBuffer("crypto-key", buffer); 536793c9fb11114c7be4636b8cae5477995aadeb71dRobert Shih memcpy(buffer->data(), data, size); 537793c9fb11114c7be4636b8cae5477995aadeb71dRobert Shih } 538793c9fb11114c7be4636b8cae5477995aadeb71dRobert Shih 5399806555d3930be43e11106281dee354820ac1c88Andreas Huber *format = msg; 5409806555d3930be43e11106281dee354820ac1c88Andreas Huber 5419806555d3930be43e11106281dee354820ac1c88Andreas Huber return OK; 5429806555d3930be43e11106281dee354820ac1c88Andreas Huber} 5439806555d3930be43e11106281dee354820ac1c88Andreas Huber 54456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissenstatic size_t reassembleAVCC(const sp<ABuffer> &csd0, const sp<ABuffer> csd1, char *avcc) { 54556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 54656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[0] = 1; // version 54756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[1] = 0x64; // profile 54856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[2] = 0; // unused (?) 54956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[3] = 0xd; // level 55056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[4] = 0xff; // reserved+size 55156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 55256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen size_t i = 0; 55356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int numparams = 0; 55456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int lastparamoffset = 0; 55556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int avccidx = 6; 55656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen do { 55756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (i >= csd0->size() - 4 || 55856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen memcmp(csd0->data() + i, "\x00\x00\x00\x01", 4) == 0) { 55956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (i >= csd0->size() - 4) { 56056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen // there can't be another param here, so use all the rest 56156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen i = csd0->size(); 56256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 563a5750e0dad9e90f2195ce36f2c4457fa04b2b83eMark Salyzyn ALOGV("block at %zu, last was %d", i, lastparamoffset); 56456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (lastparamoffset > 0) { 56556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int size = i - lastparamoffset; 56656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[avccidx++] = size >> 8; 56756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[avccidx++] = size & 0xff; 56856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen memcpy(avcc+avccidx, csd0->data() + lastparamoffset, size); 56956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avccidx += size; 57056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen numparams++; 57156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 57256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen i += 4; 57356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen lastparamoffset = i; 57456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } else { 57556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen i++; 57656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 57756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } while(i < csd0->size()); 57856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen ALOGV("csd0 contains %d params", numparams); 57956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 58056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[5] = 0xe0 | numparams; 58156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen //and now csd-1 58256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen i = 0; 58356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen numparams = 0; 58456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen lastparamoffset = 0; 58556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int numpicparamsoffset = avccidx; 58656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avccidx++; 58756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen do { 58856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (i >= csd1->size() - 4 || 58956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen memcmp(csd1->data() + i, "\x00\x00\x00\x01", 4) == 0) { 59056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (i >= csd1->size() - 4) { 59156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen // there can't be another param here, so use all the rest 59256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen i = csd1->size(); 59356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 594a5750e0dad9e90f2195ce36f2c4457fa04b2b83eMark Salyzyn ALOGV("block at %zu, last was %d", i, lastparamoffset); 59556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (lastparamoffset > 0) { 59656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int size = i - lastparamoffset; 59756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[avccidx++] = size >> 8; 59856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[avccidx++] = size & 0xff; 59956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen memcpy(avcc+avccidx, csd1->data() + lastparamoffset, size); 60056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avccidx += size; 60156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen numparams++; 60256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 60356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen i += 4; 60456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen lastparamoffset = i; 60556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } else { 60656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen i++; 60756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 60856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } while(i < csd1->size()); 60956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen avcc[numpicparamsoffset] = numparams; 61056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen return avccidx; 61156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen} 61256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 61356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissenstatic void reassembleESDS(const sp<ABuffer> &csd0, char *esds) { 61456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int csd0size = csd0->size(); 61556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[0] = 3; // kTag_ESDescriptor; 61656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int esdescriptorsize = 26 + csd0size; 61756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen CHECK(esdescriptorsize < 268435456); // 7 bits per byte, so max is 2^28-1 61856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[1] = 0x80 | (esdescriptorsize >> 21); 61956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[2] = 0x80 | ((esdescriptorsize >> 14) & 0x7f); 62056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[3] = 0x80 | ((esdescriptorsize >> 7) & 0x7f); 62156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[4] = (esdescriptorsize & 0x7f); 62256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[5] = esds[6] = 0; // es id 62356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[7] = 0; // flags 62456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[8] = 4; // kTag_DecoderConfigDescriptor 62556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int configdescriptorsize = 18 + csd0size; 62656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[9] = 0x80 | (configdescriptorsize >> 21); 62756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[10] = 0x80 | ((configdescriptorsize >> 14) & 0x7f); 62856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[11] = 0x80 | ((configdescriptorsize >> 7) & 0x7f); 62956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[12] = (configdescriptorsize & 0x7f); 63056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[13] = 0x40; // objectTypeIndication 63156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[14] = 0x15; // not sure what 14-25 mean, they are ignored by ESDS.cpp, 63256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[15] = 0x00; // but the actual values here were taken from a real file. 63356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[16] = 0x18; 63456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[17] = 0x00; 63556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[18] = 0x00; 63656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[19] = 0x00; 63756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[20] = 0xfa; 63856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[21] = 0x00; 63956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[22] = 0x00; 64056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[23] = 0x00; 64156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[24] = 0xfa; 64256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[25] = 0x00; 64356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[26] = 5; // kTag_DecoderSpecificInfo; 64456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[27] = 0x80 | (csd0size >> 21); 64556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[28] = 0x80 | ((csd0size >> 14) & 0x7f); 64656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[29] = 0x80 | ((csd0size >> 7) & 0x7f); 64756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen esds[30] = (csd0size & 0x7f); 64856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen memcpy((void*)&esds[31], csd0->data(), csd0size); 64956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen // data following this is ignored, so don't bother appending it 65056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 65156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen} 65256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 6539aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kimstatic size_t reassembleHVCC(const sp<ABuffer> &csd0, uint8_t *hvcc, size_t hvccSize, size_t nalSizeLength) { 6549aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim HevcParameterSets paramSets; 6559aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim uint8_t* data = csd0->data(); 6569aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim if (csd0->size() < 4) { 6579aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim ALOGE("csd0 too small"); 6589aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim return 0; 6599aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } 6609aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim if (memcmp(data, "\x00\x00\x00\x01", 4) != 0) { 6619aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim ALOGE("csd0 doesn't start with a start code"); 6629aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim return 0; 6639aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } 6649aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim size_t prevNalOffset = 4; 6659aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim status_t err = OK; 6669aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim for (size_t i = 1; i < csd0->size() - 4; ++i) { 6679aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim if (memcmp(&data[i], "\x00\x00\x00\x01", 4) != 0) { 6689aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim continue; 6699aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } 6709aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim err = paramSets.addNalUnit(&data[prevNalOffset], i - prevNalOffset); 6719aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim if (err != OK) { 6729aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim return 0; 6739aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } 6749aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim prevNalOffset = i + 4; 6759aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } 6769aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim err = paramSets.addNalUnit(&data[prevNalOffset], csd0->size() - prevNalOffset); 6779aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim if (err != OK) { 6789aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim return 0; 6799aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } 6809aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim size_t size = hvccSize; 6819aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim err = paramSets.makeHvcc(hvcc, &size, nalSizeLength); 6829aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim if (err != OK) { 6839aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim return 0; 6849aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } 6859aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim return size; 6869aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim} 6879aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim 688caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wustatic void convertMessageToMetaDataInt32( 689caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu const sp<AMessage> &msg, sp<MetaData> &meta, uint32_t key, const char *name) { 690caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t value; 691caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (msg->findInt32(name, &value)) { 692caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->setInt32(key, value); 693caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 694caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu} 695caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 696caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wustatic void convertMessageToMetaDataColorAspects(const sp<AMessage> &msg, sp<MetaData> &meta) { 697caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu // 0 values are unspecified 698caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu int32_t range = 0, standard = 0, transfer = 0; 699caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu (void)msg->findInt32("color-range", &range); 700caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu (void)msg->findInt32("color-standard", &standard); 701caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu (void)msg->findInt32("color-transfer", &transfer); 702caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 703caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu ColorAspects colorAspects; 704caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu memset(&colorAspects, 0, sizeof(colorAspects)); 705caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (CodecBase::convertPlatformColorAspectsToCodecAspects( 706caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu range, standard, transfer, colorAspects) != OK) { 707caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu return; 708caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 709caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 710caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu // save specified values to meta 711caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (colorAspects.mRange != 0) { 712caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->setInt32(kKeyColorRange, colorAspects.mRange); 713caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 714caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (colorAspects.mPrimaries != 0) { 715caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->setInt32(kKeyColorPrimaries, colorAspects.mPrimaries); 716caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 717caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (colorAspects.mTransfer != 0) { 718caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->setInt32(kKeyTransferFunction, colorAspects.mTransfer); 719caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 720caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu if (colorAspects.mMatrixCoeffs != 0) { 721caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu meta->setInt32(kKeyColorMatrix, colorAspects.mMatrixCoeffs); 722caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu } 723caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu} 724caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 72556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissenvoid convertMessageToMetaData(const sp<AMessage> &msg, sp<MetaData> &meta) { 72656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen AString mime; 72756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findString("mime", &mime)) { 72856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setCString(kKeyMIMEType, mime.c_str()); 72956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } else { 73056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen ALOGW("did not find mime type"); 73156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 73256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 73356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int64_t durationUs; 73456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt64("durationUs", &durationUs)) { 73556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt64(kKeyDuration, durationUs); 73656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 73756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 7388c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen int32_t isSync; 7398c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen if (msg->findInt32("is-sync-frame", &isSync) && isSync != 0) { 7408c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen meta->setInt32(kKeyIsSyncFrame, 1); 7418c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen } 7428c95fa91fff6e8726df03598d52243f22e5ff8e7Marco Nelissen 74356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (mime.startsWith("video/")) { 74456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t width; 74556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t height; 74656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("width", &width) && msg->findInt32("height", &height)) { 74756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyWidth, width); 74856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyHeight, height); 74956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } else { 75056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen ALOGW("did not find width and/or height"); 75156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 752516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber 753516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber int32_t sarWidth, sarHeight; 754516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber if (msg->findInt32("sar-width", &sarWidth) 755516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber && msg->findInt32("sar-height", &sarHeight)) { 756516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber meta->setInt32(kKeySARWidth, sarWidth); 757516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber meta->setInt32(kKeySARHeight, sarHeight); 758516dacfb02d0b0eafe21114330c98ce0e7d90da9Andreas Huber } 759475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu 760475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu int32_t colorFormat; 761475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (msg->findInt32("color-format", &colorFormat)) { 762475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu meta->setInt32(kKeyColorFormat, colorFormat); 763475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu } 764475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu 765475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu int32_t cropLeft, cropTop, cropRight, cropBottom; 766475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (msg->findRect("crop", 767475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropLeft, 768475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropTop, 769475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropRight, 770475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu &cropBottom)) { 771475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu meta->setRect(kKeyCropRect, cropLeft, cropTop, cropRight, cropBottom); 772475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu } 773475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu 774475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu int32_t rotationDegrees; 775475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu if (msg->findInt32("rotation-degrees", &rotationDegrees)) { 776475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu meta->setInt32(kKeyRotation, rotationDegrees); 777475da7ef08c05a482ced8d318832cf5aa1141affRonghua Wu } 778caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu 779caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu convertMessageToMetaDataInt32(msg, meta, kKeyMinLuminance, "min-luminance"); 780caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu convertMessageToMetaDataInt32(msg, meta, kKeyMaxLuminance, "max-luminance"); 781caaa15b1c8ca1632100cf8e64e82007239210339Ronghua Wu convertMessageToMetaDataColorAspects(msg, meta); 78256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } else if (mime.startsWith("audio/")) { 78356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t numChannels; 78456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("channel-count", &numChannels)) { 78556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyChannelCount, numChannels); 78656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 78756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t sampleRate; 78856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("sample-rate", &sampleRate)) { 78956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeySampleRate, sampleRate); 79056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 79156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t channelMask; 79256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("channel-mask", &channelMask)) { 79356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyChannelMask, channelMask); 79456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 79556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t delay = 0; 79656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("encoder-delay", &delay)) { 79756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyEncoderDelay, delay); 79856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 79956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t padding = 0; 80056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("encoder-padding", &padding)) { 80156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyEncoderPadding, padding); 80256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 80356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 80456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t isADTS; 80556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("is-adts", &isADTS)) { 80656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyIsADTS, isADTS); 80756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 80878bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar 80978bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar int32_t pcmEncoding; 81078bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar if (msg->findInt32("pcm-encoding", &pcmEncoding)) { 81178bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar meta->setInt32(kKeyPcmEncoding, pcmEncoding); 81278bd91b15ee8ea5aa2ab5a8cad7e892cb2d01c1bLajos Molnar } 81356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 81456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 81556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int32_t maxInputSize; 81656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findInt32("max-input-size", &maxInputSize)) { 81756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setInt32(kKeyMaxInputSize, maxInputSize); 81856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 81956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 820a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang int32_t maxWidth; 821a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang if (msg->findInt32("max-width", &maxWidth)) { 822a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang meta->setInt32(kKeyMaxWidth, maxWidth); 823a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang } 824a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang 825a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang int32_t maxHeight; 826a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang if (msg->findInt32("max-height", &maxHeight)) { 827a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang meta->setInt32(kKeyMaxHeight, maxHeight); 828a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang } 829a0d0ba51ad60a68117a0ee78e37ab78715b8a069Chong Zhang 8308f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang int32_t fps; 8312a886d196ae717adc353a9fb4371b6a5abbd89a5Lajos Molnar if (msg->findInt32("frame-rate", &fps) && fps > 0) { 8328f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang meta->setInt32(kKeyFrameRate, fps); 8338f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang } 8348f5919da04fb6aa7eb7cff70b061d8702627436cChong Zhang 83556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen // reassemble the csd data into its original form 83656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen sp<ABuffer> csd0; 83756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findBuffer("csd-0", &csd0)) { 83877f101b342b6d206b6f530991f3333dfedeebab6Martin Storsjo if (mime == MEDIA_MIMETYPE_VIDEO_AVC) { 83956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen sp<ABuffer> csd1; 84056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen if (msg->findBuffer("csd-1", &csd1)) { 84156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen char avcc[1024]; // that oughta be enough, right? 84256997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen size_t outsize = reassembleAVCC(csd0, csd1, avcc); 84356997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setData(kKeyAVCC, kKeyAVCC, avcc, outsize); 84456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 84577f101b342b6d206b6f530991f3333dfedeebab6Martin Storsjo } else if (mime == MEDIA_MIMETYPE_AUDIO_AAC || mime == MEDIA_MIMETYPE_VIDEO_MPEG4) { 84656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen int csd0size = csd0->size(); 84756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen char esds[csd0size + 31]; 84877f101b342b6d206b6f530991f3333dfedeebab6Martin Storsjo // The written ESDS is actually for an audio stream, but it's enough 84977f101b342b6d206b6f530991f3333dfedeebab6Martin Storsjo // for transporting the CSD to muxers. 85056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen reassembleESDS(csd0, esds); 85156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->setData(kKeyESDS, kKeyESDS, esds, sizeof(esds)); 8529aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim } else if (mime == MEDIA_MIMETYPE_VIDEO_HEVC) { 8539aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim uint8_t hvcc[1024]; // that oughta be enough, right? 8549aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim size_t outsize = reassembleHVCC(csd0, hvcc, 1024, 4); 8559aa87d4ef502c9700a31fe46dc6e1d6f99cf4e5eWonsik Kim meta->setData(kKeyHVCC, kKeyHVCC, hvcc, outsize); 85656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 85756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen } 85856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 8592c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang int32_t timeScale; 8602c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang if (msg->findInt32("time-scale", &timeScale)) { 8612c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang meta->setInt32(kKeyTimeScale, timeScale); 8622c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang } 8632c9c8cba8562cc3a27532e4cd348912cc78d8d98Chong Zhang 86456997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen // XXX TODO add whatever other keys there are 86556997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 86656997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen#if 0 86756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen ALOGI("converted %s to:", msg->debugString(0).c_str()); 86856997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen meta->dumpToLog(); 86956997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen#endif 87056997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen} 87156997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 872cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas HuberAString MakeUserAgent() { 873cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber AString ua; 874cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber ua.append("stagefright/1.2 (Linux;Android "); 875cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber 876cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber#if (PROPERTY_VALUE_MAX < 8) 877cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber#error "PROPERTY_VALUE_MAX must be at least 8" 878cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber#endif 879cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber 880cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber char value[PROPERTY_VALUE_MAX]; 881cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber property_get("ro.build.version.release", value, "Unknown"); 882cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber ua.append(value); 883cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber ua.append(")"); 884cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber 885cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber return ua; 886cd77d4a1d38b7609a03f6826a1ff5fa7c98aa34fAndreas Huber} 88756997121c5031598fbbba7b7c53980b7fd529c2dMarco Nelissen 888ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgeraldstatus_t sendMetaDataToHal(sp<MediaPlayerBase::AudioSink>& sink, 889ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald const sp<MetaData>& meta) 890ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald{ 89194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t sampleRate = 0; 89294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t bitRate = 0; 89394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t channelMask = 0; 89494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t delaySamples = 0; 89594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t paddingSamples = 0; 89694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 89794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald AudioParameter param = AudioParameter(); 89894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 89994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (meta->findInt32(kKeySampleRate, &sampleRate)) { 90094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald param.addInt(String8(AUDIO_OFFLOAD_CODEC_SAMPLE_RATE), sampleRate); 90194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 90294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (meta->findInt32(kKeyChannelMask, &channelMask)) { 90394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald param.addInt(String8(AUDIO_OFFLOAD_CODEC_NUM_CHANNEL), channelMask); 90494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 90594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (meta->findInt32(kKeyBitRate, &bitRate)) { 90694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald param.addInt(String8(AUDIO_OFFLOAD_CODEC_AVG_BIT_RATE), bitRate); 90794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 90894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (meta->findInt32(kKeyEncoderDelay, &delaySamples)) { 90994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald param.addInt(String8(AUDIO_OFFLOAD_CODEC_DELAY_SAMPLES), delaySamples); 91094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 91194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (meta->findInt32(kKeyEncoderPadding, &paddingSamples)) { 91294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald param.addInt(String8(AUDIO_OFFLOAD_CODEC_PADDING_SAMPLES), paddingSamples); 91394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 91494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 91594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGV("sendMetaDataToHal: bitRate %d, sampleRate %d, chanMask %d," 91694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald "delaySample %d, paddingSample %d", bitRate, sampleRate, 91794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald channelMask, delaySamples, paddingSamples); 91894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 91994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald sink->setParameters(param.toString()); 920ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald return OK; 921ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald} 922ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald 92394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgeraldstruct mime_conv_t { 92494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald const char* mime; 92594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald audio_format_t format; 92694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald}; 92794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 92894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgeraldstatic const struct mime_conv_t mimeLookup[] = { 92994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald { MEDIA_MIMETYPE_AUDIO_MPEG, AUDIO_FORMAT_MP3 }, 93094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald { MEDIA_MIMETYPE_AUDIO_RAW, AUDIO_FORMAT_PCM_16_BIT }, 93194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald { MEDIA_MIMETYPE_AUDIO_AMR_NB, AUDIO_FORMAT_AMR_NB }, 93294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald { MEDIA_MIMETYPE_AUDIO_AMR_WB, AUDIO_FORMAT_AMR_WB }, 93394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald { MEDIA_MIMETYPE_AUDIO_AAC, AUDIO_FORMAT_AAC }, 93494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald { MEDIA_MIMETYPE_AUDIO_VORBIS, AUDIO_FORMAT_VORBIS }, 935bf927f8ec7979f2b64331c2b2f12a6a5dba05bcaVignesh Venkatasubramanian { MEDIA_MIMETYPE_AUDIO_OPUS, AUDIO_FORMAT_OPUS}, 93694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald { 0, AUDIO_FORMAT_INVALID } 93794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald}; 93894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 93994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgeraldstatus_t mapMimeToAudioFormat( audio_format_t& format, const char* mime ) 940ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald{ 94194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgeraldconst struct mime_conv_t* p = &mimeLookup[0]; 94294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald while (p->mime != NULL) { 94394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (0 == strcasecmp(mime, p->mime)) { 94494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald format = p->format; 94594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald return OK; 94694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 94794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ++p; 94894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 94994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 950ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald return BAD_VALUE; 951ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald} 952ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald 9532829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwadstruct aac_format_conv_t { 9542829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad OMX_AUDIO_AACPROFILETYPE eAacProfileType; 9552829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad audio_format_t format; 9562829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad}; 9572829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad 9582829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwadstatic const struct aac_format_conv_t profileLookup[] = { 9592829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectMain, AUDIO_FORMAT_AAC_MAIN}, 9602829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectLC, AUDIO_FORMAT_AAC_LC}, 9612829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectSSR, AUDIO_FORMAT_AAC_SSR}, 9622829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectLTP, AUDIO_FORMAT_AAC_LTP}, 9632829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectHE, AUDIO_FORMAT_AAC_HE_V1}, 9642829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectScalable, AUDIO_FORMAT_AAC_SCALABLE}, 9652829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectERLC, AUDIO_FORMAT_AAC_ERLC}, 9662829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectLD, AUDIO_FORMAT_AAC_LD}, 9672829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectHE_PS, AUDIO_FORMAT_AAC_HE_V2}, 9682829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectELD, AUDIO_FORMAT_AAC_ELD}, 9692829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad { OMX_AUDIO_AACObjectNull, AUDIO_FORMAT_AAC}, 9702829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad}; 9712829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad 9722829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwadvoid mapAACProfileToAudioFormat( audio_format_t& format, uint64_t eAacProfile) 9732829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad{ 9742829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwadconst struct aac_format_conv_t* p = &profileLookup[0]; 9752829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad while (p->eAacProfileType != OMX_AUDIO_AACObjectNull) { 9762829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad if (eAacProfile == p->eAacProfileType) { 9772829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad format = p->format; 9782829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad return; 9792829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad } 9802829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad ++p; 9812829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad } 9822829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad format = AUDIO_FORMAT_AAC; 9832829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad return; 9842829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad} 9852829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad 98622612345ae97648d5b6db43cc1aa30aad77f7bbaEric Laurentbool canOffloadStream(const sp<MetaData>& meta, bool hasVideo, 98722612345ae97648d5b6db43cc1aa30aad77f7bbaEric Laurent bool isStreaming, audio_stream_type_t streamType) 988ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald{ 98994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald const char *mime; 990cd249c40c51584e89e065bf7d51999b04db2eb57Wei Jia if (meta == NULL) { 991cd249c40c51584e89e065bf7d51999b04db2eb57Wei Jia return false; 992cd249c40c51584e89e065bf7d51999b04db2eb57Wei Jia } 99394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald CHECK(meta->findCString(kKeyMIMEType, &mime)); 99494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 99594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald audio_offload_info_t info = AUDIO_INFO_INITIALIZER; 99694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 99794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald info.format = AUDIO_FORMAT_INVALID; 99894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (mapMimeToAudioFormat(info.format, mime) != OK) { 99994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGE(" Couldn't map mime type \"%s\" to a valid AudioSystem::audio_format !", mime); 100094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald return false; 100194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } else { 100294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGV("Mime type \"%s\" mapped to audio_format %d", mime, info.format); 100394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 100494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 100594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (AUDIO_FORMAT_INVALID == info.format) { 100694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald // can't offload if we don't know what the source format is 100794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGE("mime type \"%s\" not a known audio format", mime); 100894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald return false; 100994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 101094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 10112829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad // Redefine aac format according to its profile 10122829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad // Offloading depends on audio DSP capabilities. 1013db170bb1cae145d07efc803a3c208963de0c6087Eric Laurent int32_t aacaot = -1; 1014db170bb1cae145d07efc803a3c208963de0c6087Eric Laurent if (meta->findInt32(kKeyAACAOT, &aacaot)) { 10152829edccd7d2bb8244246f316face82b650b8949aarti jadhav-gaikwad mapAACProfileToAudioFormat(info.format,(OMX_AUDIO_AACPROFILETYPE) aacaot); 1016db170bb1cae145d07efc803a3c208963de0c6087Eric Laurent } 1017db170bb1cae145d07efc803a3c208963de0c6087Eric Laurent 101894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t srate = -1; 101994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (!meta->findInt32(kKeySampleRate, &srate)) { 102094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGV("track of type '%s' does not publish sample rate", mime); 102194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 102294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald info.sample_rate = srate; 102394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 102494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t cmask = 0; 102594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (!meta->findInt32(kKeyChannelMask, &cmask)) { 102694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGV("track of type '%s' does not publish channel mask", mime); 102794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 102894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald // Try a channel count instead 102994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t channelCount; 103094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (!meta->findInt32(kKeyChannelCount, &channelCount)) { 103194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGV("track of type '%s' does not publish channel count", mime); 103294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } else { 103394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald cmask = audio_channel_out_mask_from_count(channelCount); 103494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 103594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 103694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald info.channel_mask = cmask; 103794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 103894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int64_t duration = 0; 103994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (!meta->findInt64(kKeyDuration, &duration)) { 104094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGV("track of type '%s' does not publish duration", mime); 104194ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 104294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald info.duration_us = duration; 104394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 104494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald int32_t brate = -1; 104594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald if (!meta->findInt32(kKeyBitRate, &brate)) { 104694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald ALOGV("track of type '%s' does not publish bitrate", mime); 104794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald } 104894ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald info.bit_rate = brate; 104994ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 105094ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 105122612345ae97648d5b6db43cc1aa30aad77f7bbaEric Laurent info.stream_type = streamType; 105294ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald info.has_video = hasVideo; 105394ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald info.is_streaming = isStreaming; 105494ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald 105594ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald // Check if offload is possible for given format, stream type, sample rate, 105694ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald // bit rate, duration, video and streaming 105794ea60f975c3eb7ce6d2a4430538a42a5fc3babdRichard Fitzgerald return AudioSystem::isOffloadSupported(info); 1058ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald} 1059ad3af3305f024bcbbd55c894a4995e449498e1baRichard Fitzgerald 1060a1df816c0677185534babba6ffc29970b048e52eLajos MolnarAString uriDebugString(const AString &uri, bool incognito) { 1061a1df816c0677185534babba6ffc29970b048e52eLajos Molnar if (incognito) { 1062a1df816c0677185534babba6ffc29970b048e52eLajos Molnar return AString("<URI suppressed>"); 1063a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } 1064a1df816c0677185534babba6ffc29970b048e52eLajos Molnar 1065a1df816c0677185534babba6ffc29970b048e52eLajos Molnar char prop[PROPERTY_VALUE_MAX]; 1066a1df816c0677185534babba6ffc29970b048e52eLajos Molnar if (property_get("media.stagefright.log-uri", prop, "false") && 1067a1df816c0677185534babba6ffc29970b048e52eLajos Molnar (!strcmp(prop, "1") || !strcmp(prop, "true"))) { 1068a1df816c0677185534babba6ffc29970b048e52eLajos Molnar return uri; 1069a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } 1070a1df816c0677185534babba6ffc29970b048e52eLajos Molnar 1071a1df816c0677185534babba6ffc29970b048e52eLajos Molnar // find scheme 1072a1df816c0677185534babba6ffc29970b048e52eLajos Molnar AString scheme; 1073a1df816c0677185534babba6ffc29970b048e52eLajos Molnar const char *chars = uri.c_str(); 1074a1df816c0677185534babba6ffc29970b048e52eLajos Molnar for (size_t i = 0; i < uri.size(); i++) { 1075a1df816c0677185534babba6ffc29970b048e52eLajos Molnar const char c = chars[i]; 1076a1df816c0677185534babba6ffc29970b048e52eLajos Molnar if (!isascii(c)) { 1077a1df816c0677185534babba6ffc29970b048e52eLajos Molnar break; 1078a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } else if (isalpha(c)) { 1079a1df816c0677185534babba6ffc29970b048e52eLajos Molnar continue; 1080a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } else if (i == 0) { 1081a1df816c0677185534babba6ffc29970b048e52eLajos Molnar // first character must be a letter 1082a1df816c0677185534babba6ffc29970b048e52eLajos Molnar break; 1083a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } else if (isdigit(c) || c == '+' || c == '.' || c =='-') { 1084a1df816c0677185534babba6ffc29970b048e52eLajos Molnar continue; 1085a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } else if (c != ':') { 1086a1df816c0677185534babba6ffc29970b048e52eLajos Molnar break; 1087a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } 1088a1df816c0677185534babba6ffc29970b048e52eLajos Molnar scheme = AString(uri, 0, i); 1089a1df816c0677185534babba6ffc29970b048e52eLajos Molnar scheme.append("://<suppressed>"); 1090a1df816c0677185534babba6ffc29970b048e52eLajos Molnar return scheme; 1091a1df816c0677185534babba6ffc29970b048e52eLajos Molnar } 1092a1df816c0677185534babba6ffc29970b048e52eLajos Molnar return AString("<no-scheme URI suppressed>"); 1093a1df816c0677185534babba6ffc29970b048e52eLajos Molnar} 1094a1df816c0677185534babba6ffc29970b048e52eLajos Molnar 1095d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong ZhangHLSTime::HLSTime(const sp<AMessage>& meta) : 1096d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang mSeq(-1), 1097d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang mTimeUs(-1ll), 1098d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang mMeta(meta) { 1099d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang if (meta != NULL) { 1100d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang CHECK(meta->findInt32("discontinuitySeq", &mSeq)); 1101d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang CHECK(meta->findInt64("timeUs", &mTimeUs)); 1102d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang } 1103d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang} 1104d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang 1105978449984366946a2e5c9f7cf350746f4306caf8Chong Zhangint64_t HLSTime::getSegmentTimeUs() const { 1106d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang int64_t segmentStartTimeUs = -1ll; 1107d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang if (mMeta != NULL) { 1108d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang CHECK(mMeta->findInt64("segmentStartTimeUs", &segmentStartTimeUs)); 1109978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang 1110978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang int64_t segmentFirstTimeUs; 1111978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang if (mMeta->findInt64("segmentFirstTimeUs", &segmentFirstTimeUs)) { 1112978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang segmentStartTimeUs += mTimeUs - segmentFirstTimeUs; 1113978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang } 1114978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang 1115978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang // adjust segment time by playlist age (for live streaming) 1116978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang int64_t playlistTimeUs; 1117978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang if (mMeta->findInt64("playlistTimeUs", &playlistTimeUs)) { 1118978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang int64_t playlistAgeUs = ALooper::GetNowUs() - playlistTimeUs; 1119978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang 1120d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang int64_t durationUs; 1121d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang CHECK(mMeta->findInt64("segmentDurationUs", &durationUs)); 1122978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang 1123978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang // round to nearest whole segment 1124978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang playlistAgeUs = (playlistAgeUs + durationUs / 2) 1125978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang / durationUs * durationUs; 1126978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang 1127978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang segmentStartTimeUs -= playlistAgeUs; 1128978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang if (segmentStartTimeUs < 0) { 1129978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang segmentStartTimeUs = 0; 1130978449984366946a2e5c9f7cf350746f4306caf8Chong Zhang } 1131d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang } 1132d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang } 1133d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang return segmentStartTimeUs; 1134d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang} 1135d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang 1136d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhangbool operator <(const HLSTime &t0, const HLSTime &t1) { 1137d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang // we can only compare discontinuity sequence and timestamp. 1138d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang // (mSegmentTimeUs is not reliable in live streaming case, it's the 1139d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang // time starting from beginning of playlist but playlist could change.) 1140d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang return t0.mSeq < t1.mSeq 1141d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang || (t0.mSeq == t1.mSeq && t0.mTimeUs < t1.mTimeUs); 1142d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang} 1143d47dfcb5a2e5901c96fc92662cec7aa30f7f8843Chong Zhang 11443a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarvoid writeToAMessage(sp<AMessage> msg, const AudioPlaybackRate &rate) { 11453a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setFloat("speed", rate.mSpeed); 11463a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setFloat("pitch", rate.mPitch); 11473a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setInt32("audio-fallback-mode", rate.mFallbackMode); 11483a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setInt32("audio-stretch-mode", rate.mStretchMode); 11493a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar} 11503a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar 11513a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarvoid readFromAMessage(const sp<AMessage> &msg, AudioPlaybackRate *rate /* nonnull */) { 11523a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar *rate = AUDIO_PLAYBACK_RATE_DEFAULT; 11533a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findFloat("speed", &rate->mSpeed)); 11543a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findFloat("pitch", &rate->mPitch)); 11553a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findInt32("audio-fallback-mode", (int32_t *)&rate->mFallbackMode)); 11563a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findInt32("audio-stretch-mode", (int32_t *)&rate->mStretchMode)); 11573a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar} 11583a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar 11593a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarvoid writeToAMessage(sp<AMessage> msg, const AVSyncSettings &sync, float videoFpsHint) { 11603a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setInt32("sync-source", sync.mSource); 11613a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setInt32("audio-adjust-mode", sync.mAudioAdjustMode); 11623a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setFloat("tolerance", sync.mTolerance); 11633a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar msg->setFloat("video-fps", videoFpsHint); 11643a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar} 11653a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar 11663a474aa67fc31505740526dd249d96204c08bf79Lajos Molnarvoid readFromAMessage( 11673a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar const sp<AMessage> &msg, 11683a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar AVSyncSettings *sync /* nonnull */, 11693a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar float *videoFps /* nonnull */) { 11703a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar AVSyncSettings settings; 11713a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findInt32("sync-source", (int32_t *)&settings.mSource)); 11723a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findInt32("audio-adjust-mode", (int32_t *)&settings.mAudioAdjustMode)); 11733a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findFloat("tolerance", &settings.mTolerance)); 11743a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar CHECK(msg->findFloat("video-fps", videoFps)); 11753a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar *sync = settings; 11763a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar} 11773a474aa67fc31505740526dd249d96204c08bf79Lajos Molnar 117883b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco NelissenAString nameForFd(int fd) { 117983b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen const size_t SIZE = 256; 118083b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen char buffer[SIZE]; 118183b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen AString result; 118283b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen snprintf(buffer, SIZE, "/proc/%d/fd/%d", getpid(), fd); 118383b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen struct stat s; 118483b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen if (lstat(buffer, &s) == 0) { 118583b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen if ((s.st_mode & S_IFMT) == S_IFLNK) { 118683b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen char linkto[256]; 118783b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen int len = readlink(buffer, linkto, sizeof(linkto)); 118883b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen if(len > 0) { 118983b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen if(len > 255) { 119083b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen linkto[252] = '.'; 119183b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen linkto[253] = '.'; 119283b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen linkto[254] = '.'; 119383b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen linkto[255] = 0; 119483b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen } else { 119583b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen linkto[len] = 0; 119683b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen } 119783b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen result.append(linkto); 119883b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen } 119983b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen } else { 120083b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen result.append("unexpected type for "); 120183b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen result.append(buffer); 120283b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen } 120383b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen } else { 120483b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen result.append("couldn't open "); 120583b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen result.append(buffer); 120683b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen } 120783b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen return result; 120883b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen} 120983b0fd9997b558f6c2ebf5e6e4db20570cb233b8Marco Nelissen 121020111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber} // namespace android 121120111aa043c5f404472bc63b90bc5aad906b1101Andreas Huber 1212