diff --git a/broadcastradio/aidl/Android.bp b/broadcastradio/aidl/Android.bp
index 1540944b80..82ee9495ab 100644
--- a/broadcastradio/aidl/Android.bp
+++ b/broadcastradio/aidl/Android.bp
@@ -36,6 +36,9 @@ aidl_interface {
sdk_version: "module_current",
min_sdk_version: "Tiramisu",
},
+ rust: {
+ enabled: true,
+ },
},
versions_with_info: [
{
@@ -68,3 +71,10 @@ java_defaults {
latest_android_hardware_broadcastradio + "-java",
],
}
+
+rust_defaults {
+ name: "latest_android_hardware_broadcastradio_rust",
+ rustlibs: [
+ latest_android_hardware_broadcastradio + "-rust",
+ ],
+}
diff --git a/broadcastradio/aidl/rust_impl/Android.bp b/broadcastradio/aidl/rust_impl/Android.bp
new file mode 100644
index 0000000000..d6f984eb33
--- /dev/null
+++ b/broadcastradio/aidl/rust_impl/Android.bp
@@ -0,0 +1,31 @@
+/*
+ * Copyright (C) 2024 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.
+ */
+
+rust_binary {
+ name: "android.hardware.broadcastradio-rust-service",
+ relative_install_path: "hw",
+ vendor: true,
+ srcs: ["src/*.rs"],
+ crate_root: "src/main.rs",
+ defaults: [
+ "latest_android_hardware_broadcastradio_rust",
+ ],
+ vintf_fragments: ["broadcastradio-rust-service.xml"],
+ init_rc: ["broadcastradio-rust-service.rc"],
+ rustlibs: [
+ "libbinder_rs",
+ ],
+}
diff --git a/broadcastradio/aidl/rust_impl/README.md b/broadcastradio/aidl/rust_impl/README.md
new file mode 100644
index 0000000000..17e0c18ae9
--- /dev/null
+++ b/broadcastradio/aidl/rust_impl/README.md
@@ -0,0 +1,13 @@
+# Rust Skeleton BroadcastRadio HAL implementation.
+
+WARNING: This is not a reference BroadcastRadio HAL implementation and does
+not contain any actual implementation.
+
+This folder contains a skeleton broadcast radio HAL implementation in Rust to
+demonstrate how vendor may implement a Rust broadcast radio HAL. To run this
+broadcast radio HAL, include `android.hardware.broadcastradio-rust-service`
+in your image.
+
+This implementation returns `StatusCode::UNKNOWN_ERROR` for all operations
+and does not pass VTS/CTS. Vendor must replace the logic in
+`default_broadcastradio_hal.rs` with the actual implementation
\ No newline at end of file
diff --git a/broadcastradio/aidl/rust_impl/broadcastradio-rust-service.rc b/broadcastradio/aidl/rust_impl/broadcastradio-rust-service.rc
new file mode 100644
index 0000000000..4dad6165e1
--- /dev/null
+++ b/broadcastradio/aidl/rust_impl/broadcastradio-rust-service.rc
@@ -0,0 +1,5 @@
+service vendor.broadcastradio-default /vendor/bin/hw/android.hardware.broadcastradio-service.default
+ interface aidl android.hardware.broadcastradio.IBroadcastRadio/amfm
+ class hal
+ user audioserver
+ group audio
diff --git a/broadcastradio/aidl/rust_impl/broadcastradio-rust-service.xml b/broadcastradio/aidl/rust_impl/broadcastradio-rust-service.xml
new file mode 100644
index 0000000000..ced2d78c16
--- /dev/null
+++ b/broadcastradio/aidl/rust_impl/broadcastradio-rust-service.xml
@@ -0,0 +1,23 @@
+
+
+
+
+ android.hardware.broadcastradio
+ 2
+ IBroadcastRadio/amfm
+
+
diff --git a/broadcastradio/aidl/rust_impl/src/default_broadcastradio_hal.rs b/broadcastradio/aidl/rust_impl/src/default_broadcastradio_hal.rs
new file mode 100644
index 0000000000..ea2f9d3b6b
--- /dev/null
+++ b/broadcastradio/aidl/rust_impl/src/default_broadcastradio_hal.rs
@@ -0,0 +1,107 @@
+/*
+ * Copyright (C) 2024 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.
+ */
+use android_hardware_broadcastradio::aidl::android::hardware::broadcastradio::{
+ AmFmRegionConfig::AmFmRegionConfig,
+ AnnouncementType::AnnouncementType,
+ ConfigFlag::ConfigFlag,
+ DabTableEntry::DabTableEntry,
+ IAnnouncementListener::IAnnouncementListener,
+ IBroadcastRadio::IBroadcastRadio,
+ ICloseHandle::ICloseHandle,
+ ITunerCallback::ITunerCallback,
+ ProgramFilter::ProgramFilter,
+ ProgramSelector::ProgramSelector,
+ Properties::Properties,
+ VendorKeyValue::VendorKeyValue,
+};
+use binder::{Interface, Result as BinderResult, StatusCode, Strong};
+use std::vec::Vec;
+
+/// This struct is defined to implement IBroadcastRadio AIDL interface.
+pub struct DefaultBroadcastRadioHal;
+
+impl Interface for DefaultBroadcastRadioHal {}
+
+impl IBroadcastRadio for DefaultBroadcastRadioHal {
+ fn getAmFmRegionConfig(&self, _full : bool) -> BinderResult {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn getDabRegionConfig(&self) -> BinderResult> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn getProperties(&self) -> BinderResult {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn getImage(&self, _id : i32) -> BinderResult> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn setTunerCallback(&self, _callback : &Strong) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn unsetTunerCallback(&self) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn tune(&self, _program : &ProgramSelector) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn seek(&self, _direction_up : bool, _skip_sub_channel : bool) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn step(&self, _direction_up : bool) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn cancel(&self) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn startProgramListUpdates(&self, _filter : &ProgramFilter) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn stopProgramListUpdates(&self) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn isConfigFlagSet(&self, _flag : ConfigFlag) -> BinderResult {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn setConfigFlag(&self, _flag : ConfigFlag, _value : bool) -> BinderResult<()> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn setParameters(&self, _parameters : &[VendorKeyValue]) -> BinderResult> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn getParameters(&self, _parameters : &[String]) -> BinderResult> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+
+ fn registerAnnouncementListener(&self, _listener : &Strong,
+ _enabled : &[AnnouncementType]) -> BinderResult> {
+ Err(StatusCode::UNKNOWN_ERROR.into())
+ }
+}
diff --git a/broadcastradio/aidl/rust_impl/src/main.rs b/broadcastradio/aidl/rust_impl/src/main.rs
new file mode 100644
index 0000000000..c0bc0559da
--- /dev/null
+++ b/broadcastradio/aidl/rust_impl/src/main.rs
@@ -0,0 +1,33 @@
+/*
+ * Copyright (C) 2024 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.
+ */
+ mod default_broadcastradio_hal;
+
+use android_hardware_broadcastradio::aidl::android::hardware::broadcastradio::IBroadcastRadio::BnBroadcastRadio;
+use crate::default_broadcastradio_hal::DefaultBroadcastRadioHal;
+
+fn main() {
+ binder::ProcessState::start_thread_pool();
+ let my_service = DefaultBroadcastRadioHal;
+ let service_name = "android.hardware.broadcastradio.IBroadcastRadio/amfm";
+ let my_service_binder = BnBroadcastRadio::new_binder(
+ my_service,
+ binder::BinderFeatures::default(),
+ );
+ binder::add_service(service_name, my_service_binder.as_binder())
+ .expect(format!("Failed to register {}?", service_name).as_str());
+ // Does not return.
+ binder::ProcessState::join_thread_pool()
+}