mirror of
https://github.com/androidx/media.git
synced 2025-05-11 01:31:40 +08:00
Add a peekFully overload with allowEndOfInput.
This is in preparation for removing BufferingInput, and using peeking instead. Also add tests for peeking with allowEndOfInput and resetPeekPosition. ------------- Created by MOE: https://github.com/google/moe MOE_MIGRATED_REVID=111318236
This commit is contained in:
parent
030f26fd2d
commit
890dd5afb5
@ -301,6 +301,76 @@ public class DefaultExtractorInputTest extends TestCase {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public void testResetPeekPosition() throws IOException, InterruptedException {
|
||||||
|
DefaultExtractorInput input = createDefaultExtractorInput();
|
||||||
|
byte[] target = new byte[TEST_DATA.length];
|
||||||
|
input.peekFully(target, 0, TEST_DATA.length);
|
||||||
|
|
||||||
|
// Check that we read the whole of TEST_DATA.
|
||||||
|
assertTrue(Arrays.equals(TEST_DATA, target));
|
||||||
|
assertEquals(0, input.getPosition());
|
||||||
|
|
||||||
|
// Check that we can peek again after resetting.
|
||||||
|
input.resetPeekPosition();
|
||||||
|
byte[] target2 = new byte[TEST_DATA.length];
|
||||||
|
input.peekFully(target2, 0, TEST_DATA.length);
|
||||||
|
assertTrue(Arrays.equals(TEST_DATA, target2));
|
||||||
|
|
||||||
|
// Check that we fail with EOFException if we peek past the end of the input.
|
||||||
|
try {
|
||||||
|
input.peekFully(target, 0, 1);
|
||||||
|
fail();
|
||||||
|
} catch (EOFException e) {
|
||||||
|
// Expected.
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testPeekFullyAtEndOfStreamWithAllowEndOfInputSucceeds()
|
||||||
|
throws IOException, InterruptedException {
|
||||||
|
DefaultExtractorInput input = createDefaultExtractorInput();
|
||||||
|
byte[] target = new byte[TEST_DATA.length];
|
||||||
|
|
||||||
|
// Check peeking up to the end of input succeeds.
|
||||||
|
assertTrue(input.peekFully(target, 0, TEST_DATA.length, true));
|
||||||
|
|
||||||
|
// Check peeking at the end of input with allowEndOfInput signals the end of input.
|
||||||
|
assertFalse(input.peekFully(target, 0, 1, true));
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testPeekFullyAcrossEndOfInputWithAllowEndOfInputFails()
|
||||||
|
throws IOException, InterruptedException {
|
||||||
|
DefaultExtractorInput input = createDefaultExtractorInput();
|
||||||
|
byte[] target = new byte[TEST_DATA.length];
|
||||||
|
|
||||||
|
// Check peeking before the end of input with allowEndOfInput succeeds.
|
||||||
|
assertTrue(input.peekFully(target, 0, TEST_DATA.length - 1, true));
|
||||||
|
|
||||||
|
// Check peeking across the end of input with allowEndOfInput throws.
|
||||||
|
try {
|
||||||
|
input.peekFully(target, 0, 2, true);
|
||||||
|
fail();
|
||||||
|
} catch (EOFException e) {
|
||||||
|
// Expected.
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
public void testResetAndPeekFullyPastEndOfStreamWithAllowEndOfInputFails()
|
||||||
|
throws IOException, InterruptedException {
|
||||||
|
DefaultExtractorInput input = createDefaultExtractorInput();
|
||||||
|
byte[] target = new byte[TEST_DATA.length];
|
||||||
|
|
||||||
|
// Check peeking up to the end of input succeeds.
|
||||||
|
assertTrue(input.peekFully(target, 0, TEST_DATA.length, true));
|
||||||
|
input.resetPeekPosition();
|
||||||
|
try {
|
||||||
|
// Check peeking one more byte throws.
|
||||||
|
input.peekFully(target, 0, TEST_DATA.length + 1, true);
|
||||||
|
fail();
|
||||||
|
} catch (EOFException e) {
|
||||||
|
// Expected.
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
private static FakeDataSource buildDataSource() throws IOException {
|
private static FakeDataSource buildDataSource() throws IOException {
|
||||||
FakeDataSource.Builder builder = new FakeDataSource.Builder();
|
FakeDataSource.Builder builder = new FakeDataSource.Builder();
|
||||||
builder.appendReadData(Arrays.copyOfRange(TEST_DATA, 0, 3));
|
builder.appendReadData(Arrays.copyOfRange(TEST_DATA, 0, 3));
|
||||||
|
@ -103,21 +103,42 @@ public final class DefaultExtractorInput implements ExtractorInput {
|
|||||||
skipFully(length, false);
|
skipFully(length, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean peekFully(byte[] target, int offset, int length, boolean allowEndOfInput)
|
||||||
|
throws IOException, InterruptedException {
|
||||||
|
if (!advancePeekPosition(length, allowEndOfInput)) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
System.arraycopy(peekBuffer, peekBufferPosition - length, target, offset, length);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void peekFully(byte[] target, int offset, int length)
|
public void peekFully(byte[] target, int offset, int length)
|
||||||
throws IOException, InterruptedException {
|
throws IOException, InterruptedException {
|
||||||
advancePeekPosition(length);
|
peekFully(target, offset, length, false);
|
||||||
System.arraycopy(peekBuffer, peekBufferPosition - length, target, offset, length);
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public boolean advancePeekPosition(int length, boolean allowEndOfInput)
|
||||||
|
throws IOException, InterruptedException {
|
||||||
|
ensureSpaceForPeek(length);
|
||||||
|
int bytesPeeked = Math.min(peekBufferLength - peekBufferPosition, length);
|
||||||
|
peekBufferLength += length - bytesPeeked;
|
||||||
|
while (bytesPeeked < length) {
|
||||||
|
bytesPeeked = readFromDataSource(peekBuffer, peekBufferPosition, length, bytesPeeked,
|
||||||
|
allowEndOfInput);
|
||||||
|
if (bytesPeeked == C.RESULT_END_OF_INPUT) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
peekBufferPosition += length;
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public void advancePeekPosition(int length) throws IOException, InterruptedException {
|
public void advancePeekPosition(int length) throws IOException, InterruptedException {
|
||||||
ensureSpaceForPeek(length);
|
advancePeekPosition(length, false);
|
||||||
peekBufferPosition += length;
|
|
||||||
while (peekBufferPosition > peekBufferLength) {
|
|
||||||
peekBufferLength = readFromDataSource(peekBuffer, 0, peekBufferPosition, peekBufferLength,
|
|
||||||
false);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
@ -123,8 +123,38 @@ public interface ExtractorInput {
|
|||||||
* Peeks {@code length} bytes from the peek position, writing them into {@code target} at index
|
* Peeks {@code length} bytes from the peek position, writing them into {@code target} at index
|
||||||
* {@code offset}. The current read position is left unchanged.
|
* {@code offset}. The current read position is left unchanged.
|
||||||
* <p>
|
* <p>
|
||||||
|
* If the end of the input is found having peeked no data, then behavior is dependent on
|
||||||
|
* {@code allowEndOfInput}. If {@code allowEndOfInput == true} then {@code false} is returned.
|
||||||
|
* Otherwise an {@link EOFException} is thrown.
|
||||||
|
* <p>
|
||||||
* Calling {@link #resetPeekPosition()} resets the peek position to equal the current read
|
* Calling {@link #resetPeekPosition()} resets the peek position to equal the current read
|
||||||
* position, so the caller can peek the same data again. Reading also resets the peek position.
|
* position, so the caller can peek the same data again. Reading and skipping also reset the peek
|
||||||
|
* position.
|
||||||
|
*
|
||||||
|
* @param target A target array into which data should be written.
|
||||||
|
* @param offset The offset into the target array at which to write.
|
||||||
|
* @param length The number of bytes to peek from the input.
|
||||||
|
* @param allowEndOfInput True if encountering the end of the input having peeked no data is
|
||||||
|
* allowed, and should result in {@code false} being returned. False if it should be
|
||||||
|
* considered an error, causing an {@link EOFException} to be thrown.
|
||||||
|
* @return True if the peek was successful. False if the end of the input was encountered having
|
||||||
|
* peeked no data.
|
||||||
|
* @throws EOFException If the end of input was encountered having partially satisfied the peek
|
||||||
|
* (i.e. having peeked at least one byte, but fewer than {@code length}), or if no bytes were
|
||||||
|
* peeked and {@code allowEndOfInput} is false.
|
||||||
|
* @throws IOException If an error occurs peeking from the input.
|
||||||
|
* @throws InterruptedException If the thread is interrupted.
|
||||||
|
*/
|
||||||
|
boolean peekFully(byte[] target, int offset, int length, boolean allowEndOfInput)
|
||||||
|
throws IOException, InterruptedException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Peeks {@code length} bytes from the peek position, writing them into {@code target} at index
|
||||||
|
* {@code offset}. The current read position is left unchanged.
|
||||||
|
* <p>
|
||||||
|
* Calling {@link #resetPeekPosition()} resets the peek position to equal the current read
|
||||||
|
* position, so the caller can peek the same data again. Reading and skipping also reset the peek
|
||||||
|
* position.
|
||||||
*
|
*
|
||||||
* @param target A target array into which data should be written.
|
* @param target A target array into which data should be written.
|
||||||
* @param offset The offset into the target array at which to write.
|
* @param offset The offset into the target array at which to write.
|
||||||
@ -135,6 +165,28 @@ public interface ExtractorInput {
|
|||||||
*/
|
*/
|
||||||
void peekFully(byte[] target, int offset, int length) throws IOException, InterruptedException;
|
void peekFully(byte[] target, int offset, int length) throws IOException, InterruptedException;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Advances the peek position by {@code length} bytes.
|
||||||
|
* <p>
|
||||||
|
* If the end of the input is encountered before advancing the peek position, then behavior is
|
||||||
|
* dependent on {@code allowEndOfInput}. If {@code allowEndOfInput == true} then {@code false} is
|
||||||
|
* returned. Otherwise an {@link EOFException} is thrown.
|
||||||
|
*
|
||||||
|
* @param length The number of bytes by which to advance the peek position.
|
||||||
|
* @param allowEndOfInput True if encountering the end of the input before advancing is allowed,
|
||||||
|
* and should result in {@code false} being returned. False if it should be considered an
|
||||||
|
* error, causing an {@link EOFException} to be thrown.
|
||||||
|
* @return True if advancing the peek position was successful. False if the end of the input was
|
||||||
|
* encountered before the peek position could be advanced.
|
||||||
|
* @throws EOFException If the end of input was encountered having partially advanced (i.e. having
|
||||||
|
* advanced by at least one byte, but fewer than {@code length}), or if the end of input was
|
||||||
|
* encountered before advancing and {@code allowEndOfInput} is false.
|
||||||
|
* @throws IOException If an error occurs advancing the peek position.
|
||||||
|
* @throws InterruptedException If the thread is interrupted.
|
||||||
|
*/
|
||||||
|
boolean advancePeekPosition(int length, boolean allowEndOfInput)
|
||||||
|
throws IOException, InterruptedException;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Advances the peek position by {@code length} bytes.
|
* Advances the peek position by {@code length} bytes.
|
||||||
*
|
*
|
||||||
|
Loading…
x
Reference in New Issue
Block a user