Search in sources :

Example 51 with ParsableByteArray

use of com.google.android.exoplayer2.util.ParsableByteArray in project ExoPlayer by google.

the class XingSeekerTest method setUp.

@Override
public void setUp() throws Exception {
    MpegAudioHeader xingFrameHeader = new MpegAudioHeader();
    MpegAudioHeader.populateHeader(XING_FRAME_HEADER_DATA, xingFrameHeader);
    seeker = XingSeeker.create(xingFrameHeader, new ParsableByteArray(XING_FRAME_PAYLOAD), XING_FRAME_POSITION, C.LENGTH_UNSET);
    seekerWithInputLength = XingSeeker.create(xingFrameHeader, new ParsableByteArray(XING_FRAME_PAYLOAD), XING_FRAME_POSITION, INPUT_LENGTH);
    xingFrameSize = xingFrameHeader.frameSize;
}
Also used : ParsableByteArray(com.google.android.exoplayer2.util.ParsableByteArray) MpegAudioHeader(com.google.android.exoplayer2.extractor.MpegAudioHeader)

Example 52 with ParsableByteArray

use of com.google.android.exoplayer2.util.ParsableByteArray in project ExoPlayer by google.

the class WavHeaderReader method skipToData.

/**
   * Skips to the data in the given WAV input stream and returns its data size. After calling, the
   * input stream's position will point to the start of sample data in the WAV.
   * <p>
   * If an exception is thrown, the input position will be left pointing to a chunk header.
   *
   * @param input Input stream to skip to the data chunk in. Its peek position must be pointing to
   *     a valid chunk header.
   * @param wavHeader WAV header to populate with data bounds.
   * @throws ParserException If an error occurs parsing chunks.
   * @throws IOException If reading from the input fails.
   * @throws InterruptedException If interrupted while reading from input.
   */
public static void skipToData(ExtractorInput input, WavHeader wavHeader) throws IOException, InterruptedException {
    Assertions.checkNotNull(input);
    Assertions.checkNotNull(wavHeader);
    // Make sure the peek position is set to the read position before we peek the first header.
    input.resetPeekPosition();
    ParsableByteArray scratch = new ParsableByteArray(ChunkHeader.SIZE_IN_BYTES);
    // Skip all chunks until we hit the data header.
    ChunkHeader chunkHeader = ChunkHeader.peek(input, scratch);
    while (chunkHeader.id != Util.getIntegerCodeForString("data")) {
        Log.w(TAG, "Ignoring unknown WAV chunk: " + chunkHeader.id);
        long bytesToSkip = ChunkHeader.SIZE_IN_BYTES + chunkHeader.size;
        // Override size of RIFF chunk, since it describes its size as the entire file.
        if (chunkHeader.id == Util.getIntegerCodeForString("RIFF")) {
            bytesToSkip = ChunkHeader.SIZE_IN_BYTES + 4;
        }
        if (bytesToSkip > Integer.MAX_VALUE) {
            throw new ParserException("Chunk is too large (~2GB+) to skip; id: " + chunkHeader.id);
        }
        input.skipFully((int) bytesToSkip);
        chunkHeader = ChunkHeader.peek(input, scratch);
    }
    // Skip past the "data" header.
    input.skipFully(ChunkHeader.SIZE_IN_BYTES);
    wavHeader.setDataBounds(input.getPosition(), chunkHeader.size);
}
Also used : ParsableByteArray(com.google.android.exoplayer2.util.ParsableByteArray) ParserException(com.google.android.exoplayer2.ParserException)

Example 53 with ParsableByteArray

use of com.google.android.exoplayer2.util.ParsableByteArray in project ExoPlayer by google.

the class WebvttExtractor method processSample.

