Merge "Revert "Make BT709 support conditional on swapchain ext enable"" into tm-dev
diff --git a/libs/binder/ParcelableHolder.cpp b/libs/binder/ParcelableHolder.cpp
index 2e86b74..3cf94e3 100644
--- a/libs/binder/ParcelableHolder.cpp
+++ b/libs/binder/ParcelableHolder.cpp
@@ -52,7 +52,10 @@
 }
 
 status_t ParcelableHolder::readFromParcel(const Parcel* p) {
-    this->mStability = static_cast<Stability>(p->readInt32());
+    int32_t wireStability;
+    if (status_t status = p->readInt32(&wireStability); status != OK) return status;
+    if (static_cast<int32_t>(this->mStability) != wireStability) return BAD_VALUE;
+
     this->mParcelable = nullptr;
     this->mParcelableName = std::nullopt;
     int32_t rawDataSize;
diff --git a/libs/binder/ndk/include_cpp/android/binder_parcelable_utils.h b/libs/binder/ndk/include_cpp/android/binder_parcelable_utils.h
index 28819bb..f45aa76 100644
--- a/libs/binder/ndk/include_cpp/android/binder_parcelable_utils.h
+++ b/libs/binder/ndk/include_cpp/android/binder_parcelable_utils.h
@@ -101,7 +101,12 @@
             return STATUS_INVALID_OPERATION;
         }
 
-        RETURN_ON_FAILURE(AParcel_readInt32(parcel, &this->mStability));
+        parcelable_stability_t wireStability;
+        RETURN_ON_FAILURE(AParcel_readInt32(parcel, &wireStability));
+        if (this->mStability != wireStability) {
+            return STATUS_BAD_VALUE;
+        }
+
         int32_t dataSize;
         binder_status_t status = AParcel_readInt32(parcel, &dataSize);
 
