• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 /*
2  * Copyright (C) 2020 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 use crate::binder::{
18     AsNative, Interface, InterfaceClassMethods, Remotable, Stability, TransactionCode,
19 };
20 use crate::error::{status_result, status_t, Result, StatusCode};
21 use crate::parcel::{BorrowedParcel, Serialize};
22 use crate::proxy::SpIBinder;
23 use crate::sys;
24 
25 use std::convert::TryFrom;
26 use std::ffi::{c_void, CStr, CString};
27 use std::fs::File;
28 use std::mem::ManuallyDrop;
29 use std::ops::Deref;
30 use std::os::raw::c_char;
31 use std::os::unix::io::FromRawFd;
32 use std::slice;
33 
34 /// Rust wrapper around Binder remotable objects.
35 ///
36 /// Implements the C++ `BBinder` class, and therefore implements the C++
37 /// `IBinder` interface.
38 #[repr(C)]
39 pub struct Binder<T: Remotable> {
40     ibinder: *mut sys::AIBinder,
41     rust_object: *mut T,
42 }
43 
44 /// # Safety
45 ///
46 /// A `Binder<T>` is a pair of unique owning pointers to two values:
47 ///   * a C++ ABBinder which the C++ API guarantees can be passed between threads
48 ///   * a Rust object which implements `Remotable`; this trait requires `Send + Sync`
49 ///
50 /// Both pointers are unique (never escape the `Binder<T>` object and are not copied)
51 /// so we can essentially treat `Binder<T>` as a box-like containing the two objects;
52 /// the box-like object inherits `Send` from the two inner values, similarly
53 /// to how `Box<T>` is `Send` if `T` is `Send`.
54 unsafe impl<T: Remotable> Send for Binder<T> {}
55 
56 /// # Safety
57 ///
58 /// A `Binder<T>` is a pair of unique owning pointers to two values:
59 ///   * a C++ ABBinder which is thread-safe, i.e. `Send + Sync`
60 ///   * a Rust object which implements `Remotable`; this trait requires `Send + Sync`
61 ///
62 /// `ABBinder` contains an immutable `mUserData` pointer, which is actually a
63 /// pointer to a boxed `T: Remotable`, which is `Sync`. `ABBinder` also contains
64 /// a mutable pointer to its class, but mutation of this field is controlled by
65 /// a mutex and it is only allowed to be set once, therefore we can concurrently
66 /// access this field safely. `ABBinder` inherits from `BBinder`, which is also
67 /// thread-safe. Thus `ABBinder` is thread-safe.
68 ///
69 /// Both pointers are unique (never escape the `Binder<T>` object and are not copied)
70 /// so we can essentially treat `Binder<T>` as a box-like containing the two objects;
71 /// the box-like object inherits `Sync` from the two inner values, similarly
72 /// to how `Box<T>` is `Sync` if `T` is `Sync`.
73 unsafe impl<T: Remotable> Sync for Binder<T> {}
74 
75 impl<T: Remotable> Binder<T> {
76     /// Create a new Binder remotable object with default stability
77     ///
78     /// This moves the `rust_object` into an owned [`Box`] and Binder will
79     /// manage its lifetime.
new(rust_object: T) -> Binder<T>80     pub fn new(rust_object: T) -> Binder<T> {
81         Self::new_with_stability(rust_object, Stability::default())
82     }
83 
84     /// Create a new Binder remotable object with the given stability
85     ///
86     /// This moves the `rust_object` into an owned [`Box`] and Binder will
87     /// manage its lifetime.
new_with_stability(rust_object: T, stability: Stability) -> Binder<T>88     pub fn new_with_stability(rust_object: T, stability: Stability) -> Binder<T> {
89         let class = T::get_class();
90         let rust_object = Box::into_raw(Box::new(rust_object));
91         let ibinder = unsafe {
92             // Safety: `AIBinder_new` expects a valid class pointer (which we
93             // initialize via `get_class`), and an arbitrary pointer
94             // argument. The caller owns the returned `AIBinder` pointer, which
95             // is a strong reference to a `BBinder`. This reference should be
96             // decremented via `AIBinder_decStrong` when the reference lifetime
97             // ends.
98             sys::AIBinder_new(class.into(), rust_object as *mut c_void)
99         };
100         let mut binder = Binder {
101             ibinder,
102             rust_object,
103         };
104         binder.mark_stability(stability);
105         binder
106     }
107 
108     /// Set the extension of a binder interface. This allows a downstream
109     /// developer to add an extension to an interface without modifying its
110     /// interface file. This should be called immediately when the object is
111     /// created before it is passed to another thread.
112     ///
113     /// # Examples
114     ///
115     /// For instance, imagine if we have this Binder AIDL interface definition:
116     ///     interface IFoo { void doFoo(); }
117     ///
118     /// If an unrelated owner (perhaps in a downstream codebase) wants to make a
119     /// change to the interface, they have two options:
120     ///
121     /// 1) Historical option that has proven to be BAD! Only the original
122     ///    author of an interface should change an interface. If someone
123     ///    downstream wants additional functionality, they should not ever
124     ///    change the interface or use this method.
125     ///    ```AIDL
126     ///    BAD TO DO:  interface IFoo {                       BAD TO DO
127     ///    BAD TO DO:      void doFoo();                      BAD TO DO
128     ///    BAD TO DO: +    void doBar(); // adding a method   BAD TO DO
129     ///    BAD TO DO:  }                                      BAD TO DO
130     ///    ```
131     ///
132     /// 2) Option that this method enables!
133     ///    Leave the original interface unchanged (do not change IFoo!).
134     ///    Instead, create a new AIDL interface in a downstream package:
135     ///    ```AIDL
136     ///    package com.<name>; // new functionality in a new package
137     ///    interface IBar { void doBar(); }
138     ///    ```
139     ///
140     ///    When registering the interface, add:
141     ///
142     ///        # use binder::{Binder, Interface};
143     ///        # type MyFoo = ();
144     ///        # type MyBar = ();
145     ///        # let my_foo = ();
146     ///        # let my_bar = ();
147     ///        let mut foo: Binder<MyFoo> = Binder::new(my_foo); // class in AOSP codebase
148     ///        let bar: Binder<MyBar> = Binder::new(my_bar);     // custom extension class
149     ///        foo.set_extension(&mut bar.as_binder());          // use method in Binder
150     ///
151     ///    Then, clients of `IFoo` can get this extension:
152     ///
153     ///        # use binder::{declare_binder_interface, Binder, TransactionCode, Parcel};
154     ///        # trait IBar {}
155     ///        # declare_binder_interface! {
156     ///        #     IBar["test"] {
157     ///        #         native: BnBar(on_transact),
158     ///        #         proxy: BpBar,
159     ///        #     }
160     ///        # }
161     ///        # fn on_transact(
162     ///        #     service: &dyn IBar,
163     ///        #     code: TransactionCode,
164     ///        #     data: &BorrowedParcel,
165     ///        #     reply: &mut BorrowedParcel,
166     ///        # ) -> binder::Result<()> {
167     ///        #     Ok(())
168     ///        # }
169     ///        # impl IBar for BpBar {}
170     ///        # impl IBar for Binder<BnBar> {}
171     ///        # fn main() -> binder::Result<()> {
172     ///        # let binder = Binder::new(());
173     ///        if let Some(barBinder) = binder.get_extension()? {
174     ///            let bar = BpBar::new(barBinder)
175     ///                .expect("Extension was not of type IBar");
176     ///        } else {
177     ///            // There was no extension
178     ///        }
179     ///        # }
set_extension(&mut self, extension: &mut SpIBinder) -> Result<()>180     pub fn set_extension(&mut self, extension: &mut SpIBinder) -> Result<()> {
181         let status = unsafe {
182             // Safety: `AIBinder_setExtension` expects two valid, mutable
183             // `AIBinder` pointers. We are guaranteed that both `self` and
184             // `extension` contain valid `AIBinder` pointers, because they
185             // cannot be initialized without a valid
186             // pointer. `AIBinder_setExtension` does not take ownership of
187             // either parameter.
188             sys::AIBinder_setExtension(self.as_native_mut(), extension.as_native_mut())
189         };
190         status_result(status)
191     }
192 
193     /// Retrieve the interface descriptor string for this object's Binder
194     /// interface.
get_descriptor() -> &'static str195     pub fn get_descriptor() -> &'static str {
196         T::get_descriptor()
197     }
198 
199     /// Mark this binder object with the given stability guarantee
mark_stability(&mut self, stability: Stability)200     fn mark_stability(&mut self, stability: Stability) {
201         match stability {
202             Stability::Local => self.mark_local_stability(),
203             Stability::Vintf => {
204                 unsafe {
205                     // Safety: Self always contains a valid `AIBinder` pointer, so
206                     // we can always call this C API safely.
207                     sys::AIBinder_markVintfStability(self.as_native_mut());
208                 }
209             }
210         }
211     }
212 
213     /// Mark this binder object with local stability, which is vendor if we are
214     /// building for the VNDK and system otherwise.
215     #[cfg(any(vendor_ndk, android_vndk))]
mark_local_stability(&mut self)216     fn mark_local_stability(&mut self) {
217         unsafe {
218             // Safety: Self always contains a valid `AIBinder` pointer, so
219             // we can always call this C API safely.
220             sys::AIBinder_markVendorStability(self.as_native_mut());
221         }
222     }
223 
224     /// Mark this binder object with local stability, which is vendor if we are
225     /// building for the VNDK and system otherwise.
226     #[cfg(not(any(vendor_ndk, android_vndk)))]
mark_local_stability(&mut self)227     fn mark_local_stability(&mut self) {
228         unsafe {
229             // Safety: Self always contains a valid `AIBinder` pointer, so
230             // we can always call this C API safely.
231             sys::AIBinder_markSystemStability(self.as_native_mut());
232         }
233     }
234 }
235 
236 impl<T: Remotable> Interface for Binder<T> {
237     /// Converts the local remotable object into a generic `SpIBinder`
238     /// reference.
239     ///
240     /// The resulting `SpIBinder` will hold its own strong reference to this
241     /// remotable object, which will prevent the object from being dropped while
242     /// the `SpIBinder` is alive.
as_binder(&self) -> SpIBinder243     fn as_binder(&self) -> SpIBinder {
244         unsafe {
245             // Safety: `self.ibinder` is guaranteed to always be a valid pointer
246             // to an `AIBinder` by the `Binder` constructor. We are creating a
247             // copy of the `self.ibinder` strong reference, but
248             // `SpIBinder::from_raw` assumes it receives an owned pointer with
249             // its own strong reference. We first increment the reference count,
250             // so that the new `SpIBinder` will be tracked as a new reference.
251             sys::AIBinder_incStrong(self.ibinder);
252             SpIBinder::from_raw(self.ibinder).unwrap()
253         }
254     }
255 }
256 
257 impl<T: Remotable> InterfaceClassMethods for Binder<T> {
get_descriptor() -> &'static str258     fn get_descriptor() -> &'static str {
259         <T as Remotable>::get_descriptor()
260     }
261 
262     /// Called whenever a transaction needs to be processed by a local
263     /// implementation.
264     ///
265     /// # Safety
266     ///
267     /// Must be called with a non-null, valid pointer to a local `AIBinder` that
268     /// contains a `T` pointer in its user data. The `data` and `reply` parcel
269     /// parameters must be valid pointers to `AParcel` objects. This method does
270     /// not take ownership of any of its parameters.
271     ///
272     /// These conditions hold when invoked by `ABBinder::onTransact`.
on_transact( binder: *mut sys::AIBinder, code: u32, data: *const sys::AParcel, reply: *mut sys::AParcel, ) -> status_t273     unsafe extern "C" fn on_transact(
274         binder: *mut sys::AIBinder,
275         code: u32,
276         data: *const sys::AParcel,
277         reply: *mut sys::AParcel,
278     ) -> status_t {
279         let res = {
280             let mut reply = BorrowedParcel::from_raw(reply).unwrap();
281             let data = BorrowedParcel::from_raw(data as *mut sys::AParcel).unwrap();
282             let object = sys::AIBinder_getUserData(binder);
283             let binder: &T = &*(object as *const T);
284             binder.on_transact(code, &data, &mut reply)
285         };
286         match res {
287             Ok(()) => 0i32,
288             Err(e) => e as i32,
289         }
290     }
291 
292     /// Called whenever an `AIBinder` object is no longer referenced and needs
293     /// destroyed.
294     ///
295     /// # Safety
296     ///
297     /// Must be called with a valid pointer to a `T` object. After this call,
298     /// the pointer will be invalid and should not be dereferenced.
on_destroy(object: *mut c_void)299     unsafe extern "C" fn on_destroy(object: *mut c_void) {
300         Box::from_raw(object as *mut T);
301     }
302 
303     /// Called whenever a new, local `AIBinder` object is needed of a specific
304     /// class.
305     ///
306     /// Constructs the user data pointer that will be stored in the object,
307     /// which will be a heap-allocated `T` object.
308     ///
309     /// # Safety
310     ///
311     /// Must be called with a valid pointer to a `T` object allocated via `Box`.
on_create(args: *mut c_void) -> *mut c_void312     unsafe extern "C" fn on_create(args: *mut c_void) -> *mut c_void {
313         // We just return the argument, as it is already a pointer to the rust
314         // object created by Box.
315         args
316     }
317 
318     /// Called to handle the `dump` transaction.
319     ///
320     /// # Safety
321     ///
322     /// Must be called with a non-null, valid pointer to a local `AIBinder` that
323     /// contains a `T` pointer in its user data. fd should be a non-owned file
324     /// descriptor, and args must be an array of null-terminated string
325     /// poiinters with length num_args.
on_dump( binder: *mut sys::AIBinder, fd: i32, args: *mut *const c_char, num_args: u32, ) -> status_t326     unsafe extern "C" fn on_dump(
327         binder: *mut sys::AIBinder,
328         fd: i32,
329         args: *mut *const c_char,
330         num_args: u32,
331     ) -> status_t {
332         if fd < 0 {
333             return StatusCode::UNEXPECTED_NULL as status_t;
334         }
335         // We don't own this file, so we need to be careful not to drop it.
336         let file = ManuallyDrop::new(File::from_raw_fd(fd));
337 
338         if args.is_null() {
339             return StatusCode::UNEXPECTED_NULL as status_t;
340         }
341         let args = slice::from_raw_parts(args, num_args as usize);
342         let args: Vec<_> = args.iter().map(|s| CStr::from_ptr(*s)).collect();
343 
344         let object = sys::AIBinder_getUserData(binder);
345         let binder: &T = &*(object as *const T);
346         let res = binder.on_dump(&file, &args);
347 
348         match res {
349             Ok(()) => 0,
350             Err(e) => e as status_t,
351         }
352     }
353 }
354 
355 impl<T: Remotable> Drop for Binder<T> {
356     // This causes C++ to decrease the strong ref count of the `AIBinder`
357     // object. We specifically do not drop the `rust_object` here. When C++
358     // actually destroys the object, it calls `on_destroy` and we can drop the
359     // `rust_object` then.
drop(&mut self)360     fn drop(&mut self) {
361         unsafe {
362             // Safety: When `self` is dropped, we can no longer access the
363             // reference, so can decrement the reference count. `self.ibinder`
364             // is always a valid `AIBinder` pointer, so is valid to pass to
365             // `AIBinder_decStrong`.
366             sys::AIBinder_decStrong(self.ibinder);
367         }
368     }
369 }
370 
371 impl<T: Remotable> Deref for Binder<T> {
372     type Target = T;
373 
deref(&self) -> &Self::Target374     fn deref(&self) -> &Self::Target {
375         unsafe {
376             // Safety: While `self` is alive, the reference count of the
377             // underlying object is > 0 and therefore `on_destroy` cannot be
378             // called. Therefore while `self` is alive, we know that
379             // `rust_object` is still a valid pointer to a heap allocated object
380             // of type `T`.
381             &*self.rust_object
382         }
383     }
384 }
385 
386 impl<B: Remotable> Serialize for Binder<B> {
serialize(&self, parcel: &mut BorrowedParcel<'_>) -> Result<()>387     fn serialize(&self, parcel: &mut BorrowedParcel<'_>) -> Result<()> {
388         parcel.write_binder(Some(&self.as_binder()))
389     }
390 }
391 
392 // This implementation is an idiomatic implementation of the C++
393 // `IBinder::localBinder` interface if the binder object is a Rust binder
394 // service.
395 impl<B: Remotable> TryFrom<SpIBinder> for Binder<B> {
396     type Error = StatusCode;
397 
try_from(mut ibinder: SpIBinder) -> Result<Self>398     fn try_from(mut ibinder: SpIBinder) -> Result<Self> {
399         let class = B::get_class();
400         if Some(class) != ibinder.get_class() {
401             return Err(StatusCode::BAD_TYPE);
402         }
403         let userdata = unsafe {
404             // Safety: `SpIBinder` always holds a valid pointer pointer to an
405             // `AIBinder`, which we can safely pass to
406             // `AIBinder_getUserData`. `ibinder` retains ownership of the
407             // returned pointer.
408             sys::AIBinder_getUserData(ibinder.as_native_mut())
409         };
410         if userdata.is_null() {
411             return Err(StatusCode::UNEXPECTED_NULL);
412         }
413         // We are transferring the ownership of the AIBinder into the new Binder
414         // object.
415         let mut ibinder = ManuallyDrop::new(ibinder);
416         Ok(Binder {
417             ibinder: ibinder.as_native_mut(),
418             rust_object: userdata as *mut B,
419         })
420     }
421 }
422 
423 /// # Safety
424 ///
425 /// The constructor for `Binder` guarantees that `self.ibinder` will contain a
426 /// valid, non-null pointer to an `AIBinder`, so this implementation is type
427 /// safe. `self.ibinder` will remain valid for the entire lifetime of `self`
428 /// because we hold a strong reference to the `AIBinder` until `self` is
429 /// dropped.
430 unsafe impl<B: Remotable> AsNative<sys::AIBinder> for Binder<B> {
as_native(&self) -> *const sys::AIBinder431     fn as_native(&self) -> *const sys::AIBinder {
432         self.ibinder
433     }
434 
as_native_mut(&mut self) -> *mut sys::AIBinder435     fn as_native_mut(&mut self) -> *mut sys::AIBinder {
436         self.ibinder
437     }
438 }
439 
440 /// Register a new service with the default service manager.
441 ///
442 /// Registers the given binder object with the given identifier. If successful,
443 /// this service can then be retrieved using that identifier.
444 ///
445 /// This function will panic if the identifier contains a 0 byte (NUL).
add_service(identifier: &str, mut binder: SpIBinder) -> Result<()>446 pub fn add_service(identifier: &str, mut binder: SpIBinder) -> Result<()> {
447     let instance = CString::new(identifier).unwrap();
448     let status = unsafe {
449         // Safety: `AServiceManager_addService` expects valid `AIBinder` and C
450         // string pointers. Caller retains ownership of both
451         // pointers. `AServiceManager_addService` creates a new strong reference
452         // and copies the string, so both pointers need only be valid until the
453         // call returns.
454         sys::AServiceManager_addService(binder.as_native_mut(), instance.as_ptr())
455     };
456     status_result(status)
457 }
458 
459 /// Register a dynamic service via the LazyServiceRegistrar.
460 ///
461 /// Registers the given binder object with the given identifier. If successful,
462 /// this service can then be retrieved using that identifier. The service process
463 /// will be shut down once all registered services are no longer in use.
464 ///
465 /// If any service in the process is registered as lazy, all should be, otherwise
466 /// the process may be shut down while a service is in use.
467 ///
468 /// This function will panic if the identifier contains a 0 byte (NUL).
register_lazy_service(identifier: &str, mut binder: SpIBinder) -> Result<()>469 pub fn register_lazy_service(identifier: &str, mut binder: SpIBinder) -> Result<()> {
470     let instance = CString::new(identifier).unwrap();
471     let status = unsafe {
472         // Safety: `AServiceManager_registerLazyService` expects valid `AIBinder` and C
473         // string pointers. Caller retains ownership of both
474         // pointers. `AServiceManager_registerLazyService` creates a new strong reference
475         // and copies the string, so both pointers need only be valid until the
476         // call returns.
477 
478         sys::AServiceManager_registerLazyService(binder.as_native_mut(), instance.as_ptr())
479     };
480     status_result(status)
481 }
482 
483 /// Prevent a process which registers lazy services from being shut down even when none
484 /// of the services is in use.
485 ///
486 /// If persist is true then shut down will be blocked until this function is called again with
487 /// persist false. If this is to be the initial state, call this function before calling
488 /// register_lazy_service.
force_lazy_services_persist(persist: bool)489 pub fn force_lazy_services_persist(persist: bool) {
490     unsafe {
491         // Safety: No borrowing or transfer of ownership occurs here.
492         sys::AServiceManager_forceLazyServicesPersist(persist)
493     }
494 }
495 
496 /// Tests often create a base BBinder instance; so allowing the unit
497 /// type to be remotable translates nicely to Binder::new(()).
498 impl Remotable for () {
get_descriptor() -> &'static str499     fn get_descriptor() -> &'static str {
500         ""
501     }
502 
on_transact( &self, _code: TransactionCode, _data: &BorrowedParcel<'_>, _reply: &mut BorrowedParcel<'_>, ) -> Result<()>503     fn on_transact(
504         &self,
505         _code: TransactionCode,
506         _data: &BorrowedParcel<'_>,
507         _reply: &mut BorrowedParcel<'_>,
508     ) -> Result<()> {
509         Ok(())
510     }
511 
on_dump(&self, _file: &File, _args: &[&CStr]) -> Result<()>512     fn on_dump(&self, _file: &File, _args: &[&CStr]) -> Result<()> {
513         Ok(())
514     }
515 
516     binder_fn_get_class!(Binder::<Self>);
517 }
518 
519 impl Interface for () {}
520 
521 /// Determine whether the current thread is currently executing an incoming
522 /// transaction.
is_handling_transaction() -> bool523 pub fn is_handling_transaction() -> bool {
524     unsafe {
525         // Safety: This method is always safe to call.
526         sys::AIBinder_isHandlingTransaction()
527     }
528 }
529