+void callOnMainThreadAndWait(MainThreadFunction* function, void* context)
+{
+ ASSERT(function);
+
+ if (isMainThread()) {
+ function(context);
+ return;
+ }
+
+ ThreadCondition syncFlag;
+ Mutex& functionQueueMutex = mainThreadFunctionQueueMutex();
+ MutexLocker locker(functionQueueMutex);
+ functionQueue().append(FunctionWithContext(function, context, &syncFlag));
+ if (functionQueue().size() == 1)
+ scheduleDispatchFunctionsOnMainThread();
+ syncFlag.wait(functionQueueMutex);
+}
+
+void cancelCallOnMainThread(MainThreadFunction* function, void* context)
+{
+ ASSERT(function);
+
+ MutexLocker locker(mainThreadFunctionQueueMutex());
+
+ FunctionWithContextFinder pred(FunctionWithContext(function, context));
+
+ while (true) {
+ // We must redefine 'i' each pass, because the itererator's operator=
+ // requires 'this' to be valid, and remove() invalidates all iterators
+ FunctionQueue::iterator i(functionQueue().findIf(pred));
+ if (i == functionQueue().end())
+ break;
+ functionQueue().remove(i);
+ }
+}
+