Loading dom/public/nsIScriptChannel.idl +15 −1 Original line number Diff line number Diff line Loading @@ -54,7 +54,7 @@ * principal of the environment in which the program is to be executed the * execution will be forced to happen in a sandbox. */ [scriptable, uuid(6dec981b-6fce-4f57-bf97-d518c6079c77)] [scriptable, uuid(33234b99-9588-4c7d-9da6-86b8b7cba565)] interface nsIScriptChannel : nsISupports { /** Loading Loading @@ -85,4 +85,18 @@ interface nsIScriptChannel : nsISupports * @throws NS_ERROR_INVALID_ARG when set to an unrecognized value. */ attribute unsigned long executionPolicy; /** * Control whether the program should be executed synchronosly when * the channel's AsyncOpen method is called or whether it should be * executed asynchronously. In both cases, any data that the * channel returns will be returned asynchronously; the only thing * this property affects is when the program executes. * * The default value of this property is TRUE. * * Setting this property after asyncOpen has been called on the * channel has no effect. */ attribute boolean executeAsync; }; dom/src/jsurl/nsJSProtocolHandler.cpp +66 −11 Original line number Diff line number Diff line Loading @@ -429,6 +429,7 @@ protected: nsRefPtr<nsJSThunk> mIOThunk; PopupControlState mPopupState; PRUint32 mExecutionPolicy; PRPackedBool mIsAsync; PRPackedBool mIsActive; PRPackedBool mOpenedStreamChannel; }; Loading @@ -439,6 +440,7 @@ nsJSChannel::nsJSChannel() : mActualLoadFlags(LOAD_NORMAL), mPopupState(openOverridden), mExecutionPolicy(EXECUTE_IN_SANDBOX), mIsAsync(PR_TRUE), mIsActive(PR_FALSE), mOpenedStreamChannel(PR_FALSE) { Loading Loading @@ -630,9 +632,42 @@ nsJSChannel::AsyncOpen(nsIStreamListener *aListener, nsISupports *aContext) loadGroup->AddRequest(this, nsnull); } mPopupState = win->GetPopupControlState(); nsRunnableMethod<nsJSChannel>::Method method; if (mIsAsync) { // post an event to do the rest nsCOMPtr<nsIRunnable> ev = new nsRunnableMethod<nsJSChannel>(this, &nsJSChannel::EvaluateScript); method = &nsJSChannel::EvaluateScript; } else { EvaluateScript(); if (mOpenedStreamChannel) { // That will handle notifying things return NS_OK; } NS_ASSERTION(NS_FAILED(mStatus), "We should have failed _somehow_"); // mStatus is going to be NS_ERROR_DOM_RETVAL_UNDEFINED if we didn't // have any content resulting from the execution and NS_BINDING_ABORTED // if something we did causes our own load to be stopped. Return // success in those cases, and error out in all others. if (mStatus != NS_ERROR_DOM_RETVAL_UNDEFINED && mStatus != NS_BINDING_ABORTED) { // Note that calling EvaluateScript() handled removing us from the // loadgroup and marking us as not active anymore. mListener = nsnull; mContext = nsnull; mOriginalInnerWindow = nsnull; return mStatus; } // We're returning success from asyncOpen(), but we didn't open a // stream channel. We'll have to notify ourselves, but make sure to do // it asynchronously. method = &nsJSChannel::NotifyListener; } nsCOMPtr<nsIRunnable> ev = new nsRunnableMethod<nsJSChannel>(this, method); nsresult rv = NS_DispatchToCurrentThread(ev); if (NS_FAILED(rv)) { Loading @@ -642,9 +677,6 @@ nsJSChannel::AsyncOpen(nsIStreamListener *aListener, nsISupports *aContext) mContext = nsnull; mOriginalInnerWindow = nsnull; } mPopupState = win->GetPopupControlState(); return rv; } Loading Loading @@ -687,7 +719,9 @@ nsJSChannel::EvaluateScript() mIsActive = PR_FALSE; if (NS_FAILED(mStatus)) { if (mIsAsync) { NotifyListener(); } return; } Loading Loading @@ -729,17 +763,19 @@ nsJSChannel::EvaluateScript() } if (NS_FAILED(mStatus)) { if (mIsAsync) { NotifyListener(); } return; } mStatus = mStreamChannel->AsyncOpen(this, mContext); if (NS_FAILED(mStatus)) { NotifyListener(); } else { if (NS_SUCCEEDED(mStatus)) { // mStreamChannel will call OnStartRequest and OnStopRequest on // us, so we'll be sure to call them on our listener. mOpenedStreamChannel = PR_TRUE; } else if (mIsAsync) { NotifyListener(); } return; Loading Loading @@ -920,6 +956,25 @@ nsJSChannel::GetExecutionPolicy(PRUint32* aPolicy) return NS_OK; } NS_IMETHODIMP nsJSChannel::SetExecuteAsync(PRBool aIsAsync) { if (!mIsActive) { mIsAsync = aIsAsync; } // else ignore this call NS_WARN_IF_FALSE(!mIsActive, "Calling SetExecuteAsync on active channel?"); return NS_OK; } NS_IMETHODIMP nsJSChannel::GetExecuteAsync(PRBool* aIsAsync) { *aIsAsync = mIsAsync; return NS_OK; } //////////////////////////////////////////////////////////////////////////////// nsJSProtocolHandler::nsJSProtocolHandler() Loading modules/plugin/base/src/nsPluginHostImpl.cpp +2 −0 Original line number Diff line number Diff line Loading @@ -5809,6 +5809,8 @@ NS_IMETHODIMP nsPluginHostImpl::NewPluginURLStream(const nsString& aURL, nsCOMPtr<nsIScriptChannel> scriptChannel(do_QueryInterface(channel)); if (scriptChannel) { scriptChannel->SetExecutionPolicy(nsIScriptChannel::EXECUTE_NORMAL); // Plug-ins seem to depend on javascript: URIs running synchronously scriptChannel->SetExecuteAsync(PR_FALSE); } } Loading Loading
dom/public/nsIScriptChannel.idl +15 −1 Original line number Diff line number Diff line Loading @@ -54,7 +54,7 @@ * principal of the environment in which the program is to be executed the * execution will be forced to happen in a sandbox. */ [scriptable, uuid(6dec981b-6fce-4f57-bf97-d518c6079c77)] [scriptable, uuid(33234b99-9588-4c7d-9da6-86b8b7cba565)] interface nsIScriptChannel : nsISupports { /** Loading Loading @@ -85,4 +85,18 @@ interface nsIScriptChannel : nsISupports * @throws NS_ERROR_INVALID_ARG when set to an unrecognized value. */ attribute unsigned long executionPolicy; /** * Control whether the program should be executed synchronosly when * the channel's AsyncOpen method is called or whether it should be * executed asynchronously. In both cases, any data that the * channel returns will be returned asynchronously; the only thing * this property affects is when the program executes. * * The default value of this property is TRUE. * * Setting this property after asyncOpen has been called on the * channel has no effect. */ attribute boolean executeAsync; };
dom/src/jsurl/nsJSProtocolHandler.cpp +66 −11 Original line number Diff line number Diff line Loading @@ -429,6 +429,7 @@ protected: nsRefPtr<nsJSThunk> mIOThunk; PopupControlState mPopupState; PRUint32 mExecutionPolicy; PRPackedBool mIsAsync; PRPackedBool mIsActive; PRPackedBool mOpenedStreamChannel; }; Loading @@ -439,6 +440,7 @@ nsJSChannel::nsJSChannel() : mActualLoadFlags(LOAD_NORMAL), mPopupState(openOverridden), mExecutionPolicy(EXECUTE_IN_SANDBOX), mIsAsync(PR_TRUE), mIsActive(PR_FALSE), mOpenedStreamChannel(PR_FALSE) { Loading Loading @@ -630,9 +632,42 @@ nsJSChannel::AsyncOpen(nsIStreamListener *aListener, nsISupports *aContext) loadGroup->AddRequest(this, nsnull); } mPopupState = win->GetPopupControlState(); nsRunnableMethod<nsJSChannel>::Method method; if (mIsAsync) { // post an event to do the rest nsCOMPtr<nsIRunnable> ev = new nsRunnableMethod<nsJSChannel>(this, &nsJSChannel::EvaluateScript); method = &nsJSChannel::EvaluateScript; } else { EvaluateScript(); if (mOpenedStreamChannel) { // That will handle notifying things return NS_OK; } NS_ASSERTION(NS_FAILED(mStatus), "We should have failed _somehow_"); // mStatus is going to be NS_ERROR_DOM_RETVAL_UNDEFINED if we didn't // have any content resulting from the execution and NS_BINDING_ABORTED // if something we did causes our own load to be stopped. Return // success in those cases, and error out in all others. if (mStatus != NS_ERROR_DOM_RETVAL_UNDEFINED && mStatus != NS_BINDING_ABORTED) { // Note that calling EvaluateScript() handled removing us from the // loadgroup and marking us as not active anymore. mListener = nsnull; mContext = nsnull; mOriginalInnerWindow = nsnull; return mStatus; } // We're returning success from asyncOpen(), but we didn't open a // stream channel. We'll have to notify ourselves, but make sure to do // it asynchronously. method = &nsJSChannel::NotifyListener; } nsCOMPtr<nsIRunnable> ev = new nsRunnableMethod<nsJSChannel>(this, method); nsresult rv = NS_DispatchToCurrentThread(ev); if (NS_FAILED(rv)) { Loading @@ -642,9 +677,6 @@ nsJSChannel::AsyncOpen(nsIStreamListener *aListener, nsISupports *aContext) mContext = nsnull; mOriginalInnerWindow = nsnull; } mPopupState = win->GetPopupControlState(); return rv; } Loading Loading @@ -687,7 +719,9 @@ nsJSChannel::EvaluateScript() mIsActive = PR_FALSE; if (NS_FAILED(mStatus)) { if (mIsAsync) { NotifyListener(); } return; } Loading Loading @@ -729,17 +763,19 @@ nsJSChannel::EvaluateScript() } if (NS_FAILED(mStatus)) { if (mIsAsync) { NotifyListener(); } return; } mStatus = mStreamChannel->AsyncOpen(this, mContext); if (NS_FAILED(mStatus)) { NotifyListener(); } else { if (NS_SUCCEEDED(mStatus)) { // mStreamChannel will call OnStartRequest and OnStopRequest on // us, so we'll be sure to call them on our listener. mOpenedStreamChannel = PR_TRUE; } else if (mIsAsync) { NotifyListener(); } return; Loading Loading @@ -920,6 +956,25 @@ nsJSChannel::GetExecutionPolicy(PRUint32* aPolicy) return NS_OK; } NS_IMETHODIMP nsJSChannel::SetExecuteAsync(PRBool aIsAsync) { if (!mIsActive) { mIsAsync = aIsAsync; } // else ignore this call NS_WARN_IF_FALSE(!mIsActive, "Calling SetExecuteAsync on active channel?"); return NS_OK; } NS_IMETHODIMP nsJSChannel::GetExecuteAsync(PRBool* aIsAsync) { *aIsAsync = mIsAsync; return NS_OK; } //////////////////////////////////////////////////////////////////////////////// nsJSProtocolHandler::nsJSProtocolHandler() Loading
modules/plugin/base/src/nsPluginHostImpl.cpp +2 −0 Original line number Diff line number Diff line Loading @@ -5809,6 +5809,8 @@ NS_IMETHODIMP nsPluginHostImpl::NewPluginURLStream(const nsString& aURL, nsCOMPtr<nsIScriptChannel> scriptChannel(do_QueryInterface(channel)); if (scriptChannel) { scriptChannel->SetExecutionPolicy(nsIScriptChannel::EXECUTE_NORMAL); // Plug-ins seem to depend on javascript: URIs running synchronously scriptChannel->SetExecuteAsync(PR_FALSE); } } Loading