diff --git a/libs/binder/rust/src/parcel/parcelable_holder.rs b/libs/binder/rust/src/parcel/parcelable_holder.rs
index d58e839..432da5d 100644
--- a/libs/binder/rust/src/parcel/parcelable_holder.rs
+++ b/libs/binder/rust/src/parcel/parcelable_holder.rs
@@ -233,7 +233,9 @@
     }
 
     fn read_from_parcel(&mut self, parcel: &BorrowedParcel<'_>) -> Result<(), StatusCode> {
-        self.stability = parcel.read()?;
+        if self.stability != parcel.read()? {
+            return Err(StatusCode::BAD_VALUE);
+        }
 
         let data_size: i32 = parcel.read()?;
         if data_size < 0 {
diff --git a/libs/binder/tests/parcel_fuzzer/Android.bp b/libs/binder/tests/parcel_fuzzer/Android.bp
index 38bde3a..57d496d 100644
--- a/libs/binder/tests/parcel_fuzzer/Android.bp
+++ b/libs/binder/tests/parcel_fuzzer/Android.bp
@@ -66,10 +66,13 @@
     srcs: [
         "random_fd.cpp",
         "random_parcel.cpp",
+        "libbinder_driver.cpp",
+        "libbinder_ndk_driver.cpp",
     ],
     shared_libs: [
         "libbase",
         "libbinder",
+        "libbinder_ndk",
         "libcutils",
         "libutils",
     ],
diff --git a/libs/binder/tests/parcel_fuzzer/include_random_parcel/fuzzbinder/libbinder_driver.h b/libs/binder/tests/parcel_fuzzer/include_random_parcel/fuzzbinder/libbinder_driver.h
new file mode 100644
index 0000000..a9a6197
--- /dev/null
+++ b/libs/binder/tests/parcel_fuzzer/include_random_parcel/fuzzbinder/libbinder_driver.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#pragma once
+
+#include <binder/IBinder.h>
+#include <fuzzer/FuzzedDataProvider.h>
+
+namespace android {
+/**
+ * Based on the random data in provider, construct an arbitrary number of
+ * Parcel objects and send them to the service in serial.
+ *
+ * Usage:
+ *
+ *   extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
+ *       FuzzedDataProvider provider = FuzzedDataProvider(data, size);
+ *       // can use provider here to create a service with different options
+ *       sp<IFoo> myService = sp<IFoo>::make(...);
+ *       fuzzService(myService, std::move(provider));
+ *   }
+ */
+void fuzzService(const sp<IBinder>& binder, FuzzedDataProvider&& provider);
+} // namespace android
diff --git a/libs/binder/tests/parcel_fuzzer/include_random_parcel/fuzzbinder/libbinder_ndk_driver.h b/libs/binder/tests/parcel_fuzzer/include_random_parcel/fuzzbinder/libbinder_ndk_driver.h
new file mode 100644
index 0000000..f2b7823
--- /dev/null
+++ b/libs/binder/tests/parcel_fuzzer/include_random_parcel/fuzzbinder/libbinder_ndk_driver.h
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#pragma once
+
+#include <android/binder_parcel.h>
+#include <fuzzer/FuzzedDataProvider.h>
+
+namespace android {
+/**
+ * Based on the random data in provider, construct an arbitrary number of
+ * Parcel objects and send them to the service in serial.
+ *
+ * Usage:
+ *
+ *   extern "C" int LLVMFuzzerTestOneInput(const uint8_t* data, size_t size) {
+ *       FuzzedDataProvider provider = FuzzedDataProvider(data, size);
+ *       // can use provider here to create a service with different options
+ *       std::shared_ptr<IFoo> myService = ndk::SharedRefBase<IFoo>::make(...);
+ *       fuzzService(myService->asBinder().get(), std::move(provider));
+ *   }
+ */
+void fuzzService(AIBinder* binder, FuzzedDataProvider&& provider);
+} // namespace android
diff --git a/libs/binder/tests/parcel_fuzzer/libbinder_driver.cpp b/libs/binder/tests/parcel_fuzzer/libbinder_driver.cpp
new file mode 100644
index 0000000..e849c9b
--- /dev/null
+++ b/libs/binder/tests/parcel_fuzzer/libbinder_driver.cpp
@@ -0,0 +1,37 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#include <fuzzbinder/libbinder_driver.h>
+
+#include <fuzzbinder/random_parcel.h>
+
+namespace android {
+
+void fuzzService(const sp<IBinder>& binder, FuzzedDataProvider&& provider) {
+    while (provider.remaining_bytes() > 0) {
+        uint32_t code = provider.ConsumeIntegral<uint32_t>();
+        uint32_t flags = provider.ConsumeIntegral<uint32_t>();
+        Parcel data;
+
+        std::vector<uint8_t> subData = provider.ConsumeBytes<uint8_t>(
+                provider.ConsumeIntegralInRange<size_t>(0, provider.remaining_bytes()));
+        fillRandomParcel(&data, FuzzedDataProvider(subData.data(), subData.size()));
+
+        Parcel reply;
+        (void)binder->transact(code, data, &reply, flags);
+    }
+}
+
+} // namespace android
diff --git a/libs/binder/tests/parcel_fuzzer/libbinder_ndk_driver.cpp b/libs/binder/tests/parcel_fuzzer/libbinder_ndk_driver.cpp
new file mode 100644
index 0000000..462ef9a
--- /dev/null
+++ b/libs/binder/tests/parcel_fuzzer/libbinder_ndk_driver.cpp
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2022 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+#include <fuzzbinder/libbinder_ndk_driver.h>
+
+#include <fuzzbinder/libbinder_driver.h>
+#include <fuzzbinder/random_parcel.h>
+
+// libbinder_ndk doesn't export this header which breaks down its API for NDK
+// and APEX users, but we need access to it to fuzz.
+#include "../../ndk/ibinder_internal.h"
+
+namespace android {
+
+void fuzzService(AIBinder* binder, FuzzedDataProvider&& provider) {
+    fuzzService(binder->getBinder(), std::move(provider));
+}
+
+} // namespace android