DO NOT MERGE - Merge Android 13
Bug: 242648940
Merged-In: I424015a4ec7e28c4775f7d2614d10d0958dcdb2e
Change-Id: Ibe015956ef9921009ca08e842d7160ff0555f163
diff --git a/AndroidManifest.xml b/AndroidManifest.xml
index 2cff92d..75e2c4d 100644
--- a/AndroidManifest.xml
+++ b/AndroidManifest.xml
@@ -42,6 +42,7 @@
<uses-permission android:name="com.android.providers.tv.permission.ACCESS_WATCHED_PROGRAMS"/>
<!-- Permissions/feature for USB tuner -->
<uses-permission android:name="android.permission.DVB_DEVICE"/>
+ <uses-permission android:name="android.permission.POST_NOTIFICATIONS"/>
<uses-feature android:name="android.hardware.usb.host"
android:required="false"/>
diff --git a/common/src/com/android/tv/common/CommonPreferences.java b/common/src/com/android/tv/common/CommonPreferences.java
index 5a94eec..72acfd1 100644
--- a/common/src/com/android/tv/common/CommonPreferences.java
+++ b/common/src/com/android/tv/common/CommonPreferences.java
@@ -164,7 +164,8 @@
}
}
- public static synchronized @TrickplaySetting int getTrickplaySetting(Context context) {
+ @TrickplaySetting
+ public static synchronized int getTrickplaySetting(Context context) {
SoftPreconditions.checkState(sInitialized);
if (useContentProvider(context)) {
return sPreferenceValues.getInt(PREFS_KEY_TRICKPLAY_SETTING, TRICKPLAY_SETTING_NOT_SET);
diff --git a/tuner/sampletunertvinput/Android.bp b/tuner/sampletunertvinput/Android.bp
index ba08611..4e5900b 100644
--- a/tuner/sampletunertvinput/Android.bp
+++ b/tuner/sampletunertvinput/Android.bp
@@ -29,7 +29,6 @@
platform_apis: true,
system_ext_specific: true,
-
privileged: true,
certificate: "platform",
// product_specific: true,
@@ -63,5 +62,13 @@
"tv-auto-value",
"tv-auto-factory",
],
+ required: ["com.android.tv.samples.sampletunertvinput.xml"],
// min_sdk_version: "29",
}
+
+prebuilt_etc {
+ name: "com.android.tv.samples.sampletunertvinput.xml",
+ sub_dir: "permissions",
+ src: "com.android.tv.samples.sampletunertvinput.xml",
+ system_ext_specific: true,
+}
diff --git a/tuner/sampletunertvinput/com.android.tv.samples.sampletunertvinput.xml b/tuner/sampletunertvinput/com.android.tv.samples.sampletunertvinput.xml
new file mode 100644
index 0000000..d98e36c
--- /dev/null
+++ b/tuner/sampletunertvinput/com.android.tv.samples.sampletunertvinput.xml
@@ -0,0 +1,8 @@
+<?xml version="1.0" encoding="utf-8"?>
+<permissions>
+ <privapp-permissions package="com.android.tv.samples.sampletunertvinput">
+ <permission name="android.permission.ACCESS_TV_DESCRAMBLER"/>
+ <permission name="android.permission.ACCESS_TV_TUNER"/>
+ <permission name="android.permission.TUNER_RESOURCE_ACCESS"/>
+ </privapp-permissions>
+</permissions>
diff --git a/tuner/sampletunertvinput/src/com/android/tv/samples/sampletunertvinput/SampleTunerTvInputService.java b/tuner/sampletunertvinput/src/com/android/tv/samples/sampletunertvinput/SampleTunerTvInputService.java
index e86ced1..03e7965 100644
--- a/tuner/sampletunertvinput/src/com/android/tv/samples/sampletunertvinput/SampleTunerTvInputService.java
+++ b/tuner/sampletunertvinput/src/com/android/tv/samples/sampletunertvinput/SampleTunerTvInputService.java
@@ -5,6 +5,7 @@
import android.content.Context;
import android.media.MediaCodec;
import android.media.MediaCodec.BufferInfo;
+import android.media.MediaCodec.LinearBlock;
import android.media.MediaFormat;
import android.media.tv.tuner.dvr.DvrPlayback;
import android.media.tv.tuner.dvr.DvrSettings;
@@ -53,13 +54,13 @@
private static final int PACKET_SIZE = 188;
private static final int TIMEOUT_US = 100000;
- private static final boolean SAVE_DATA = true;
- private static final String ES_PATH = "/data/local/tmp/test.es";
+ private static final boolean SAVE_DATA = false;
+ private static final String ES_FILE_NAME = "test.es";
private static final MediaFormat VIDEO_FORMAT;
static {
// format extracted for the specific input file
- VIDEO_FORMAT = MediaFormat.createVideoFormat("video/avc", 320, 240);
+ VIDEO_FORMAT = MediaFormat.createVideoFormat(MediaFormat.MIMETYPE_VIDEO_AVC, 320, 240);
VIDEO_FORMAT.setInteger(MediaFormat.KEY_TRACK_ID, 1);
VIDEO_FORMAT.setLong(MediaFormat.KEY_DURATION, 9933333);
VIDEO_FORMAT.setInteger(MediaFormat.KEY_LEVEL, 32);
@@ -134,9 +135,11 @@
}
if (mDvr != null) {
mDvr.close();
+ mDvr = null;
}
if (mTuner != null) {
mTuner.close();
+ mTuner = null;
}
mDataQueue = null;
mSavedData = null;
@@ -243,9 +246,9 @@
public void onFilterStatusChanged(Filter filter, int status) {
if (DEBUG) {
Log.d(TAG, "onFilterEvent video, status=" + status);
- if (status == Filter.STATUS_DATA_READY) {
- mDataReady = true;
- }
+ }
+ if (status == Filter.STATUS_DATA_READY) {
+ mDataReady = true;
}
}
});
@@ -275,7 +278,8 @@
if (DEBUG) {
Log.d(TAG, "config res=" + res);
}
- File file = new File(ES_PATH);
+ String testFile = mContext.getFilesDir().getAbsolutePath() + "/" + ES_FILE_NAME;
+ File file = new File(testFile);
if (file.exists()) {
try {
dvr.setFileDescriptor(
@@ -323,10 +327,10 @@
mMediaCodec = null;
}
try {
- mMediaCodec = MediaCodec.createDecoderByType("video/avc");
+ mMediaCodec = MediaCodec.createDecoderByType(MediaFormat.MIMETYPE_VIDEO_AVC);
mMediaCodec.configure(VIDEO_FORMAT, mSurface, null, 0);
} catch (IOException e) {
- Log.e(TAG, "Error: " + e.getMessage());
+ Log.e(TAG, "Error in initCodec: " + e.getMessage());
}
if (mMediaCodec == null) {
@@ -357,23 +361,41 @@
while (!Thread.interrupted()) {
if (!mDataReady) {
Thread.sleep(100);
+ continue;
}
if (!mDataQueue.isEmpty()) {
- if (queueCodecInputBuffer(mDataQueue.getFirst())) {
+ if (handleDataBuffer(mDataQueue.getFirst())) {
// data consumed, remove.
mDataQueue.pollFirst();
}
- } else if (SAVE_DATA) {
+ }
+ if (SAVE_DATA) {
mDataQueue.addAll(mSavedData);
}
- releaseCodecOutputBuffer();
}
} catch (Exception e) {
- Log.e(TAG, "Error: " + e.getMessage());
+ Log.e(TAG, "Error in decodeInternal: " + e.getMessage());
}
}
- private boolean queueCodecInputBuffer(MediaEvent mediaEvent) {
+ private boolean handleDataBuffer(MediaEvent mediaEvent) {
+ if (mediaEvent.getLinearBlock() == null) {
+ if (DEBUG) Log.d(TAG, "getLinearBlock() == null");
+ return true;
+ }
+ boolean success = false;
+ LinearBlock block = mediaEvent.getLinearBlock();
+ if (queueCodecInputBuffer(block, mediaEvent.getDataLength(), mediaEvent.getOffset(),
+ mediaEvent.getPts())) {
+ releaseCodecOutputBuffer();
+ success = true;
+ }
+ mediaEvent.release();
+ return success;
+ }
+
+ private boolean queueCodecInputBuffer(LinearBlock block, long sampleSize,
+ long offset, long pts) {
int res = mMediaCodec.dequeueInputBuffer(TIMEOUT_US);
if (res >= 0) {
ByteBuffer buffer = mMediaCodec.getInputBuffer(res);
@@ -381,13 +403,9 @@
throw new RuntimeException("Null decoder input buffer");
}
- ByteBuffer data = mediaEvent.getLinearBlock().map();
- int sampleSize = (int) mediaEvent.getDataLength();
- int offset = (int) mediaEvent.getOffset();
- long pts = mediaEvent.getPts();
-
+ ByteBuffer data = block.map();
if (offset > 0 && offset < data.limit()) {
- data.position(offset);
+ data.position((int) offset);
} else {
data.position(0);
}
@@ -407,14 +425,21 @@
+ " size="
+ (data.limit() - data.position()));
}
- while (data.position() < data.limit()) {
- // fill codec input buffer
- buffer.put(data.get());
+ // fill codec input buffer
+ int size = sampleSize > data.limit() ? data.limit() : (int) sampleSize;
+ if (DEBUG) Log.d(TAG, "limit " + data.limit() + " sampleSize " + sampleSize);
+ if (data.hasArray()) {
+ Log.d(TAG, "hasArray");
+ buffer.put(data.array(), 0, size);
+ } else {
+ byte[] array = new byte[size];
+ data.get(array, 0, size);
+ buffer.put(array, 0, size);
}
- mMediaCodec.queueInputBuffer(res, 0, sampleSize, pts, 0);
+ mMediaCodec.queueInputBuffer(res, 0, (int) sampleSize, pts, 0);
} else {
- Log.d(TAG, "queueCodecInputBuffer res=" + res);
+ if (DEBUG) Log.d(TAG, "queueCodecInputBuffer res=" + res);
return false;
}
return true;
@@ -447,4 +472,4 @@
}
}
-}
\ No newline at end of file
+}