API CHANGE: expose backup/restore to the SDK

The core backup/restore classes [BackupManager, BackupAgent, RestoreSession, and
RestoreObserver] are now published for 3rd party developers, as well as the suite
of helper classes that exist so far to aid authorship of backup/restore agents.

In conjunction with the API change, the restore-time automatic data wipe has now
been removed:  applications are responsible for managing the logic of wipe vs
merge themselves.  If the app's agent onRestore() callback throws, the data
is presumed to be incoherent and a wipe is issued via the Activity Manager;
otherwise, no automatic action is ever taken.

Change-Id: I0b3418b829d4689b58b88be3d9c4ace37a8583a9
diff --git a/api/current.xml b/api/current.xml
index 9c663fe..b5469e7 100644
--- a/api/current.xml
+++ b/api/current.xml
@@ -19850,6 +19850,83 @@
 >
 </method>
 </class>
+<class name="BackupAgent"
+ extends="android.content.ContextWrapper"
+ abstract="true"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<constructor name="BackupAgent"
+ type="android.app.BackupAgent"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</constructor>
+<method name="onBackup"
+ return="void"
+ abstract="true"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="oldState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<parameter name="data" type="android.backup.BackupDataOutput">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+<method name="onCreate"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="onDestroy"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="onRestore"
+ return="void"
+ abstract="true"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="android.backup.BackupDataInput">
+</parameter>
+<parameter name="appVersionCode" type="int">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+</class>
 <class name="DatePickerDialog"
  extends="android.app.AlertDialog"
  abstract="false"
@@ -27399,6 +27476,615 @@
 </field>
 </class>
 </package>
