blob: ea8ba2f1e6dfeb7d220d1b7277ab0e6019f7fedf [file] [log] [blame]
The Android Open Source Project9066cfe2009-03-03 19:31:44 -08001/*
2 * Copyright (C) 2006 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
17package android.os;
18
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080019import android.util.Log;
Dianne Hackborn017c6a22014-09-25 17:41:34 -070020import android.util.Slog;
Dianne Hackborndb4e33f2013-04-01 17:28:16 -070021import com.android.internal.util.FastPrintWriter;
Dianne Hackborn9461b6f2015-10-07 17:33:16 -070022import libcore.io.IoUtils;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080023
24import java.io.FileDescriptor;
25import java.io.FileOutputStream;
26import java.io.IOException;
27import java.io.PrintWriter;
28import java.lang.ref.WeakReference;
29import java.lang.reflect.Modifier;
30
31/**
32 * Base class for a remotable object, the core part of a lightweight
33 * remote procedure call mechanism defined by {@link IBinder}.
34 * This class is an implementation of IBinder that provides
Dianne Hackbornab4a81b2014-10-09 17:59:38 -070035 * standard local implementation of such an object.
36 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080037 * <p>Most developers will not implement this class directly, instead using the
Scott Main40eee612012-08-06 17:48:37 -070038 * <a href="{@docRoot}guide/components/aidl.html">aidl</a> tool to describe the desired
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080039 * interface, having it generate the appropriate Binder subclass. You can,
40 * however, derive directly from Binder to implement your own custom RPC
41 * protocol or simply instantiate a raw Binder object directly to use as a
42 * token that can be shared across processes.
Dianne Hackbornab4a81b2014-10-09 17:59:38 -070043 *
44 * <p>This class is just a basic IPC primitive; it has no impact on an application's
45 * lifecycle, and is valid only as long as the process that created it continues to run.
46 * To use this correctly, you must be doing so within the context of a top-level
47 * application component (a {@link android.app.Service}, {@link android.app.Activity},
48 * or {@link android.content.ContentProvider}) that lets the system know your process
49 * should remain running.</p>
50 *
51 * <p>You must keep in mind the situations in which your process
52 * could go away, and thus require that you later re-create a new Binder and re-attach
53 * it when the process starts again. For example, if you are using this within an
54 * {@link android.app.Activity}, your activity's process may be killed any time the
55 * activity is not started; if the activity is later re-created you will need to
56 * create a new Binder and hand it back to the correct place again; you need to be
57 * aware that your process may be started for another reason (for example to receive
58 * a broadcast) that will not involve re-creating the activity and thus run its code
59 * to create a new Binder.</p>
60 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080061 * @see IBinder
62 */
63public class Binder implements IBinder {
64 /*
65 * Set this flag to true to detect anonymous, local or member classes
66 * that extend this Binder class and that are not static. These kind
67 * of classes can potentially create leaks.
68 */
69 private static final boolean FIND_POTENTIAL_LEAKS = false;
Dianne Hackborn73d6a822014-09-29 10:52:47 -070070 private static final boolean CHECK_PARCEL_SIZE = false;
Dianne Hackborn017c6a22014-09-25 17:41:34 -070071 static final String TAG = "Binder";
The Android Open Source Project9066cfe2009-03-03 19:31:44 -080072
Makoto Onukif9b941f2016-03-10 17:19:08 -080073 /** @hide */
74 public static boolean LOG_RUNTIME_EXCEPTION = false; // DO NOT SUBMIT WITH TRUE
75
Dianne Hackborn5b88a2f2013-05-03 16:25:11 -070076 /**
77 * Control whether dump() calls are allowed.
78 */
79 private static String sDumpDisabled = null;
80
Rahul Chaturvedi52613f92015-06-17 23:54:08 -040081 /**
82 * Global transaction tracker instance for this process.
83 */
84 private static TransactionTracker sTransactionTracker = null;
85
86 // Transaction tracking code.
87
88 /**
89 * Flag indicating whether we should be tracing transact calls.
90 *
91 */
92 private static boolean sTracingEnabled = false;
93
94 /**
95 * Enable Binder IPC tracing.
96 *
97 * @hide
98 */
99 public static void enableTracing() {
100 sTracingEnabled = true;
101 };
102
103 /**
104 * Disable Binder IPC tracing.
105 *
106 * @hide
107 */
108 public static void disableTracing() {
109 sTracingEnabled = false;
110 }
111
112 /**
113 * Check if binder transaction tracing is enabled.
114 *
115 * @hide
116 */
117 public static boolean isTracingEnabled() {
118 return sTracingEnabled;
119 }
120
121 /**
122 * Get the binder transaction tracker for this process.
123 *
124 * @hide
125 */
126 public synchronized static TransactionTracker getTransactionTracker() {
127 if (sTransactionTracker == null)
128 sTransactionTracker = new TransactionTracker();
129 return sTransactionTracker;
130 }
131
Amith Yamasani742a6712011-05-04 14:49:28 -0700132 /* mObject is used by native code, do not remove or rename */
Ashok Bhat8ab665d2014-01-22 16:00:20 +0000133 private long mObject;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800134 private IInterface mOwner;
135 private String mDescriptor;
Rahul Chaturvedi52613f92015-06-17 23:54:08 -0400136
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800137 /**
138 * Return the ID of the process that sent you the current transaction
139 * that is being processed. This pid can be used with higher-level
140 * system services to determine its identity and check permissions.
141 * If the current thread is not currently executing an incoming transaction,
142 * then its own pid is returned.
143 */
144 public static final native int getCallingPid();
145
146 /**
Dianne Hackborn74ee8652012-09-07 18:33:18 -0700147 * Return the Linux uid assigned to the process that sent you the
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800148 * current transaction that is being processed. This uid can be used with
149 * higher-level system services to determine its identity and check
150 * permissions. If the current thread is not currently executing an
151 * incoming transaction, then its own uid is returned.
152 */
153 public static final native int getCallingUid();
Amith Yamasani742a6712011-05-04 14:49:28 -0700154
155 /**
Dianne Hackborn74ee8652012-09-07 18:33:18 -0700156 * Return the UserHandle assigned to the process that sent you the
157 * current transaction that is being processed. This is the user
158 * of the caller. It is distinct from {@link #getCallingUid()} in that a
159 * particular user will have multiple distinct apps running under it each
160 * with their own uid. If the current thread is not currently executing an
161 * incoming transaction, then its own UserHandle is returned.
162 */
163 public static final UserHandle getCallingUserHandle() {
Fyodor Kupolov02cb6e72015-09-18 18:20:55 -0700164 return UserHandle.of(UserHandle.getUserId(getCallingUid()));
Dianne Hackborn74ee8652012-09-07 18:33:18 -0700165 }
166
167 /**
Brad Fitzpatricka0527f22010-03-25 20:40:34 -0700168 * Reset the identity of the incoming IPC on the current thread. This can
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800169 * be useful if, while handling an incoming call, you will be calling
170 * on interfaces of other objects that may be local to your process and
171 * need to do permission checks on the calls coming into them (so they
172 * will check the permission of your own local process, and not whatever
173 * process originally called you).
Brad Fitzpatricka0527f22010-03-25 20:40:34 -0700174 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800175 * @return Returns an opaque token that can be used to restore the
176 * original calling identity by passing it to
177 * {@link #restoreCallingIdentity(long)}.
Brad Fitzpatricka0527f22010-03-25 20:40:34 -0700178 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800179 * @see #getCallingPid()
180 * @see #getCallingUid()
181 * @see #restoreCallingIdentity(long)
182 */
183 public static final native long clearCallingIdentity();
Brad Fitzpatricka0527f22010-03-25 20:40:34 -0700184
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800185 /**
Brad Fitzpatricka0527f22010-03-25 20:40:34 -0700186 * Restore the identity of the incoming IPC on the current thread
187 * back to a previously identity that was returned by {@link
188 * #clearCallingIdentity}.
189 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800190 * @param token The opaque token that was previously returned by
191 * {@link #clearCallingIdentity}.
Brad Fitzpatricka0527f22010-03-25 20:40:34 -0700192 *
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800193 * @see #clearCallingIdentity
194 */
195 public static final native void restoreCallingIdentity(long token);
Brad Fitzpatrick727de402010-07-07 16:06:39 -0700196
197 /**
198 * Sets the native thread-local StrictMode policy mask.
199 *
200 * <p>The StrictMode settings are kept in two places: a Java-level
201 * threadlocal for libcore/Dalvik, and a native threadlocal (set
202 * here) for propagation via Binder calls. This is a little
203 * unfortunate, but necessary to break otherwise more unfortunate
204 * dependencies either of Dalvik on Android, or Android
205 * native-only code on Dalvik.
206 *
207 * @see StrictMode
208 * @hide
209 */
210 public static final native void setThreadStrictModePolicy(int policyMask);
211
212 /**
213 * Gets the current native thread-local StrictMode policy mask.
214 *
215 * @see #setThreadStrictModePolicy
216 * @hide
217 */
218 public static final native int getThreadStrictModePolicy();
219
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800220 /**
221 * Flush any Binder commands pending in the current thread to the kernel
222 * driver. This can be
223 * useful to call before performing an operation that may block for a long
224 * time, to ensure that any pending object references have been released
225 * in order to prevent the process from holding on to objects longer than
226 * it needs to.
227 */
228 public static final native void flushPendingCommands();
229
230 /**
231 * Add the calling thread to the IPC thread pool. This function does
232 * not return until the current process is exiting.
233 */
234 public static final native void joinThreadPool();
Jeff Brown1951ce82013-04-04 22:45:12 -0700235
236 /**
237 * Returns true if the specified interface is a proxy.
238 * @hide
239 */
240 public static final boolean isProxy(IInterface iface) {
241 return iface.asBinder() != iface;
242 }
243
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800244 /**
Wale Ogunwaled7fdd022015-04-13 16:22:38 -0700245 * Call blocks until the number of executing binder threads is less
246 * than the maximum number of binder threads allowed for this process.
Wale Ogunwale8d906342015-04-15 09:10:03 -0700247 * @hide
Wale Ogunwaled7fdd022015-04-13 16:22:38 -0700248 */
249 public static final native void blockUntilThreadAvailable();
250
251 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800252 * Default constructor initializes the object.
253 */
254 public Binder() {
255 init();
256
257 if (FIND_POTENTIAL_LEAKS) {
258 final Class<? extends Binder> klass = getClass();
259 if ((klass.isAnonymousClass() || klass.isMemberClass() || klass.isLocalClass()) &&
260 (klass.getModifiers() & Modifier.STATIC) == 0) {
261 Log.w(TAG, "The following Binder class should be static or leaks might occur: " +
262 klass.getCanonicalName());
263 }
264 }
265 }
266
267 /**
268 * Convenience method for associating a specific interface with the Binder.
269 * After calling, queryLocalInterface() will be implemented for you
270 * to return the given owner IInterface when the corresponding
271 * descriptor is requested.
272 */
273 public void attachInterface(IInterface owner, String descriptor) {
274 mOwner = owner;
275 mDescriptor = descriptor;
276 }
277
278 /**
279 * Default implementation returns an empty interface name.
280 */
281 public String getInterfaceDescriptor() {
282 return mDescriptor;
283 }
284
285 /**
286 * Default implementation always returns true -- if you got here,
287 * the object is alive.
288 */
289 public boolean pingBinder() {
290 return true;
291 }
292
293 /**
294 * {@inheritDoc}
295 *
296 * Note that if you're calling on a local binder, this always returns true
297 * because your process is alive if you're calling it.
298 */
299 public boolean isBinderAlive() {
300 return true;
301 }
302
303 /**
304 * Use information supplied to attachInterface() to return the
305 * associated IInterface if it matches the requested
306 * descriptor.
307 */
308 public IInterface queryLocalInterface(String descriptor) {
309 if (mDescriptor.equals(descriptor)) {
310 return mOwner;
311 }
312 return null;
313 }
Dianne Hackborn5b88a2f2013-05-03 16:25:11 -0700314
315 /**
316 * Control disabling of dump calls in this process. This is used by the system
317 * process watchdog to disable incoming dump calls while it has detecting the system
318 * is hung and is reporting that back to the activity controller. This is to
319 * prevent the controller from getting hung up on bug reports at this point.
320 * @hide
321 *
322 * @param msg The message to show instead of the dump; if null, dumps are
323 * re-enabled.
324 */
325 public static void setDumpDisabled(String msg) {
326 synchronized (Binder.class) {
327 sDumpDisabled = msg;
328 }
329 }
330
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800331 /**
332 * Default implementation is a stub that returns false. You will want
333 * to override this to do the appropriate unmarshalling of transactions.
334 *
335 * <p>If you want to call this, call transact().
336 */
337 protected boolean onTransact(int code, Parcel data, Parcel reply,
338 int flags) throws RemoteException {
339 if (code == INTERFACE_TRANSACTION) {
340 reply.writeString(getInterfaceDescriptor());
341 return true;
342 } else if (code == DUMP_TRANSACTION) {
343 ParcelFileDescriptor fd = data.readFileDescriptor();
344 String[] args = data.readStringArray();
345 if (fd != null) {
346 try {
347 dump(fd.getFileDescriptor(), args);
348 } finally {
Dianne Hackborn9461b6f2015-10-07 17:33:16 -0700349 IoUtils.closeQuietly(fd);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800350 }
351 }
Brad Fitzpatrickeb75888e2010-07-26 17:47:45 -0700352 // Write the StrictMode header.
353 if (reply != null) {
354 reply.writeNoException();
355 } else {
356 StrictMode.clearGatheredViolations();
357 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800358 return true;
Dianne Hackborn9461b6f2015-10-07 17:33:16 -0700359 } else if (code == SHELL_COMMAND_TRANSACTION) {
360 ParcelFileDescriptor in = data.readFileDescriptor();
361 ParcelFileDescriptor out = data.readFileDescriptor();
362 ParcelFileDescriptor err = data.readFileDescriptor();
363 String[] args = data.readStringArray();
364 ResultReceiver resultReceiver = ResultReceiver.CREATOR.createFromParcel(data);
365 try {
366 if (out != null) {
367 shellCommand(in != null ? in.getFileDescriptor() : null,
368 out.getFileDescriptor(),
369 err != null ? err.getFileDescriptor() : out.getFileDescriptor(),
370 args, resultReceiver);
371 }
372 } finally {
373 IoUtils.closeQuietly(in);
374 IoUtils.closeQuietly(out);
375 IoUtils.closeQuietly(err);
376 // Write the StrictMode header.
377 if (reply != null) {
378 reply.writeNoException();
379 } else {
380 StrictMode.clearGatheredViolations();
381 }
382 }
383 return true;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800384 }
385 return false;
386 }
387
388 /**
389 * Implemented to call the more convenient version
390 * {@link #dump(FileDescriptor, PrintWriter, String[])}.
391 */
392 public void dump(FileDescriptor fd, String[] args) {
393 FileOutputStream fout = new FileOutputStream(fd);
Dianne Hackborndb4e33f2013-04-01 17:28:16 -0700394 PrintWriter pw = new FastPrintWriter(fout);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800395 try {
Dianne Hackborn9461b6f2015-10-07 17:33:16 -0700396 doDump(fd, pw, args);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800397 } finally {
398 pw.flush();
399 }
400 }
Dianne Hackborn9461b6f2015-10-07 17:33:16 -0700401
402 void doDump(FileDescriptor fd, PrintWriter pw, String[] args) {
403 final String disabled;
404 synchronized (Binder.class) {
405 disabled = sDumpDisabled;
406 }
407 if (disabled == null) {
408 try {
409 dump(fd, pw, args);
410 } catch (SecurityException e) {
411 pw.println("Security exception: " + e.getMessage());
412 throw e;
413 } catch (Throwable e) {
414 // Unlike usual calls, in this case if an exception gets thrown
415 // back to us we want to print it back in to the dump data, since
416 // that is where the caller expects all interesting information to
417 // go.
418 pw.println();
419 pw.println("Exception occurred while dumping:");
420 e.printStackTrace(pw);
421 }
422 } else {
423 pw.println(sDumpDisabled);
424 }
425 }
426
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800427 /**
Dianne Hackborne17aeb32011-04-07 15:11:57 -0700428 * Like {@link #dump(FileDescriptor, String[])}, but ensures the target
429 * executes asynchronously.
430 */
431 public void dumpAsync(final FileDescriptor fd, final String[] args) {
432 final FileOutputStream fout = new FileOutputStream(fd);
Dianne Hackborndb4e33f2013-04-01 17:28:16 -0700433 final PrintWriter pw = new FastPrintWriter(fout);
Dianne Hackborne17aeb32011-04-07 15:11:57 -0700434 Thread thr = new Thread("Binder.dumpAsync") {
435 public void run() {
436 try {
437 dump(fd, pw, args);
438 } finally {
439 pw.flush();
440 }
441 }
442 };
443 thr.start();
444 }
445
446 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800447 * Print the object's state into the given stream.
448 *
449 * @param fd The raw file descriptor that the dump is being sent to.
450 * @param fout The file to which you should dump your state. This will be
451 * closed for you after you return.
452 * @param args additional arguments to the dump request.
453 */
454 protected void dump(FileDescriptor fd, PrintWriter fout, String[] args) {
455 }
456
457 /**
Dianne Hackborn9461b6f2015-10-07 17:33:16 -0700458 * @param in The raw file descriptor that an input data stream can be read from.
459 * @param out The raw file descriptor that normal command messages should be written to.
460 * @param err The raw file descriptor that command error messages should be written to.
461 * @param args Command-line arguments.
462 * @param resultReceiver Called when the command has finished executing, with the result code.
463 * @throws RemoteException
464 * @hide
465 */
466 public void shellCommand(FileDescriptor in, FileDescriptor out, FileDescriptor err,
467 String[] args, ResultReceiver resultReceiver) throws RemoteException {
468 onShellCommand(in, out, err, args, resultReceiver);
469 }
470
471 /**
472 * Handle a call to {@link #shellCommand}. The default implementation simply prints
473 * an error message. Override and replace with your own.
Dianne Hackborn2e931f52016-01-28 12:21:17 -0800474 * <p class="caution">Note: no permission checking is done before calling this method; you must
475 * apply any security checks as appropriate for the command being executed.
476 * Consider using {@link ShellCommand} to help in the implementation.</p>
Dianne Hackborn9461b6f2015-10-07 17:33:16 -0700477 * @hide
478 */
479 public void onShellCommand(FileDescriptor in, FileDescriptor out, FileDescriptor err,
480 String[] args, ResultReceiver resultReceiver) throws RemoteException {
481 FileOutputStream fout = new FileOutputStream(err != null ? err : out);
482 PrintWriter pw = new FastPrintWriter(fout);
483 pw.println("No shell command implementation.");
484 pw.flush();
485 resultReceiver.send(0, null);
486 }
487
488 /**
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800489 * Default implementation rewinds the parcels and calls onTransact. On
490 * the remote side, transact calls into the binder to do the IPC.
491 */
492 public final boolean transact(int code, Parcel data, Parcel reply,
493 int flags) throws RemoteException {
Joe Onorato43a17652011-04-06 19:22:23 -0700494 if (false) Log.v("Binder", "Transact: " + code + " to " + this);
Rahul Chaturvedi52613f92015-06-17 23:54:08 -0400495
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800496 if (data != null) {
497 data.setDataPosition(0);
498 }
499 boolean r = onTransact(code, data, reply, flags);
500 if (reply != null) {
501 reply.setDataPosition(0);
502 }
503 return r;
504 }
505
506 /**
507 * Local implementation is a no-op.
508 */
509 public void linkToDeath(DeathRecipient recipient, int flags) {
510 }
511
512 /**
513 * Local implementation is a no-op.
514 */
515 public boolean unlinkToDeath(DeathRecipient recipient, int flags) {
516 return true;
517 }
518
519 protected void finalize() throws Throwable {
520 try {
521 destroy();
522 } finally {
523 super.finalize();
524 }
525 }
Dianne Hackborn017c6a22014-09-25 17:41:34 -0700526
Dianne Hackbornfad079d2014-09-26 15:46:24 -0700527 static void checkParcel(IBinder obj, int code, Parcel parcel, String msg) {
Dianne Hackborn73d6a822014-09-29 10:52:47 -0700528 if (CHECK_PARCEL_SIZE && parcel.dataSize() >= 800*1024) {
Dianne Hackborn017c6a22014-09-25 17:41:34 -0700529 // Trying to send > 800k, this is way too much
Dianne Hackbornfad079d2014-09-26 15:46:24 -0700530 StringBuilder sb = new StringBuilder();
531 sb.append(msg);
532 sb.append(": on ");
533 sb.append(obj);
534 sb.append(" calling ");
535 sb.append(code);
536 sb.append(" size ");
537 sb.append(parcel.dataSize());
538 sb.append(" (data: ");
539 parcel.setDataPosition(0);
540 sb.append(parcel.readInt());
541 sb.append(", ");
542 sb.append(parcel.readInt());
543 sb.append(", ");
544 sb.append(parcel.readInt());
545 sb.append(")");
546 Slog.wtfStack(TAG, sb.toString());
Dianne Hackborn017c6a22014-09-25 17:41:34 -0700547 }
548 }
549
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800550 private native final void init();
551 private native final void destroy();
Brad Fitzpatrick5b747192010-07-12 11:05:38 -0700552
553 // Entry point from android_util_Binder.cpp's onTransact
Ashok Bhat8ab665d2014-01-22 16:00:20 +0000554 private boolean execTransact(int code, long dataObj, long replyObj,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800555 int flags) {
556 Parcel data = Parcel.obtain(dataObj);
557 Parcel reply = Parcel.obtain(replyObj);
558 // theoretically, we should call transact, which will call onTransact,
559 // but all that does is rewind it, and we just got these from an IPC,
560 // so we'll just call it directly.
561 boolean res;
Igor Murashkin7eb6cfe2013-08-16 14:07:11 -0700562 // Log any exceptions as warnings, don't silently suppress them.
563 // If the call was FLAG_ONEWAY then these exceptions disappear into the ether.
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800564 try {
565 res = onTransact(code, data, reply, flags);
Makoto Onukif9b941f2016-03-10 17:19:08 -0800566 } catch (RemoteException|RuntimeException e) {
567 if (LOG_RUNTIME_EXCEPTION) {
Igor Murashkin7eb6cfe2013-08-16 14:07:11 -0700568 Log.w(TAG, "Caught a RuntimeException from the binder stub implementation.", e);
Makoto Onukif9b941f2016-03-10 17:19:08 -0800569 }
570 if ((flags & FLAG_ONEWAY) != 0) {
571 if (e instanceof RemoteException) {
572 Log.w(TAG, "Binder call failed.", e);
573 } else {
574 Log.w(TAG, "Caught a RuntimeException from the binder stub implementation.", e);
575 }
Dianne Hackbornce92b0d2014-09-30 11:28:18 -0700576 } else {
577 reply.setDataPosition(0);
578 reply.writeException(e);
Igor Murashkin7eb6cfe2013-08-16 14:07:11 -0700579 }
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800580 res = true;
Mattias Petersson19f22742010-11-05 08:25:38 +0100581 } catch (OutOfMemoryError e) {
Igor Murashkin7eb6cfe2013-08-16 14:07:11 -0700582 // Unconditionally log this, since this is generally unrecoverable.
583 Log.e(TAG, "Caught an OutOfMemoryError from the binder stub implementation.", e);
Mattias Petersson19f22742010-11-05 08:25:38 +0100584 RuntimeException re = new RuntimeException("Out of memory", e);
Jeff Sharkey7f97e652011-12-14 18:07:54 -0800585 reply.setDataPosition(0);
Mattias Petersson19f22742010-11-05 08:25:38 +0100586 reply.writeException(re);
587 res = true;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800588 }
Dianne Hackbornfad079d2014-09-26 15:46:24 -0700589 checkParcel(this, code, reply, "Unreasonably large binder reply buffer");
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800590 reply.recycle();
591 data.recycle();
Dianne Hackbornce92b0d2014-09-30 11:28:18 -0700592
593 // Just in case -- we are done with the IPC, so there should be no more strict
594 // mode violations that have gathered for this thread. Either they have been
595 // parceled and are now in transport off to the caller, or we are returning back
596 // to the main transaction loop to wait for another incoming transaction. Either
597 // way, strict mode begone!
598 StrictMode.clearGatheredViolations();
599
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800600 return res;
601 }
602}
603
604final class BinderProxy implements IBinder {
605 public native boolean pingBinder();
606 public native boolean isBinderAlive();
Dianne Hackborn017c6a22014-09-25 17:41:34 -0700607
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800608 public IInterface queryLocalInterface(String descriptor) {
609 return null;
610 }
Dianne Hackborn017c6a22014-09-25 17:41:34 -0700611
612 public boolean transact(int code, Parcel data, Parcel reply, int flags) throws RemoteException {
Dianne Hackbornfad079d2014-09-26 15:46:24 -0700613 Binder.checkParcel(this, code, data, "Unreasonably large binder buffer");
Rahul Chaturvedi52613f92015-06-17 23:54:08 -0400614 if (Binder.isTracingEnabled()) { Binder.getTransactionTracker().addTrace(); }
Dianne Hackborn017c6a22014-09-25 17:41:34 -0700615 return transactNative(code, data, reply, flags);
616 }
617
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800618 public native String getInterfaceDescriptor() throws RemoteException;
Dianne Hackborn017c6a22014-09-25 17:41:34 -0700619 public native boolean transactNative(int code, Parcel data, Parcel reply,
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800620 int flags) throws RemoteException;
621 public native void linkToDeath(DeathRecipient recipient, int flags)
622 throws RemoteException;
623 public native boolean unlinkToDeath(DeathRecipient recipient, int flags);
624
625 public void dump(FileDescriptor fd, String[] args) throws RemoteException {
626 Parcel data = Parcel.obtain();
Brad Fitzpatrickeb75888e2010-07-26 17:47:45 -0700627 Parcel reply = Parcel.obtain();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800628 data.writeFileDescriptor(fd);
629 data.writeStringArray(args);
630 try {
Brad Fitzpatrickeb75888e2010-07-26 17:47:45 -0700631 transact(DUMP_TRANSACTION, data, reply, 0);
632 reply.readException();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800633 } finally {
634 data.recycle();
Brad Fitzpatrickeb75888e2010-07-26 17:47:45 -0700635 reply.recycle();
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800636 }
637 }
638
Dianne Hackborne17aeb32011-04-07 15:11:57 -0700639 public void dumpAsync(FileDescriptor fd, String[] args) throws RemoteException {
640 Parcel data = Parcel.obtain();
641 Parcel reply = Parcel.obtain();
642 data.writeFileDescriptor(fd);
643 data.writeStringArray(args);
644 try {
645 transact(DUMP_TRANSACTION, data, reply, FLAG_ONEWAY);
Dianne Hackborne17aeb32011-04-07 15:11:57 -0700646 } finally {
647 data.recycle();
648 reply.recycle();
649 }
650 }
651
Dianne Hackborn9461b6f2015-10-07 17:33:16 -0700652 public void shellCommand(FileDescriptor in, FileDescriptor out, FileDescriptor err,
653 String[] args, ResultReceiver resultReceiver) throws RemoteException {
654 Parcel data = Parcel.obtain();
655 Parcel reply = Parcel.obtain();
656 data.writeFileDescriptor(in);
657 data.writeFileDescriptor(out);
658 data.writeFileDescriptor(err);
659 data.writeStringArray(args);
660 resultReceiver.writeToParcel(data, 0);
661 try {
662 transact(SHELL_COMMAND_TRANSACTION, data, reply, 0);
663 reply.readException();
664 } finally {
665 data.recycle();
666 reply.recycle();
667 }
668 }
669
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800670 BinderProxy() {
671 mSelf = new WeakReference(this);
672 }
673
674 @Override
675 protected void finalize() throws Throwable {
676 try {
677 destroy();
678 } finally {
679 super.finalize();
680 }
681 }
682
683 private native final void destroy();
684
685 private static final void sendDeathNotice(DeathRecipient recipient) {
Joe Onorato43a17652011-04-06 19:22:23 -0700686 if (false) Log.v("JavaBinder", "sendDeathNotice to " + recipient);
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800687 try {
688 recipient.binderDied();
689 }
690 catch (RuntimeException exc) {
691 Log.w("BinderNative", "Uncaught exception from death notification",
692 exc);
693 }
694 }
695
696 final private WeakReference mSelf;
Ashok Bhat8ab665d2014-01-22 16:00:20 +0000697 private long mObject;
698 private long mOrgue;
The Android Open Source Project9066cfe2009-03-03 19:31:44 -0800699}