Di Android 8.0, Android OS dirancang ulang untuk menentukan antarmuka yang jelas
antara platform Android yang tidak bergantung pada perangkat, dan kode khusus
perangkat dan vendor. Android telah menentukan banyak antarmuka tersebut dalam bentuk antarmuka
HAL, yang ditentukan sebagai header C di hardware/libhardware
. HIDL
mengganti antarmuka HAL ini dengan antarmuka berversi stabil, yang dapat
berada di Java (dijelaskan di bawah) atau antarmuka HIDL sisi klien dan server
di C++.
Antarmuka HIDL dimaksudkan untuk digunakan terutama dari kode native, dan sebagai akibatnya, HIDL berfokus pada pembuatan kode yang efisien secara otomatis di C++. Namun, antarmuka HIDL juga harus tersedia untuk digunakan langsung dari Java, karena beberapa subsistem Android (seperti Telepon) memiliki antarmuka HIDL Java.
Halaman di bagian ini menjelaskan frontend Java untuk antarmuka HIDL, menjelaskan cara membuat, mendaftarkan, dan menggunakan layanan, serta menjelaskan cara HAL dan klien HAL yang ditulis dalam Java berinteraksi dengan sistem RPC HIDL.
Contoh klien
Ini adalah contoh klien untuk antarmuka IFoo
dalam paket
android.hardware.foo@1.0
yang terdaftar sebagai nama layanan
default
dan layanan tambahan dengan nama layanan kustom
second_impl
.
Menambahkan library
Anda perlu menambahkan dependensi pada library stub HIDL yang sesuai jika ingin menggunakannya. Biasanya, ini adalah library statis:
// in Android.bp static_libs: [ "android.hardware.foo-V1.0-java", ], // in Android.mk LOCAL_STATIC_JAVA_LIBRARIES += android.hardware.foo-V1.0-java
Jika Anda tahu bahwa Anda sudah menarik dependensi pada library ini, Anda juga dapat menggunakan penautan bersama:
// in Android.bp libs: [ "android.hardware.foo-V1.0-java", ], // in Android.mk LOCAL_JAVA_LIBRARIES += android.hardware.foo-V1.0-java
Pertimbangan tambahan untuk menambahkan library di Android 10
Jika memiliki aplikasi sistem atau vendor yang menargetkan Android 10 atau yang lebih baru,
Anda dapat menyertakan library ini secara statis. Anda juga dapat menggunakan (hanya) class HIDL
dari JAR kustom yang diinstal di perangkat dengan Java API stabil yang tersedia
menggunakan mekanisme uses-library
yang ada untuk aplikasi sistem. Pendekatan
terakhir menghemat ruang di perangkat. Untuk mengetahui detail selengkapnya, lihat Mengimplementasikan Library Java SDK. Untuk
aplikasi lama, perilaku lama akan dipertahankan.
Mulai Android 10, versi "dangkal" library ini
juga tersedia. Ini mencakup class yang dimaksud, tetapi tidak menyertakan
class dependen. Misalnya,
android.hardware.foo-V1.0-java-shallow
menyertakan class dalam paket
foo, tetapi tidak menyertakan class dalam
android.hidl.base-V1.0-java
, yang berisi class dasar dari semua
antarmuka HIDL. Jika membuat library yang sudah memiliki class dasar
antarmuka pilihan yang tersedia sebagai dependensi, Anda dapat menggunakan hal berikut:
// in Android.bp static_libs: [ "android.hardware.foo-V1.0-java-shallow", ], // in Android.mk LOCAL_STATIC_JAVA_LIBRARIES += android.hardware.foo-V1.0-java-shallow
Library dasar dan pengelola HIDL juga tidak lagi tersedia di classpath
boot untuk aplikasi (sebelumnya, library tersebut terkadang digunakan sebagai API tersembunyi, karena
classloader delegasi-pertama Android). Sebagai gantinya, keduanya telah dipindahkan ke namespace
baru dengan jarjar
, dan aplikasi yang menggunakannya (harus aplikasi
priv) harus memiliki salinan terpisahnya sendiri. Modul di classpath booting yang menggunakan
HIDL harus menggunakan varian dangkal library Java ini dan menambahkan
jarjar_rules: ":framework-jarjar-rules"
ke
Android.bp
untuk menggunakan versi library ini yang ada
di classpath booting.
Mengubah sumber Java
Hanya ada satu versi (@1.0
) layanan ini, sehingga kode ini hanya mengambil versi tersebut. Lihat
ekstensi antarmuka
untuk mengetahui cara menangani beberapa versi layanan yang berbeda.
import android.hardware.foo.V1_0.IFoo; ... // retry to wait until the service starts up if it is in the manifest IFoo server = IFoo.getService(true /* retry */); // throws NoSuchElementException if not available IFoo anotherServer = IFoo.getService("second_impl", true /* retry */); server.doSomething(…);
Menyediakan layanan
Kode framework di Java mungkin perlu menayangkan antarmuka untuk menerima callback asinkron dari HAL.
Untuk antarmuka IFooCallback
dalam paket android.hardware.foo
versi 1.0, Anda dapat menerapkan antarmuka di Java menggunakan langkah-langkah berikut:
- Tentukan antarmuka Anda di HIDL.
- Buka
/tmp/android/hardware/foo/IFooCallback.java
sebagai referensi. - Buat modul baru untuk implementasi Java Anda.
- Periksa class abstrak
android.hardware.foo.V1_0.IFooCallback.Stub
, lalu tulis class baru untuk memperluasnya dan menerapkan metode abstrak.
Melihat file yang dibuat secara otomatis
Untuk melihat file yang dibuat secara otomatis, jalankan:
hidl-gen -o /tmp -Ljava \ -randroid.hardware:hardware/interfaces \ -randroid.hidl:system/libhidl/transport android.hardware.foo@1.0
Perintah ini menghasilkan direktori
/tmp/android/hardware/foo/1.0
. Untuk file
hardware/interfaces/foo/1.0/IFooCallback.hal
, tindakan ini akan menghasilkan
file /tmp/android/hardware/foo/1.0/IFooCallback.java
, yang
mengaitkan antarmuka Java, kode proxy, dan stub (baik proxy maupun
stub sesuai dengan antarmuka).
-Lmakefile
menghasilkan aturan yang menjalankan perintah ini pada waktu
build dan memungkinkan Anda menyertakan
android.hardware.foo-V1.0-java
dan menautkan ke
file yang sesuai. Skrip yang otomatis melakukan hal ini untuk project yang penuh dengan
antarmuka dapat ditemukan di hardware/interfaces/update-makefiles.sh
.
Jalur dalam contoh ini bersifat relatif; hardware/antarmuka dapat berupa direktori sementara
di bawah hierarki kode Anda agar Anda dapat mengembangkan HAL sebelum
memublikasikannya.
Menjalankan layanan
HAL menyediakan antarmuka IFoo
, yang harus membuat callback
asinkron ke framework melalui antarmuka IFooCallback
. Antarmuka
IFooCallback
tidak terdaftar berdasarkan nama sebagai layanan
yang dapat ditemukan; sebagai gantinya, IFoo
harus berisi metode seperti
setFooCallback(IFooCallback x)
.
Untuk menyiapkan IFooCallback
dari paket android.hardware.foo
versi 1.0, tambahkan android.hardware.foo-V1.0-java
ke Android.mk
. Kode
untuk menjalankan layanan adalah:
import android.hardware.foo.V1_0.IFoo; import android.hardware.foo.V1_0.IFooCallback.Stub; .... class FooCallback extends IFooCallback.Stub { // implement methods } .... // Get the service from which you will be receiving callbacks. // This also starts the threadpool for your callback service. IFoo server = IFoo.getService(true /* retry */); // throws NoSuchElementException if not available .... // This must be a persistent instance variable, not local, // to avoid premature garbage collection. FooCallback mFooCallback = new FooCallback(); .... // Do this once to create the callback service and tell the "foo-bar" service server.setFooCallback(mFooCallback);
Ekstensi antarmuka
Dengan asumsi bahwa layanan tertentu menerapkan antarmuka IFoo
di semua
perangkat, layanan tersebut mungkin menyediakan
kemampuan tambahan yang diterapkan di ekstensi antarmuka
IBetterFoo
, sebagai berikut:
interface IFoo { ... }; interface IBetterFoo extends IFoo { ... };
Kode panggilan yang mengetahui antarmuka yang diperluas dapat menggunakan
metode Java castFrom()
untuk mentransmisikan antarmuka dasar ke
antarmuka yang diperluas dengan aman:
IFoo baseService = IFoo.getService(true /* retry */); // throws NoSuchElementException if not available IBetterFoo extendedService = IBetterFoo.castFrom(baseService); if (extendedService != null) { // The service implements the extended interface. } else { // The service implements only the base interface. }