Merge "Fix ClipboardManager#hasText"
diff --git a/api/current.xml b/api/current.xml
index 9422552..3ccb4e9 100644
--- a/api/current.xml
+++ b/api/current.xml
@@ -58662,6 +58662,21 @@
 <parameter name="flags" type="int">
 </parameter>
 </method>
+<method name="setInstallerPackageName"
+ return="void"
+ abstract="true"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="targetPackage" type="java.lang.String">
+</parameter>
+<parameter name="installerPackageName" type="java.lang.String">
+</parameter>
+</method>
 <field name="COMPONENT_ENABLED_STATE_DEFAULT"
  type="int"
  transient="false"
@@ -175729,6 +175744,21 @@
 <parameter name="flags" type="int">
 </parameter>
 </method>
+<method name="setInstallerPackageName"
+ return="void"
+ abstract="false"
+ native="false"
+ synchronized="false"
+ static="false"
+ final="false"
+ deprecated="not deprecated"
+ visibility="public"
+>
+<parameter name="targetPackage" type="java.lang.String">
+</parameter>
+<parameter name="installerPackageName" type="java.lang.String">
+</parameter>
+</method>
 <method name="setPackageObbPath"
  return="void"
  abstract="false"
@@ -194129,53 +194159,6 @@
  visibility="public"
 >
 </method>
-<method name="obtain"
- return="android.view.DragEvent"
- abstract="false"
- native="false"
- synchronized="false"
- static="true"
- final="false"
- deprecated="not deprecated"
- visibility="public"
->
-<parameter name="action" type="int">
-</parameter>
-<parameter name="x" type="float">
-</parameter>
-<parameter name="y" type="float">
-</parameter>
-<parameter name="description" type="android.content.ClipDescription">
-</parameter>
-<parameter name="data" type="android.content.ClipData">
-</parameter>
-<parameter name="result" type="boolean">
-</parameter>
-</method>
-<method name="obtain"
- return="android.view.DragEvent"
- abstract="false"
- native="false"
- synchronized="false"
- static="true"
- final="false"
- deprecated="not deprecated"
- visibility="public"
->
-<parameter name="source" type="android.view.DragEvent">
-</parameter>
-</method>
-<method name="recycle"
- return="void"
- abstract="false"
- native="false"
- synchronized="false"
- static="false"
- final="true"
- deprecated="not deprecated"
- visibility="public"
->
-</method>
 <method name="writeToParcel"
  return="void"
  abstract="false"
diff --git a/core/java/android/app/ApplicationPackageManager.java b/core/java/android/app/ApplicationPackageManager.java
index ce9501a..abb26e3 100644
--- a/core/java/android/app/ApplicationPackageManager.java
+++ b/core/java/android/app/ApplicationPackageManager.java
@@ -914,6 +914,16 @@
     }
 
     @Override
