Loading media/libstagefright/Android.mk +4 −2 Original line number Diff line number Diff line Loading @@ -58,7 +58,8 @@ LOCAL_C_INCLUDES:= \ $(TOP)/frameworks/base/include/media/stagefright/openmax \ $(TOP)/external/flac/include \ $(TOP)/external/tremolo \ $(TOP)/frameworks/base/media/libstagefright/rtsp $(TOP)/frameworks/base/media/libstagefright/rtsp \ $(TOP)/external/openssl/include \ LOCAL_SHARED_LIBRARIES := \ libbinder \ Loading @@ -72,7 +73,8 @@ LOCAL_SHARED_LIBRARIES := \ libstagefright_yuv \ libcamera_client \ libdrmframework \ libcrypto libcrypto \ libssl LOCAL_STATIC_LIBRARIES := \ libstagefright_color_conversion \ Loading media/libstagefright/AwesomePlayer.cpp +2 −1 Original line number Diff line number Diff line Loading @@ -1481,7 +1481,8 @@ status_t AwesomePlayer::prepareAsync_l() { status_t AwesomePlayer::finishSetDataSource_l() { sp<DataSource> dataSource; if (!strncasecmp("http://", mUri.string(), 7)) { if (!strncasecmp("http://", mUri.string(), 7) || !strncasecmp("https://", mUri.string(), 8)) { mConnectingDataSource = new NuHTTPDataSource; mLock.unlock(); Loading media/libstagefright/DataSource.cpp +2 −1 Original line number Diff line number Diff line Loading @@ -125,7 +125,8 @@ sp<DataSource> DataSource::CreateFromURI( sp<DataSource> source; if (!strncasecmp("file://", uri, 7)) { source = new FileSource(uri + 7); } else if (!strncasecmp("http://", uri, 7)) { } else if (!strncasecmp("http://", uri, 7) || !strncasecmp("https://", uri, 8)) { sp<NuHTTPDataSource> httpSource = new NuHTTPDataSource; if (httpSource->connect(uri, headers) != OK) { return NULL; Loading media/libstagefright/HTTPStream.cpp +94 −5 Original line number Diff line number Diff line Loading @@ -34,6 +34,8 @@ #include <media/stagefright/foundation/ADebug.h> #include <openssl/ssl.h> namespace android { // static Loading @@ -41,11 +43,18 @@ const char *HTTPStream::kStatusKey = ":status:"; // MUST be lowercase. HTTPStream::HTTPStream() : mState(READY), mSocket(-1) { mSocket(-1), mSSLContext(NULL), mSSL(NULL) { } HTTPStream::~HTTPStream() { disconnect(); if (mSSLContext != NULL) { SSL_CTX_free((SSL_CTX *)mSSLContext); mSSLContext = NULL; } } static bool MakeSocketBlocking(int s, bool blocking) { Loading Loading @@ -198,7 +207,11 @@ static ssize_t MyReceive(int s, void *data, size_t size, int flags) { return MySendReceive(s, data, size, flags, false /* sendData */); } status_t HTTPStream::connect(const char *server, int port) { status_t HTTPStream::connect(const char *server, int port, bool https) { if (port < 0) { port = https ? 443 : 80; } Mutex::Autolock autoLock(mLock); status_t err = OK; Loading Loading @@ -249,6 +262,47 @@ status_t HTTPStream::connect(const char *server, int port) { return res; } if (https) { CHECK(mSSL == NULL); if (mSSLContext == NULL) { SSL_library_init(); mSSLContext = SSL_CTX_new(TLSv1_client_method()); if (mSSLContext == NULL) { LOGE("failed to create SSL context"); mState = READY; return ERROR_IO; } } mSSL = SSL_new((SSL_CTX *)mSSLContext); if (mSSL == NULL) { LOGE("failed to create SSL session"); mState = READY; return ERROR_IO; } int res = SSL_set_fd((SSL *)mSSL, mSocket); if (res == 1) { res = SSL_connect((SSL *)mSSL); } if (res != 1) { SSL_free((SSL *)mSSL); mSSL = NULL; LOGE("failed to connect over SSL"); mState = READY; return ERROR_IO; } } mState = CONNECTED; return OK; Loading @@ -261,6 +315,13 @@ status_t HTTPStream::disconnect() { return ERROR_NOT_CONNECTED; } if (mSSL != NULL) { SSL_shutdown((SSL *)mSSL); SSL_free((SSL *)mSSL); mSSL = NULL; } CHECK(mSocket >= 0); close(mSocket); mSocket = -1; Loading @@ -276,7 +337,16 @@ status_t HTTPStream::send(const char *data, size_t size) { } while (size > 0) { ssize_t n = MySend(mSocket, data, size, 0); ssize_t n; if (mSSL != NULL) { n = SSL_write((SSL *)mSSL, data, size); if (n < 0) { n = -SSL_get_error((SSL *)mSSL, n); } } else { n = MySend(mSocket, data, size, 0); } if (n < 0) { disconnect(); Loading Loading @@ -317,7 +387,17 @@ status_t HTTPStream::receive_line(char *line, size_t size) { for (;;) { char c; ssize_t n = MyReceive(mSocket, &c, 1, 0); ssize_t n; if (mSSL != NULL) { n = SSL_read((SSL *)mSSL, &c, 1); if (n < 0) { n = -SSL_get_error((SSL *)mSSL, n); } } else { n = MyReceive(mSocket, &c, 1, 0); } if (n < 0) { disconnect(); Loading Loading @@ -437,7 +517,16 @@ status_t HTTPStream::receive_header(int *http_status) { ssize_t HTTPStream::receive(void *data, size_t size) { size_t total = 0; while (total < size) { ssize_t n = MyReceive(mSocket, (char *)data + total, size - total, 0); ssize_t n; if (mSSL != NULL) { n = SSL_read((SSL *)mSSL, (char *)data + total, size - total); if (n < 0) { n = -SSL_get_error((SSL *)mSSL, n); } } else { n = MyReceive(mSocket, (char *)data + total, size - total, 0); } if (n < 0) { LOGE("recv failed, errno = %d (%s)", (int)n, strerror(-n)); Loading media/libstagefright/NuHTTPDataSource.cpp +23 −11 Original line number Diff line number Diff line Loading @@ -24,22 +24,30 @@ static bool ParseSingleUnsignedLong( } static bool ParseURL( const char *url, String8 *host, unsigned *port, String8 *path) { const char *url, String8 *host, unsigned *port, String8 *path, bool *https) { host->setTo(""); *port = 0; path->setTo(""); if (strncasecmp("http://", url, 7)) { size_t hostStart; if (!strncasecmp("http://", url, 7)) { hostStart = 7; *https = false; } else if (!strncasecmp("https://", url, 8)) { hostStart = 8; *https = true; } else { return false; } const char *slashPos = strchr(&url[7], '/'); const char *slashPos = strchr(&url[hostStart], '/'); if (slashPos == NULL) { host->setTo(&url[7]); host->setTo(&url[hostStart]); path->setTo("/"); } else { host->setTo(&url[7], slashPos - &url[7]); host->setTo(&url[hostStart], slashPos - &url[hostStart]); path->setTo(slashPos); } Loading @@ -57,7 +65,7 @@ static bool ParseURL( String8 tmp(host->string(), colonOffset); *host = tmp; } else { *port = 80; *port = (*https) ? 443 : 80; } return true; Loading @@ -66,6 +74,7 @@ static bool ParseURL( NuHTTPDataSource::NuHTTPDataSource() : mState(DISCONNECTED), mPort(0), mHTTPS(false), mOffset(0), mContentLength(0), mContentLengthValid(false), Loading Loading @@ -111,11 +120,12 @@ status_t NuHTTPDataSource::connect( mUri = uri; if (!ParseURL(uri, &host, &port, &path)) { bool https; if (!ParseURL(uri, &host, &port, &path, &https)) { return ERROR_MALFORMED; } return connect(host, port, path, headers, offset); return connect(host, port, path, https, headers, offset); } static bool IsRedirectStatusCode(int httpStatus) { Loading @@ -125,6 +135,7 @@ static bool IsRedirectStatusCode(int httpStatus) { status_t NuHTTPDataSource::connect( const char *host, unsigned port, const char *path, bool https, const String8 &headers, off64_t offset) { LOGI("connect to %s:%u%s @%lld", host, port, path, offset); Loading @@ -132,7 +143,7 @@ status_t NuHTTPDataSource::connect( bool needsToReconnect = true; if (mState == CONNECTED && host == mHost && port == mPort && offset == mOffset) { && https == mHTTPS && offset == mOffset) { if (mContentLengthValid && mOffset == mContentLength) { LOGI("Didn't have to reconnect, old one's still good."); needsToReconnect = false; Loading @@ -142,6 +153,7 @@ status_t NuHTTPDataSource::connect( mHost = host; mPort = port; mPath = path; mHTTPS = https; mHeaders = headers; status_t err = OK; Loading @@ -150,7 +162,7 @@ status_t NuHTTPDataSource::connect( if (needsToReconnect) { mHTTP.disconnect(); err = mHTTP.connect(host, port); err = mHTTP.connect(host, port, https); } if (err != OK) { Loading Loading @@ -353,7 +365,7 @@ ssize_t NuHTTPDataSource::readAt(off64_t offset, void *data, size_t size) { String8 host = mHost; String8 path = mPath; String8 headers = mHeaders; status_t err = connect(host, mPort, path, headers, offset); status_t err = connect(host, mPort, path, mHTTPS, headers, offset); if (err != OK) { return err; Loading Loading
media/libstagefright/Android.mk +4 −2 Original line number Diff line number Diff line Loading @@ -58,7 +58,8 @@ LOCAL_C_INCLUDES:= \ $(TOP)/frameworks/base/include/media/stagefright/openmax \ $(TOP)/external/flac/include \ $(TOP)/external/tremolo \ $(TOP)/frameworks/base/media/libstagefright/rtsp $(TOP)/frameworks/base/media/libstagefright/rtsp \ $(TOP)/external/openssl/include \ LOCAL_SHARED_LIBRARIES := \ libbinder \ Loading @@ -72,7 +73,8 @@ LOCAL_SHARED_LIBRARIES := \ libstagefright_yuv \ libcamera_client \ libdrmframework \ libcrypto libcrypto \ libssl LOCAL_STATIC_LIBRARIES := \ libstagefright_color_conversion \ Loading
media/libstagefright/AwesomePlayer.cpp +2 −1 Original line number Diff line number Diff line Loading @@ -1481,7 +1481,8 @@ status_t AwesomePlayer::prepareAsync_l() { status_t AwesomePlayer::finishSetDataSource_l() { sp<DataSource> dataSource; if (!strncasecmp("http://", mUri.string(), 7)) { if (!strncasecmp("http://", mUri.string(), 7) || !strncasecmp("https://", mUri.string(), 8)) { mConnectingDataSource = new NuHTTPDataSource; mLock.unlock(); Loading
media/libstagefright/DataSource.cpp +2 −1 Original line number Diff line number Diff line Loading @@ -125,7 +125,8 @@ sp<DataSource> DataSource::CreateFromURI( sp<DataSource> source; if (!strncasecmp("file://", uri, 7)) { source = new FileSource(uri + 7); } else if (!strncasecmp("http://", uri, 7)) { } else if (!strncasecmp("http://", uri, 7) || !strncasecmp("https://", uri, 8)) { sp<NuHTTPDataSource> httpSource = new NuHTTPDataSource; if (httpSource->connect(uri, headers) != OK) { return NULL; Loading
media/libstagefright/HTTPStream.cpp +94 −5 Original line number Diff line number Diff line Loading @@ -34,6 +34,8 @@ #include <media/stagefright/foundation/ADebug.h> #include <openssl/ssl.h> namespace android { // static Loading @@ -41,11 +43,18 @@ const char *HTTPStream::kStatusKey = ":status:"; // MUST be lowercase. HTTPStream::HTTPStream() : mState(READY), mSocket(-1) { mSocket(-1), mSSLContext(NULL), mSSL(NULL) { } HTTPStream::~HTTPStream() { disconnect(); if (mSSLContext != NULL) { SSL_CTX_free((SSL_CTX *)mSSLContext); mSSLContext = NULL; } } static bool MakeSocketBlocking(int s, bool blocking) { Loading Loading @@ -198,7 +207,11 @@ static ssize_t MyReceive(int s, void *data, size_t size, int flags) { return MySendReceive(s, data, size, flags, false /* sendData */); } status_t HTTPStream::connect(const char *server, int port) { status_t HTTPStream::connect(const char *server, int port, bool https) { if (port < 0) { port = https ? 443 : 80; } Mutex::Autolock autoLock(mLock); status_t err = OK; Loading Loading @@ -249,6 +262,47 @@ status_t HTTPStream::connect(const char *server, int port) { return res; } if (https) { CHECK(mSSL == NULL); if (mSSLContext == NULL) { SSL_library_init(); mSSLContext = SSL_CTX_new(TLSv1_client_method()); if (mSSLContext == NULL) { LOGE("failed to create SSL context"); mState = READY; return ERROR_IO; } } mSSL = SSL_new((SSL_CTX *)mSSLContext); if (mSSL == NULL) { LOGE("failed to create SSL session"); mState = READY; return ERROR_IO; } int res = SSL_set_fd((SSL *)mSSL, mSocket); if (res == 1) { res = SSL_connect((SSL *)mSSL); } if (res != 1) { SSL_free((SSL *)mSSL); mSSL = NULL; LOGE("failed to connect over SSL"); mState = READY; return ERROR_IO; } } mState = CONNECTED; return OK; Loading @@ -261,6 +315,13 @@ status_t HTTPStream::disconnect() { return ERROR_NOT_CONNECTED; } if (mSSL != NULL) { SSL_shutdown((SSL *)mSSL); SSL_free((SSL *)mSSL); mSSL = NULL; } CHECK(mSocket >= 0); close(mSocket); mSocket = -1; Loading @@ -276,7 +337,16 @@ status_t HTTPStream::send(const char *data, size_t size) { } while (size > 0) { ssize_t n = MySend(mSocket, data, size, 0); ssize_t n; if (mSSL != NULL) { n = SSL_write((SSL *)mSSL, data, size); if (n < 0) { n = -SSL_get_error((SSL *)mSSL, n); } } else { n = MySend(mSocket, data, size, 0); } if (n < 0) { disconnect(); Loading Loading @@ -317,7 +387,17 @@ status_t HTTPStream::receive_line(char *line, size_t size) { for (;;) { char c; ssize_t n = MyReceive(mSocket, &c, 1, 0); ssize_t n; if (mSSL != NULL) { n = SSL_read((SSL *)mSSL, &c, 1); if (n < 0) { n = -SSL_get_error((SSL *)mSSL, n); } } else { n = MyReceive(mSocket, &c, 1, 0); } if (n < 0) { disconnect(); Loading Loading @@ -437,7 +517,16 @@ status_t HTTPStream::receive_header(int *http_status) { ssize_t HTTPStream::receive(void *data, size_t size) { size_t total = 0; while (total < size) { ssize_t n = MyReceive(mSocket, (char *)data + total, size - total, 0); ssize_t n; if (mSSL != NULL) { n = SSL_read((SSL *)mSSL, (char *)data + total, size - total); if (n < 0) { n = -SSL_get_error((SSL *)mSSL, n); } } else { n = MyReceive(mSocket, (char *)data + total, size - total, 0); } if (n < 0) { LOGE("recv failed, errno = %d (%s)", (int)n, strerror(-n)); Loading
media/libstagefright/NuHTTPDataSource.cpp +23 −11 Original line number Diff line number Diff line Loading @@ -24,22 +24,30 @@ static bool ParseSingleUnsignedLong( } static bool ParseURL( const char *url, String8 *host, unsigned *port, String8 *path) { const char *url, String8 *host, unsigned *port, String8 *path, bool *https) { host->setTo(""); *port = 0; path->setTo(""); if (strncasecmp("http://", url, 7)) { size_t hostStart; if (!strncasecmp("http://", url, 7)) { hostStart = 7; *https = false; } else if (!strncasecmp("https://", url, 8)) { hostStart = 8; *https = true; } else { return false; } const char *slashPos = strchr(&url[7], '/'); const char *slashPos = strchr(&url[hostStart], '/'); if (slashPos == NULL) { host->setTo(&url[7]); host->setTo(&url[hostStart]); path->setTo("/"); } else { host->setTo(&url[7], slashPos - &url[7]); host->setTo(&url[hostStart], slashPos - &url[hostStart]); path->setTo(slashPos); } Loading @@ -57,7 +65,7 @@ static bool ParseURL( String8 tmp(host->string(), colonOffset); *host = tmp; } else { *port = 80; *port = (*https) ? 443 : 80; } return true; Loading @@ -66,6 +74,7 @@ static bool ParseURL( NuHTTPDataSource::NuHTTPDataSource() : mState(DISCONNECTED), mPort(0), mHTTPS(false), mOffset(0), mContentLength(0), mContentLengthValid(false), Loading Loading @@ -111,11 +120,12 @@ status_t NuHTTPDataSource::connect( mUri = uri; if (!ParseURL(uri, &host, &port, &path)) { bool https; if (!ParseURL(uri, &host, &port, &path, &https)) { return ERROR_MALFORMED; } return connect(host, port, path, headers, offset); return connect(host, port, path, https, headers, offset); } static bool IsRedirectStatusCode(int httpStatus) { Loading @@ -125,6 +135,7 @@ static bool IsRedirectStatusCode(int httpStatus) { status_t NuHTTPDataSource::connect( const char *host, unsigned port, const char *path, bool https, const String8 &headers, off64_t offset) { LOGI("connect to %s:%u%s @%lld", host, port, path, offset); Loading @@ -132,7 +143,7 @@ status_t NuHTTPDataSource::connect( bool needsToReconnect = true; if (mState == CONNECTED && host == mHost && port == mPort && offset == mOffset) { && https == mHTTPS && offset == mOffset) { if (mContentLengthValid && mOffset == mContentLength) { LOGI("Didn't have to reconnect, old one's still good."); needsToReconnect = false; Loading @@ -142,6 +153,7 @@ status_t NuHTTPDataSource::connect( mHost = host; mPort = port; mPath = path; mHTTPS = https; mHeaders = headers; status_t err = OK; Loading @@ -150,7 +162,7 @@ status_t NuHTTPDataSource::connect( if (needsToReconnect) { mHTTP.disconnect(); err = mHTTP.connect(host, port); err = mHTTP.connect(host, port, https); } if (err != OK) { Loading Loading @@ -353,7 +365,7 @@ ssize_t NuHTTPDataSource::readAt(off64_t offset, void *data, size_t size) { String8 host = mHost; String8 path = mPath; String8 headers = mHeaders; status_t err = connect(host, mPort, path, headers, offset); status_t err = connect(host, mPort, path, mHTTPS, headers, offset); if (err != OK) { return err; Loading