private void processSample() throws ParserException {
    ParsableByteArray webvttData = new ParsableByteArray(sampleData);
    // Validate the first line of the header.
    try {
        WebvttParserUtil.validateWebvttHeaderLine(webvttData);
    } catch (SubtitleDecoderException e) {
        throw new ParserException(e);
    }
    // Defaults to use if the header doesn't contain an X-TIMESTAMP-MAP header.
    long vttTimestampUs = 0;
    long tsTimestampUs = 0;
    // Parse the remainder of the header looking for X-TIMESTAMP-MAP.
    String line;
    while (!TextUtils.isEmpty(line = webvttData.readLine())) {
        if (line.startsWith("X-TIMESTAMP-MAP")) {
            Matcher localTimestampMatcher = LOCAL_TIMESTAMP.matcher(line);
            if (!localTimestampMatcher.find()) {
                throw new ParserException("X-TIMESTAMP-MAP doesn't contain local timestamp: " + line);
            }
            Matcher mediaTimestampMatcher = MEDIA_TIMESTAMP.matcher(line);
            if (!mediaTimestampMatcher.find()) {
                throw new ParserException("X-TIMESTAMP-MAP doesn't contain media timestamp: " + line);
            }
            vttTimestampUs = WebvttParserUtil.parseTimestampUs(localTimestampMatcher.group(1));
            tsTimestampUs = TimestampAdjuster.ptsToUs(Long.parseLong(mediaTimestampMatcher.group(1)));
        }
    }
    // Find the first cue header and parse the start time.
    Matcher cueHeaderMatcher = WebvttParserUtil.findNextCueHeader(webvttData);
    if (cueHeaderMatcher == null) {
        // No cues found. Don't output a sample, but still output a corresponding track.
        buildTrackOutput(0);
        return;
    }
    long firstCueTimeUs = WebvttParserUtil.parseTimestampUs(cueHeaderMatcher.group(1));
    long sampleTimeUs = timestampAdjuster.adjustSampleTimestamp(firstCueTimeUs + tsTimestampUs - vttTimestampUs);
    long subsampleOffsetUs = sampleTimeUs - firstCueTimeUs;
    // Output the track.
    TrackOutput trackOutput = buildTrackOutput(subsampleOffsetUs);
    // Output the sample.
    sampleDataWrapper.reset(sampleData, sampleSize);
    trackOutput.sampleData(sampleDataWrapper, sampleSize);
    trackOutput.sampleMetadata(sampleTimeUs, C.BUFFER_FLAG_KEY_FRAME, sampleSize, 0, null);
}
Also used : ParsableByteArray(com.google.android.exoplayer2.util.ParsableByteArray) ParserException(com.google.android.exoplayer2.ParserException) Matcher(java.util.regex.Matcher) TrackOutput(com.google.android.exoplayer2.extractor.TrackOutput) SubtitleDecoderException(com.google.android.exoplayer2.text.SubtitleDecoderException)

Example 54 with ParsableByteArray

use of com.google.android.exoplayer2.util.ParsableByteArray in project ExoPlayer by google.

the class Ac3Extractor method sniff.

@Override
public boolean sniff(ExtractorInput input) throws IOException, InterruptedException {
    // Skip any ID3 headers.
    ParsableByteArray scratch = new ParsableByteArray(10);
    int startPosition = 0;
    while (true) {
        input.peekFully(scratch.data, 0, 10);
        scratch.setPosition(0);
        if (scratch.readUnsignedInt24() != ID3_TAG) {
            break;
        }
        scratch.skipBytes(3);
        int length = scratch.readSynchSafeInt();
        startPosition += 10 + length;
        input.advancePeekPosition(length);
    }
    input.resetPeekPosition();
    input.advancePeekPosition(startPosition);
    int headerPosition = startPosition;
    int validFramesCount = 0;
    while (true) {
        input.peekFully(scratch.data, 0, 5);
        scratch.setPosition(0);
        int syncBytes = scratch.readUnsignedShort();
        if (syncBytes != AC3_SYNC_WORD) {
            validFramesCount = 0;
            input.resetPeekPosition();
            if (++headerPosition - startPosition >= MAX_SNIFF_BYTES) {
                return false;
            }
            input.advancePeekPosition(headerPosition);
        } else {
            if (++validFramesCount >= 4) {
                return true;
            }
            int frameSize = Ac3Util.parseAc3SyncframeSize(scratch.data);
            if (frameSize == C.LENGTH_UNSET) {
                return false;
            }
            input.advancePeekPosition(frameSize - 5);
        }
    }
}
Also used : ParsableByteArray(com.google.android.exoplayer2.util.ParsableByteArray)

