mirror of
https://github.com/mozilla/gecko-dev.git
synced 2024-11-24 13:21:05 +00:00
Bug 1426887 - Avoid adding/removing streams to nsMultiplexInputStream when reading in Presentation API, r=jdm
This commit is contained in:
parent
b672b51cf7
commit
e832cff45e
@ -61,7 +61,7 @@ CopierCallbacks::OnStopRequest(nsIRequest* aRequest, nsISupports* aContext, nsre
|
|||||||
NS_IMPL_CYCLE_COLLECTION(PresentationTCPSessionTransport, mTransport,
|
NS_IMPL_CYCLE_COLLECTION(PresentationTCPSessionTransport, mTransport,
|
||||||
mSocketInputStream, mSocketOutputStream,
|
mSocketInputStream, mSocketOutputStream,
|
||||||
mInputStreamPump, mInputStreamScriptable,
|
mInputStreamPump, mInputStreamScriptable,
|
||||||
mMultiplexStream, mMultiplexStreamCopier, mCallback)
|
mCallback)
|
||||||
|
|
||||||
NS_IMPL_CYCLE_COLLECTING_ADDREF(PresentationTCPSessionTransport)
|
NS_IMPL_CYCLE_COLLECTING_ADDREF(PresentationTCPSessionTransport)
|
||||||
NS_IMPL_CYCLE_COLLECTING_RELEASE(PresentationTCPSessionTransport)
|
NS_IMPL_CYCLE_COLLECTING_RELEASE(PresentationTCPSessionTransport)
|
||||||
@ -236,36 +236,6 @@ PresentationTCPSessionTransport::CreateStream()
|
|||||||
return rv;
|
return rv;
|
||||||
}
|
}
|
||||||
|
|
||||||
mMultiplexStream = do_CreateInstance("@mozilla.org/io/multiplex-input-stream;1", &rv);
|
|
||||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
|
||||||
return rv;
|
|
||||||
}
|
|
||||||
nsCOMPtr<nsIInputStream> stream = do_QueryInterface(mMultiplexStream);
|
|
||||||
|
|
||||||
mMultiplexStreamCopier = do_CreateInstance("@mozilla.org/network/async-stream-copier;1", &rv);
|
|
||||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
|
||||||
return rv;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsCOMPtr<nsISocketTransportService> sts =
|
|
||||||
do_GetService(NS_SOCKETTRANSPORTSERVICE_CONTRACTID);
|
|
||||||
if (NS_WARN_IF(!sts)) {
|
|
||||||
return NS_ERROR_NOT_AVAILABLE;
|
|
||||||
}
|
|
||||||
|
|
||||||
nsCOMPtr<nsIEventTarget> target = do_QueryInterface(sts);
|
|
||||||
rv = mMultiplexStreamCopier->Init(stream,
|
|
||||||
mSocketOutputStream,
|
|
||||||
target,
|
|
||||||
true, /* source buffered */
|
|
||||||
false, /* sink buffered */
|
|
||||||
BUFFER_SIZE,
|
|
||||||
false, /* close source */
|
|
||||||
false); /* close sink */
|
|
||||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
|
||||||
return rv;
|
|
||||||
}
|
|
||||||
|
|
||||||
return NS_OK;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -347,23 +317,59 @@ PresentationTCPSessionTransport::GetSelfAddress(nsINetAddr** aSelfAddress)
|
|||||||
return mTransport->GetScriptableSelfAddr(aSelfAddress);
|
return mTransport->GetScriptableSelfAddr(aSelfAddress);
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
nsresult
|
||||||
PresentationTCPSessionTransport::EnsureCopying()
|
PresentationTCPSessionTransport::EnsureCopying()
|
||||||
{
|
{
|
||||||
if (mAsyncCopierActive) {
|
if (mAsyncCopierActive) {
|
||||||
return;
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
mAsyncCopierActive = true;
|
mAsyncCopierActive = true;
|
||||||
|
|
||||||
|
nsresult rv;
|
||||||
|
|
||||||
|
nsCOMPtr<nsIMultiplexInputStream> multiplexStream =
|
||||||
|
do_CreateInstance("@mozilla.org/io/multiplex-input-stream;1", &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsCOMPtr<nsIInputStream> stream = do_QueryInterface(multiplexStream);
|
||||||
|
|
||||||
|
while (!mPendingData.IsEmpty()) {
|
||||||
|
nsCOMPtr<nsIInputStream> stream = mPendingData[0];
|
||||||
|
multiplexStream->AppendStream(stream);
|
||||||
|
mPendingData.RemoveElementAt(0);
|
||||||
|
}
|
||||||
|
|
||||||
|
nsCOMPtr<nsIAsyncStreamCopier> copier =
|
||||||
|
do_CreateInstance("@mozilla.org/network/async-stream-copier;1", &rv);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
nsCOMPtr<nsISocketTransportService> sts =
|
||||||
|
do_GetService("@mozilla.org/network/socket-transport-service;1");
|
||||||
|
|
||||||
|
nsCOMPtr<nsIEventTarget> target = do_QueryInterface(sts);
|
||||||
|
rv = copier->Init(stream,
|
||||||
|
mSocketOutputStream,
|
||||||
|
target,
|
||||||
|
true, /* source buffered */
|
||||||
|
false, /* sink buffered */
|
||||||
|
BUFFER_SIZE,
|
||||||
|
false, /* close source */
|
||||||
|
false); /* close sink */
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
RefPtr<CopierCallbacks> callbacks = new CopierCallbacks(this);
|
RefPtr<CopierCallbacks> callbacks = new CopierCallbacks(this);
|
||||||
Unused << NS_WARN_IF(NS_FAILED(mMultiplexStreamCopier->AsyncCopy(callbacks, nullptr)));
|
rv = copier->AsyncCopy(callbacks, nullptr);
|
||||||
|
NS_ENSURE_SUCCESS(rv, rv);
|
||||||
|
|
||||||
|
return NS_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
PresentationTCPSessionTransport::NotifyCopyComplete(nsresult aStatus)
|
PresentationTCPSessionTransport::NotifyCopyComplete(nsresult aStatus)
|
||||||
{
|
{
|
||||||
mAsyncCopierActive = false;
|
mAsyncCopierActive = false;
|
||||||
mMultiplexStream->RemoveStream(0);
|
|
||||||
if (NS_WARN_IF(NS_FAILED(aStatus))) {
|
if (NS_WARN_IF(NS_FAILED(aStatus))) {
|
||||||
if (mReadyState != ReadyState::CLOSED) {
|
if (mReadyState != ReadyState::CLOSED) {
|
||||||
mCloseStatus = aStatus;
|
mCloseStatus = aStatus;
|
||||||
@ -372,13 +378,7 @@ PresentationTCPSessionTransport::NotifyCopyComplete(nsresult aStatus)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
uint32_t count;
|
if (!mPendingData.IsEmpty()) {
|
||||||
nsresult rv = mMultiplexStream->GetCount(&count);
|
|
||||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (count) {
|
|
||||||
EnsureCopying();
|
EnsureCopying();
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -410,7 +410,7 @@ PresentationTCPSessionTransport::Send(const nsAString& aData)
|
|||||||
return NS_ERROR_DOM_INVALID_STATE_ERR;
|
return NS_ERROR_DOM_INVALID_STATE_ERR;
|
||||||
}
|
}
|
||||||
|
|
||||||
mMultiplexStream->AppendStream(stream);
|
mPendingData.AppendElement(stream);
|
||||||
|
|
||||||
EnsureCopying();
|
EnsureCopying();
|
||||||
|
|
||||||
@ -441,9 +441,8 @@ PresentationTCPSessionTransport::Close(nsresult aReason)
|
|||||||
mCloseStatus = aReason;
|
mCloseStatus = aReason;
|
||||||
SetReadyState(ReadyState::CLOSING);
|
SetReadyState(ReadyState::CLOSING);
|
||||||
|
|
||||||
uint32_t count = 0;
|
if (!mAsyncCopierActive) {
|
||||||
mMultiplexStream->GetCount(&count);
|
mPendingData.Clear();
|
||||||
if (!count) {
|
|
||||||
mSocketOutputStream->Close();
|
mSocketOutputStream->Close();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -540,15 +539,9 @@ PresentationTCPSessionTransport::OnStopRequest(nsIRequest* aRequest,
|
|||||||
|
|
||||||
MOZ_ASSERT(NS_IsMainThread());
|
MOZ_ASSERT(NS_IsMainThread());
|
||||||
|
|
||||||
uint32_t count;
|
|
||||||
nsresult rv = mMultiplexStream->GetCount(&count);
|
|
||||||
if (NS_WARN_IF(NS_FAILED(rv))) {
|
|
||||||
return rv;
|
|
||||||
}
|
|
||||||
|
|
||||||
mInputStreamPump = nullptr;
|
mInputStreamPump = nullptr;
|
||||||
|
|
||||||
if (count != 0 && NS_SUCCEEDED(aStatusCode)) {
|
if (mAsyncCopierActive && NS_SUCCEEDED(aStatusCode)) {
|
||||||
// If we have some buffered output still, and status is not an error, the
|
// If we have some buffered output still, and status is not an error, the
|
||||||
// other side has done a half-close, but we don't want to be in the close
|
// other side has done a half-close, but we don't want to be in the close
|
||||||
// state until we are done sending everything that was buffered. We also
|
// state until we are done sending everything that was buffered. We also
|
||||||
|
@ -64,7 +64,7 @@ private:
|
|||||||
|
|
||||||
nsresult CreateInputStreamPump();
|
nsresult CreateInputStreamPump();
|
||||||
|
|
||||||
void EnsureCopying();
|
nsresult EnsureCopying();
|
||||||
|
|
||||||
enum class ReadyState {
|
enum class ReadyState {
|
||||||
CONNECTING,
|
CONNECTING,
|
||||||
@ -96,12 +96,11 @@ private:
|
|||||||
nsCOMPtr<nsIInputStreamPump> mInputStreamPump;
|
nsCOMPtr<nsIInputStreamPump> mInputStreamPump;
|
||||||
nsCOMPtr<nsIScriptableInputStream> mInputStreamScriptable;
|
nsCOMPtr<nsIScriptableInputStream> mInputStreamScriptable;
|
||||||
|
|
||||||
// Output stream machinery
|
|
||||||
nsCOMPtr<nsIMultiplexInputStream> mMultiplexStream;
|
|
||||||
nsCOMPtr<nsIAsyncStreamCopier> mMultiplexStreamCopier;
|
|
||||||
|
|
||||||
nsCOMPtr<nsIPresentationSessionTransportCallback> mCallback;
|
nsCOMPtr<nsIPresentationSessionTransportCallback> mCallback;
|
||||||
nsCOMPtr<nsIPresentationSessionTransportBuilderListener> mListener;
|
nsCOMPtr<nsIPresentationSessionTransportBuilderListener> mListener;
|
||||||
|
|
||||||
|
// The data to be sent.
|
||||||
|
nsTArray<nsCOMPtr<nsIInputStream>> mPendingData;
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace dom
|
} // namespace dom
|
||||||
|
Loading…
Reference in New Issue
Block a user