+<package name="android.backup"
+>
+<class name="AbsoluteFileBackupHelper"
+ extends="android.backup.FileBackupHelperBase"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<implements name="android.backup.BackupHelper">
+</implements>
+<constructor name="AbsoluteFileBackupHelper"
+ type="android.backup.AbsoluteFileBackupHelper"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="context" type="android.content.Context">
+</parameter>
+<parameter name="files" type="java.lang.String...">
+</parameter>
+</constructor>
+<method name="performBackup"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="oldState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<parameter name="data" type="android.backup.BackupDataOutput">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+</method>
+<method name="restoreEntity"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="android.backup.BackupDataInputStream">
+</parameter>
+</method>
+</class>
+<class name="BackupDataInput"
+ extends="java.lang.Object"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<method name="getDataSize"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="getKey"
+ return="java.lang.String"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="readEntityData"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="byte[]">
+</parameter>
+<parameter name="offset" type="int">
+</parameter>
+<parameter name="size" type="int">
+</parameter>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+<method name="readNextHeader"
+ return="boolean"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+<method name="skipEntityData"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+</class>
+<class name="BackupDataInputStream"
+ extends="java.io.InputStream"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<method name="getKey"
+ return="java.lang.String"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="read"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+<method name="size"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+</class>
+<class name="BackupDataOutput"
+ extends="java.lang.Object"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<method name="setKeyPrefix"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="keyPrefix" type="java.lang.String">
+</parameter>
+</method>
+<method name="writeEntityData"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="byte[]">
+</parameter>
+<parameter name="size" type="int">
+</parameter>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+<method name="writeEntityHeader"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="key" type="java.lang.String">
+</parameter>
+<parameter name="dataSize" type="int">
+</parameter>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+<field name="OP_DELETE"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="2"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+<field name="OP_UPDATE"
+ type="int"
+ transient="false"
+ volatile="false"
+ value="1"
+ static="true"
+ final="true"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</field>
+</class>
+<interface name="BackupHelper"
+ abstract="true"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<method name="performBackup"
+ return="void"
+ abstract="true"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="oldState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<parameter name="data" type="android.backup.BackupDataOutput">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+</method>
+<method name="restoreEntity"
+ return="void"
+ abstract="true"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="android.backup.BackupDataInputStream">
+</parameter>
+</method>
+<method name="writeRestoreSnapshot"
+ return="void"
+ abstract="true"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="fd" type="android.os.ParcelFileDescriptor">
+</parameter>
+</method>
+</interface>
+<class name="BackupHelperAgent"
+ extends="android.app.BackupAgent"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<constructor name="BackupHelperAgent"
+ type="android.backup.BackupHelperAgent"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</constructor>
+<method name="addHelper"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="keyPrefix" type="java.lang.String">
+</parameter>
+<parameter name="helper" type="android.backup.BackupHelper">
+</parameter>
+</method>
+<method name="onBackup"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="oldState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<parameter name="data" type="android.backup.BackupDataOutput">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+<method name="onRestore"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="android.backup.BackupDataInput">
+</parameter>
+<parameter name="appVersionCode" type="int">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<exception name="IOException" type="java.io.IOException">
+</exception>
+</method>
+</class>
+<class name="BackupManager"
+ extends="java.lang.Object"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<constructor name="BackupManager"
+ type="android.backup.BackupManager"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="context" type="android.content.Context">
+</parameter>
+</constructor>
+<method name="beginRestoreSession"
+ return="android.backup.RestoreSession"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="dataChanged"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="dataChanged"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="true"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="packageName" type="java.lang.String">
+</parameter>
+</method>
+</class>
+<class name="FileBackupHelper"
+ extends="android.backup.FileBackupHelperBase"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<implements name="android.backup.BackupHelper">
+</implements>
+<constructor name="FileBackupHelper"
+ type="android.backup.FileBackupHelper"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="context" type="android.content.Context">
+</parameter>
+<parameter name="files" type="java.lang.String...">
+</parameter>
+</constructor>
+<method name="performBackup"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="oldState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<parameter name="data" type="android.backup.BackupDataOutput">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+</method>
+<method name="restoreEntity"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="android.backup.BackupDataInputStream">
+</parameter>
+</method>
+</class>
+<class name="FileBackupHelperBase"
+ extends="java.lang.Object"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility=""
+>
+<method name="writeRestoreSnapshot"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="fd" type="android.os.ParcelFileDescriptor">
+</parameter>
+</method>
+</class>
+<class name="RestoreObserver"
+ extends="java.lang.Object"
+ abstract="true"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<constructor name="RestoreObserver"
+ type="android.backup.RestoreObserver"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</constructor>
+</class>
+<class name="RestoreSession"
+ extends="java.lang.Object"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<method name="endRestoreSession"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+</method>
+<method name="restorePackage"
+ return="int"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="packageName" type="java.lang.String">
+</parameter>
+<parameter name="observer" type="android.backup.RestoreObserver">
+</parameter>
+</method>
+</class>
+<class name="SharedPreferencesBackupHelper"
+ extends="android.backup.FileBackupHelperBase"
+ abstract="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<implements name="android.backup.BackupHelper">
+</implements>
+<constructor name="SharedPreferencesBackupHelper"
+ type="android.backup.SharedPreferencesBackupHelper"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="context" type="android.content.Context">
+</parameter>
+<parameter name="prefGroups" type="java.lang.String...">
+</parameter>
+</constructor>
+<method name="performBackup"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="oldState" type="android.os.ParcelFileDescriptor">
+</parameter>
+<parameter name="data" type="android.backup.BackupDataOutput">
+</parameter>
+<parameter name="newState" type="android.os.ParcelFileDescriptor">
+</parameter>
+</method>
+<method name="restoreEntity"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="data" type="android.backup.BackupDataInputStream">
+</parameter>
+</method>
+</class>
+</package>
 <package name="android.bluetooth"
 >
 <class name="BluetoothAdapter"