Example 55 with ParsableByteArray

use of com.google.android.exoplayer2.util.ParsableByteArray in project ExoPlayer by google.

the class AdtsExtractor method sniff.

@Override
public boolean sniff(ExtractorInput input) throws IOException, InterruptedException {
    // Skip any ID3 headers.
    ParsableByteArray scratch = new ParsableByteArray(10);
    ParsableBitArray scratchBits = new ParsableBitArray(scratch.data);
    int startPosition = 0;
    while (true) {
        input.peekFully(scratch.data, 0, 10);
        scratch.setPosition(0);
        if (scratch.readUnsignedInt24() != ID3_TAG) {
            break;
        }
        scratch.skipBytes(3);
        int length = scratch.readSynchSafeInt();
        startPosition += 10 + length;
        input.advancePeekPosition(length);
    }
    input.resetPeekPosition();
    input.advancePeekPosition(startPosition);
    // Try to find four or more consecutive AAC audio frames, exceeding the MPEG TS packet size.
    int headerPosition = startPosition;
    int validFramesSize = 0;
    int validFramesCount = 0;
    while (true) {
        input.peekFully(scratch.data, 0, 2);
        scratch.setPosition(0);
        int syncBytes = scratch.readUnsignedShort();
        if ((syncBytes & 0xFFF6) != 0xFFF0) {
            validFramesCount = 0;
            validFramesSize = 0;
            input.resetPeekPosition();
            if (++headerPosition - startPosition >= MAX_SNIFF_BYTES) {
                return false;
            }
            input.advancePeekPosition(headerPosition);
        } else {
            if (++validFramesCount >= 4 && validFramesSize > 188) {
                return true;
            }
            // Skip the frame.
            input.peekFully(scratch.data, 0, 4);
            scratchBits.setPosition(14);
            int frameSize = scratchBits.readBits(13);
            // Either the stream is malformed OR we're not parsing an ADTS stream.
            if (frameSize <= 6) {
                return false;
            }
            input.advancePeekPosition(frameSize - 6);
            validFramesSize += frameSize;
        }
    }
}
Also used : ParsableByteArray(com.google.android.exoplayer2.util.ParsableByteArray) ParsableBitArray(com.google.android.exoplayer2.util.ParsableBitArray)

Aggregations

ParsableByteArray (com.google.android.exoplayer2.util.ParsableByteArray)48 ParserException (com.google.android.exoplayer2.ParserException)11 Format (com.google.android.exoplayer2.Format)6 ArrayList (java.util.ArrayList)4 SeekMap (com.google.android.exoplayer2.extractor.SeekMap)3 Metadata (com.google.android.exoplayer2.metadata.Metadata)3 TrackOutput (com.google.android.exoplayer2.extractor.TrackOutput)2 ContainerAtom (com.google.android.exoplayer2.extractor.mp4.Atom.ContainerAtom)2 FlacStreamInfo (com.google.android.exoplayer2.util.FlacStreamInfo)2 AvcConfig (com.google.android.exoplayer2.video.AvcConfig)2 ByteBuffer (java.nio.ByteBuffer)2 Matcher (java.util.regex.Matcher)2 Spanned (android.text.Spanned)1 ChunkIndex (com.google.android.exoplayer2.extractor.ChunkIndex)1 MpegAudioHeader (com.google.android.exoplayer2.extractor.MpegAudioHeader)1 LeafAtom (com.google.android.exoplayer2.extractor.mp4.Atom.LeafAtom)1 TrackIdGenerator (com.google.android.exoplayer2.extractor.ts.TsPayloadReader.TrackIdGenerator)1 CommentFrame (com.google.android.exoplayer2.metadata.id3.CommentFrame)1 TextInformationFrame (com.google.android.exoplayer2.metadata.id3.TextInformationFrame)1 FakeExtractorOutput (com.google.android.exoplayer2.testutil.FakeExtractorOutput)1