Binder.java revision 1951ce86c21445ac191e4d2d95233f4f5c096b56
1/* 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 19import android.util.Log; 20 21import java.io.FileDescriptor; 22import java.io.FileOutputStream; 23import java.io.IOException; 24import java.io.PrintWriter; 25import java.lang.ref.WeakReference; 26import java.lang.reflect.Modifier; 27 28/** 29 * Base class for a remotable object, the core part of a lightweight 30 * remote procedure call mechanism defined by {@link IBinder}. 31 * This class is an implementation of IBinder that provides 32 * the standard support creating a local implementation of such an object. 33 * 34 * <p>Most developers will not implement this class directly, instead using the 35 * <a href="{@docRoot}guide/components/aidl.html">aidl</a> tool to describe the desired 36 * interface, having it generate the appropriate Binder subclass. You can, 37 * however, derive directly from Binder to implement your own custom RPC 38 * protocol or simply instantiate a raw Binder object directly to use as a 39 * token that can be shared across processes. 40 * 41 * @see IBinder 42 */ 43public class Binder implements IBinder { 44 /* 45 * Set this flag to true to detect anonymous, local or member classes 46 * that extend this Binder class and that are not static. These kind 47 * of classes can potentially create leaks. 48 */ 49 private static final boolean FIND_POTENTIAL_LEAKS = false; 50 private static final String TAG = "Binder"; 51 52 /* mObject is used by native code, do not remove or rename */ 53 private int mObject; 54 private IInterface mOwner; 55 private String mDescriptor; 56 57 /** 58 * Return the ID of the process that sent you the current transaction 59 * that is being processed. This pid can be used with higher-level 60 * system services to determine its identity and check permissions. 61 * If the current thread is not currently executing an incoming transaction, 62 * then its own pid is returned. 63 */ 64 public static final native int getCallingPid(); 65 66 /** 67 * Return the Linux uid assigned to the process that sent you the 68 * current transaction that is being processed. This uid can be used with 69 * higher-level system services to determine its identity and check 70 * permissions. If the current thread is not currently executing an 71 * incoming transaction, then its own uid is returned. 72 */ 73 public static final native int getCallingUid(); 74 75 /** 76 * Return the UserHandle assigned to the process that sent you the 77 * current transaction that is being processed. This is the user 78 * of the caller. It is distinct from {@link #getCallingUid()} in that a 79 * particular user will have multiple distinct apps running under it each 80 * with their own uid. If the current thread is not currently executing an 81 * incoming transaction, then its own UserHandle is returned. 82 */ 83 public static final UserHandle getCallingUserHandle() { 84 return new UserHandle(UserHandle.getUserId(getCallingUid())); 85 } 86 87 /** 88 * Reset the identity of the incoming IPC on the current thread. This can 89 * be useful if, while handling an incoming call, you will be calling 90 * on interfaces of other objects that may be local to your process and 91 * need to do permission checks on the calls coming into them (so they 92 * will check the permission of your own local process, and not whatever 93 * process originally called you). 94 * 95 * @return Returns an opaque token that can be used to restore the 96 * original calling identity by passing it to 97 * {@link #restoreCallingIdentity(long)}. 98 * 99 * @see #getCallingPid() 100 * @see #getCallingUid() 101 * @see #restoreCallingIdentity(long) 102 */ 103 public static final native long clearCallingIdentity(); 104 105 /** 106 * Restore the identity of the incoming IPC on the current thread 107 * back to a previously identity that was returned by {@link 108 * #clearCallingIdentity}. 109 * 110 * @param token The opaque token that was previously returned by 111 * {@link #clearCallingIdentity}. 112 * 113 * @see #clearCallingIdentity 114 */ 115 public static final native void restoreCallingIdentity(long token); 116 117 /** 118 * Sets the native thread-local StrictMode policy mask. 119 * 120 * <p>The StrictMode settings are kept in two places: a Java-level 121 * threadlocal for libcore/Dalvik, and a native threadlocal (set 122 * here) for propagation via Binder calls. This is a little 123 * unfortunate, but necessary to break otherwise more unfortunate 124 * dependencies either of Dalvik on Android, or Android 125 * native-only code on Dalvik. 126 * 127 * @see StrictMode 128 * @hide 129 */ 130 public static final native void setThreadStrictModePolicy(int policyMask); 131 132 /** 133 * Gets the current native thread-local StrictMode policy mask. 134 * 135 * @see #setThreadStrictModePolicy 136 * @hide 137 */ 138 public static final native int getThreadStrictModePolicy(); 139 140 /** 141 * Flush any Binder commands pending in the current thread to the kernel 142 * driver. This can be 143 * useful to call before performing an operation that may block for a long 144 * time, to ensure that any pending object references have been released 145 * in order to prevent the process from holding on to objects longer than 146 * it needs to. 147 */ 148 public static final native void flushPendingCommands(); 149 150 /** 151 * Add the calling thread to the IPC thread pool. This function does 152 * not return until the current process is exiting. 153 */ 154 public static final native void joinThreadPool(); 155 156 /** 157 * Returns true if the specified interface is a proxy. 158 * @hide 159 */ 160 public static final boolean isProxy(IInterface iface) { 161 return iface.asBinder() != iface; 162 } 163 164 /** 165 * Default constructor initializes the object. 166 */ 167 public Binder() { 168 init(); 169 170 if (FIND_POTENTIAL_LEAKS) { 171 final Class<? extends Binder> klass = getClass(); 172 if ((klass.isAnonymousClass() || klass.isMemberClass() || klass.isLocalClass()) && 173 (klass.getModifiers() & Modifier.STATIC) == 0) { 174 Log.w(TAG, "The following Binder class should be static or leaks might occur: " + 175 klass.getCanonicalName()); 176 } 177 } 178 } 179 180 /** 181 * Convenience method for associating a specific interface with the Binder. 182 * After calling, queryLocalInterface() will be implemented for you 183 * to return the given owner IInterface when the corresponding 184 * descriptor is requested. 185 */ 186 public void attachInterface(IInterface owner, String descriptor) { 187 mOwner = owner; 188 mDescriptor = descriptor; 189 } 190 191 /** 192 * Default implementation returns an empty interface name. 193 */ 194 public String getInterfaceDescriptor() { 195 return mDescriptor; 196 } 197 198 /** 199 * Default implementation always returns true -- if you got here, 200 * the object is alive. 201 */ 202 public boolean pingBinder() { 203 return true; 204 } 205 206 /** 207 * {@inheritDoc} 208 * 209 * Note that if you're calling on a local binder, this always returns true 210 * because your process is alive if you're calling it. 211 */ 212 public boolean isBinderAlive() { 213 return true; 214 } 215 216 /** 217 * Use information supplied to attachInterface() to return the 218 * associated IInterface if it matches the requested 219 * descriptor. 220 */ 221 public IInterface queryLocalInterface(String descriptor) { 222 if (mDescriptor.equals(descriptor)) { 223 return mOwner; 224 } 225 return null; 226 } 227 228 /** 229 * Default implementation is a stub that returns false. You will want 230 * to override this to do the appropriate unmarshalling of transactions. 231 * 232 * <p>If you want to call this, call transact(). 233 */ 234 protected boolean onTransact(int code, Parcel data, Parcel reply, 235 int flags) throws RemoteException { 236 if (code == INTERFACE_TRANSACTION) { 237 reply.writeString(getInterfaceDescriptor()); 238 return true; 239 } else if (code == DUMP_TRANSACTION) { 240 ParcelFileDescriptor fd = data.readFileDescriptor(); 241 String[] args = data.readStringArray(); 242 if (fd != null) { 243 try { 244 dump(fd.getFileDescriptor(), args); 245 } finally { 246 try { 247 fd.close(); 248 } catch (IOException e) { 249 // swallowed, not propagated back to the caller 250 } 251 } 252 } 253 // Write the StrictMode header. 254 if (reply != null) { 255 reply.writeNoException(); 256 } else { 257 StrictMode.clearGatheredViolations(); 258 } 259 return true; 260 } 261 return false; 262 } 263 264 /** 265 * Implemented to call the more convenient version 266 * {@link #dump(FileDescriptor, PrintWriter, String[])}. 267 */ 268 public void dump(FileDescriptor fd, String[] args) { 269 FileOutputStream fout = new FileOutputStream(fd); 270 PrintWriter pw = new PrintWriter(fout); 271 try { 272 dump(fd, pw, args); 273 } finally { 274 pw.flush(); 275 } 276 } 277 278 /** 279 * Like {@link #dump(FileDescriptor, String[])}, but ensures the target 280 * executes asynchronously. 281 */ 282 public void dumpAsync(final FileDescriptor fd, final String[] args) { 283 final FileOutputStream fout = new FileOutputStream(fd); 284 final PrintWriter pw = new PrintWriter(fout); 285 Thread thr = new Thread("Binder.dumpAsync") { 286 public void run() { 287 try { 288 dump(fd, pw, args); 289 } finally { 290 pw.flush(); 291 } 292 } 293 }; 294 thr.start(); 295 } 296 297 /** 298 * Print the object's state into the given stream. 299 * 300 * @param fd The raw file descriptor that the dump is being sent to. 301 * @param fout The file to which you should dump your state. This will be 302 * closed for you after you return. 303 * @param args additional arguments to the dump request. 304 */ 305 protected void dump(FileDescriptor fd, PrintWriter fout, String[] args) { 306 } 307 308 /** 309 * Default implementation rewinds the parcels and calls onTransact. On 310 * the remote side, transact calls into the binder to do the IPC. 311 */ 312 public final boolean transact(int code, Parcel data, Parcel reply, 313 int flags) throws RemoteException { 314 if (false) Log.v("Binder", "Transact: " + code + " to " + this); 315 if (data != null) { 316 data.setDataPosition(0); 317 } 318 boolean r = onTransact(code, data, reply, flags); 319 if (reply != null) { 320 reply.setDataPosition(0); 321 } 322 return r; 323 } 324 325 /** 326 * Local implementation is a no-op. 327 */ 328 public void linkToDeath(DeathRecipient recipient, int flags) { 329 } 330 331 /** 332 * Local implementation is a no-op. 333 */ 334 public boolean unlinkToDeath(DeathRecipient recipient, int flags) { 335 return true; 336 } 337 338 protected void finalize() throws Throwable { 339 try { 340 destroy(); 341 } finally { 342 super.finalize(); 343 } 344 } 345 346 private native final void init(); 347 private native final void destroy(); 348 349 // Entry point from android_util_Binder.cpp's onTransact 350 private boolean execTransact(int code, int dataObj, int replyObj, 351 int flags) { 352 Parcel data = Parcel.obtain(dataObj); 353 Parcel reply = Parcel.obtain(replyObj); 354 // theoretically, we should call transact, which will call onTransact, 355 // but all that does is rewind it, and we just got these from an IPC, 356 // so we'll just call it directly. 357 boolean res; 358 try { 359 res = onTransact(code, data, reply, flags); 360 } catch (RemoteException e) { 361 reply.setDataPosition(0); 362 reply.writeException(e); 363 res = true; 364 } catch (RuntimeException e) { 365 reply.setDataPosition(0); 366 reply.writeException(e); 367 res = true; 368 } catch (OutOfMemoryError e) { 369 RuntimeException re = new RuntimeException("Out of memory", e); 370 reply.setDataPosition(0); 371 reply.writeException(re); 372 res = true; 373 } 374 reply.recycle(); 375 data.recycle(); 376 return res; 377 } 378} 379 380final class BinderProxy implements IBinder { 381 public native boolean pingBinder(); 382 public native boolean isBinderAlive(); 383 384 public IInterface queryLocalInterface(String descriptor) { 385 return null; 386 } 387 388 public native String getInterfaceDescriptor() throws RemoteException; 389 public native boolean transact(int code, Parcel data, Parcel reply, 390 int flags) throws RemoteException; 391 public native void linkToDeath(DeathRecipient recipient, int flags) 392 throws RemoteException; 393 public native boolean unlinkToDeath(DeathRecipient recipient, int flags); 394 395 public void dump(FileDescriptor fd, String[] args) throws RemoteException { 396 Parcel data = Parcel.obtain(); 397 Parcel reply = Parcel.obtain(); 398 data.writeFileDescriptor(fd); 399 data.writeStringArray(args); 400 try { 401 transact(DUMP_TRANSACTION, data, reply, 0); 402 reply.readException(); 403 } finally { 404 data.recycle(); 405 reply.recycle(); 406 } 407 } 408 409 public void dumpAsync(FileDescriptor fd, String[] args) throws RemoteException { 410 Parcel data = Parcel.obtain(); 411 Parcel reply = Parcel.obtain(); 412 data.writeFileDescriptor(fd); 413 data.writeStringArray(args); 414 try { 415 transact(DUMP_TRANSACTION, data, reply, FLAG_ONEWAY); 416 reply.readException(); 417 } finally { 418 data.recycle(); 419 reply.recycle(); 420 } 421 } 422 423 BinderProxy() { 424 mSelf = new WeakReference(this); 425 } 426 427 @Override 428 protected void finalize() throws Throwable { 429 try { 430 destroy(); 431 } finally { 432 super.finalize(); 433 } 434 } 435 436 private native final void destroy(); 437 438 private static final void sendDeathNotice(DeathRecipient recipient) { 439 if (false) Log.v("JavaBinder", "sendDeathNotice to " + recipient); 440 try { 441 recipient.binderDied(); 442 } 443 catch (RuntimeException exc) { 444 Log.w("BinderNative", "Uncaught exception from death notification", 445 exc); 446 } 447 } 448 449 final private WeakReference mSelf; 450 private int mObject; 451 private int mOrgue; 452} 453