diff --git a/core/java/android/app/BackupAgent.java b/core/java/android/app/BackupAgent.java
index 35b6fed..a2bfc76 100644
--- a/core/java/android/app/BackupAgent.java
+++ b/core/java/android/app/BackupAgent.java
@@ -33,8 +33,8 @@
 /**
  * This is the central interface between an application and Android's
  * settings backup mechanism.
- * 
- * @hide pending API solidification
+ *
+ * <p>STOPSHIP write more documentation about the backup process here.
  */
 public abstract class BackupAgent extends ContextWrapper {
     private static final String TAG = "BackupAgent";
@@ -62,9 +62,9 @@
      *                 state provided by the application.  May be null, in which
      *                 case no prior state is being provided and the application should
      *                 perform a full backup.
-     * @param data An open, read/write ParcelFileDescriptor pointing to the backup data
-     *             destination.  Typically the application will use backup helper
-     *             classes to write to this file.
+     * @param data A structured wrapper around an open, read/write ParcelFileDescriptor
+     *             pointing to the backup data destination.  Typically the application will use
+     *             backup helper classes to write to this file.
      * @param newState An open, read/write ParcelFileDescriptor pointing to an empty
      *                 file.  The application should record the final backup state
      *                 here after writing the requested data to dataFd.
@@ -77,10 +77,18 @@
      * existing data with the contents of the backup.  The backup data is
      * provided in the file pointed to by the dataFd file descriptor.  Once
      * the restore is finished, the application should write a representation
-     * of the final state to the newStateFd file descriptor, 
+     * of the final state to the newStateFd file descriptor,
      *
-     * @param data An open, read-only ParcelFileDescriptor pointing to a full snapshot
-     *             of the application's data.
+     * <p>The application is responsible for properly erasing its old data and
+     * replacing it with the data supplied to this method.  No "clear user data"
+     * operation will be performed automatically by the operating system.  The
+     * exception to this is in the case of a failed restore attempt:  if onRestore()
+     * throws an exception, the OS will assume that the application's data may now
+     * be in an incoherent state, and will clear it before proceeding.
+     *
+     * @param data A structured wrapper around an open, read-only ParcelFileDescriptor
+     *             pointing to a full snapshot of the application's data.  Typically the
+     *             application will use helper classes to read this data.
      * @param appVersionCode The android:versionCode value of the application that backed
      *        up this particular data set.  This makes it easier for an application's
      *        agent to distinguish among several possible older data versions when
diff --git a/core/java/android/backup/AbsoluteFileBackupHelper.java b/core/java/android/backup/AbsoluteFileBackupHelper.java
index 1dbccc9..6bf848f 100644
--- a/core/java/android/backup/AbsoluteFileBackupHelper.java
+++ b/core/java/android/backup/AbsoluteFileBackupHelper.java
@@ -27,7 +27,7 @@
  * Like FileBackupHelper, but takes absolute paths for the files instead of
  * subpaths of getFilesDir()
  *
- * @hide
+ * STOPSHIP: document!
  */
 public class AbsoluteFileBackupHelper extends FileBackupHelperBase implements BackupHelper {
     private static final String TAG = "AbsoluteFileBackupHelper";
@@ -36,6 +36,13 @@
     Context mContext;
     String[] mFiles;
 
+    /**
+     * Construct a helper for backing up / restoring the files at the given absolute locations
+     * within the file system.
+     *
+     * @param context
+     * @param files
+     */
     public AbsoluteFileBackupHelper(Context context, String... files) {
         super(context);
 
@@ -54,6 +61,9 @@
         performBackup_checked(oldState, data, newState, mFiles, mFiles);
     }
 
+    /**
+     * Restore one absolute file entity from the restore stream
+     */
     public void restoreEntity(BackupDataInputStream data) {
         if (DEBUG) Log.d(TAG, "got entity '" + data.getKey() + "' size=" + data.size());
         String key = data.getKey();
diff --git a/core/java/android/backup/BackupDataInput.java b/core/java/android/backup/BackupDataInput.java
index e67b0be..67d51ea 100644
--- a/core/java/android/backup/BackupDataInput.java
+++ b/core/java/android/backup/BackupDataInput.java
@@ -21,7 +21,9 @@
 import java.io.FileDescriptor;
 import java.io.IOException;
 
-/** @hide */
+/**
+ * STOPSHIP: document!
+ */
 public class BackupDataInput {
     int mBackupReader;
 
@@ -33,6 +35,7 @@
         int dataSize;
     }
 
+    /** @hide */
     public BackupDataInput(FileDescriptor fd) {
         if (fd == null) throw new NullPointerException();
         mBackupReader = ctor(fd);
@@ -41,6 +44,7 @@
         }
     }
 
+    /** @hide */
     protected void finalize() throws Throwable {
         try {
             dtor(mBackupReader);
@@ -49,6 +53,13 @@
         }
     }
 
+    /**
+     * Consumes the next header from the restore stream.
+     *
+     * @return true when there is an entity ready for consumption from the restore stream,
+     *    false if the restore stream has been fully consumed.
+     * @throws IOException if an error occurred while reading the restore stream
+     */
     public boolean readNextHeader() throws IOException {
         int result = readNextHeader_native(mBackupReader, mHeader);
         if (result == 0) {
@@ -66,6 +77,11 @@
         }
     }
 
+    /**
+     * Report the key associated with the current record in the restore stream
+     * @return the current record's key string
+     * @throws IllegalStateException if the next record header has not yet been read
+     */
     public String getKey() {
         if (mHeaderReady) {
             return mHeader.key;
@@ -74,6 +90,13 @@
         }
     }
 
+    /**
+     * Report the size in bytes of the data associated with the current record in the
+     * restore stream.
+     *
+     * @return The size of the record's raw data, in bytes
+     * @throws IllegalStateException if the next record header has not yet been read
+     */
     public int getDataSize() {
         if (mHeaderReady) {
             return mHeader.dataSize;
@@ -82,6 +105,19 @@
         }
     }
 
+    /**
+     * Read a record's raw data from the restore stream.  The record's header must first
+     * have been processed by the {@link #readNextHeader()} method.  Multiple calls to
+     * this method may be made in order to process the data in chunks; not all of it
+     * must be read in a single call.
+     *
+     * @param data An allocated byte array of at least 'size' bytes
+     * @param offset Offset within the 'data' array at which the data will be placed
+     *    when read from the stream.
+     * @param size The number of bytes to read in this pass.
+     * @return The number of bytes of data read
+     * @throws IOException if an error occurred when trying to read the restore data stream
+     */
     public int readEntityData(byte[] data, int offset, int size) throws IOException {
         if (mHeaderReady) {
             int result = readEntityData_native(mBackupReader, data, offset, size);
@@ -95,6 +131,14 @@
         }
     }
 
+    /**
+     * Consume the current record's data without actually reading it into a buffer
+     * for further processing.  This allows a {@link android.backup.BackupAgent} to
+     * efficiently discard obsolete or otherwise uninteresting records during the
+     * restore operation.
+     * 
+     * @throws IOException if an error occurred when trying to read the restore data stream
+     */
     public void skipEntityData() throws IOException {
         if (mHeaderReady) {
             skipEntityData_native(mBackupReader);
diff --git a/core/java/android/backup/BackupDataInputStream.java b/core/java/android/backup/BackupDataInputStream.java
index b705c4c..503b3c1 100644
--- a/core/java/android/backup/BackupDataInputStream.java
+++ b/core/java/android/backup/BackupDataInputStream.java
@@ -16,12 +16,11 @@
 
 package android.backup;
 
-import android.util.Log;
-
 import java.io.InputStream;
 import java.io.IOException;
 
-/** @hide */
+/**
+ * STOPSHIP: document */
 public class BackupDataInputStream extends InputStream {
 
     String key;
@@ -30,6 +29,7 @@
     BackupDataInput mData;
     byte[] mOneByte;
 
+    /** @hide */
     BackupDataInputStream(BackupDataInput data) {
         mData = data;
     }
diff --git a/core/java/android/backup/BackupDataOutput.java b/core/java/android/backup/BackupDataOutput.java
index d29c5ba..672d01f 100644
--- a/core/java/android/backup/BackupDataOutput.java
+++ b/core/java/android/backup/BackupDataOutput.java
@@ -21,13 +21,16 @@
 import java.io.FileDescriptor;
 import java.io.IOException;
 
-/** @hide */
+/**
+ * STOPSHIP: document 
+ */
 public class BackupDataOutput {
     int mBackupWriter;
 
     public static final int OP_UPDATE = 1;
     public static final int OP_DELETE = 2;
 
+    /** @hide */
     public BackupDataOutput(FileDescriptor fd) {
         if (fd == null) throw new NullPointerException();
         mBackupWriter = ctor(fd);
@@ -36,7 +39,15 @@
         }
     }
 
-    // A dataSize of -1 indicates that the record under this key should be deleted
+    /**
+     * Mark the beginning of one record in the backup data stream.
+     *
+     * @param key
+     * @param dataSize The size in bytes of this record's data.  Passing a dataSize
+     *    of -1 indicates that the record under this key should be deleted.
+     * @return The number of bytes written to the backup stream
+     * @throws IOException if the write failed
+     */
     public int writeEntityHeader(String key, int dataSize) throws IOException {
         int result = writeEntityHeader_native(mBackupWriter, key, dataSize);
         if (result >= 0) {
@@ -46,6 +57,13 @@
         }
     }
 
+    /**
+     * Write a chunk of data under the current entity to the backup transport.
+     * @param data A raw data buffer to send
+     * @param size The number of bytes to be sent in this chunk
+     * @return the number of bytes written
+     * @throws IOException if the write failed
+     */
     public int writeEntityData(byte[] data, int size) throws IOException {
         int result = writeEntityData_native(mBackupWriter, data, size);
         if (result >= 0) {
@@ -59,6 +77,7 @@
         setKeyPrefix_native(mBackupWriter, keyPrefix);
     }
 
+    /** @hide */
     protected void finalize() throws Throwable {
         try {
             dtor(mBackupWriter);
diff --git a/core/java/android/backup/BackupHelper.java b/core/java/android/backup/BackupHelper.java
index 3983e28..fc48cf2 100644
--- a/core/java/android/backup/BackupHelper.java
+++ b/core/java/android/backup/BackupHelper.java
@@ -20,7 +20,9 @@
 
 import java.io.InputStream;
 
-/** @hide */
+/**
+ * STOPSHIP: document!
+ */
 public interface BackupHelper {
     /**
      * Based on oldState, determine which of the files from the application's data directory
@@ -31,16 +33,18 @@
             ParcelFileDescriptor newState);
 
     /**
-     * Called by BackupHelperDispatcher to dispatch one entity of data.
+     * Called by BackupHelperAgent to restore one entity from the restore dataset.
      * <p class=note>
      * Do not close the <code>data</code> stream.  Do not read more than
-     * <code>dataSize</code> bytes from <code>data</code>.
+     * <code>data.size()</code> bytes from <code>data</code>.
      */
     public void restoreEntity(BackupDataInputStream data);
 
     /**
-     *
+     * Called by BackupHelperAgent to write the new backup state file corresponding to
+     * the current state of the app's data at the time the backup operation was
+     * performed.
      */
-    public void writeRestoreSnapshot(ParcelFileDescriptor fd);
+    public void writeNewStateDescription(ParcelFileDescriptor fd);
 }
 
diff --git a/core/java/android/backup/BackupHelperAgent.java b/core/java/android/backup/BackupHelperAgent.java
index 5d0c4a2..dc17154f 100644
--- a/core/java/android/backup/BackupHelperAgent.java
+++ b/core/java/android/backup/BackupHelperAgent.java
@@ -26,28 +26,54 @@
 
 import java.io.IOException;
 
-/** @hide */
+/**
+ * A convenient BackupAgent wrapper class that automatically manages heterogeneous
+ * data sets within the backup data, each identified by a unique key prefix.  An
+ * application will typically extend this class in their own backup agent.  Then,
+ * within the agent's onBackup() and onRestore() methods, it will call
+ * {@link #addHelper(String, BackupHelper)} one or more times to specify the data
+ * sets, then invoke super.onBackup() or super.onRestore() to have the BackupHelperAgent
+ * implementation process the data.
+ *
+ * STOPSHIP: document!
+ */
 public class BackupHelperAgent extends BackupAgent {
     static final String TAG = "BackupHelperAgent";
 
     BackupHelperDispatcher mDispatcher = new BackupHelperDispatcher();
 
+    /**
+     * Run the backup process on each of the configured handlers.
+     */
     @Override
     public void onBackup(ParcelFileDescriptor oldState, BackupDataOutput data,
              ParcelFileDescriptor newState) throws IOException {
         mDispatcher.performBackup(oldState, data, newState);
     }
 
+    /**
+     * Run the restore process on each of the configured handlers.
+     */
     @Override
     public void onRestore(BackupDataInput data, int appVersionCode, ParcelFileDescriptor newState)
             throws IOException {
         mDispatcher.performRestore(data, appVersionCode, newState);
     }
 
+    /** @hide */
     public BackupHelperDispatcher getDispatcher() {
         return mDispatcher;
     }
 
+    /**
+     * Add a helper for a given data subset to the agent's configuration.  Each helper
+     * must have a prefix string that is unique within this backup agent's set of
+     * helpers.
+     *
+     * @param keyPrefix A string used to disambiguate the various helpers within this agent
+     * @param helper A backup/restore helper object to be invoked during backup and restore
+     *    operations.
+     */
     public void addHelper(String keyPrefix, BackupHelper helper) {
         mDispatcher.addHelper(keyPrefix, helper);
     }
diff --git a/core/java/android/backup/BackupHelperDispatcher.java b/core/java/android/backup/BackupHelperDispatcher.java
index 6ccb83e..bf2c44d 100644
--- a/core/java/android/backup/BackupHelperDispatcher.java
+++ b/core/java/android/backup/BackupHelperDispatcher.java
@@ -138,7 +138,7 @@
 
         // Write out the state files -- mHelpers is a TreeMap, so the order is well defined.
         for (BackupHelper helper: mHelpers.values()) {
-            helper.writeRestoreSnapshot(newState);
+            helper.writeNewStateDescription(newState);
         }
     }
 
diff --git a/core/java/android/backup/BackupManager.java b/core/java/android/backup/BackupManager.java
index 0b27117..4bf59eb 100644
--- a/core/java/android/backup/BackupManager.java
+++ b/core/java/android/backup/BackupManager.java
@@ -38,7 +38,11 @@
  * documentation for {@link android.app.BackupAgent} for a detailed description
  * of how the backup then proceeds.
  *
- * @hide pending API solidification
+ * <p>STOPSHIP more documentation here!  Include the attributes:
+ *    android:backupAgent
+ *    android:allowBackup
+ *    android:restoreNeedsApplication
+ *    android:killAfterRestore
  */
 public class BackupManager {
     private static final String TAG = "BackupManager";
@@ -110,11 +114,8 @@
     }
 
     /**
-     * Begin the process of restoring system data from backup.  This method requires
-     * that the application hold the "android.permission.BACKUP" permission, and is
-     * not public.
-     *
-     * {@hide}
+     * Begin the process of restoring data from backup.  See the
+     * {@link android.backup.RestoreSession} class for documentation on that process.
      */
     public RestoreSession beginRestoreSession() {
         if (!EVEN_THINK_ABOUT_DOING_RESTORE) {
@@ -128,7 +129,7 @@
                 IRestoreSession binder = sService.beginRestoreSession(transport);
                 session = new RestoreSession(mContext, binder);
             } catch (RemoteException e) {
-                Log.d(TAG, "beginRestoreSession() couldn't connect");
+                Log.w(TAG, "beginRestoreSession() couldn't connect");
             }
         }
         return session;
diff --git a/core/java/android/backup/FileBackupHelper.java b/core/java/android/backup/FileBackupHelper.java
index dacfc8f..68b4d42 100644
--- a/core/java/android/backup/FileBackupHelper.java
+++ b/core/java/android/backup/FileBackupHelper.java
@@ -23,7 +23,9 @@
 import java.io.File;
 import java.io.FileDescriptor;
 
-/** @hide */
+/**
+ * STOPSHIP: document!  [manages backup of a set of files; restore is totally opaque]
+ */
 public class FileBackupHelper extends FileBackupHelperBase implements BackupHelper {
     private static final String TAG = "FileBackupHelper";
     private static final boolean DEBUG = false;
@@ -32,6 +34,13 @@
     File mFilesDir;
     String[] mFiles;
 
+    /**
+     * Construct a helper to manage backup/restore of entire files within the
+     * application's data directory hierarchy.
+     *
+     * @param context The backup agent's Context object
+     * @param files A list of the files to be backed up or restored.
+     */
     public FileBackupHelper(Context context, String... files) {
         super(context);
 
@@ -60,6 +69,9 @@
         performBackup_checked(oldState, data, newState, fullPaths, files);
     }
 
+    /**
+     * Restore one record [representing a single file] from the restore dataset.
+     */
     public void restoreEntity(BackupDataInputStream data) {
         if (DEBUG) Log.d(TAG, "got entity '" + data.getKey() + "' size=" + data.size());
         String key = data.getKey();
diff --git a/core/java/android/backup/FileBackupHelperBase.java b/core/java/android/backup/FileBackupHelperBase.java
index 03ae476..a0ff38b 100644
--- a/core/java/android/backup/FileBackupHelperBase.java
+++ b/core/java/android/backup/FileBackupHelperBase.java
@@ -20,7 +20,6 @@
 import android.os.ParcelFileDescriptor;
 import android.util.Log;
 
-import java.io.InputStream;
 import java.io.File;
 import java.io.FileDescriptor;
 import java.io.FileOutputStream;
@@ -80,18 +79,14 @@
         }
     }
 
-    void writeFile(File f, InputStream in) {
-        if (!(in instanceof BackupDataInputStream)) {
-            throw new IllegalStateException("input stream must be a BackupDataInputStream");
-        }
+    void writeFile(File f, BackupDataInputStream in) {
         int result = -1;
 
         // Create the enclosing directory.
         File parent = f.getParentFile();
         parent.mkdirs();
 
-        result = writeFile_native(mPtr, f.getAbsolutePath(),
-                ((BackupDataInputStream)in).mData.mBackupReader);
+        result = writeFile_native(mPtr, f.getAbsolutePath(), in.mData.mBackupReader);
         if (result != 0) {
             // Bail on this entity.  Only log one failure per helper object.
             if (!mExceptionLogged) {
@@ -103,7 +98,7 @@
         }
     }
 
-    public void writeRestoreSnapshot(ParcelFileDescriptor fd) {
+    public void writeNewStateDescription(ParcelFileDescriptor fd) {
         int result = writeSnapshot_native(mPtr, fd.getFileDescriptor());
         // TODO: Do something with the error.
     }
diff --git a/core/java/android/backup/RestoreObserver.java b/core/java/android/backup/RestoreObserver.java
index 3be8c08..e4182750 100644
--- a/core/java/android/backup/RestoreObserver.java
+++ b/core/java/android/backup/RestoreObserver.java
@@ -19,7 +19,6 @@
 /**
  * Callback class for receiving progress reports during a restore operation.  These
  * methods will all be called on your application's main thread.
- * @hide
  */
 public abstract class RestoreObserver {
     /**
diff --git a/core/java/android/backup/RestoreSession.java b/core/java/android/backup/RestoreSession.java
index d10831e..fc53854 100644
--- a/core/java/android/backup/RestoreSession.java
+++ b/core/java/android/backup/RestoreSession.java
@@ -27,7 +27,6 @@
 
 /**
  * Interface for applications to use when managing a restore session.
- * @hide
  */
 public class RestoreSession {
     static final String TAG = "RestoreSession";
@@ -44,6 +43,8 @@
      *   and a String array under the key "names" whose entries are the user-meaningful
      *   text corresponding to the backup sets at each index in the tokens array.
      *   On error, returns null.
+     *
+     * {@hide}
      */
     public RestoreSet[] getAvailableRestoreSets() {
         try {
@@ -66,6 +67,8 @@
      *   the restore set that should be used.
      * @param observer If non-null, this binder points to an object that will receive
      *   progress callbacks during the restore operation.
+     *
+     * {@hide}
      */
     public int restoreAll(long token, RestoreObserver observer) {
         int err = -1;
diff --git a/core/java/android/backup/SharedPreferencesBackupHelper.java b/core/java/android/backup/SharedPreferencesBackupHelper.java
index 6a0bc96..f9c97a3 100644
--- a/core/java/android/backup/SharedPreferencesBackupHelper.java
+++ b/core/java/android/backup/SharedPreferencesBackupHelper.java
@@ -23,7 +23,9 @@
 import java.io.File;
 import java.io.FileDescriptor;
 
-/** @hide */
+/**
+ * STOPSHIP: document!
+ */
 public class SharedPreferencesBackupHelper extends FileBackupHelperBase implements BackupHelper {
     private static final String TAG = "SharedPreferencesBackupHelper";
     private static final boolean DEBUG = false;
@@ -31,6 +33,13 @@
     private Context mContext;
     private String[] mPrefGroups;
 
+    /**
+     * Construct a helper for backing up and restoring the
+     * {@link android.content.SharedPreferences} under the given names.
+     *
+     * @param context
+     * @param prefGroups
+     */
     public SharedPreferencesBackupHelper(Context context, String... prefGroups) {
         super(context);
 
@@ -38,6 +47,9 @@
         mPrefGroups = prefGroups;
     }
 
+    /**
+     * Backs up the configured SharedPreferences groups
+     */
     public void performBackup(ParcelFileDescriptor oldState, BackupDataOutput data,
             ParcelFileDescriptor newState) {
         Context context = mContext;
@@ -54,6 +66,10 @@
         performBackup_checked(oldState, data, newState, files, prefGroups);
     }
 
+    /**
+     * Restores one entity from the restore data stream to its proper shared
+     * preferences file store.
+     */
     public void restoreEntity(BackupDataInputStream data) {
         Context context = mContext;
         
diff --git a/services/java/com/android/server/BackupManagerService.java b/services/java/com/android/server/BackupManagerService.java
index a7a6df5..d43039d 100644
--- a/services/java/com/android/server/BackupManagerService.java
+++ b/services/java/com/android/server/BackupManagerService.java
@@ -1083,15 +1083,11 @@
 
         synchronized(mClearDataLock) {
             mClearingData = true;
-            /* This is causing some critical processes to be killed during setup.
-               Temporarily revert this change until we find a better solution.
             try {
                 mActivityManager.clearApplicationUserData(packageName, observer);
             } catch (RemoteException e) {
                 // can't happen because the activity manager is in this process
             }
-            */
-            mPackageManager.clearApplicationUserData(packageName, observer);
 
             // only wait 10 seconds for the clear data to happen
             long timeoutMark = System.currentTimeMillis() + TIMEOUT_INTERVAL;
@@ -1660,10 +1656,6 @@
                             + "] is compatible with installed version ["
                             + packageInfo.versionCode + "]");
 
-                    // Now perform the actual restore:  first clear the app's data
-                    // if appropriate
-                    clearApplicationDataSynchronous(packageName);
-
                     // Then set up and bind the agent (with a restricted Application object
                     // unless the application says otherwise)
                     boolean useRealApp = (packageInfo.applicationInfo.flags