MP3Extractor.cpp revision 57515f334bcc1f66f95e342bfcaa13bf9ca802ad
1e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber/* 2e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * Copyright (C) 2009 The Android Open Source Project 3e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * 4e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * Licensed under the Apache License, Version 2.0 (the "License"); 5e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * you may not use this file except in compliance with the License. 6e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * You may obtain a copy of the License at 7e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * 8e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * http://www.apache.org/licenses/LICENSE-2.0 9e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * 10e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * Unless required by applicable law or agreed to in writing, software 11e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * distributed under the License is distributed on an "AS IS" BASIS, 12e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * See the License for the specific language governing permissions and 14e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber * limitations under the License. 15e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber */ 16e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 17e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber//#define LOG_NDEBUG 0 18e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#define LOG_TAG "MP3Extractor" 19e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <utils/Log.h> 20e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2157515f334bcc1f66f95e342bfcaa13bf9ca802adAndreas Huber#include "include/MP3Extractor.h" 2257515f334bcc1f66f95e342bfcaa13bf9ca802adAndreas Huber 23e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <media/stagefright/DataSource.h> 24e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <media/stagefright/MediaBuffer.h> 25e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <media/stagefright/MediaBufferGroup.h> 26b5ceb9ee21f37ae0817c16490c1fc148dd3eb5e2Andreas Huber#include <media/stagefright/MediaDebug.h> 27e6c409632f773e41f33188272a0072be9fcb783fAndreas Huber#include <media/stagefright/MediaDefs.h> 28e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <media/stagefright/MediaErrors.h> 29e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <media/stagefright/MediaSource.h> 30e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <media/stagefright/MetaData.h> 31e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <media/stagefright/Utils.h> 32e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber#include <utils/String8.h> 33e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 34e46b7be812d68e49710b34048662cbf18e2a6550Andreas Hubernamespace android { 35e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 36e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberstatic bool get_mp3_frame_size( 37e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber uint32_t header, size_t *frame_size, 38e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int *out_sampling_rate = NULL, int *out_channels = NULL, 39e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int *out_bitrate = NULL) { 40e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *frame_size = 0; 41e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 42e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_sampling_rate) { 43e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_sampling_rate = 0; 44e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 45e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 46e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_channels) { 47e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_channels = 0; 48e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 49e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 50e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_bitrate) { 51e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_bitrate = 0; 52e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 53e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 54e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if ((header & 0xffe00000) != 0xffe00000) { 55e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return false; 56e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 57e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 58e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber unsigned version = (header >> 19) & 3; 59e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 60e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (version == 0x01) { 61e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return false; 62e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 63e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 64e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber unsigned layer = (header >> 17) & 3; 65e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 66e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (layer == 0x00) { 67e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return false; 68e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 69e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 70e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber unsigned protection = (header >> 16) & 1; 71e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 72e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber unsigned bitrate_index = (header >> 12) & 0x0f; 73e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 74e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (bitrate_index == 0 || bitrate_index == 0x0f) { 75e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // Disallow "free" bitrate. 76e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return false; 77e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 78e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 79e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber unsigned sampling_rate_index = (header >> 10) & 3; 80e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 81e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (sampling_rate_index == 3) { 82e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return false; 83e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 84e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 85e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber static const int kSamplingRateV1[] = { 44100, 48000, 32000 }; 86e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int sampling_rate = kSamplingRateV1[sampling_rate_index]; 87e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (version == 2 /* V2 */) { 88e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber sampling_rate /= 2; 89e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } else if (version == 0 /* V2.5 */) { 90e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber sampling_rate /= 4; 91e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 92e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 93e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber unsigned padding = (header >> 9) & 1; 94e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 95e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (layer == 3) { 96e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // layer I 97e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 98e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber static const int kBitrateV1[] = { 99e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 32, 64, 96, 128, 160, 192, 224, 256, 100e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 288, 320, 352, 384, 416, 448 101e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber }; 102e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 103e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber static const int kBitrateV2[] = { 104e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 32, 48, 56, 64, 80, 96, 112, 128, 105e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 144, 160, 176, 192, 224, 256 106e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber }; 107e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 108e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int bitrate = 109e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber (version == 3 /* V1 */) 110e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber ? kBitrateV1[bitrate_index - 1] 111e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber : kBitrateV2[bitrate_index - 1]; 112e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 113e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_bitrate) { 114e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_bitrate = bitrate; 115e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 116e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 117e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *frame_size = (12000 * bitrate / sampling_rate + padding) * 4; 118e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } else { 119e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // layer II or III 120e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 121e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber static const int kBitrateV1L2[] = { 122e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 32, 48, 56, 64, 80, 96, 112, 128, 123e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 160, 192, 224, 256, 320, 384 124e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber }; 125e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 126e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber static const int kBitrateV1L3[] = { 127e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 32, 40, 48, 56, 64, 80, 96, 112, 128e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 128, 160, 192, 224, 256, 320 129e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber }; 130e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 131e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber static const int kBitrateV2[] = { 132e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 8, 16, 24, 32, 40, 48, 56, 64, 133e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 80, 96, 112, 128, 144, 160 134e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber }; 135e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 136e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int bitrate; 137e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (version == 3 /* V1 */) { 138e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber bitrate = (layer == 2 /* L2 */) 139e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber ? kBitrateV1L2[bitrate_index - 1] 140e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber : kBitrateV1L3[bitrate_index - 1]; 141e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } else { 142e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // V2 (or 2.5) 143e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 144e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber bitrate = kBitrateV2[bitrate_index - 1]; 145e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 146e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 147e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_bitrate) { 148e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_bitrate = bitrate; 149e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 150e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 15163f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber if (version == 3 /* V1 */) { 15263f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber *frame_size = 144000 * bitrate / sampling_rate + padding; 15363f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber } else { 15463f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber // V2 or V2.5 15563f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber *frame_size = 72000 * bitrate / sampling_rate + padding; 15663f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber } 157e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 158e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 159e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_sampling_rate) { 160e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_sampling_rate = sampling_rate; 161e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 162e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 163e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_channels) { 164e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int channel_mode = (header >> 6) & 3; 165e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 166e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_channels = (channel_mode == 3) ? 1 : 2; 167e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 168e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 169e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return true; 170e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 171e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 172e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberstatic bool Resync( 173be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber const sp<DataSource> &source, uint32_t match_header, 174e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t *inout_pos, uint32_t *out_header) { 17563f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber if (*inout_pos == 0) { 17663f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber // Skip an optional ID3 header if syncing at the very beginning 17763f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber // of the datasource. 17863f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber 17963f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber uint8_t id3header[10]; 18063f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber if (source->read_at(0, id3header, sizeof(id3header)) 18163f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber < (ssize_t)sizeof(id3header)) { 18263f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber // If we can't even read these 10 bytes, we might as well bail out, 18363f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber // even if there _were_ 10 bytes of valid mp3 audio data... 18463f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber return false; 18563f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber } 18663f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber 18763f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber if (id3header[0] == 'I' && id3header[1] == 'D' && id3header[2] == '3') { 18863f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber // Skip the ID3v2 header. 18963f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber 19063f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber size_t len = 19163f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber ((id3header[6] & 0x7f) << 21) 19263f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber | ((id3header[7] & 0x7f) << 14) 19363f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber | ((id3header[8] & 0x7f) << 7) 19463f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber | (id3header[9] & 0x7f); 19563f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber 19663f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber len += 10; 19763f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber 19863f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber *inout_pos += len; 19963f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber } 20063f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber } 20163f20ec1a8d31c85261056c6c171140b93bcde0aAndreas Huber 202e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // Everything must match except for 203e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // protection, bitrate, padding, private bits and mode extension. 204e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber const uint32_t kMask = 0xfffe0ccf; 205e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 206e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber const size_t kMaxFrameSize = 4096; 207e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber uint8_t *buffer = new uint8_t[kMaxFrameSize]; 208e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2092e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber off_t pos = *inout_pos - kMaxFrameSize; 210e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber size_t buffer_offset = kMaxFrameSize; 211e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber size_t buffer_length = kMaxFrameSize; 212e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber bool valid = false; 213e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber do { 214e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (buffer_offset + 3 >= buffer_length) { 215e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (buffer_length < kMaxFrameSize) { 216e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber break; 217e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 218e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2192e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber pos += buffer_offset; 220e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 221e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (pos >= *inout_pos + 128 * 1024) { 222e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // Don't scan forever. 223e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber LOGV("giving up at offset %ld", pos); 224e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber break; 225e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 226e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 227e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber memmove(buffer, &buffer[buffer_offset], buffer_length - buffer_offset); 228e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer_length = buffer_length - buffer_offset; 229e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer_offset = 0; 230e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 231e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber ssize_t n = source->read_at( 232e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber pos, &buffer[buffer_length], kMaxFrameSize - buffer_length); 233e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 234e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (n <= 0) { 235e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber break; 236e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 237e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 238e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer_length += (size_t)n; 239e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 240e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber continue; 241e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 242e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 243e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber uint32_t header = U32_AT(&buffer[buffer_offset]); 244e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 245e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (match_header != 0 && (header & kMask) != (match_header & kMask)) { 246e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber ++buffer_offset; 247e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber continue; 248e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 249e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 250e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber size_t frame_size; 251e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int sample_rate, num_channels, bitrate; 2522e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber if (!get_mp3_frame_size(header, &frame_size, 253e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber &sample_rate, &num_channels, &bitrate)) { 2542e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber ++buffer_offset; 2552e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber continue; 2562e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber } 257e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2582e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber LOGV("found possible 1st frame at %ld", pos + buffer_offset); 259e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2602e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber // We found what looks like a valid frame, 2612e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber // now find its successors. 262e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2632e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber off_t test_pos = pos + buffer_offset + frame_size; 264e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2652e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber valid = true; 2662e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber for (int j = 0; j < 3; ++j) { 2672e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber uint8_t tmp[4]; 2682e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber if (source->read_at(test_pos, tmp, 4) < 4) { 2692e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber valid = false; 2702e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber break; 2712e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber } 2722e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber 2732e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber uint32_t test_header = U32_AT(tmp); 274e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2752e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber LOGV("subsequent header is %08x", test_header); 276e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2772e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber if ((test_header & kMask) != (header & kMask)) { 2782e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber valid = false; 2792e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber break; 2802e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber } 281e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 2822e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber size_t test_frame_size; 2832e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber if (!get_mp3_frame_size(test_header, &test_frame_size)) { 2842e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber valid = false; 2852e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber break; 286e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 2872e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber 2882e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber LOGV("found subsequent frame #%d at %ld", j + 2, test_pos); 2892e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber 2902e337a4e4b5d36228619d426255f7aa500b5b4acAndreas Huber test_pos += test_frame_size; 291e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 292e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 293e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (valid) { 294e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *inout_pos = pos + buffer_offset; 295e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 296e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (out_header != NULL) { 297e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out_header = header; 298e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 299e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } else { 300e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber LOGV("no dice, no valid sequence of frames found."); 301e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 302e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 303e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber ++buffer_offset; 304e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 305e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } while (!valid); 306e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 307e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber delete[] buffer; 308e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer = NULL; 309e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 310e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return valid; 311e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 312e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 313e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberclass MP3Source : public MediaSource { 314e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberpublic: 315e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber MP3Source( 316be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber const sp<MetaData> &meta, const sp<DataSource> &source, 317e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t first_frame_pos, uint32_t fixed_header); 318e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 319e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber virtual status_t start(MetaData *params = NULL); 320e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber virtual status_t stop(); 321e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 322e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber virtual sp<MetaData> getFormat(); 323e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 324e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber virtual status_t read( 325e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber MediaBuffer **buffer, const ReadOptions *options = NULL); 326e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 327be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huberprotected: 328be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber virtual ~MP3Source(); 329be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber 330e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberprivate: 331e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber sp<MetaData> mMeta; 332be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber sp<DataSource> mDataSource; 333e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t mFirstFramePos; 334e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber uint32_t mFixedHeader; 335e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t mCurrentPos; 336e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int64_t mCurrentTimeUs; 337e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber bool mStarted; 338e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 339e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber MediaBufferGroup *mGroup; 340e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 341e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber MP3Source(const MP3Source &); 342e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber MP3Source &operator=(const MP3Source &); 343e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber}; 344e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 345be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas HuberMP3Extractor::MP3Extractor(const sp<DataSource> &source) 346e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber : mDataSource(source), 347e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mFirstFramePos(-1), 348e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mFixedHeader(0) { 349e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t pos = 0; 350e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber uint32_t header; 351e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber bool success = Resync(mDataSource, 0, &pos, &header); 352b5ceb9ee21f37ae0817c16490c1fc148dd3eb5e2Andreas Huber CHECK(success); 353e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 354e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (success) { 355e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mFirstFramePos = pos; 356e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mFixedHeader = header; 357e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 358e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber size_t frame_size; 359e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int sample_rate; 360e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int num_channels; 361e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int bitrate; 362e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber get_mp3_frame_size( 363e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber header, &frame_size, &sample_rate, &num_channels, &bitrate); 364e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 365e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mMeta = new MetaData; 366e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 367e6c409632f773e41f33188272a0072be9fcb783fAndreas Huber mMeta->setCString(kKeyMIMEType, MEDIA_MIMETYPE_AUDIO_MPEG); 368e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mMeta->setInt32(kKeySampleRate, sample_rate); 369e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mMeta->setInt32(kKeyBitRate, bitrate); 370e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mMeta->setInt32(kKeyChannelCount, num_channels); 371e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 372e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t fileSize; 373e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (mDataSource->getSize(&fileSize) == OK) { 374fa8de752507feaca695123911915070c1ce463b2Andreas Huber mMeta->setInt64( 375e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber kKeyDuration, 376fa8de752507feaca695123911915070c1ce463b2Andreas Huber 8000 * (fileSize - mFirstFramePos) / bitrate); 377e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 378e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 379e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 380e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 381e46b7be812d68e49710b34048662cbf18e2a6550Andreas HuberMP3Extractor::~MP3Extractor() { 382e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 383e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 384be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Hubersize_t MP3Extractor::countTracks() { 385be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber return (mFirstFramePos < 0) ? 0 : 1; 386e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 387e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 388be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Hubersp<MediaSource> MP3Extractor::getTrack(size_t index) { 389e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (mFirstFramePos < 0 || index != 0) { 390be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber return NULL; 391e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 392e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 393be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber return new MP3Source( 394e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mMeta, mDataSource, mFirstFramePos, mFixedHeader); 395e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 396e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 397e981c33446a98d5ccc0d73c1a840696d77cf0732Andreas Hubersp<MetaData> MP3Extractor::getTrackMetaData(size_t index, uint32_t flags) { 398e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (mFirstFramePos < 0 || index != 0) { 399e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return NULL; 400e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 401e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 402e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return mMeta; 403e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 404e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 405e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber//////////////////////////////////////////////////////////////////////////////// 406e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 407e46b7be812d68e49710b34048662cbf18e2a6550Andreas HuberMP3Source::MP3Source( 408be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber const sp<MetaData> &meta, const sp<DataSource> &source, 409e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t first_frame_pos, uint32_t fixed_header) 410e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber : mMeta(meta), 411e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mDataSource(source), 412e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mFirstFramePos(first_frame_pos), 413e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mFixedHeader(fixed_header), 414e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentPos(0), 415e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentTimeUs(0), 416e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mStarted(false), 417e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mGroup(NULL) { 418e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 419e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 420e46b7be812d68e49710b34048662cbf18e2a6550Andreas HuberMP3Source::~MP3Source() { 421e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (mStarted) { 422e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber stop(); 423e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 424e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 425e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 426e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberstatus_t MP3Source::start(MetaData *) { 427b5ceb9ee21f37ae0817c16490c1fc148dd3eb5e2Andreas Huber CHECK(!mStarted); 428e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 429e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mGroup = new MediaBufferGroup; 430e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 431e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber const size_t kMaxFrameSize = 32768; 432e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mGroup->add_buffer(new MediaBuffer(kMaxFrameSize)); 433e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 434e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentPos = mFirstFramePos; 435e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentTimeUs = 0; 436e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 437e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mStarted = true; 438e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 439e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return OK; 440e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 441e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 442e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberstatus_t MP3Source::stop() { 443b5ceb9ee21f37ae0817c16490c1fc148dd3eb5e2Andreas Huber CHECK(mStarted); 444e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 445e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber delete mGroup; 446e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mGroup = NULL; 447e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 448e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mStarted = false; 449e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 450e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return OK; 451e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 452e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 453e46b7be812d68e49710b34048662cbf18e2a6550Andreas Hubersp<MetaData> MP3Source::getFormat() { 454e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return mMeta; 455e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 456e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 457e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huberstatus_t MP3Source::read( 458e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber MediaBuffer **out, const ReadOptions *options) { 459e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out = NULL; 460e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 461e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int64_t seekTimeUs; 462e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (options != NULL && options->getSeekTo(&seekTimeUs)) { 463e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber int32_t bitrate; 464e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (!mMeta->findInt32(kKeyBitRate, &bitrate)) { 465e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // bitrate is in kbits/sec. 466e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber LOGI("no bitrate"); 467e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 468e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return ERROR_UNSUPPORTED; 469e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 470e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 471e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentTimeUs = seekTimeUs; 472e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentPos = mFirstFramePos + seekTimeUs * bitrate / 1000000 * 125; 473e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 474e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 475e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber MediaBuffer *buffer; 476e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber status_t err = mGroup->acquire_buffer(&buffer); 477e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (err != OK) { 478e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return err; 479e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 480e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 481e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber size_t frame_size; 482e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber for (;;) { 483e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber ssize_t n = mDataSource->read_at(mCurrentPos, buffer->data(), 4); 484e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (n < 4) { 485e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer->release(); 486e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer = NULL; 487e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 488e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return ERROR_END_OF_STREAM; 489e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 490e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 491e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber uint32_t header = U32_AT((const uint8_t *)buffer->data()); 492e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 493e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (get_mp3_frame_size(header, &frame_size)) { 494e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber break; 495e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 496e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 497e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // Lost sync. 498e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber LOGW("lost sync!\n"); 499e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 500e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t pos = mCurrentPos; 501e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (!Resync(mDataSource, mFixedHeader, &pos, NULL)) { 502e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber LOGE("Unable to resync. Signalling end of stream."); 503e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 504e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer->release(); 505e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer = NULL; 506e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 507e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return ERROR_END_OF_STREAM; 508e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 509e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 510e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentPos = pos; 511e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 512e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber // Try again with the new position. 513e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 514e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 515b5ceb9ee21f37ae0817c16490c1fc148dd3eb5e2Andreas Huber CHECK(frame_size <= buffer->size()); 516e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 517e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber ssize_t n = mDataSource->read_at(mCurrentPos, buffer->data(), frame_size); 518e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (n < (ssize_t)frame_size) { 519e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer->release(); 520e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer = NULL; 521e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 522e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return ERROR_END_OF_STREAM; 523e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 524e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 525e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber buffer->set_range(0, frame_size); 526e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 527fa8de752507feaca695123911915070c1ce463b2Andreas Huber buffer->meta_data()->setInt64(kKeyTime, mCurrentTimeUs); 528e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 529e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentPos += frame_size; 530e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber mCurrentTimeUs += 1152 * 1000000 / 44100; 531e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 532e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *out = buffer; 533e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 534e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return OK; 535e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 536e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 537be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huberbool SniffMP3( 538be06d26cdc70070654f1eedcd08c1c68cd587ad6Andreas Huber const sp<DataSource> &source, String8 *mimeType, float *confidence) { 539e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber off_t pos = 0; 540e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber uint32_t header; 541e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber if (!Resync(source, 0, &pos, &header)) { 542e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return false; 543e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber } 544e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 545e6c409632f773e41f33188272a0072be9fcb783fAndreas Huber *mimeType = MEDIA_MIMETYPE_AUDIO_MPEG; 546e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber *confidence = 0.3f; 547e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 548e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber return true; 549e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} 550e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber 551e46b7be812d68e49710b34048662cbf18e2a6550Andreas Huber} // namespace android 552