Merge "Move MediaExtractor back to libstagefright"
diff --git a/cmds/screenrecord/screenrecord.cpp b/cmds/screenrecord/screenrecord.cpp
index a7ac2d7..c559ff9 100644
--- a/cmds/screenrecord/screenrecord.cpp
+++ b/cmds/screenrecord/screenrecord.cpp
@@ -140,14 +140,6 @@
 }
 
 /*
- * Returns "true" if the device is rotated 90 degrees.
- */
-static bool isDeviceRotated(int orientation) {
-    return orientation != DISPLAY_ORIENTATION_0 &&
-            orientation != DISPLAY_ORIENTATION_180;
-}
-
-/*
  * Configures and starts the MediaCodec encoder.  Obtains an input surface
  * from the codec.
  */
@@ -242,22 +234,11 @@
         const DisplayInfo& mainDpyInfo) {
 
     // Set the region of the layer stack we're interested in, which in our
-    // case is "all of it".  If the app is rotated (so that the width of the
-    // app is based on the height of the display), reverse width/height.
-    bool deviceRotated = isDeviceRotated(mainDpyInfo.orientation);
-    uint32_t sourceWidth, sourceHeight;
-    if (!deviceRotated) {
-        sourceWidth = mainDpyInfo.w;
-        sourceHeight = mainDpyInfo.h;
-    } else {
-        ALOGV("using rotated width/height");
-        sourceHeight = mainDpyInfo.w;
-        sourceWidth = mainDpyInfo.h;
-    }
-    Rect layerStackRect(sourceWidth, sourceHeight);
+    // case is "all of it".
+    Rect layerStackRect(mainDpyInfo.w, mainDpyInfo.h);
 
     // We need to preserve the aspect ratio of the display.
-    float displayAspect = (float) sourceHeight / (float) sourceWidth;
+    float displayAspect = (float) mainDpyInfo.h / (float) mainDpyInfo.w;
 
 
     // Set the way we map the output onto the display surface (which will
@@ -334,6 +315,22 @@
 }
 
 /*
+ * Set the main display width and height to the actual width and height
+ */
+static status_t getActualDisplaySize(const sp<IBinder>& mainDpy, DisplayInfo* mainDpyInfo) {
+    Rect viewport;
+    status_t err = SurfaceComposerClient::getDisplayViewport(mainDpy, &viewport);
+    if (err != NO_ERROR) {
+        fprintf(stderr, "ERROR: unable to get display viewport\n");
+        return err;
+    }
+    mainDpyInfo->w = viewport.width();
+    mainDpyInfo->h = viewport.height();
+
+    return NO_ERROR;
+}
+
+/*
  * Runs the MediaCodec encoder, sending the output to the MediaMuxer.  The
  * input frames are coming from the virtual display as fast as SurfaceFlinger
  * wants to send them.
@@ -403,14 +400,22 @@
                     // useful stuff is hard to get at without a Dalvik VM.
                     err = SurfaceComposerClient::getDisplayInfo(mainDpy,
                             &mainDpyInfo);
-                    if (err != NO_ERROR) {
+                    if (err == NO_ERROR) {
+                        err = getActualDisplaySize(mainDpy, &mainDpyInfo);
+                        if (err != NO_ERROR) {
+                            fprintf(stderr, "ERROR: unable to set actual display size\n");
+                            return err;
+                        }
+
+                        if (orientation != mainDpyInfo.orientation) {
+                            ALOGD("orientation changed, now %d", mainDpyInfo.orientation);
+                            SurfaceComposerClient::Transaction t;
+                            setDisplayProjection(t, virtualDpy, mainDpyInfo);
+                            t.apply();
+                            orientation = mainDpyInfo.orientation;
+                        }
+                    } else {
                         ALOGW("getDisplayInfo(main) failed: %d", err);
-                    } else if (orientation != mainDpyInfo.orientation) {
-                        ALOGD("orientation changed, now %d", mainDpyInfo.orientation);
-                        SurfaceComposerClient::Transaction t;
-                        setDisplayProjection(t, virtualDpy, mainDpyInfo);
-                        t.apply();
-                        orientation = mainDpyInfo.orientation;
                     }
                 }
 
@@ -552,6 +557,10 @@
     return rawFp;
 }
 
+static inline uint32_t floorToEven(uint32_t num) {
+    return num & ~1;
+}
+
 /*
  * Main "do work" start point.
  *
@@ -579,6 +588,13 @@
         fprintf(stderr, "ERROR: unable to get display characteristics\n");
         return err;
     }
+
+    err = getActualDisplaySize(mainDpy, &mainDpyInfo);
+    if (err != NO_ERROR) {
+        fprintf(stderr, "ERROR: unable to set actual display size\n");
+        return err;
+    }
+
     if (gVerbose) {
         printf("Main display is %dx%d @%.2ffps (orientation=%u)\n",
                 mainDpyInfo.w, mainDpyInfo.h, mainDpyInfo.fps,
@@ -586,12 +602,12 @@
         fflush(stdout);
     }
 
-    bool rotated = isDeviceRotated(mainDpyInfo.orientation);
+    // Encoder can't take odd number as config
     if (gVideoWidth == 0) {
-        gVideoWidth = rotated ? mainDpyInfo.h : mainDpyInfo.w;
+        gVideoWidth = floorToEven(mainDpyInfo.w);
     }
     if (gVideoHeight == 0) {
-        gVideoHeight = rotated ? mainDpyInfo.w : mainDpyInfo.h;
+        gVideoHeight = floorToEven(mainDpyInfo.h);
     }
 
     // Configure and start the encoder.
diff --git a/media/mtp/MtpServer.cpp b/media/mtp/MtpServer.cpp
index ccddd6e..cff2803 100644
--- a/media/mtp/MtpServer.cpp
+++ b/media/mtp/MtpServer.cpp
@@ -99,6 +99,7 @@
     MTP_EVENT_STORE_ADDED,
     MTP_EVENT_STORE_REMOVED,
     MTP_EVENT_DEVICE_PROP_CHANGED,
+    MTP_EVENT_OBJECT_INFO_CHANGED,
 };
 
 MtpServer::MtpServer(IMtpDatabase* database, int controlFd, bool ptp,
@@ -259,6 +260,11 @@
     sendEvent(MTP_EVENT_OBJECT_REMOVED, handle);
 }
 
+void MtpServer::sendObjectInfoChanged(MtpObjectHandle handle) {
+    ALOGV("sendObjectInfoChanged %d\n", handle);
+    sendEvent(MTP_EVENT_OBJECT_INFO_CHANGED, handle);
+}
+
 void MtpServer::sendStoreAdded(MtpStorageID id) {
     ALOGV("sendStoreAdded %08X\n", id);
     sendEvent(MTP_EVENT_STORE_ADDED, id);
diff --git a/media/mtp/MtpServer.h b/media/mtp/MtpServer.h
index f6939d7..1f8799f 100644
--- a/media/mtp/MtpServer.h
+++ b/media/mtp/MtpServer.h
@@ -115,6 +115,7 @@
 
     void                sendObjectAdded(MtpObjectHandle handle);
     void                sendObjectRemoved(MtpObjectHandle handle);
+    void                sendObjectInfoChanged(MtpObjectHandle handle);
     void                sendDevicePropertyChanged(MtpDeviceProperty property);
 
 private:
diff --git a/services/camera/libcameraservice/tests/Android.mk b/services/camera/libcameraservice/tests/Android.mk
index f77069c..8d80ff1 100644
--- a/services/camera/libcameraservice/tests/Android.mk
+++ b/services/camera/libcameraservice/tests/Android.mk
@@ -38,6 +38,7 @@
 LOCAL_CFLAGS += -Wall -Wextra -Werror
 
 LOCAL_MODULE:= cameraservice_test
+LOCAL_COMPATIBILITY_SUITE := device-tests
 LOCAL_MODULE_TAGS := tests
 
 include $(BUILD_NATIVE_TEST)