+    public void setInstallerPackageName(String targetPackage,
+            String installerPackageName) {
+        try {
+            mPM.setInstallerPackageName(targetPackage, installerPackageName);
+        } catch (RemoteException e) {
+            // Should never happen!
+        }
+    }
+
+    @Override
     public void movePackage(String packageName, IPackageMoveObserver observer, int flags) {
         try {
             mPM.movePackage(packageName, observer, flags);
diff --git a/core/java/android/app/admin/DevicePolicyManager.java b/core/java/android/app/admin/DevicePolicyManager.java
index a18fdac..f169cd7 100644
--- a/core/java/android/app/admin/DevicePolicyManager.java
+++ b/core/java/android/app/admin/DevicePolicyManager.java
@@ -691,8 +691,6 @@
      *
      * <p>To disable password expiration, a value of 0 may be used for timeout.
      *
-     * <p>Timeout must be at least 1 day or IllegalArgumentException will be thrown.
-     *
      * <p>The calling device admin must have requested
      * {@link DeviceAdminInfo#USES_POLICY_EXPIRE_PASSWORD} to be able to call this
      * method; if it has not, a security exception will be thrown.
diff --git a/core/java/android/content/pm/IPackageManager.aidl b/core/java/android/content/pm/IPackageManager.aidl
index 4cff3bb..d01a68a 100644
--- a/core/java/android/content/pm/IPackageManager.aidl
+++ b/core/java/android/content/pm/IPackageManager.aidl
@@ -158,6 +158,8 @@
 
     void finishPackageInstall(int token);
 
+    void setInstallerPackageName(in String targetPackage, in String installerPackageName);
+
     /**
      * Delete a package.
      *
diff --git a/core/java/android/content/pm/PackageManager.java b/core/java/android/content/pm/PackageManager.java
index b5d1653..ac7a95a 100644
--- a/core/java/android/content/pm/PackageManager.java
+++ b/core/java/android/content/pm/PackageManager.java
@@ -1918,6 +1918,24 @@
             String installerPackageName);
 
     /**
+     * Change the installer associated with a given package.  There are limitations
+     * on how the installer package can be changed; in particular:
+     * <ul>
+     * <li> A SecurityException will be thrown if <var>installerPackageName</var>
+     * is not signed with the same certificate as the calling application.
+     * <li> A SecurityException will be thrown if <var>targetPackage</var> already
+     * has an installer package, and that installer package is not signed with
+     * the same certificate as the calling application.
+     * </ul>
+     *
+     * @param targetPackage The installed package whose installer will be changed.
+     * @param installerPackageName The package name of the new installer.  May be
+     * null to clear the association.
+     */
+    public abstract void setInstallerPackageName(String targetPackage,
+            String installerPackageName);
+
+    /**
      * Attempts to delete a package.  Since this may take a little while, the result will
      * be posted back to the given observer.  A deletion will fail if the calling context
      * lacks the {@link android.Manifest.permission#DELETE_PACKAGES} permission, if the
diff --git a/core/java/android/view/DragEvent.java b/core/java/android/view/DragEvent.java
index bbac14c..07e87d6 100644
--- a/core/java/android/view/DragEvent.java
+++ b/core/java/android/view/DragEvent.java
@@ -41,16 +41,90 @@
     private static DragEvent gRecyclerTop = null;
 
     /**
-     * action constants for DragEvent dispatch
+     * Action constant returned by {@link #getAction()}.  Delivery of a DragEvent whose
+     * action is ACTION_DRAG_STARTED means that a drag operation has been initiated.  The
+     * view receiving this DragEvent should inspect the metadata of the dragged content,
+     * available via {@link #getClipDescription()}, and return {@code true} from
+     * {@link View#onDragEvent(DragEvent)} if the view is prepared to accept a drop of
+     * that clip data.  If the view chooses to present a visual indication that it is
+     * a valid target of the ongoing drag, then it should draw that indication in response
+     * to this event.
+     * <p>
+     * A view will only receive ACTION_DRAG_ENTERED, ACTION_DRAG_LOCATION, ACTION_DRAG_EXITED,
+     * and ACTION_DRAG_LOCATION events if it returns {@code true} in response to the
+     * ACTION_DRAG_STARTED event.
      */
     public static final int ACTION_DRAG_STARTED = 1;
-    public static final int ACTION_DRAG_LOCATION = 2;
-    public static final int ACTION_DROP = 3;
-    public static final int ACTION_DRAG_ENDED = 4;
-    public static final int ACTION_DRAG_ENTERED = 5;
-    public static final int ACTION_DRAG_EXITED = 6;
 
-    /* hide the constructor behind package scope */
+    /**
+     * Action constant returned by {@link #getAction()}.  Delivery of a DragEvent whose
+     * action is ACTION_DRAG_LOCATION means that the drag operation is currently hovering
+     * over the view.  The {@link #getX()} and {@link #getY()} methods supply the location
+     * of the drag point within the view's coordinate system.
+     * <p>
+     * A view will receive an ACTION_DRAG_ENTERED event before receiving any
+     * ACTION_DRAG_LOCATION events.  If the drag point leaves the view, then an
+     * ACTION_DRAG_EXITED event is delivered to the view, after which no more
+     * ACTION_DRAG_LOCATION events will be sent (unless the drag re-enters the view,
+     * of course).
+     */
+    public static final int ACTION_DRAG_LOCATION = 2;
+
+    /**
+     * Action constant returned by {@link #getAction()}.  Delivery of a DragEvent whose
+     * action is ACTION_DROP means that the dragged content has been dropped on this view.
+     * The view should retrieve the content via {@link #getClipData()} and act on it
+     * appropriately.  The {@link #getX()} and {@link #getY()} methods supply the location
+     * of the drop point within the view's coordinate system.
+     * <p>
+     * The view should return {@code true} from its {@link View#onDragEvent(DragEvent)}
+     * method in response to this event if it accepted the content, and {@code false}
+     * if it ignored the drop.
+     */
+    public static final int ACTION_DROP = 3;
+
+    /**
+     * Action constant returned by {@link #getAction()}.  Delivery of a DragEvent whose
+     * action is ACTION_DRAG_ENDED means that the drag operation has concluded.  A view
+     * that is drawing a visual indication of drag acceptance should return to its usual
+     * drawing state in response to this event.
+     * <p>
+     * All views that received an ACTION_DRAG_STARTED event will receive the
+     * ACTION_DRAG_ENDED event even if they are not currently visible when the drag
+     * ends.
+     */
+    public static final int ACTION_DRAG_ENDED = 4;
+
+    /**
+     * Action constant returned by {@link #getAction()}.  Delivery of a DragEvent whose
+     * action is ACTION_DRAG_ENTERED means that the drag point has entered the view's
+     * bounds.  If the view changed its visual state in response to the ACTION_DRAG_ENTERED
+     * event, it should return to its normal drag-in-progress visual state in response to
+     * this event.
+     * <p>
+     * A view will receive an ACTION_DRAG_ENTERED event before receiving any
+     * ACTION_DRAG_LOCATION events.  If the drag point leaves the view, then an
+     * ACTION_DRAG_EXITED event is delivered to the view, after which no more
+     * ACTION_DRAG_LOCATION events will be sent (unless the drag re-enters the view,
+     * of course).
+     */
+    public static final int ACTION_DRAG_ENTERED = 5;
+
+    /**
+     * Action constant returned by {@link #getAction()}.  Delivery of a DragEvent whose
+     * action is ACTION_DRAG_ENTERED means that the drag point has entered the view's
+     * bounds.  If the view chooses to present a visual indication that it will receive
+     * the drop if it occurs now, then it should draw that indication in response to
+     * this event.
+     * <p>
+     * A view will receive an ACTION_DRAG_ENTERED event before receiving any
+     * ACTION_DRAG_LOCATION events.  If the drag point leaves the view, then an
+     * ACTION_DRAG_EXITED event is delivered to the view, after which no more
+     * ACTION_DRAG_LOCATION events will be sent (unless the drag re-enters the view,
+     * of course).
+     */
+public static final int ACTION_DRAG_EXITED = 6;
+
     private DragEvent() {
     }
 
@@ -68,6 +142,7 @@
         return DragEvent.obtain(0, 0f, 0f, null, null, false);
     }
 
+    /** @hide */
     public static DragEvent obtain(int action, float x, float y,
             ClipDescription description, ClipData data, boolean result) {
         final DragEvent ev;
@@ -90,31 +165,64 @@
         return ev;
     }
 
+    /** @hide */
     public static DragEvent obtain(DragEvent source) {
         return obtain(source.mAction, source.mX, source.mY,
                 source.mClipDescription, source.mClipData, source.mDragResult);
     }
 
+    /**
+     * Inspect the action value of this event.
+     * @return One of {@link #ACTION_DRAG_STARTED}, {@link #ACTION_DRAG_ENDED},
+     *         {@link #ACTION_DROP}, {@link #ACTION_DRAG_ENTERED}, {@link #ACTION_DRAG_EXITED},
+     *         or {@link #ACTION_DRAG_LOCATION}.
+     */
     public int getAction() {
         return mAction;
     }
 
+    /**
+     * For ACTION_DRAG_LOCATION and ACTION_DROP events, returns the x coordinate of the
+     * drag point.
+     * @return The current drag point's x coordinate, when relevant.
+     */
     public float getX() {
         return mX;
     }
 
+    /**
+     * For ACTION_DRAG_LOCATION and ACTION_DROP events, returns the y coordinate of the
+     * drag point.
+     * @return The current drag point's y coordinate, when relevant.
+     */
     public float getY() {
         return mY;
     }
 
+    /**
+     * Provides the data payload of the drag operation.  This payload is only available
+     * for events whose action value is ACTION_DROP.
+     * @return The ClipData containing the data being dropped on the view.
+     */
     public ClipData getClipData() {
         return mClipData;
     }
 
+    /**
+     * Provides a description of the drag operation's data payload.  This payload is
+     * available for all DragEvents other than ACTION_DROP.
+     * @return A ClipDescription describing the contents of the data being dragged.
+     */
     public ClipDescription getClipDescription() {
         return mClipDescription;
     }
 
+    /**
+     * Provides an indication of whether the drag operation concluded successfully.
+     * This method is only available on ACTION_DRAG_ENDED events.
+     * @return {@code true} if the drag operation ended with an accepted drop; {@code false}
+     *         otherwise.
+     */
     public boolean getResult() {
         return mDragResult;
     }
@@ -122,6 +230,8 @@
     /**
      * Recycle the DragEvent, to be re-used by a later caller.  After calling
      * this function you must never touch the event again.
+     *
+     * @hide
      */
     public final void recycle() {
         // Ensure recycle is only called once!
diff --git a/core/java/android/view/animation/Animation.java b/core/java/android/view/animation/Animation.java
index c6fae9d..13d0ec1 100644
--- a/core/java/android/view/animation/Animation.java
+++ b/core/java/android/view/animation/Animation.java
@@ -18,9 +18,11 @@
 
 import android.content.Context;
 import android.content.res.TypedArray;
+import android.graphics.RectF;
+import android.os.SystemProperties;
 import android.util.AttributeSet;
 import android.util.TypedValue;
-import android.graphics.RectF;
+import dalvik.system.CloseGuard;
 
 /**
  * Abstraction for an Animation that can be applied to Views, Surfaces, or
@@ -86,7 +88,10 @@
      * content for the duration of the animation.
      */
     public static final int ZORDER_BOTTOM = -1;
-    
+
+    private static final boolean USE_CLOSEGUARD
+            = SystemProperties.getBoolean("log.closeguard.Animation", false);
+
     /**
      * Set by {@link #getTransformation(long, Transformation)} when the animation ends.
      */
@@ -194,6 +199,8 @@
     Transformation mTransformation = new Transformation();
     Transformation mPreviousTransformation = new Transformation();
 
+    private final CloseGuard guard = CloseGuard.get();
+
     /**
      * Creates a new animation with a duration of 0ms, the default interpolator, with
      * fillBefore set to true and fillAfter set to false
@@ -276,6 +283,7 @@
         if (mStarted && !mEnded) {
             if (mListener != null) mListener.onAnimationEnd(this);
             mEnded = true;
+            guard.close();
         }
         // Make sure we move the animation to the end
         mStartTime = Long.MIN_VALUE;
@@ -288,6 +296,7 @@
     public void detach() {
         if (mStarted && !mEnded) {
             mEnded = true;
+            guard.close();
             if (mListener != null) mListener.onAnimationEnd(this);
         }
     }
@@ -781,6 +790,9 @@
                     mListener.onAnimationStart(this);
                 }
                 mStarted = true;
+                if (USE_CLOSEGUARD) {
+                    guard.open("cancel or detach or getTransformation");
+                }
             }
 
             if (mFillEnabled) normalizedTime = Math.max(Math.min(normalizedTime, 1.0f), 0.0f);
@@ -797,6 +809,7 @@
             if (mRepeatCount == mRepeated) {
                 if (!mEnded) {
                     mEnded = true;
+                    guard.close();
                     if (mListener != null) {
                         mListener.onAnimationEnd(this);
                     }
@@ -953,6 +966,16 @@
         }
     }
 
+    protected void finalize() throws Throwable {
+        try {
+            if (guard != null) {
+                guard.warnIfOpen();
+            }
+        } finally {
+            super.finalize();
+        }
+    }
+
     /**
      * Utility class to parse a string description of a size.
      */
diff --git a/core/java/android/webkit/WebView.java b/core/java/android/webkit/WebView.java
index 383e977..5bf2ad4 100644
--- a/core/java/android/webkit/WebView.java
+++ b/core/java/android/webkit/WebView.java
@@ -2187,14 +2187,6 @@
     private View mTitleBar;
 
     /**
-     * Since we draw the title bar ourselves, we removed the shadow from the
-     * browser's activity.  We do want a shadow at the bottom of the title bar,
-     * or at the top of the screen if the title bar is not visible.  This
-     * drawable serves that purpose.
-     */
-    private Drawable mTitleShadow;
-
-    /**
      * Add or remove a title bar to be embedded into the WebView, and scroll
      * along with it vertically, while remaining in view horizontally. Pass
      * null to remove the title bar from the WebView, and return to drawing
@@ -2220,10 +2212,6 @@
             addView(v, new AbsoluteLayout.LayoutParams(
                     ViewGroup.LayoutParams.MATCH_PARENT,
                     ViewGroup.LayoutParams.WRAP_CONTENT, 0, 0));
-            if (mTitleShadow == null) {
-                mTitleShadow = (Drawable) mContext.getResources().getDrawable(
-                        com.android.internal.R.drawable.title_bar_shadow);
-            }
         }
         mTitleBar = v;
     }
@@ -3470,15 +3458,6 @@
         drawContent(canvas);
         canvas.restoreToCount(saveCount);
 
-        // Now draw the shadow.
-        int titleH = getVisibleTitleHeight();
-        if (mTitleBar != null && titleH == 0) {
-            int height = (int) (5f * getContext().getResources()
-                    .getDisplayMetrics().density);
-            mTitleShadow.setBounds(mScrollX, mScrollY, mScrollX + getWidth(),
-                    mScrollY + height);
-            mTitleShadow.draw(canvas);
-        }
         if (AUTO_REDRAW_HACK && mAutoRedraw) {
             invalidate();
         }
diff --git a/core/res/res/drawable-hdpi/title_bar_shadow.9.png b/core/res/res/drawable-hdpi/title_bar_shadow.9.png
deleted file mode 100644
index e6dab63..0000000
--- a/core/res/res/drawable-hdpi/title_bar_shadow.9.png
+++ /dev/null
Binary files differ
diff --git a/core/res/res/drawable-ldpi/title_bar_shadow.9.png b/core/res/res/drawable-ldpi/title_bar_shadow.9.png
deleted file mode 100644
index fc45ee8..0000000
--- a/core/res/res/drawable-ldpi/title_bar_shadow.9.png
+++ /dev/null
Binary files differ
diff --git a/core/res/res/drawable-mdpi/title_bar_shadow.9.png b/core/res/res/drawable-mdpi/title_bar_shadow.9.png
deleted file mode 100644
index dbcefee..0000000
--- a/core/res/res/drawable-mdpi/title_bar_shadow.9.png
+++ /dev/null
Binary files differ
diff --git a/core/res/res/layout/grant_credentials_permission.xml b/core/res/res/layout/grant_credentials_permission.xml
index 4133ea9..0ffe8de 100644
--- a/core/res/res/layout/grant_credentials_permission.xml
+++ b/core/res/res/layout/grant_credentials_permission.xml
@@ -47,8 +47,7 @@
         android:layout_height="wrap_content"
         android:fillViewport="true"
         android:layout_weight="1"
-        android:gravity="top|center_horizontal"
-        android:foreground="@drawable/title_bar_shadow">
+        android:gravity="top|center_horizontal">
 
         <LinearLayout
             android:layout_width="match_parent"
diff --git a/core/res/res/values/arrays.xml b/core/res/res/values/arrays.xml
index 3e546a1..04c6538 100644
--- a/core/res/res/values/arrays.xml
+++ b/core/res/res/values/arrays.xml
@@ -67,7 +67,6 @@
         <item>@drawable/text_select_handle_middle</item>
         <item>@drawable/text_select_handle_right</item>
         <item>@drawable/title_bar</item>
-        <item>@drawable/title_bar_shadow</item>
         <!-- Visual lock screen -->
         <item>@drawable/indicator_code_lock_drag_direction_green_up</item>
         <item>@drawable/indicator_code_lock_drag_direction_red_up</item>
diff --git a/core/res/res/values/themes.xml b/core/res/res/values/themes.xml
index f5dca47..9215bf2 100644
--- a/core/res/res/values/themes.xml
+++ b/core/res/res/values/themes.xml
@@ -130,7 +130,7 @@
         <item name="windowNoTitle">false</item>
         <item name="windowFullscreen">false</item>
         <item name="windowIsFloating">false</item>
-        <item name="windowContentOverlay">@android:drawable/title_bar_shadow</item>
+        <item name="windowContentOverlay">@null</item>
         <item name="windowShowWallpaper">false</item>
         <item name="windowTitleStyle">@android:style/WindowTitle</item>
         <item name="windowTitleSize">25dip</item>
diff --git a/include/media/AudioEffect.h b/include/media/AudioEffect.h
index c967efb..cda2be0 100644
--- a/include/media/AudioEffect.h
+++ b/include/media/AudioEffect.h
@@ -403,7 +403,7 @@
      static status_t guidToString(const effect_uuid_t *guid, char *str, size_t maxLen);
 
 protected:
-     volatile int32_t        mEnabled;           // enable state
+     bool                    mEnabled;           // enable state
      int32_t                 mSessionId;         // audio session ID
      int32_t                 mPriority;          // priority for effect control
      status_t                mStatus;            // effect status
@@ -412,6 +412,7 @@
      void*                   mUserData;          // client context for callback function
      effect_descriptor_t     mDescriptor;        // effect descriptor
      int32_t                 mId;                // system wide unique effect engine instance ID
+     Mutex                   mLock;               // Mutex for mEnabled access
 
 private:
 
diff --git a/include/media/AudioRecord.h b/include/media/AudioRecord.h
index 38e3d44..5f7cd90 100644
--- a/include/media/AudioRecord.h
+++ b/include/media/AudioRecord.h
@@ -356,7 +356,7 @@
     sp<IAudioRecord>        mAudioRecord;
     sp<IMemory>             mCblkMemory;
     sp<ClientRecordThread>  mClientRecordThread;
-    Mutex                   mRecordThreadLock;
+    Mutex                   mLock;
 
     uint32_t                mFrameCount;
 
diff --git a/include/media/AudioTrack.h b/include/media/AudioTrack.h
index 4475d4a..813a905 100644
--- a/include/media/AudioTrack.h
+++ b/include/media/AudioTrack.h
@@ -480,6 +480,7 @@
     uint32_t                mFlags;
     int                     mSessionId;
     int                     mAuxEffectId;
+    Mutex                   mLock;
 };
 
 
diff --git a/include/media/stagefright/AMRWriter.h b/include/media/stagefright/AMRWriter.h
index d8410a9..62d57b4 100644
--- a/include/media/stagefright/AMRWriter.h
+++ b/include/media/stagefright/AMRWriter.h
@@ -44,7 +44,6 @@
     virtual ~AMRWriter();
 
 private:
-    FILE *mFile;
     int   mFd;
     status_t mInitCheck;
     sp<MediaSource> mSource;
diff --git a/include/media/stagefright/FileSource.h b/include/media/stagefright/FileSource.h
index a7f7181..72a0403 100644
--- a/include/media/stagefright/FileSource.h
+++ b/include/media/stagefright/FileSource.h
@@ -46,7 +46,6 @@
     virtual ~FileSource();
 
 private:
-    FILE *mFile;
     int mFd;
     int64_t mOffset;
     int64_t mLength;
diff --git a/include/media/stagefright/MPEG4Writer.h b/include/media/stagefright/MPEG4Writer.h
index e6d8a26..f7618e9 100644
--- a/include/media/stagefright/MPEG4Writer.h
+++ b/include/media/stagefright/MPEG4Writer.h
@@ -61,8 +61,8 @@
 private:
     class Track;
 
-    FILE *mFile;
     int  mFd;
+    status_t mInitCheck;
     bool mUse4ByteNalLength;
     bool mUse32BitOffset;
     bool mIsFileSizeLimitExplicitlyRequested;
@@ -149,7 +149,7 @@
     off64_t addSample_l(MediaBuffer *buffer);
     off64_t addLengthPrefixedSample_l(MediaBuffer *buffer);
 
-    inline size_t write(const void *ptr, size_t size, size_t nmemb, FILE* stream);
+    inline size_t write(const void *ptr, size_t size, size_t nmemb);
     bool exceedsFileSizeLimit();
     bool use32BitFileOffset() const;
     bool exceedsFileDurationLimit();
diff --git a/media/jni/soundpool/SoundPool.h b/media/jni/soundpool/SoundPool.h
index 42037af..1b0fd38 100644
--- a/media/jni/soundpool/SoundPool.h
+++ b/media/jni/soundpool/SoundPool.h
@@ -22,7 +22,6 @@
 #include <utils/Vector.h>
 #include <utils/KeyedVector.h>
 #include <media/AudioTrack.h>
-#include <cutils/atomic.h>
 
 namespace android {
 
diff --git a/media/libmedia/AudioEffect.cpp b/media/libmedia/AudioEffect.cpp
index 88b8c86..aadeba5 100644
--- a/media/libmedia/AudioEffect.cpp
+++ b/media/libmedia/AudioEffect.cpp
@@ -27,7 +27,6 @@
 #include <media/AudioEffect.h>
 
 #include <utils/Log.h>
-#include <cutils/atomic.h>
 #include <binder/IPCThreadState.h>
 
 
@@ -207,18 +206,22 @@
         return INVALID_OPERATION;
     }
 
-    if (enabled) {
-        LOGV("enable %p", this);
-        if (android_atomic_or(1, &mEnabled) == 0) {
-           return mIEffect->enable();
+    status_t status = NO_ERROR;
+
+    AutoMutex lock(mLock);
+    if (enabled != mEnabled) {
+        if (enabled) {
+            LOGV("enable %p", this);
+            status = mIEffect->enable();
+        } else {
+            LOGV("disable %p", this);
+            status = mIEffect->disable();
         }
-    } else {
-        LOGV("disable %p", this);
-        if (android_atomic_and(~1, &mEnabled) == 1) {
-           return mIEffect->disable();
+        if (status == NO_ERROR) {
+            mEnabled = enabled;
         }
     }
-    return NO_ERROR;
+    return status;
 }
 
 status_t AudioEffect::command(uint32_t cmdCode,
@@ -232,26 +235,26 @@
         return INVALID_OPERATION;
     }
 
-    if ((cmdCode == EFFECT_CMD_ENABLE || cmdCode == EFFECT_CMD_DISABLE) &&
-            (replySize == NULL || *replySize != sizeof(status_t) || replyData == NULL)) {
-        return BAD_VALUE;
+    if (cmdCode == EFFECT_CMD_ENABLE || cmdCode == EFFECT_CMD_DISABLE) {
+        if (mEnabled == (cmdCode == EFFECT_CMD_ENABLE)) {
+            return NO_ERROR;
+        }
+        if (replySize == NULL || *replySize != sizeof(status_t) || replyData == NULL) {
+            return BAD_VALUE;
+        }
+        mLock.lock();
     }
 
     status_t status = mIEffect->command(cmdCode, cmdSize, cmdData, replySize, replyData);
-    if (status != NO_ERROR) {
-        return status;
-    }
 
     if (cmdCode == EFFECT_CMD_ENABLE || cmdCode == EFFECT_CMD_DISABLE) {
-        status = *(status_t *)replyData;
-        if (status != NO_ERROR) {
-            return status;
+        if (status == NO_ERROR) {
+            status = *(status_t *)replyData;
         }
-        if (cmdCode == EFFECT_CMD_ENABLE) {
-            android_atomic_or(1, &mEnabled);
-        } else {
-            android_atomic_and(~1, &mEnabled);
+        if (status == NO_ERROR) {
+            mEnabled = (cmdCode == EFFECT_CMD_ENABLE);
         }
+        mLock.unlock();
     }
 
     return status;
@@ -370,11 +373,7 @@
 {
     LOGV("enableStatusChanged %p enabled %d mCbf %p", this, enabled, mCbf);
     if (mStatus == ALREADY_EXISTS) {
-        if (enabled) {
-            android_atomic_or(1, &mEnabled);
-        } else {
-            android_atomic_and(~1, &mEnabled);
-        }
+        mEnabled = enabled;
         if (mCbf) {
             mCbf(EVENT_ENABLE_STATUS_CHANGED, mUserData, &enabled);
         }
diff --git a/media/libmedia/AudioRecord.cpp b/media/libmedia/AudioRecord.cpp
index a6c515c..1d6ffa0 100644
--- a/media/libmedia/AudioRecord.cpp
+++ b/media/libmedia/AudioRecord.cpp
@@ -35,7 +35,6 @@
 #include <binder/Parcel.h>
 #include <binder/IPCThreadState.h>
 #include <utils/Timers.h>
-#include <cutils/atomic.h>
 
 #define LIKELY( exp )       (__builtin_expect( (exp) != 0, true  ))
 #define UNLIKELY( exp )     (__builtin_expect( (exp) != 0, false ))
@@ -282,7 +281,9 @@
         t->mLock.lock();
      }
 
-    if (android_atomic_or(1, &mActive) == 0) {
+    AutoMutex lock(mLock);
+    if (mActive == 0) {
+        mActive = 1;
         ret = mAudioRecord->start();
         if (ret == DEAD_OBJECT) {
             LOGV("start() dead IAudioRecord: creating a new one");
@@ -302,8 +303,7 @@
                 setpriority(PRIO_PROCESS, 0, THREAD_PRIORITY_AUDIO_CLIENT);
             }
         } else {
-            LOGV("start() failed");
-            android_atomic_and(~1, &mActive);
+            mActive = 0;
         }
     }
 
@@ -322,9 +322,11 @@
 
     if (t != 0) {
         t->mLock.lock();
-     }
+    }
 
-    if (android_atomic_and(~1, &mActive) == 1) {
+    AutoMutex lock(mLock);
+    if (mActive == 1) {
+        mActive = 0;
         mCblk->cv.signal();
         mAudioRecord->stop();
         // the record head position will reset to 0, so if a marker is set, we need
diff --git a/media/libmedia/AudioTrack.cpp b/media/libmedia/AudioTrack.cpp
index 587c8ff..c1bed59 100644
--- a/media/libmedia/AudioTrack.cpp
+++ b/media/libmedia/AudioTrack.cpp
@@ -35,7 +35,6 @@
 #include <binder/Parcel.h>
 #include <binder/IPCThreadState.h>
 #include <utils/Timers.h>
-#include <cutils/atomic.h>
 
 #define LIKELY( exp )       (__builtin_expect( (exp) != 0, true  ))
 #define UNLIKELY( exp )     (__builtin_expect( (exp) != 0, false ))
@@ -312,7 +311,9 @@
         t->mLock.lock();
      }
 
-    if (android_atomic_or(1, &mActive) == 0) {
+    AutoMutex lock(mLock);
+    if (mActive == 0) {
+        mActive = 1;
         mNewPosition = mCblk->server + mUpdatePeriod;
         mCblk->bufferTimeoutMs = MAX_STARTUP_TIMEOUT_MS;
         mCblk->waitTimeMs = 0;
@@ -344,7 +345,7 @@
         }
         if (status != NO_ERROR) {
             LOGV("start() failed");
-            android_atomic_and(~1, &mActive);
+            mActive = 0;
             if (t != 0) {
                 t->requestExit();
             } else {
@@ -367,7 +368,9 @@
         t->mLock.lock();
     }
 
-    if (android_atomic_and(~1, &mActive) == 1) {
+    AutoMutex lock(mLock);
+    if (mActive == 1) {
+        mActive = 0;
         mCblk->cv.signal();
         mAudioTrack->stop();
         // Cancel loops (If we are in the middle of a loop, playback
@@ -407,7 +410,6 @@
     mMarkerReached = false;
     mUpdatePeriod = 0;
 
-
     if (!mActive) {
         mAudioTrack->flush();
         // Release AudioTrack callback thread in case it was waiting for new buffers
@@ -419,7 +421,9 @@
 void AudioTrack::pause()
 {
     LOGV("pause");
-    if (android_atomic_and(~1, &mActive) == 1) {
+    AutoMutex lock(mLock);
+    if (mActive == 1) {
+        mActive = 0;
         mAudioTrack->pause();
     }
 }
diff --git a/media/libmediaplayerservice/StagefrightRecorder.cpp b/media/libmediaplayerservice/StagefrightRecorder.cpp
index dadd1db..ec3b5a2 100644
--- a/media/libmediaplayerservice/StagefrightRecorder.cpp
+++ b/media/libmediaplayerservice/StagefrightRecorder.cpp
@@ -864,7 +864,7 @@
         return UNKNOWN_ERROR;
     }
 
-    mWriter = new AMRWriter(dup(mOutputFd));
+    mWriter = new AMRWriter(mOutputFd);
     mWriter->addSource(audioEncoder);
 
     if (mMaxFileDurationUs != 0) {
@@ -912,7 +912,7 @@
         }
     }
 
-    mWriter = new ARTPWriter(dup(mOutputFd));
+    mWriter = new ARTPWriter(mOutputFd);
     mWriter->addSource(source);
     mWriter->setListener(mListener);
 
@@ -922,7 +922,7 @@
 status_t StagefrightRecorder::startMPEG2TSRecording() {
     CHECK_EQ(mOutputFormat, OUTPUT_FORMAT_MPEG2TS);
 
-    sp<MediaWriter> writer = new MPEG2TSWriter(dup(mOutputFd));
+    sp<MediaWriter> writer = new MPEG2TSWriter(mOutputFd);
 
     if (mAudioSource != AUDIO_SOURCE_LIST_END) {
         if (mAudioEncoder != AUDIO_ENCODER_AAC) {
@@ -1204,7 +1204,7 @@
     mediaWriter->clear();
     *totalBitRate = 0;
     status_t err = OK;
-    sp<MediaWriter> writer = new MPEG4Writer(dup(outputFd));
+    sp<MediaWriter> writer = new MPEG4Writer(outputFd);
 
     // Add audio source first if it exists
     if (!mCaptureTimeLapse && (mAudioSource != AUDIO_SOURCE_LIST_END)) {
diff --git a/media/libstagefright/AMRWriter.cpp b/media/libstagefright/AMRWriter.cpp
index ecbd96c..0db3d1d 100644
--- a/media/libstagefright/AMRWriter.cpp
+++ b/media/libstagefright/AMRWriter.cpp
@@ -24,22 +24,28 @@
 #include <media/mediarecorder.h>
 #include <sys/prctl.h>
 #include <sys/resource.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
 
 namespace android {
 
 AMRWriter::AMRWriter(const char *filename)
-    : mFile(fopen(filename, "wb")),
-      mFd(mFile == NULL? -1: fileno(mFile)),
-      mInitCheck(mFile != NULL ? OK : NO_INIT),
+    : mFd(-1),
+      mInitCheck(NO_INIT),
       mStarted(false),
       mPaused(false),
       mResumed(false) {
+
+    mFd = open(filename, O_CREAT | O_LARGEFILE | O_TRUNC);
+    if (mFd >= 0) {
+        mInitCheck = OK;
+    }
 }
 
 AMRWriter::AMRWriter(int fd)
-    : mFile(fdopen(fd, "wb")),
-      mFd(mFile == NULL? -1: fileno(mFile)),
-      mInitCheck(mFile != NULL ? OK : NO_INIT),
+    : mFd(dup(fd)),
+      mInitCheck(mFd < 0? NO_INIT: OK),
       mStarted(false),
       mPaused(false),
       mResumed(false) {
@@ -50,9 +56,9 @@
         stop();
     }
 
-    if (mFile != NULL) {
-        fclose(mFile);
-        mFile = NULL;
+    if (mFd != -1) {
+        close(mFd);
+        mFd = -1;
     }
 }
 
@@ -92,7 +98,7 @@
     mSource = source;
 
     const char *kHeader = isWide ? "#!AMR-WB\n" : "#!AMR\n";
-    size_t n = strlen(kHeader);
+    ssize_t n = strlen(kHeader);
     if (write(mFd, kHeader, n) != n) {
         return ERROR_IO;
     }
@@ -266,9 +272,8 @@
         notify(MEDIA_RECORDER_EVENT_INFO, MEDIA_RECORDER_INFO_COMPLETION_STATUS, UNKNOWN_ERROR);
     }
 
-    fflush(mFile);
-    fclose(mFile);
-    mFile = NULL;
+    close(mFd);
+    mFd = -1;
     mReachedEOS = true;
     if (err == ERROR_END_OF_STREAM) {
         return OK;
diff --git a/media/libstagefright/FileSource.cpp b/media/libstagefright/FileSource.cpp
index c9f68e9..98d5b50 100644
--- a/media/libstagefright/FileSource.cpp
+++ b/media/libstagefright/FileSource.cpp
@@ -18,12 +18,14 @@
 #include <media/stagefright/MediaDebug.h>
 #include <sys/types.h>
 #include <unistd.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
 
 namespace android {
 
 FileSource::FileSource(const char *filename)
-    : mFile(fopen(filename, "rb")),
-      mFd(mFile == NULL ? -1 : fileno(mFile)),
+    : mFd(-1),
       mOffset(0),
       mLength(-1),
       mDecryptHandle(NULL),
@@ -31,11 +33,12 @@
       mDrmBufOffset(0),
       mDrmBufSize(0),
       mDrmBuf(NULL){
+
+    mFd = open(filename, O_LARGEFILE | O_RDONLY);
 }
 
 FileSource::FileSource(int fd, int64_t offset, int64_t length)
-    : mFile(fdopen(fd, "rb")),
-      mFd(fd),
+    : mFd(fd),
       mOffset(offset),
       mLength(length),
       mDecryptHandle(NULL),
@@ -48,9 +51,9 @@
 }
 
 FileSource::~FileSource() {
-    if (mFile != NULL) {
-        fclose(mFile);
-        mFile = NULL;
+    if (mFd >= 0) {
+        close(mFd);
+        mFd = -1;
     }
 
     if (mDrmBuf != NULL) {
@@ -60,11 +63,11 @@
 }
 
 status_t FileSource::initCheck() const {
-    return mFile != NULL ? OK : NO_INIT;
+    return mFd >= 0 ? OK : NO_INIT;
 }
 
 ssize_t FileSource::readAt(off64_t offset, void *data, size_t size) {
-    if (mFile == NULL) {
+    if (mFd < 0) {
         return NO_INIT;
     }
 
@@ -95,7 +98,7 @@
 }
 
 status_t FileSource::getSize(off64_t *size) {
-    if (mFile == NULL) {
+    if (mFd < 0) {
         return NO_INIT;
     }
 
diff --git a/media/libstagefright/MPEG2TSWriter.cpp b/media/libstagefright/MPEG2TSWriter.cpp
index 81a2b0d..4d8165e 100644
--- a/media/libstagefright/MPEG2TSWriter.cpp
+++ b/media/libstagefright/MPEG2TSWriter.cpp
@@ -410,7 +410,7 @@
 ////////////////////////////////////////////////////////////////////////////////
 
 MPEG2TSWriter::MPEG2TSWriter(int fd)
-    : mFile(fdopen(fd, "wb")),
+    : mFile(fdopen(dup(fd), "wb")),
       mStarted(false),
       mNumSourcesDone(0),
       mNumTSPacketsWritten(0),
diff --git a/media/libstagefright/MPEG4Writer.cpp b/media/libstagefright/MPEG4Writer.cpp
index 19e3eae..6760707 100644
--- a/media/libstagefright/MPEG4Writer.cpp
+++ b/media/libstagefright/MPEG4Writer.cpp
@@ -33,6 +33,10 @@
 #include <media/stagefright/MediaSource.h>
 #include <media/stagefright/Utils.h>
 #include <media/mediarecorder.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <unistd.h>
 
 #include "include/ESDS.h"
 
@@ -214,8 +218,8 @@
 };
 
 MPEG4Writer::MPEG4Writer(const char *filename)
-    : mFile(fopen(filename, "wb")),
-      mFd(mFile == NULL? -1: fileno(mFile)),
+    : mFd(-1),
+      mInitCheck(NO_INIT),
       mUse4ByteNalLength(true),
       mUse32BitOffset(true),
       mIsFileSizeLimitExplicitlyRequested(false),
@@ -225,12 +229,16 @@
       mMdatOffset(0),
       mEstimatedMoovBoxSize(0),
       mInterleaveDurationUs(1000000) {
-    CHECK(mFile != NULL);
+
+    mFd = open(filename, O_CREAT | O_LARGEFILE | O_TRUNC);
+    if (mFd >= 0) {
+        mInitCheck = OK;
+    }
 }
 
 MPEG4Writer::MPEG4Writer(int fd)
-    : mFile(fdopen(fd, "wb")),
-      mFd(mFile == NULL? -1: fileno(mFile)),
+    : mFd(dup(fd)),
+      mInitCheck(mFd < 0? NO_INIT: OK),
       mUse4ByteNalLength(true),
       mUse32BitOffset(true),
       mIsFileSizeLimitExplicitlyRequested(false),
@@ -240,7 +248,6 @@
       mMdatOffset(0),
       mEstimatedMoovBoxSize(0),
       mInterleaveDurationUs(1000000) {
-    CHECK(mFile != NULL);
 }
 
 MPEG4Writer::~MPEG4Writer() {
@@ -370,7 +377,7 @@
 }
 
 status_t MPEG4Writer::start(MetaData *param) {
-    if (mFile == NULL) {
+    if (mInitCheck != OK) {
         return UNKNOWN_ERROR;
     }
 
@@ -493,7 +500,7 @@
 }
 
 status_t MPEG4Writer::pause() {
-    if (mFile == NULL) {
+    if (mInitCheck != OK) {
         return OK;
     }
     mPaused = true;
@@ -577,7 +584,7 @@
 
 
 status_t MPEG4Writer::stop() {
-    if (mFile == NULL) {
+    if (mInitCheck != OK) {
         return OK;
     }
 
@@ -600,9 +607,9 @@
 
     // Do not write out movie header on error.
     if (err != OK) {
-        fflush(mFile);
-        fclose(mFile);
-        mFile = NULL;
+        close(mFd);
+        mFd = -1;
+        mInitCheck = NO_INIT;
         mStarted = false;
         return err;
     }
@@ -665,7 +672,7 @@
         // Moov box
         lseek64(mFd, mFreeBoxOffset, SEEK_SET);
         mOffset = mFreeBoxOffset;
-        write(mMoovBoxBuffer, 1, mMoovBoxBufferOffset, mFile);
+        write(mMoovBoxBuffer, 1, mMoovBoxBufferOffset);
 
         // Free box
         lseek64(mFd, mOffset, SEEK_SET);
@@ -682,9 +689,9 @@
 
     CHECK(mBoxes.empty());
 
-    fflush(mFile);
-    fclose(mFile);
-    mFile = NULL;
+    close(mFd);
+    mFd = -1;
+    mInitCheck = NO_INIT;
     mStarted = false;
     return err;
 }
@@ -763,20 +770,21 @@
 }
 
 size_t MPEG4Writer::write(
-        const void *ptr, size_t size, size_t nmemb, FILE *stream) {
+        const void *ptr, size_t size, size_t nmemb) {
 
     const size_t bytes = size * nmemb;
-    int fd = fileno(stream);
     if (mWriteMoovBoxToMemory) {
+        // This happens only when we write the moov box at the end of
+        // recording, not for each output video/audio frame we receive.
         off64_t moovBoxSize = 8 + mMoovBoxBufferOffset + bytes;
         if (moovBoxSize > mEstimatedMoovBoxSize) {
             for (List<off64_t>::iterator it = mBoxes.begin();
                  it != mBoxes.end(); ++it) {
                 (*it) += mOffset;
             }
-            lseek64(fd, mOffset, SEEK_SET);
-            ::write(fd, mMoovBoxBuffer, mMoovBoxBufferOffset);
-            ::write(fd, ptr, size * nmemb);
+            lseek64(mFd, mOffset, SEEK_SET);
+            ::write(mFd, mMoovBoxBuffer, mMoovBoxBufferOffset);
+            ::write(mFd, ptr, size * nmemb);
             mOffset += (bytes + mMoovBoxBufferOffset);
             free(mMoovBoxBuffer);
             mMoovBoxBuffer = NULL;
@@ -788,7 +796,7 @@
             mMoovBoxBufferOffset += bytes;
         }
     } else {
-        ::write(fd, ptr, size * nmemb);
+        ::write(mFd, ptr, size * nmemb);
         mOffset += bytes;
     }
     return bytes;
@@ -822,36 +830,36 @@
 }
 
 void MPEG4Writer::writeInt8(int8_t x) {
-    write(&x, 1, 1, mFile);
+    write(&x, 1, 1);
 }
 
 void MPEG4Writer::writeInt16(int16_t x) {
     x = htons(x);
-    write(&x, 1, 2, mFile);
+    write(&x, 1, 2);
 }
 
 void MPEG4Writer::writeInt32(int32_t x) {
     x = htonl(x);
-    write(&x, 1, 4, mFile);
+    write(&x, 1, 4);
 }
 
 void MPEG4Writer::writeInt64(int64_t x) {
     x = hton64(x);
-    write(&x, 1, 8, mFile);
+    write(&x, 1, 8);
 }
 
 void MPEG4Writer::writeCString(const char *s) {
     size_t n = strlen(s);
-    write(s, 1, n + 1, mFile);
+    write(s, 1, n + 1);
 }
 
 void MPEG4Writer::writeFourcc(const char *s) {
     CHECK_EQ(strlen(s), 4);
-    write(s, 1, 4, mFile);
+    write(s, 1, 4);
 }
 
 void MPEG4Writer::write(const void *data, size_t size) {
-    write(data, 1, size, mFile);
+    write(data, 1, size);
 }
 
 bool MPEG4Writer::isFileStreamable() const {
diff --git a/media/libstagefright/rtsp/ARTPWriter.cpp b/media/libstagefright/rtsp/ARTPWriter.cpp
index 155fd96..5a033e1 100644
--- a/media/libstagefright/rtsp/ARTPWriter.cpp
+++ b/media/libstagefright/rtsp/ARTPWriter.cpp
@@ -46,7 +46,7 @@
 
 ARTPWriter::ARTPWriter(int fd)
     : mFlags(0),
-      mFd(fd),
+      mFd(dup(fd)),
       mLooper(new ALooper),
       mReflector(new AHandlerReflector<ARTPWriter>(this)) {
     CHECK_GE(fd, 0);
diff --git a/media/tests/CameraBrowser/Android.mk b/media/tests/CameraBrowser/Android.mk
index 1d81129..295b3e6 100644
--- a/media/tests/CameraBrowser/Android.mk
+++ b/media/tests/CameraBrowser/Android.mk
@@ -1,7 +1,7 @@
 LOCAL_PATH:= $(call my-dir)
 include $(CLEAR_VARS)
 
-LOCAL_MODULE_TAGS := tests
+LOCAL_MODULE_TAGS := optional
 
 LOCAL_SRC_FILES := $(call all-subdir-java-files)
 
diff --git a/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java b/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java
index 34dbace..82753b2 100644
--- a/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java
+++ b/policy/src/com/android/internal/policy/impl/KeyguardViewBase.java
@@ -43,13 +43,6 @@
 
     public KeyguardViewBase(Context context) {
         super(context);
-
-        // drop shadow below status bar in keyguard too
-        mForegroundInPadding = false;
-        setForegroundGravity(Gravity.FILL_HORIZONTAL | Gravity.TOP);
-        setForeground(
-                context.getResources().getDrawable(
-                        com.android.internal.R.drawable.title_bar_shadow));
     }
 
     // used to inject callback
diff --git a/services/audioflinger/AudioFlinger.cpp b/services/audioflinger/AudioFlinger.cpp
index 84dd022..51b5947 100644
--- a/services/audioflinger/AudioFlinger.cpp
+++ b/services/audioflinger/AudioFlinger.cpp
@@ -343,7 +343,7 @@
             lSessionId = *sessionId;
         } else {
             // if no audio session id is provided, create one here
-            lSessionId = nextUniqueId();
+            lSessionId = nextUniqueId_l();
             if (sessionId != NULL) {
                 *sessionId = lSessionId;
             }
@@ -3699,7 +3699,7 @@
         if (sessionId != NULL && *sessionId != AudioSystem::SESSION_OUTPUT_MIX) {
             lSessionId = *sessionId;
         } else {
-            lSessionId = nextUniqueId();
+            lSessionId = nextUniqueId_l();
             if (sessionId != NULL) {
                 *sessionId = lSessionId;
             }
@@ -4300,7 +4300,7 @@
 
     mHardwareStatus = AUDIO_HW_IDLE;
     if (output != 0) {
-        int id = nextUniqueId();
+        int id = nextUniqueId_l();
         if ((flags & AudioSystem::OUTPUT_FLAG_DIRECT) ||
             (format != AudioSystem::PCM_16_BIT) ||
             (channels != AudioSystem::CHANNEL_OUT_STEREO)) {
@@ -4348,7 +4348,7 @@
         return 0;
     }
 
-    int id = nextUniqueId();
+    int id = nextUniqueId_l();
     DuplicatingThread *thread = new DuplicatingThread(this, thread1, id);
     thread->addOutputTrack(thread2);
     mPlaybackThreads.add(id, thread);
@@ -4473,7 +4473,7 @@
     }
 
     if (input != 0) {
-        int id = nextUniqueId();
+        int id = nextUniqueId_l();
          // Start record thread
         thread = new RecordThread(this, input, reqSamplingRate, reqChannels, id);
         mRecordThreads.add(id, thread);
@@ -4543,7 +4543,8 @@
 
 int AudioFlinger::newAudioSessionId()
 {
-    return nextUniqueId();
+    AutoMutex _l(mLock);
+    return nextUniqueId_l();
 }
 
 // checkPlaybackThread_l() must be called with AudioFlinger::mLock held
@@ -4578,9 +4579,10 @@
     return thread;
 }
 
-int AudioFlinger::nextUniqueId()
+// nextUniqueId_l() must be called with AudioFlinger::mLock held
+int AudioFlinger::nextUniqueId_l()
 {
-    return android_atomic_inc(&mNextUniqueId);
+    return mNextUniqueId++;
 }
 
 // ----------------------------------------------------------------------------
@@ -4967,7 +4969,7 @@
         LOGV("createEffect_l() got effect %p on chain %p", effect == 0 ? 0 : effect.get(), chain.get());
 
         if (effect == 0) {
-            int id = mAudioFlinger->nextUniqueId();
+            int id = mAudioFlinger->nextUniqueId_l();
             // Check CPU and memory usage
             lStatus = AudioSystem::registerEffect(desc, mId, chain->strategy(), sessionId, id);
             if (lStatus != NO_ERROR) {
diff --git a/services/audioflinger/AudioFlinger.h b/services/audioflinger/AudioFlinger.h
index 5917632..f0ef867 100644
--- a/services/audioflinger/AudioFlinger.h
+++ b/services/audioflinger/AudioFlinger.h
@@ -785,7 +785,7 @@
               float streamVolumeInternal(int stream) const { return mStreamTypes[stream].volume; }
               void audioConfigChanged_l(int event, int ioHandle, void *param2);
 
-              int  nextUniqueId();
+              int  nextUniqueId_l();
               status_t moveEffectChain_l(int session,
                                      AudioFlinger::PlaybackThread *srcThread,
                                      AudioFlinger::PlaybackThread *dstThread,
diff --git a/services/java/com/android/server/DevicePolicyManagerService.java b/services/java/com/android/server/DevicePolicyManagerService.java
index 2b43b013..53a19f5 100644
--- a/services/java/com/android/server/DevicePolicyManagerService.java
+++ b/services/java/com/android/server/DevicePolicyManagerService.java
@@ -41,9 +41,8 @@
 import android.content.Intent;
 import android.content.IntentFilter;
 import android.content.pm.PackageManager;
-import android.content.pm.ResolveInfo;
 import android.content.pm.PackageManager.NameNotFoundException;
-import android.net.ConnectivityManager;
+import android.content.pm.ResolveInfo;
 import android.os.Binder;
 import android.os.Handler;
 import android.os.IBinder;
@@ -55,9 +54,9 @@
 import android.os.ServiceManager;
 import android.os.SystemClock;
 import android.provider.Settings;
-import android.util.Slog;
 import android.util.PrintWriterPrinter;
 import android.util.Printer;
+import android.util.Slog;
 import android.util.Xml;
 import android.view.WindowManagerPolicy;
 
@@ -89,9 +88,6 @@
             = "com.android.server.ACTION_EXPIRED_PASSWORD_NOTIFICATION";
 
     private static final long MS_PER_DAY = 86400 * 1000;
-    private static final long MS_PER_HOUR = 3600 * 1000;
-    private static final long MS_PER_MINUTE = 60 * 1000;
-    private static final long MIN_TIMEOUT = 86400 * 1000; // minimum expiration timeout is 1 day
 
     final Context mContext;
     final MyPackageMonitor mMonitor;
@@ -364,6 +360,7 @@
     }
 
     class MyPackageMonitor extends PackageMonitor {
+        @Override
         public void onSomePackagesChanged() {
             synchronized (DevicePolicyManagerService.this) {
                 boolean removed = false;
@@ -410,13 +407,6 @@
         context.registerReceiver(mReceiver, filter);
     }
 
-    static String countdownString(long time) {
-        long days = time / MS_PER_DAY;
-        long hours = (time / MS_PER_HOUR) % 24;
-        long minutes = (time / MS_PER_MINUTE) % 60;
-        return days + "d" + hours + "h" + minutes + "m";
-    }
-
     protected void setExpirationAlarmCheckLocked(Context context) {
         final long expiration = getPasswordExpirationLocked(null);
         final long now = System.currentTimeMillis();
@@ -430,12 +420,17 @@
             alarmTime = now + MS_PER_DAY;
         }
 
-        AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
-        PendingIntent pi = PendingIntent.getBroadcast(context, REQUEST_EXPIRE_PASSWORD,
-                new Intent(ACTION_EXPIRED_PASSWORD_NOTIFICATION),
-                PendingIntent.FLAG_ONE_SHOT | PendingIntent.FLAG_UPDATE_CURRENT);
-        am.cancel(pi);
-        am.set(AlarmManager.RTC, alarmTime, pi);
+        long token = Binder.clearCallingIdentity();
+        try {
+            AlarmManager am = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
+            PendingIntent pi = PendingIntent.getBroadcast(context, REQUEST_EXPIRE_PASSWORD,
+                    new Intent(ACTION_EXPIRED_PASSWORD_NOTIFICATION),
+                    PendingIntent.FLAG_ONE_SHOT | PendingIntent.FLAG_UPDATE_CURRENT);
+            am.cancel(pi);
+            am.set(AlarmManager.RTC, alarmTime, pi);
+        } finally {
+            Binder.restoreCallingIdentity(token);
+        }
     }
 
     private IPowerManager getIPowerManager() {
@@ -993,8 +988,8 @@
             if (who == null) {
                 throw new NullPointerException("ComponentName is null");
             }
-            if (timeout != 0L && timeout < MIN_TIMEOUT) {
-                throw new IllegalArgumentException("Timeout must be > " + MIN_TIMEOUT + "ms");
+            if (timeout < 0) {
+                throw new IllegalArgumentException("Timeout must be >= 0 ms");
             }
             ActiveAdmin ap = getActiveAdminForCallerLocked(who,
                     DeviceAdminInfo.USES_POLICY_EXPIRE_PASSWORD);
diff --git a/services/java/com/android/server/PackageManagerService.java b/services/java/com/android/server/PackageManagerService.java
index a0a1974..c121808 100644
--- a/services/java/com/android/server/PackageManagerService.java
+++ b/services/java/com/android/server/PackageManagerService.java
@@ -4578,6 +4578,80 @@
         mHandler.sendMessage(msg);
     }
 
+    public void setInstallerPackageName(String targetPackage,
+            String installerPackageName) {
+        PackageSetting pkgSetting;
+        final int uid = Binder.getCallingUid();
+        final int permission = mContext.checkCallingPermission(
+                android.Manifest.permission.INSTALL_PACKAGES);
+        final boolean allowedByPermission = (permission == PackageManager.PERMISSION_GRANTED);
+        synchronized (mPackages) {
+            PackageSetting targetPackageSetting = mSettings.mPackages.get(targetPackage);
+            if (targetPackageSetting == null) {
+                throw new IllegalArgumentException("Unknown target package: " + targetPackage);
+            }
+
+            PackageSetting installerPackageSetting;
+            if (installerPackageName != null) {
+                installerPackageSetting = mSettings.mPackages.get(installerPackageName);
+                if (installerPackageSetting == null) {
+                    throw new IllegalArgumentException("Unknown installer package: "
+                            + installerPackageName);
+                }
+            } else {
+                installerPackageSetting = null;
+            }
+
+            Signature[] callerSignature;
+            Object obj = mSettings.getUserIdLP(uid);
+            if (obj != null) {
+                if (obj instanceof SharedUserSetting) {
+                    callerSignature = ((SharedUserSetting)obj).signatures.mSignatures;
+                } else if (obj instanceof PackageSetting) {
+                    callerSignature = ((PackageSetting)obj).signatures.mSignatures;
+                } else {
+                    throw new SecurityException("Bad object " + obj + " for uid " + uid);
+                }
+            } else {
+                throw new SecurityException("Unknown calling uid " + uid);
+            }
+
+            // Verify: can't set installerPackageName to a package that is
+            // not signed with the same cert as the caller.
+            if (installerPackageSetting != null) {
+                if (checkSignaturesLP(callerSignature,
+                        installerPackageSetting.signatures.mSignatures)
+                        != PackageManager.SIGNATURE_MATCH) {
+                    throw new SecurityException(
+                            "Caller does not have same cert as new installer package "
+                            + installerPackageName);
+                }
+            }
+
+            // Verify: if target already has an installer package, it must
+            // be signed with the same cert as the caller.
+            if (targetPackageSetting.installerPackageName != null) {
+                PackageSetting setting = mSettings.mPackages.get(
+                        targetPackageSetting.installerPackageName);
+                // If the currently set package isn't valid, then it's always
+                // okay to change it.
+                if (setting != null) {
+                    if (checkSignaturesLP(callerSignature,
+                            setting.signatures.mSignatures)
+                            != PackageManager.SIGNATURE_MATCH) {
+                        throw new SecurityException(
+                                "Caller does not have same cert as old installer package "
+                                + targetPackageSetting.installerPackageName);
+                    }
+                }
+            }
+
+            // Okay!
+            targetPackageSetting.installerPackageName = installerPackageName;
+            scheduleWriteSettingsLocked();
+        }
+    }
+
     public void setPackageObbPath(String packageName, String path) {
         if (DEBUG_OBB)
             Log.v(TAG, "Setting .obb path for " + packageName + " to: " + path);
diff --git a/test-runner/src/android/test/mock/MockPackageManager.java b/test-runner/src/android/test/mock/MockPackageManager.java
index f0cbaa0..615870b1 100644
--- a/test-runner/src/android/test/mock/MockPackageManager.java
+++ b/test-runner/src/android/test/mock/MockPackageManager.java
@@ -341,6 +341,12 @@
         throw new UnsupportedOperationException();
     }
 
+    @Override
+    public void setInstallerPackageName(String targetPackage,
+            String installerPackageName) {
+        throw new UnsupportedOperationException();
+    }
+
     /**
      * @hide - to match hiding in superclass
      */
diff --git a/tools/layoutlib/bridge/src/android/graphics/Canvas_Delegate.java b/tools/layoutlib/bridge/src/android/graphics/Canvas_Delegate.java
index a5f3456..cea07af 100644
--- a/tools/layoutlib/bridge/src/android/graphics/Canvas_Delegate.java
+++ b/tools/layoutlib/bridge/src/android/graphics/Canvas_Delegate.java
@@ -18,6 +18,7 @@
 
 import com.android.layoutlib.api.ILayoutLog;
 import com.android.layoutlib.bridge.impl.DelegateManager;
+import com.android.layoutlib.bridge.impl.Stack;
 
 import android.graphics.Paint_Delegate.FontInfo;
 import android.text.TextUtils;
@@ -32,7 +33,6 @@
 import java.awt.geom.AffineTransform;
 import java.awt.image.BufferedImage;
 import java.util.List;
-import java.util.Stack;
 
 
 /**
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java
index ac7fada..2ddabdf 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeContext.java
@@ -22,6 +22,7 @@
 import com.android.layoutlib.api.IStyleResourceValue;
 import com.android.layoutlib.bridge.Bridge;
 import com.android.layoutlib.bridge.BridgeConstants;
+import com.android.layoutlib.bridge.impl.Stack;
 import com.android.layoutlib.bridge.impl.TempResourceValue;
 
 import android.app.Activity;
@@ -65,7 +66,6 @@
 import java.util.HashMap;
 import java.util.IdentityHashMap;
 import java.util.Map;
-import java.util.Stack;
 import java.util.TreeMap;
 import java.util.Map.Entry;
 
@@ -191,14 +191,33 @@
         return mDefaultPropMaps.get(key);
     }
 
+    /**
+     * Adds a parser to the stack.
+     * @param parser the parser to add.
+     */
     public void pushParser(BridgeXmlBlockParser parser) {
         mParserStack.push(parser);
     }
 
+    /**
+     * Removes the parser at the top of the stack
+     */
     public void popParser() {
         mParserStack.pop();
     }
 
+    /**
+     * Returns the current parser at the top the of the stack.
+     * @return a parser or null.
+     */
+    public BridgeXmlBlockParser getCurrentParser() {
+        return mParserStack.peek();
+    }
+
+    /**
+     * Returns the previous parser.
+     * @return a parser or null if there isn't any previous parser
+     */
     public BridgeXmlBlockParser getPreviousParser() {
         if (mParserStack.size() < 2) {
             return null;
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeResources.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeResources.java
index bfbb01a8..1011173 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeResources.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeResources.java
@@ -220,24 +220,37 @@
         IResourceValue value = getResourceValue(id, mPlatformResourceFlag);
 
         if (value != null) {
-            File xml = new File(value.getValue());
-            if (xml.isFile()) {
-                // we need to create a pull parser around the layout XML file, and then
-                // give that to our XmlBlockParser
-                try {
-                    KXmlParser parser = new KXmlParser();
-                    parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
-                    parser.setInput(new FileReader(xml));
+            XmlPullParser parser = null;
 
-                    return new BridgeXmlBlockParser(parser, mContext, mPlatformResourceFlag[0]);
-                } catch (XmlPullParserException e) {
-                    mContext.getLogger().error(e);
-
-                    // we'll return null below.
-                } catch (FileNotFoundException e) {
-                    // this shouldn't happen since we check above.
+            try {
+                // check if the current parser can provide us with a custom parser.
+                BridgeXmlBlockParser currentParser = mContext.getCurrentParser();
+                if (currentParser != null) {
+                    parser = currentParser.getParser(value.getName());
                 }
+
+                // create a new one manually if needed.
+                if (parser == null) {
+                    File xml = new File(value.getValue());
+                    if (xml.isFile()) {
+                        // we need to create a pull parser around the layout XML file, and then
+                        // give that to our XmlBlockParser
+                        parser = new KXmlParser();
+                        parser.setFeature(XmlPullParser.FEATURE_PROCESS_NAMESPACES, true);
+                        parser.setInput(new FileReader(xml));
+                    }
+                }
+
+                if (parser != null) {
+                    return new BridgeXmlBlockParser(parser, mContext, mPlatformResourceFlag[0]);
+                }
+            } catch (XmlPullParserException e) {
+                mContext.getLogger().error(e);
+                // we'll return null below.
+            } catch (FileNotFoundException e) {
+                // this shouldn't happen since we check above.
             }
+
         }
 
         // id was not found or not resolved. Throw a NotFoundException.
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeXmlBlockParser.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeXmlBlockParser.java
index 073a019..c3d0b14a 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeXmlBlockParser.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/android/BridgeXmlBlockParser.java
@@ -56,13 +56,23 @@
         mPlatformFile = platformFile;
         mAttrib = new BridgeXmlPullAttributes(parser, context, mPlatformFile);
 
-        mContext.pushParser(this);
+        if (mContext != null) {
+            mContext.pushParser(this);
+        }
     }
 
     public boolean isPlatformFile() {
         return mPlatformFile;
     }
 
+    public IXmlPullParser getParser(String layoutName) {
+        if (mParser instanceof IXmlPullParser) {
+            return ((IXmlPullParser)mParser).getParser(layoutName);
+        }
+
+        return null;
+    }
+
     public Object getViewKey() {
         if (mParser instanceof IXmlPullParser) {
             return ((IXmlPullParser)mParser).getViewKey();
@@ -238,7 +248,7 @@
         }
         int ev = mParser.next();
 
-        if (ev == END_TAG && mParser.getDepth() == 1) {
+        if (ev == END_TAG && mParser.getDepth() == 1 && mContext != null) {
             // done with parser remove it from the context stack.
             mContext.popParser();
         }
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/LayoutSceneImpl.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/LayoutSceneImpl.java
index b0316a3..2e3f9a8 100644
--- a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/LayoutSceneImpl.java
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/LayoutSceneImpl.java
@@ -25,6 +25,7 @@
 import com.android.layoutlib.api.SceneResult;
 import com.android.layoutlib.api.ViewInfo;
 import com.android.layoutlib.api.IDensityBasedResourceValue.Density;
+import com.android.layoutlib.api.SceneParams.RenderingMode;
 import com.android.layoutlib.bridge.BridgeConstants;
 import com.android.layoutlib.bridge.android.BridgeContext;
 import com.android.layoutlib.bridge.android.BridgeInflater;
@@ -259,22 +260,32 @@
             int renderScreenWidth = mParams.getScreenWidth();
             int renderScreenHeight = mParams.getScreenHeight();
 
-            if (mParams.getRenderFullSize()) {
+            RenderingMode renderingMode = mParams.getRenderingMode();
+
+            if (renderingMode != RenderingMode.NORMAL) {
                 // measure the full size needed by the layout.
                 w_spec = MeasureSpec.makeMeasureSpec(renderScreenWidth,
-                        MeasureSpec.UNSPECIFIED); // this lets us know the actual needed size
+                        renderingMode.isHorizExpand() ?
+                                MeasureSpec.UNSPECIFIED // this lets us know the actual needed size
+                                : MeasureSpec.EXACTLY);
                 h_spec = MeasureSpec.makeMeasureSpec(renderScreenHeight - mScreenOffset,
-                        MeasureSpec.UNSPECIFIED); // this lets us know the actual needed size
+                        renderingMode.isVertExpand() ?
+                                MeasureSpec.UNSPECIFIED // this lets us know the actual needed size
+                                : MeasureSpec.EXACTLY);
                 mViewRoot.measure(w_spec, h_spec);
 
-                int neededWidth = mViewRoot.getChildAt(0).getMeasuredWidth();
-                if (neededWidth > renderScreenWidth) {
-                    renderScreenWidth = neededWidth;
+                if (renderingMode.isHorizExpand()) {
+                    int neededWidth = mViewRoot.getChildAt(0).getMeasuredWidth();
+                    if (neededWidth > renderScreenWidth) {
+                        renderScreenWidth = neededWidth;
+                    }
                 }
 
-                int neededHeight = mViewRoot.getChildAt(0).getMeasuredHeight();
-                if (neededHeight > renderScreenHeight - mScreenOffset) {
-                    renderScreenHeight = neededHeight + mScreenOffset;
+                if (renderingMode.isVertExpand()) {
+                    int neededHeight = mViewRoot.getChildAt(0).getMeasuredHeight();
+                    if (neededHeight > renderScreenHeight - mScreenOffset) {
+                        renderScreenHeight = neededHeight + mScreenOffset;
+                    }
                 }
             }
 
diff --git a/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/Stack.java b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/Stack.java
new file mode 100644
index 0000000..9bd0015
--- /dev/null
+++ b/tools/layoutlib/bridge/src/com/android/layoutlib/bridge/impl/Stack.java
@@ -0,0 +1,70 @@
+/*
+ * Copyright (C) 2010 The Android Open Source Project
+ *
+ * Licensed under the Apache License, Version 2.0 (the "License");
+ * you may not use this file except in compliance with the License.
+ * You may obtain a copy of the License at
+ *
+ *      http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+package com.android.layoutlib.bridge.impl;
+
+import java.util.ArrayList;
+
+/**
+ * Custom Stack implementation on top of an {@link ArrayList} instead of
+ * using {@link java.util.Stack} which is on top of a vector.
+ *
+ * @param <T>
+ */
+public class Stack<T> extends ArrayList<T> {
+
+    private static final long serialVersionUID = 1L;
+
+    public Stack() {
+        super();
+    }
+
+    public Stack(int size) {
+        super(size);
+    }
+
+    /**
+     * Pushes the given object to the stack
+     * @param object the object to push
+     */
+    public void push(T object) {
+        add(object);
+    }
+
+    /**
+     * Remove the object at the top of the stack and returns it.
+     * @return the removed object or null if the stack was empty.
+     */
+    public T pop() {
+        if (size() > 0) {
+            return remove(size() - 1);
+        }
+
+        return null;
+    }
+
+    /**
+     * Returns the object at the top of the stack.
+     * @return the object at the top or null if the stack is empty.
+     */
+    public T peek() {
+        if (size() > 0) {
+            return get(size() - 1);
+        }
+
+        return null;
+    }
+}