Expose an IRemoteDisplay to trigger wifi display connections setup and feedback.

Change-Id: I7602cda0e38073c9f0e63fa4de238ca0d4b4ce8e
diff --git a/media/libmediaplayerservice/MediaPlayerService.cpp b/media/libmediaplayerservice/MediaPlayerService.cpp
index ae55642..9005500 100644
--- a/media/libmediaplayerservice/MediaPlayerService.cpp
+++ b/media/libmediaplayerservice/MediaPlayerService.cpp
@@ -283,8 +283,7 @@
 
 sp<IRemoteDisplay> MediaPlayerService::listenForRemoteDisplay(
         const sp<IRemoteDisplayClient>& client, const String8& iface) {
-    // TODO: implement me!
-    return NULL;
+    return new RemoteDisplay(client, iface.string());;
 }
 
 status_t MediaPlayerService::enableRemoteDisplay(const char *iface) {
@@ -295,20 +294,12 @@
             return INVALID_OPERATION;
         }
 
-        mRemoteDisplay = new RemoteDisplay;
-
-        status_t err = mRemoteDisplay->start(iface);
-
-        if (err != OK) {
-            mRemoteDisplay.clear();
-            return err;
-        }
-
+        mRemoteDisplay = new RemoteDisplay(NULL /* client */, iface);
         return OK;
     }
 
     if (mRemoteDisplay != NULL) {
-        mRemoteDisplay->stop();
+        mRemoteDisplay->disconnect();
         mRemoteDisplay.clear();
     }
 
diff --git a/media/libmediaplayerservice/RemoteDisplay.cpp b/media/libmediaplayerservice/RemoteDisplay.cpp
index 49f7278..1cc605e 100644
--- a/media/libmediaplayerservice/RemoteDisplay.cpp
+++ b/media/libmediaplayerservice/RemoteDisplay.cpp
@@ -19,29 +19,27 @@
 #include "ANetworkSession.h"
 #include "source/WifiDisplaySource.h"
 
