NS_IMETHODIMP WorkerThread::Dispatch(already_AddRefed<nsIRunnable> aRunnable, uint32_t aFlags) { // May be called on any thread! nsCOMPtr<nsIRunnable> runnable(aRunnable); // in case we exit early // Workers only support asynchronous dispatch. if (NS_WARN_IF(aFlags != NS_DISPATCH_NORMAL)) { return NS_ERROR_UNEXPECTED; } const bool onWorkerThread = PR_GetCurrentThread() == mThread; #ifdef DEBUG if (runnable && !onWorkerThread) { nsCOMPtr<nsICancelableRunnable> cancelable = do_QueryInterface(runnable); { MutexAutoLock lock(mLock); // Only enforce cancelable runnables after we've started the worker loop. if (!mAcceptingNonWorkerRunnables) { MOZ_ASSERT(cancelable, "Only nsICancelableRunnable may be dispatched to a worker!"); } } } #endif WorkerPrivate* workerPrivate = nullptr; if (onWorkerThread) { // No need to lock here because it is only modified on this thread. MOZ_ASSERT(mWorkerPrivate); mWorkerPrivate->AssertIsOnWorkerThread(); workerPrivate = mWorkerPrivate; } else { MutexAutoLock lock(mLock); MOZ_ASSERT(mOtherThreadsDispatchingViaEventTarget < UINT32_MAX); if (mWorkerPrivate) { workerPrivate = mWorkerPrivate; // Incrementing this counter will make the worker thread sleep if it // somehow tries to unset mWorkerPrivate while we're using it. mOtherThreadsDispatchingViaEventTarget++; } } nsresult rv; if (runnable && onWorkerThread) { RefPtr<WorkerRunnable> workerRunnable = workerPrivate->MaybeWrapAsWorkerRunnable(runnable.forget()); rv = nsThread::Dispatch(workerRunnable.forget(), NS_DISPATCH_NORMAL); } else { rv = nsThread::Dispatch(runnable.forget(), NS_DISPATCH_NORMAL); } if (!onWorkerThread && workerPrivate) { // We need to wake the worker thread if we're not already on the right // thread and the dispatch succeeded. if (NS_SUCCEEDED(rv)) { MutexAutoLock workerLock(workerPrivate->mMutex); workerPrivate->mCondVar.Notify(); } // Now unset our waiting flag. { MutexAutoLock lock(mLock); MOZ_ASSERT(mOtherThreadsDispatchingViaEventTarget); if (!--mOtherThreadsDispatchingViaEventTarget) { mWorkerPrivateCondVar.Notify(); } } } if (NS_WARN_IF(NS_FAILED(rv))) { return rv; } return NS_OK; }
// Extracts whatever information we need out of fd (using SSL_*) and passes it // to SSLServerCertVerificationJob::Dispatch. SSLServerCertVerificationJob should // never do anything with fd except logging. SECStatus AuthCertificateHook(void *arg, PRFileDesc *fd, PRBool checkSig, PRBool isServer) { // Runs on the socket transport thread PR_LOG(gPIPNSSLog, PR_LOG_DEBUG, ("[%p] starting AuthCertificateHook\n", fd)); // Modern libssl always passes PR_TRUE for checkSig, and we have no means of // doing verification without checking signatures. NS_ASSERTION(checkSig, "AuthCertificateHook: checkSig unexpectedly false"); // PSM never causes libssl to call this function with PR_TRUE for isServer, // and many things in PSM assume that we are a client. NS_ASSERTION(!isServer, "AuthCertificateHook: isServer unexpectedly true"); nsNSSSocketInfo *socketInfo = static_cast<nsNSSSocketInfo*>(arg); if (socketInfo) { // This is the first callback during full handshakes. socketInfo->SetFirstServerHelloReceived(); } ScopedCERTCertificate serverCert(SSL_PeerCertificate(fd)); if (!checkSig || isServer || !socketInfo || !serverCert) { PR_SetError(PR_INVALID_STATE_ERROR, 0); return SECFailure; } if (BlockServerCertChangeForSpdy(socketInfo, serverCert) != SECSuccess) return SECFailure; bool onSTSThread; nsresult nrv; nsCOMPtr<nsIEventTarget> sts = do_GetService(NS_SOCKETTRANSPORTSERVICE_CONTRACTID, &nrv); if (NS_SUCCEEDED(nrv)) { nrv = sts->IsOnCurrentThread(&onSTSThread); } if (NS_FAILED(nrv)) { NS_ERROR("Could not get STS service or IsOnCurrentThread failed"); PR_SetError(PR_UNKNOWN_ERROR, 0); return SECFailure; } if (onSTSThread) { // We *must* do certificate verification on a background thread because // we need the socket transport thread to be free for our OCSP requests, // and we *want* to do certificate verification on a background thread // because of the performance benefits of doing so. socketInfo->SetCertVerificationWaiting(); SECStatus rv = SSLServerCertVerificationJob::Dispatch( static_cast<const void *>(fd), socketInfo, serverCert); return rv; } // We can't do certificate verification on a background thread, because the // thread doing the network I/O may not interrupt its network I/O on receipt // of our SSLServerCertVerificationResult event, and/or it might not even be // a non-blocking socket. SECStatus rv = AuthCertificate(socketInfo, serverCert); if (rv == SECSuccess) { return SECSuccess; } PRErrorCode error = PR_GetError(); if (error != 0) { RefPtr<CertErrorRunnable> runnable(CreateCertErrorRunnable( error, socketInfo, serverCert, static_cast<const void *>(fd))); if (!runnable) { // CreateCertErrorRunnable sets a new error code when it fails error = PR_GetError(); } else { // We have to return SECSuccess or SECFailure based on the result of the // override processing, so we must block this thread waiting for it. The // CertErrorRunnable will NOT dispatch the result at all, since we passed // false for CreateCertErrorRunnable's async parameter nrv = runnable->DispatchToMainThreadAndWait(); if (NS_FAILED(nrv)) { NS_ERROR("Failed to dispatch CertErrorRunnable"); PR_SetError(PR_INVALID_STATE_ERROR, 0); return SECFailure; } if (!runnable->mResult) { NS_ERROR("CertErrorRunnable did not set result"); PR_SetError(PR_INVALID_STATE_ERROR, 0); return SECFailure; } if (runnable->mResult->mErrorCode == 0) { return SECSuccess; // cert error override occurred. } // We must call SetCanceled here to set the error message type // in case it isn't PlainErrorMessage, which is what we would // default to if we just called // PR_SetError(runnable->mResult->mErrorCode, 0) and returned // SECFailure without doing this. socketInfo->SetCanceled(runnable->mResult->mErrorCode, runnable->mResult->mErrorMessageType); error = runnable->mResult->mErrorCode; } } if (error == 0) { NS_ERROR("error code not set"); error = PR_UNKNOWN_ERROR; } PR_SetError(error, 0); return SECFailure; }
NS_IMETHODIMP WorkerThread::DispatchFromScript(nsIRunnable* aRunnable, uint32_t aFlags) { nsCOMPtr<nsIRunnable> runnable(aRunnable); return Dispatch(runnable.forget(), aFlags); }
NS_IMETHOD Run() { NS_ASSERTION(NS_IsMainThread(), "Only call on main thread"); // Create a media stream. nsRefPtr<nsDOMLocalMediaStream> stream; uint32_t hints = (mAudioSource ? nsDOMMediaStream::HINT_CONTENTS_AUDIO : 0); hints |= (mVideoSource ? nsDOMMediaStream::HINT_CONTENTS_VIDEO : 0); stream = nsDOMLocalMediaStream::CreateSourceStream(hints); nsPIDOMWindow *window = static_cast<nsPIDOMWindow*> (nsGlobalWindow::GetInnerWindowWithId(mWindowID)); { if (!stream) { if (!(MediaManager::Get()->IsWindowStillActive(mWindowID))) { return NS_OK; } // This is safe since we're on main-thread, and the windowlist can only // be invalidated from the main-thread (see OnNavigation) nsCOMPtr<nsIDOMGetUserMediaErrorCallback> error(mError); LOG(("Returning error for getUserMedia() - no stream")); error->OnError(NS_LITERAL_STRING("NO_STREAM")); return NS_OK; } } if (window && window->GetExtantDoc()) { stream->CombineWithPrincipal(window->GetExtantDoc()->NodePrincipal()); } // Ensure there's a thread for gum to proxy to off main thread nsIThread *mediaThread = MediaManager::GetThread(); // Add our listener. We'll call Start() on the source when get a callback // that the MediaStream has started consuming. The listener is freed // when the page is invalidated (on navigation or close). GetUserMediaCallbackMediaStreamListener* listener = new GetUserMediaCallbackMediaStreamListener(mediaThread, stream, mAudioSource, mVideoSource); stream->GetStream()->AddListener(listener); // No need for locking because we always do this in the main thread. mListeners->AppendElement(listener); // Dispatch to the media thread to ask it to start the sources, // because that can take a while nsRefPtr<MediaOperationRunnable> runnable( new MediaOperationRunnable(MEDIA_START, stream, mAudioSource, mVideoSource)); mediaThread->Dispatch(runnable, NS_DISPATCH_NORMAL); // We're in the main thread, so no worries here either. nsCOMPtr<nsIDOMGetUserMediaSuccessCallback> success(mSuccess); nsCOMPtr<nsIDOMGetUserMediaErrorCallback> error(mError); if (!(MediaManager::Get()->IsWindowStillActive(mWindowID))) { return NS_OK; } // This is safe since we're on main-thread, and the windowlist can only // be invalidated from the main-thread (see OnNavigation) LOG(("Returning success for getUserMedia()")); success->OnSuccess(static_cast<nsIDOMLocalMediaStream*>(stream)); return NS_OK; }
void NetLibraryView::search(const std::string &title, const std::string &author, const std::string &series, const std::string &category, const std::string &description) { AdvancedSearchRunnable runnable(title, author, series, category, description); search(runnable); }
bool PROJECT::potentially_runnable() { if (runnable(RSC_TYPE_ANY)) return true; if (can_request_work()) return true; if (downloading()) return true; return false; }
bool PROJECT::nearly_runnable() { if (runnable(RSC_TYPE_ANY)) return true; if (downloading()) return true; return false; }
{ setRunnable(rc->runnable()); setIcon(Utils::Icons::RUN_SMALL_TOOLBAR); connect(&m_applicationLauncher, &ApplicationLauncher::appendMessage, this, static_cast<void(RunControl::*)(const QString &, Utils::OutputFormat)>(&RunControl::appendMessage)); connect(&m_applicationLauncher, &ApplicationLauncher::processStarted, this, &LocalApplicationRunControl::processStarted); connect(&m_applicationLauncher, &ApplicationLauncher::processExited, this, &LocalApplicationRunControl::processExited); connect(&m_applicationLauncher, &ApplicationLauncher::bringToForegroundRequested, this, &RunControl::bringApplicationToForeground); } void LocalApplicationRunControl::start() { QTC_ASSERT(runnable().is<StandardRunnable>(), return); auto r = runnable().as<StandardRunnable>(); emit started(); if (r.executable.isEmpty()) { appendMessage(tr("No executable specified.") + QLatin1Char('\n'), Utils::ErrorMessageFormat); emit finished(); } else if (!QFileInfo::exists(r.executable)) { appendMessage(tr("Executable %1 does not exist.") .arg(QDir::toNativeSeparators(r.executable)) + QLatin1Char('\n'), Utils::ErrorMessageFormat); emit finished(); } else { m_running = true; QString msg = tr("Starting %1...").arg(QDir::toNativeSeparators(r.executable)) + QLatin1Char('\n'); appendMessage(msg, Utils::NormalMessageFormat); m_applicationLauncher.start(r);
NS_IMETHOD Run() { NS_ASSERTION(NS_IsMainThread(), "Only call on main thread"); // We're on main-thread, and the windowlist can only // be invalidated from the main-thread (see OnNavigation) StreamListeners* listeners = mManager->GetWindowListeners(mWindowID); if (!listeners) { // This window is no longer live. mListener has already been removed return NS_OK; } // Create a media stream. uint32_t hints = (mAudioSource ? nsDOMMediaStream::HINT_CONTENTS_AUDIO : 0); hints |= (mVideoSource ? nsDOMMediaStream::HINT_CONTENTS_VIDEO : 0); nsRefPtr<nsDOMUserMediaStream> trackunion = nsDOMUserMediaStream::CreateTrackUnionStream(hints); if (!trackunion) { nsCOMPtr<nsIDOMGetUserMediaErrorCallback> error(mError); LOG(("Returning error for getUserMedia() - no stream")); error->OnError(NS_LITERAL_STRING("NO_STREAM")); return NS_OK; } MediaStreamGraph* gm = MediaStreamGraph::GetInstance(); nsRefPtr<SourceMediaStream> stream = gm->CreateSourceStream(nullptr); // connect the source stream to the track union stream to avoid us blocking trackunion->GetStream()->AsProcessedStream()->SetAutofinish(true); nsRefPtr<MediaInputPort> port = trackunion->GetStream()->AsProcessedStream()-> AllocateInputPort(stream, MediaInputPort::FLAG_BLOCK_OUTPUT); trackunion->mSourceStream = stream; trackunion->mPort = port.forget(); nsPIDOMWindow *window = static_cast<nsPIDOMWindow*> (nsGlobalWindow::GetInnerWindowWithId(mWindowID)); if (window && window->GetExtantDoc()) { trackunion->CombineWithPrincipal(window->GetExtantDoc()->NodePrincipal()); } // The listener was added at the begining in an inactive state. // Activate our listener. We'll call Start() on the source when get a callback // that the MediaStream has started consuming. The listener is freed // when the page is invalidated (on navigation or close). mListener->Activate(stream.forget(), mAudioSource, mVideoSource); // Dispatch to the media thread to ask it to start the sources, // because that can take a while nsIThread *mediaThread = MediaManager::GetThread(); nsRefPtr<MediaOperationRunnable> runnable( new MediaOperationRunnable(MEDIA_START, mListener, mAudioSource, mVideoSource, false)); mediaThread->Dispatch(runnable, NS_DISPATCH_NORMAL); // We're in the main thread, so no worries here either. nsCOMPtr<nsIDOMGetUserMediaSuccessCallback> success(mSuccess); nsCOMPtr<nsIDOMGetUserMediaErrorCallback> error(mError); if (!(mManager->IsWindowStillActive(mWindowID))) { return NS_OK; } // This is safe since we're on main-thread, and the windowlist can only // be invalidated from the main-thread (see OnNavigation) LOG(("Returning success for getUserMedia()")); success->OnSuccess(static_cast<nsIDOMLocalMediaStream*>(trackunion)); return NS_OK; }
void UnlambdaEval_eval(UnlambdaEval* self, char* xs){ char x; Stack* stack; Memory * memory; stack = UnlambdaEval_getStack(self); memory = UnlambdaEval_getMemory(self); while (*xs){ x = *xs; switch(x){ case '`': Stack_push(stack, quote()); break; case '.': xs++; Stack_push(stack, (print(*xs))); break; case 'r': Stack_push(stack, (print('\n'))); break; case 'i': Stack_push(stack, identity()); break; case 'k': Stack_push(stack, constant_function()); break; case 's': Stack_push(stack, generalized_evaluation()); break; default: break; } while (runnable()){ if(World_getDebug(getWorld())) Stack_print(stack); UnlambdaEval_runOnce(self); Memory_mark(memory, stack); Memory_sweep(memory); if(World_getDebug(getWorld())) Memory_stat(memory); } xs++; } while (runnable()){ if(World_getDebug(getWorld())) Stack_print(stack); UnlambdaEval_runOnce(self); Memory_mark(memory, stack); Memory_sweep(memory); if(World_getDebug(getWorld())) Memory_stat(memory); } return; }
void FBReader::openBook(BookDescriptionPtr description) { OpenBookRunnable runnable(*this, description); ZLDialogManager::instance().wait(ZLResourceKey("loadingBook"), runnable); resetWindowCaption(); }
void FBReader::openBook(shared_ptr<Book> book) { OpenBookRunnable runnable(book); ZLDialogManager::Instance().wait(ZLResourceKey("loadingBook"), runnable); resetWindowCaption(); }