+#include <media/IRemoteDisplayClient.h>
+
 namespace android {
 
-RemoteDisplay::RemoteDisplay()
-    : mInitCheck(NO_INIT),
-      mLooper(new ALooper),
+RemoteDisplay::RemoteDisplay(
+        const sp<IRemoteDisplayClient> &client, const char *iface)
+    : mLooper(new ALooper),
       mNetSession(new ANetworkSession),
-      mSource(new WifiDisplaySource(mNetSession)) {
+      mSource(new WifiDisplaySource(mNetSession, client)) {
     mLooper->registerHandler(mSource);
+
+    mNetSession->start();
+    mLooper->start();
+
+    mSource->start(iface);
 }
 
 RemoteDisplay::~RemoteDisplay() {
 }
 
-status_t RemoteDisplay::start(const char *iface) {
-    mNetSession->start();
-    mLooper->start();
-
-    mSource->start(iface);
-
-    return OK;
-}
-
-status_t RemoteDisplay::stop() {
+status_t RemoteDisplay::disconnect() {
     mSource->stop();
 
     mLooper->stop();
@@ -51,4 +49,3 @@
 }
 
 }  // namespace android
-
diff --git a/media/libmediaplayerservice/RemoteDisplay.h b/media/libmediaplayerservice/RemoteDisplay.h
index 3607d06..63c5286 100644
--- a/media/libmediaplayerservice/RemoteDisplay.h
+++ b/media/libmediaplayerservice/RemoteDisplay.h
@@ -18,6 +18,7 @@
 
 #define REMOTE_DISPLAY_H_
 
+#include <media/IRemoteDisplay.h>
 #include <media/stagefright/foundation/ABase.h>
 #include <utils/Errors.h>
 #include <utils/RefBase.h>
@@ -26,20 +27,18 @@
 
 struct ALooper;
 struct ANetworkSession;
+struct IRemoteDisplayClient;
 struct WifiDisplaySource;
 
-struct RemoteDisplay : public RefBase {
-    RemoteDisplay();
+struct RemoteDisplay : public BnRemoteDisplay {
+    RemoteDisplay(const sp<IRemoteDisplayClient> &client, const char *iface);
 
-    status_t start(const char *iface);
-    status_t stop();
+    virtual status_t disconnect();
 
 protected:
     virtual ~RemoteDisplay();
 
 private:
-    status_t mInitCheck;
-
     sp<ALooper> mNetLooper;
     sp<ALooper> mLooper;
     sp<ANetworkSession> mNetSession;
diff --git a/media/libstagefright/wifi-display/source/PlaybackSession.cpp b/media/libstagefright/wifi-display/source/PlaybackSession.cpp
index c9d6562..6c01c7b 100644
--- a/media/libstagefright/wifi-display/source/PlaybackSession.cpp
+++ b/media/libstagefright/wifi-display/source/PlaybackSession.cpp
@@ -113,9 +113,11 @@
 
 WifiDisplaySource::PlaybackSession::PlaybackSession(
         const sp<ANetworkSession> &netSession,
-        const sp<AMessage> &notify)
+        const sp<AMessage> &notify,
+        bool legacyMode)
     : mNetSession(netSession),
       mNotify(notify),
+      mLegacyMode(legacyMode),
       mLastLifesignUs(),
       mTSQueue(new ABuffer(12 + kMaxNumTSPacketsPerRTPPacket * 188)),
       mPrevTimeUs(-1ll),
@@ -240,11 +242,6 @@
 
     mPacketizer.clear();
 
-    sp<IServiceManager> sm = defaultServiceManager();
-    sp<IBinder> binder = sm->getService(String16("SurfaceFlinger"));
-    sp<ISurfaceComposer> service = interface_cast<ISurfaceComposer>(binder);
-    CHECK(service != NULL);
-
     if (mSerializer != NULL) {
         mSerializer->stop();
 
@@ -257,7 +254,14 @@
         mSerializerLooper.clear();
     }
 
-    service->connectDisplay(NULL);
+    if (mLegacyMode) {
+        sp<IServiceManager> sm = defaultServiceManager();
+        sp<IBinder> binder = sm->getService(String16("SurfaceFlinger"));
+        sp<ISurfaceComposer> service = interface_cast<ISurfaceComposer>(binder);
+        CHECK(service != NULL);
+
+        service->connectDisplay(NULL);
+    }
 
     if (mRTCPSessionID != 0) {
         mNetSession->destroySession(mRTCPSessionID);
@@ -598,7 +602,7 @@
     SurfaceComposerClient::getDisplayInfo(0, &info);
 
     // sp<SurfaceMediaSource> source = new SurfaceMediaSource(info.w, info.h);
-    sp<SurfaceMediaSource> source = new SurfaceMediaSource(720, 1280);
+    sp<SurfaceMediaSource> source = new SurfaceMediaSource(width(), height());
 
 #if 0
     ssize_t index = mSerializer->addSource(source);
@@ -641,7 +645,11 @@
     err = source->setMaxAcquiredBufferCount(numInputBuffers + 1);
     CHECK_EQ(err, (status_t)OK);
 
-    service->connectDisplay(source->getBufferQueue());
+    mBufferQueue = source->getBufferQueue();
+
+    if (mLegacyMode) {
+        service->connectDisplay(mBufferQueue);
+    }
 #endif
 
 #if 0
@@ -673,6 +681,18 @@
     return OK;
 }
 
+sp<ISurfaceTexture> WifiDisplaySource::PlaybackSession::getSurfaceTexture() {
+    return mBufferQueue;
+}
+
+int32_t WifiDisplaySource::PlaybackSession::width() const {
+    return 720;
+}
+
+int32_t WifiDisplaySource::PlaybackSession::height() const {
+    return 1280;
+}
+
 void WifiDisplaySource::PlaybackSession::scheduleSendSR() {
     if (mSendSRPending) {
         return;
diff --git a/media/libstagefright/wifi-display/source/PlaybackSession.h b/media/libstagefright/wifi-display/source/PlaybackSession.h
index a6c9f27..5c228f6 100644
--- a/media/libstagefright/wifi-display/source/PlaybackSession.h
+++ b/media/libstagefright/wifi-display/source/PlaybackSession.h
@@ -23,6 +23,8 @@
 namespace android {
 
 struct ABuffer;
+struct BufferQueue;
+struct ISurfaceTexture;
 struct Serializer;
 struct TSPacketizer;
 
@@ -32,7 +34,9 @@
 // display.
 struct WifiDisplaySource::PlaybackSession : public AHandler {
     PlaybackSession(
-            const sp<ANetworkSession> &netSession, const sp<AMessage> &notify);
+            const sp<ANetworkSession> &netSession,
+            const sp<AMessage> &notify,
+            bool legacyMode);
 
     status_t init(
             const char *clientIP, int32_t clientRtp, int32_t clientRtcp,
@@ -46,6 +50,10 @@
     status_t play();
     status_t pause();
 
+    sp<ISurfaceTexture> getSurfaceTexture();
+    int32_t width() const;
+    int32_t height() const;
+
     enum {
         kWhatSessionDead,
         kWhatBinaryData,
@@ -73,6 +81,7 @@
 
     sp<ANetworkSession> mNetSession;
     sp<AMessage> mNotify;
+    bool mLegacyMode;
 
     int64_t mLastLifesignUs;
 
@@ -80,6 +89,7 @@
     sp<Serializer> mSerializer;
     sp<TSPacketizer> mPacketizer;
     sp<ALooper> mCodecLooper;
+    sp<BufferQueue> mBufferQueue;
 
     KeyedVector<size_t, sp<Track> > mTracks;
 
diff --git a/media/libstagefright/wifi-display/source/WifiDisplaySource.cpp b/media/libstagefright/wifi-display/source/WifiDisplaySource.cpp
index a998dcd..0786f2b 100644
--- a/media/libstagefright/wifi-display/source/WifiDisplaySource.cpp
+++ b/media/libstagefright/wifi-display/source/WifiDisplaySource.cpp
@@ -22,6 +22,9 @@
 #include "PlaybackSession.h"
 #include "ParsedMessage.h"
 
+#include <gui/ISurfaceTexture.h>
+
+#include <media/IRemoteDisplayClient.h>
 #include <media/stagefright/foundation/ABuffer.h>
 #include <media/stagefright/foundation/ADebug.h>
 #include <media/stagefright/foundation/AMessage.h>
@@ -32,8 +35,11 @@
 
 namespace android {
 
-WifiDisplaySource::WifiDisplaySource(const sp<ANetworkSession> &netSession)
+WifiDisplaySource::WifiDisplaySource(
+        const sp<ANetworkSession> &netSession,
+        const sp<IRemoteDisplayClient> &client)
     : mNetSession(netSession),
+      mClient(client),
       mSessionID(0),
       mReaperPending(false),
       mNextCSeq(1) {
@@ -201,6 +207,10 @@
                 mPlaybackSessions.removeItemsAt(i);
             }
 
+            if (mClient != NULL) {
+                mClient->onDisplayDisconnected();
+            }
+
             status_t err = OK;
 
             sp<AMessage> response = new AMessage;
@@ -768,7 +778,8 @@
     notify->setInt32("sessionID", sessionID);
 
     sp<PlaybackSession> playbackSession =
-        new PlaybackSession(mNetSession, notify);
+        new PlaybackSession(
+                mNetSession, notify, mClient == NULL /* legacyMode */);
 
     looper()->registerHandler(playbackSession);
 
@@ -869,6 +880,14 @@
 
     err = mNetSession->sendRequest(sessionID, response.c_str());
     CHECK_EQ(err, (status_t)OK);
+
+    if (mClient != NULL) {
+        mClient->onDisplayConnected(
+                playbackSession->getSurfaceTexture(),
+                playbackSession->width(),
+                playbackSession->height(),
+                0 /* flags */);
+    }
 }
 
 void WifiDisplaySource::onPauseRequest(
diff --git a/media/libstagefright/wifi-display/source/WifiDisplaySource.h b/media/libstagefright/wifi-display/source/WifiDisplaySource.h
index f56347d..99eb4f5 100644
--- a/media/libstagefright/wifi-display/source/WifiDisplaySource.h
+++ b/media/libstagefright/wifi-display/source/WifiDisplaySource.h
@@ -24,6 +24,7 @@
 
 namespace android {
 
+struct IRemoteDisplayClient;
 struct ParsedMessage;
 
 // Represents the RTSP server acting as a wifi display source.
@@ -31,7 +32,9 @@
 struct WifiDisplaySource : public AHandler {
     static const unsigned kWifiDisplayDefaultPort = 7236;
 
-    WifiDisplaySource(const sp<ANetworkSession> &netSession);
+    WifiDisplaySource(
+            const sp<ANetworkSession> &netSession,
+            const sp<IRemoteDisplayClient> &client);
 
     status_t start(const char *iface);
     status_t stop();
@@ -74,6 +77,7 @@
         kPlaybackSessionTimeoutSecs * 1000000ll;
 
     sp<ANetworkSession> mNetSession;
+    sp<IRemoteDisplayClient> mClient;
     int32_t mSessionID;
 
     struct ClientInfo {