From af552fb4c070a7228b4fc3c39ee9cd79faedd682 Mon Sep 17 00:00:00 2001 From: John Preston Date: Sun, 31 Dec 2017 00:28:38 +0300 Subject: [PATCH] Replace base/task_queue with crl. --- Telegram/SourceFiles/base/task_queue.cpp | 393 ------------------ Telegram/SourceFiles/base/task_queue.h | 102 ----- Telegram/SourceFiles/base/weak_ptr.h | 49 +++ Telegram/SourceFiles/calls/calls_panel.cpp | 7 +- Telegram/SourceFiles/core/file_utilities.cpp | 17 +- Telegram/SourceFiles/facades.cpp | 15 - .../SourceFiles/history/history_widget.cpp | 6 +- Telegram/SourceFiles/mainwindow.cpp | 10 +- Telegram/SourceFiles/media/media_audio.cpp | 26 +- Telegram/SourceFiles/mediaview.cpp | 56 +-- .../linux/notifications_manager_linux.cpp | 8 +- .../platform/mac/notifications_manager_mac.mm | 23 +- .../win/notifications_manager_win.cpp | 8 +- .../SourceFiles/platform/win/specific_win.cpp | 1 - .../storage/storage_media_prepare.cpp | 5 +- .../storage/storage_shared_media.cpp | 1 - .../storage/storage_user_photos.cpp | 2 - .../window/themes/window_theme_editor.cpp | 5 +- Telegram/ThirdParty/crl | 2 +- Telegram/gyp/crl.gyp | 1 + Telegram/gyp/telegram_sources.txt | 2 - 21 files changed, 135 insertions(+), 604 deletions(-) delete mode 100644 Telegram/SourceFiles/base/task_queue.cpp delete mode 100644 Telegram/SourceFiles/base/task_queue.h diff --git a/Telegram/SourceFiles/base/task_queue.cpp b/Telegram/SourceFiles/base/task_queue.cpp deleted file mode 100644 index 02395e481..000000000 --- a/Telegram/SourceFiles/base/task_queue.cpp +++ /dev/null @@ -1,393 +0,0 @@ -/* -This file is part of Telegram Desktop, -the official desktop version of Telegram messaging app, see https://telegram.org - -Telegram Desktop is free software: you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation, either version 3 of the License, or -(at your option) any later version. - -It is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -In addition, as a special exception, the copyright holders give permission -to link the code of portions of this program with the OpenSSL library. - -Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE -Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org -*/ -#include "base/task_queue.h" - -#include -#include - -namespace base { -namespace { - -auto MainThreadId = std::this_thread::get_id(); -const auto MaxThreadsCount = qMax(std::thread::hardware_concurrency(), 2U); - -} // namespace - -class TaskQueue::TaskQueueList { -public: - TaskQueueList(); - - void Register(TaskQueue *queue); - void Unregister(TaskQueue *queue); - bool IsInList(TaskQueue *queue) const; - void Clear(); - bool Empty(int list_index_) const; - TaskQueue *TakeFirst(int list_index_); - -private: - void Insert(TaskQueue *queue, int list_index_); - void Remove(TaskQueue *queue, int list_index_); - - TaskQueue *Tail() { return &tail_; } - const TaskQueue *Tail() const { return &tail_; } - - TaskQueue tail_ = { Type::Special, Priority::Normal }; - TaskQueue *(lists_[kQueuesListsCount]); - -}; - -class TaskQueue::TaskThreadPool { - struct Private { - }; - -public: - TaskThreadPool(const Private &) { } - static const std::shared_ptr &Instance(); - - void AddQueueTask(TaskQueue *queue, Task &&task); - void RemoveQueue(TaskQueue *queue); - - ~TaskThreadPool(); - -private: - void ThreadFunction(); - - std::vector threads_; - QMutex queues_mutex_; - - // queues_mutex_ must be locked when working with the list. - TaskQueueList queue_list_; - - QWaitCondition thread_condition_; - bool stopped_ = false; - int tasks_in_process_ = 0; - int background_tasks_in_process_ = 0; - -}; - -TaskQueue::TaskQueueList::TaskQueueList() { - for (auto &list : lists_) { - list = &tail_; - } -} - -void TaskQueue::TaskQueueList::Register(TaskQueue *queue) { - Assert(!queue->SerialTaskInProcess()); - - Insert(queue, kAllQueuesList); - if (queue->priority_ == Priority::Normal) { - Insert(queue, kOnlyNormalQueuesList); - } -} - -void TaskQueue::TaskQueueList::Unregister(TaskQueue *queue) { - Remove(queue, kAllQueuesList); - if (queue->priority_ == Priority::Normal) { - Remove(queue, kOnlyNormalQueuesList); - } -} - -void TaskQueue::TaskQueueList::Insert(TaskQueue *queue, int list_index_) { - Assert(list_index_ < kQueuesListsCount); - - auto tail = Tail(); - if (lists_[list_index_] == tail) { - lists_[list_index_] = queue; - } - - auto &list_entry = queue->list_entries_[list_index_]; - Assert(list_entry.after == nullptr); - if ((list_entry.before = tail->list_entries_[list_index_].before)) { - list_entry.before->list_entries_[list_index_].after = queue; - } - list_entry.after = tail; - tail->list_entries_[list_index_].before = queue; -} - -void TaskQueue::TaskQueueList::Remove(TaskQueue *queue, int list_index_) { - Assert(list_index_ < kQueuesListsCount); - - auto &list_entry = queue->list_entries_[list_index_]; - Assert(list_entry.after != nullptr); - if (lists_[list_index_] == queue) { - lists_[list_index_] = list_entry.after; - } else { - Assert(list_entry.before != nullptr); - list_entry.before->list_entries_[list_index_].after = list_entry.after; - } - list_entry.after->list_entries_[list_index_].before = list_entry.before; - list_entry.before = list_entry.after = nullptr; -} - -bool TaskQueue::TaskQueueList::IsInList(TaskQueue *queue) const { - if (queue->list_entries_[kAllQueuesList].after) { - return true; - } - Assert(queue->list_entries_[kOnlyNormalQueuesList].after == nullptr); - return false; -} - -void TaskQueue::TaskQueueList::Clear() { - auto tail = Tail(); - for (int i = 0; i < kQueuesListsCount; ++i) { - for (auto j = lists_[i], next = j; j != tail; j = next) { - auto &list_entry = j->list_entries_[i]; - next = list_entry.after; - list_entry.before = list_entry.after = nullptr; - } - lists_[i] = tail; - } -} - -bool TaskQueue::TaskQueueList::Empty(int list_index_) const { - Assert(list_index_ < kQueuesListsCount); - - auto list = lists_[list_index_]; - Assert(list != nullptr); - return (list->list_entries_[list_index_].after == nullptr); -} - -TaskQueue *TaskQueue::TaskQueueList::TakeFirst(int list_index_) { - Assert(!Empty(list_index_)); - - auto queue = lists_[list_index_]; - Unregister(queue); -// log_msgs.push_back("Unregistered from list in TakeFirst"); - return queue; -} - -void TaskQueue::TaskThreadPool::AddQueueTask(TaskQueue *queue, Task &&task) { - QMutexLocker lock(&queues_mutex_); - - queue->tasks_.push_back(std::move(task)); - auto list_was_empty = queue_list_.Empty(kAllQueuesList); - auto threads_count = threads_.size(); - auto all_threads_processing = (threads_count == tasks_in_process_); - auto some_threads_are_vacant = !all_threads_processing && list_was_empty; - auto will_create_thread = !some_threads_are_vacant && (threads_count < MaxThreadsCount); - - if (!queue->SerialTaskInProcess()) { - if (!queue_list_.IsInList(queue)) { - queue_list_.Register(queue); - } - } - if (will_create_thread) { - threads_.emplace_back([this]() { - ThreadFunction(); - }); - } else if (some_threads_are_vacant) { - Assert(threads_count > tasks_in_process_); - thread_condition_.wakeOne(); - } -} - -void TaskQueue::TaskThreadPool::RemoveQueue(TaskQueue *queue) { - QMutexLocker lock(&queues_mutex_); - if (queue_list_.IsInList(queue)) { - queue_list_.Unregister(queue); - } - if (queue->destroyed_flag_) { - *queue->destroyed_flag_ = true; - } -} - -TaskQueue::TaskThreadPool::~TaskThreadPool() { - { - QMutexLocker lock(&queues_mutex_); - queue_list_.Clear(); - stopped_ = true; - } - thread_condition_.wakeAll(); - for (auto &thread : threads_) { - thread.join(); - } -} - -const std::shared_ptr &TaskQueue::TaskThreadPool::Instance() { // static - static auto Pool = std::make_shared(Private()); - return Pool; -} - -void TaskQueue::TaskThreadPool::ThreadFunction() { - // Flag marking that the previous processed task was - // with a Background priority. We count all the background - // tasks being processed. - bool background_task = false; - - // Saved serial queue pointer. When we process a serial - // queue task we don't return the queue to the list until - // the task is processed and we return it on the next cycle. - TaskQueue *serial_queue = nullptr; - bool serial_queue_destroyed = false; - bool task_was_processed = false; - while (true) { - Task task; - { - QMutexLocker lock(&queues_mutex_); - - // Finish the previous task processing. - if (task_was_processed) { - --tasks_in_process_; - } - if (background_task) { - --background_tasks_in_process_; - background_task = false; - } - if (serial_queue) { - if (!serial_queue_destroyed) { - serial_queue->destroyed_flag_ = nullptr; - if (!serial_queue->tasks_.empty()) { - queue_list_.Register(serial_queue); - } - } - serial_queue = nullptr; - serial_queue_destroyed = false; - } - - // Wait for a task to appear in the queues list. - while (queue_list_.Empty(kAllQueuesList)) { - if (stopped_) { - return; - } - thread_condition_.wait(&queues_mutex_); - } - - // Select a task we will be processing. - auto processing_background = (background_tasks_in_process_ > 0); - auto take_only_normal = processing_background && !queue_list_.Empty(kOnlyNormalQueuesList); - auto take_from_list_ = take_only_normal ? kOnlyNormalQueuesList : kAllQueuesList; - auto queue = queue_list_.TakeFirst(take_from_list_); - - Assert(!queue->tasks_.empty()); - - task = std::move(queue->tasks_.front()); - queue->tasks_.pop_front(); - - if (queue->type_ == Type::Serial) { - // Serial queues are returned in the list for processing - // only after the task is finished. - serial_queue = queue; - Assert(serial_queue->destroyed_flag_ == nullptr); - serial_queue->destroyed_flag_ = &serial_queue_destroyed; - } else if (!queue->tasks_.empty()) { - queue_list_.Register(queue); - } - - ++tasks_in_process_; - task_was_processed = true; - if (queue->priority_ == Priority::Background) { - ++background_tasks_in_process_; - background_task = true; - } - } - - task(); - } -} - -TaskQueue::TaskQueue(Type type, Priority priority) -: type_(type) -, priority_(priority) { - if (type_ != Type::Main && type_ != Type::Special) { - weak_thread_pool_ = TaskThreadPool::Instance(); - } -} - -TaskQueue::~TaskQueue() { - if (type_ != Type::Main && type_ != Type::Special) { - if (auto thread_pool = weak_thread_pool_.lock()) { - thread_pool->RemoveQueue(this); - } - } -} - -void TaskQueue::Put(Task &&task) { - if (type_ == Type::Main) { - QMutexLocker lock(&tasks_mutex_); - tasks_.push_back(std::move(task)); - - Sandbox::MainThreadTaskAdded(); - } else { - Assert(type_ != Type::Special); - TaskThreadPool::Instance()->AddQueueTask(this, std::move(task)); - } -} - -void TaskQueue::ProcessMainTasks() { // static - Assert(std::this_thread::get_id() == MainThreadId); - - while (ProcessOneMainTask()) { - } -} - -void TaskQueue::ProcessMainTasks(TimeMs max_time_spent) { // static - Assert(std::this_thread::get_id() == MainThreadId); - - auto start_time = getms(); - while (ProcessOneMainTask()) { - if (getms() >= start_time + max_time_spent) { - break; - } - } -} - -bool TaskQueue::ProcessOneMainTask() { // static - Task task; - { - QMutexLocker lock(&Main().tasks_mutex_); - auto &tasks = Main().tasks_; - if (tasks.empty()) { - return false; - } - - task = std::move(tasks.front()); - tasks.pop_front(); - } - - task(); - return true; -} - -bool TaskQueue::IsMyThread() const { - if (type_ == Type::Main) { - return (std::this_thread::get_id() == MainThreadId); - } - Assert(type_ != Type::Special); - return false; -} - -// Default queues. -TaskQueue &TaskQueue::Main() { // static - static TaskQueue MainQueue { Type::Main, Priority::Normal }; - return MainQueue; -} - -TaskQueue &TaskQueue::Normal() { // static - static TaskQueue NormalQueue { Type::Concurrent, Priority::Normal }; - return NormalQueue; -} - -TaskQueue &TaskQueue::Background() { // static - static TaskQueue BackgroundQueue { Type::Concurrent, Priority::Background }; - return BackgroundQueue; -} - -} // namespace base diff --git a/Telegram/SourceFiles/base/task_queue.h b/Telegram/SourceFiles/base/task_queue.h deleted file mode 100644 index f444e8d0a..000000000 --- a/Telegram/SourceFiles/base/task_queue.h +++ /dev/null @@ -1,102 +0,0 @@ -/* -This file is part of Telegram Desktop, -the official desktop version of Telegram messaging app, see https://telegram.org - -Telegram Desktop is free software: you can redistribute it and/or modify -it under the terms of the GNU General Public License as published by -the Free Software Foundation, either version 3 of the License, or -(at your option) any later version. - -It is distributed in the hope that it will be useful, -but WITHOUT ANY WARRANTY; without even the implied warranty of -MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -GNU General Public License for more details. - -In addition, as a special exception, the copyright holders give permission -to link the code of portions of this program with the OpenSSL library. - -Full license: https://github.com/telegramdesktop/tdesktop/blob/master/LICENSE -Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org -*/ -#pragma once - -#include - -namespace base { - -using Task = lambda_once; - -// An attempt to create/use a TaskQueue or one of the default queues -// after the main() has returned leads to an undefined behaviour. -class TaskQueue { - enum class Type { - Main, // Unique queue for main thread tasks. - Serial, - Concurrent, - Special, // Unique special queue for thread pool lists terminal item. - }; - -public: - enum class Priority { - Normal, - Background, - }; - - // Creating custom serial queues. - TaskQueue(Priority priority) : TaskQueue(Type::Serial, priority) { - } - - // Default main and two concurrent queues. - static TaskQueue &Main(); - static TaskQueue &Normal(); - static TaskQueue &Background(); - - void Put(Task &&task); - - static void ProcessMainTasks(); - static void ProcessMainTasks(TimeMs max_time_spent); - - ~TaskQueue(); - -private: - static bool ProcessOneMainTask(); - - TaskQueue(Type type, Priority priority); - - bool IsMyThread() const; - bool SerialTaskInProcess() const { - return (destroyed_flag_ != nullptr); - } - - const Type type_; - const Priority priority_; - - std::deque tasks_; - QMutex tasks_mutex_; // Only for the main queue. - - // Only for the other queues, not main. - class TaskThreadPool; - std::weak_ptr weak_thread_pool_; - - class TaskQueueList; - - struct TaskQueueListEntry { - TaskQueue *before = nullptr; - TaskQueue *after = nullptr; - }; - - // Thread pool queues linked list. - static constexpr int kAllQueuesList = 0; - - // Thread pool queues linked list with excluded Background queues. - static constexpr int kOnlyNormalQueuesList = 1; - - static constexpr int kQueuesListsCount = 2; - TaskQueueListEntry list_entries_[kQueuesListsCount]; - - // Only for Serial queues: non-null value means a task is currently processed. - bool *destroyed_flag_ = nullptr; - -}; - -} // namespace base diff --git a/Telegram/SourceFiles/base/weak_ptr.h b/Telegram/SourceFiles/base/weak_ptr.h index 6f6d3c6da..5c0faa9c0 100644 --- a/Telegram/SourceFiles/base/weak_ptr.h +++ b/Telegram/SourceFiles/base/weak_ptr.h @@ -280,6 +280,55 @@ weak_ptr make_weak(const std::weak_ptr &value) { } // namespace base +namespace crl { + +template +struct guard_traits; + +template +struct guard_traits, void> { + static base::weak_ptr create(const base::weak_ptr &value) { + return value; + } + static base::weak_ptr create(base::weak_ptr &&value) { + return std::move(value); + } + static bool check(const base::weak_ptr &guard) { + return guard.get() != nullptr; + } + +}; + +template +struct guard_traits< + T*, + std::enable_if_t< + std::is_base_of_v>>> { + static base::weak_ptr create(T *value) { + return value; + } + static bool check(const base::weak_ptr &guard) { + return guard.get() != nullptr; + } + +}; + +template +struct guard_traits< + gsl::not_null, + std::enable_if_t< + std::is_base_of_v>>> { + static base::weak_ptr create(gsl::not_null value) { + return value.get(); + } + static bool check(const base::weak_ptr &guard) { + return guard.get() != nullptr; + } + +}; + +} // namespace crl + #ifdef QT_VERSION template inline void InvokeQueued(const base::has_weak_ptr *context, Lambda &&lambda) { diff --git a/Telegram/SourceFiles/calls/calls_panel.cpp b/Telegram/SourceFiles/calls/calls_panel.cpp index 025d47533..0935f7bb6 100644 --- a/Telegram/SourceFiles/calls/calls_panel.cpp +++ b/Telegram/SourceFiles/calls/calls_panel.cpp @@ -37,7 +37,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "apiwrap.h" #include "observer_peer.h" #include "platform/platform_specific.h" -#include "base/task_queue.h" #include "window/main_window.h" namespace Calls { @@ -425,10 +424,8 @@ void Panel::showControls() { void Panel::destroyDelayed() { hide(); - base::TaskQueue::Main().Put([weak = QPointer(this)] { - if (weak) { - delete weak.data(); - } + crl::on_main(this, [=] { + delete this; }); } diff --git a/Telegram/SourceFiles/core/file_utilities.cpp b/Telegram/SourceFiles/core/file_utilities.cpp index cc622560c..15f1e2d9f 100644 --- a/Telegram/SourceFiles/core/file_utilities.cpp +++ b/Telegram/SourceFiles/core/file_utilities.cpp @@ -23,7 +23,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "mainwindow.h" #include "storage/localstorage.h" #include "platform/platform_file_utilities.h" -#include "base/task_queue.h" #include "messenger.h" bool filedialogGetSaveFile( @@ -99,13 +98,13 @@ QString filedialogNextFilename( namespace File { void OpenEmailLink(const QString &email) { - base::TaskQueue::Main().Put([email] { + crl::on_main([=] { Platform::File::UnsafeOpenEmailLink(email); }); } void OpenWith(const QString &filepath, QPoint menuPosition) { - base::TaskQueue::Main().Put([filepath, menuPosition] { + crl::on_main([=] { if (!Platform::File::UnsafeShowOpenWithDropdown(filepath, menuPosition)) { if (!Platform::File::UnsafeShowOpenWith(filepath)) { Platform::File::UnsafeLaunch(filepath); @@ -115,13 +114,13 @@ void OpenWith(const QString &filepath, QPoint menuPosition) { } void Launch(const QString &filepath) { - base::TaskQueue::Main().Put([filepath] { + crl::on_main([=] { Platform::File::UnsafeLaunch(filepath); }); } void ShowInFolder(const QString &filepath) { - base::TaskQueue::Main().Put([filepath] { + crl::on_main([=] { Platform::File::UnsafeShowInFolder(filepath); }); } @@ -147,7 +146,7 @@ void GetOpenPath( const QString &filter, base::lambda callback, base::lambda failed) { - base::TaskQueue::Main().Put([=] { + crl::on_main([=] { auto files = QStringList(); auto remoteContent = QByteArray(); const auto success = Platform::FileDialog::Get( @@ -178,7 +177,7 @@ void GetOpenPaths( const QString &filter, base::lambda callback, base::lambda failed) { - base::TaskQueue::Main().Put([=] { + crl::on_main([=] { auto files = QStringList(); auto remoteContent = QByteArray(); const auto success = Platform::FileDialog::Get( @@ -206,7 +205,7 @@ void GetWritePath( const QString &initialPath, base::lambda callback, base::lambda failed) { - base::TaskQueue::Main().Put([=] { + crl::on_main([=] { auto file = QString(); if (filedialogGetSaveFile(file, caption, filter, initialPath)) { if (callback) { @@ -223,7 +222,7 @@ void GetFolder( const QString &initialPath, base::lambda callback, base::lambda failed) { - base::TaskQueue::Main().Put([=] { + crl::on_main([=] { auto files = QStringList(); auto remoteContent = QByteArray(); const auto success = Platform::FileDialog::Get( diff --git a/Telegram/SourceFiles/facades.cpp b/Telegram/SourceFiles/facades.cpp index fd457e688..5ece89b30 100644 --- a/Telegram/SourceFiles/facades.cpp +++ b/Telegram/SourceFiles/facades.cpp @@ -35,7 +35,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "window/layer_widget.h" #include "lang/lang_keys.h" #include "base/observer.h" -#include "base/task_queue.h" #include "history/history_media.h" #include "styles/style_history.h" @@ -508,20 +507,7 @@ void WorkingDirReady() { } } -object_ptr MainThreadTaskHandler = { nullptr }; - -void MainThreadTaskAdded() { - if (!started()) { - return; - } - - MainThreadTaskHandler->call(); -} - void start() { - MainThreadTaskHandler.create([] { - base::TaskQueue::ProcessMainTasks(); - }); SandboxData = std::make_unique(); } @@ -531,7 +517,6 @@ bool started() { void finish() { SandboxData.reset(); - MainThreadTaskHandler.destroy(); } uint64 UserTag() { diff --git a/Telegram/SourceFiles/history/history_widget.cpp b/Telegram/SourceFiles/history/history_widget.cpp index 28eb5ed49..95ec3dae0 100644 --- a/Telegram/SourceFiles/history/history_widget.cpp +++ b/Telegram/SourceFiles/history/history_widget.cpp @@ -111,10 +111,8 @@ void ActivateWindowDelayed(not_null controller) { const auto window = controller->window(); const auto weak = make_weak(window.get()); window->activateWindow(); - crl::on_main([=] { - if (weak) { - weak->activateWindow(); - } + crl::on_main(window, [=] { + window->activateWindow(); }); } diff --git a/Telegram/SourceFiles/mainwindow.cpp b/Telegram/SourceFiles/mainwindow.cpp index d4c808137..7cb3ca206 100644 --- a/Telegram/SourceFiles/mainwindow.cpp +++ b/Telegram/SourceFiles/mainwindow.cpp @@ -51,7 +51,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "window/themes/window_theme.h" #include "window/themes/window_theme_warning.h" #include "window/window_main_menu.h" -#include "base/task_queue.h" #include "auth_session.h" #include "window/window_controller.h" @@ -535,24 +534,23 @@ void MainWindow::themeUpdated(const Window::Theme::BackgroundUpdate &data) { _testingThemeWarning->setGeometry(rect()); _testingThemeWarning->setHiddenCallback([this] { _testingThemeWarning.destroyDelayed(); }); } - - base::TaskQueue::Main().Put(base::lambda_guarded(this, [this] { + crl::on_main(this, [=] { if (_testingThemeWarning) { _testingThemeWarning->showAnimated(); } - })); + }); } else if (data.type == Type::RevertingTheme || data.type == Type::ApplyingTheme) { if (_testingThemeWarning) { if (_testingThemeWarning->isHidden()) { _testingThemeWarning.destroy(); } else { - base::TaskQueue::Main().Put(base::lambda_guarded(this, [this] { + crl::on_main(this, [=] { if (_testingThemeWarning) { _testingThemeWarning->hideAnimated(); _testingThemeWarning = nullptr; } setInnerFocus(); - })); + }); } } } diff --git a/Telegram/SourceFiles/media/media_audio.cpp b/Telegram/SourceFiles/media/media_audio.cpp index 89d4302e1..8b5a0aca5 100644 --- a/Telegram/SourceFiles/media/media_audio.cpp +++ b/Telegram/SourceFiles/media/media_audio.cpp @@ -26,7 +26,7 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "media/media_audio_loaders.h" #include "media/media_audio_track.h" #include "platform/platform_audio.h" -#include "base/task_queue.h" +#include "messenger.h" #include #include @@ -230,27 +230,35 @@ bool AttachToDevice() { emit m->faderOnTimer(); } - base::TaskQueue::Main().Put([] { - Current().reattachTracks(); + crl::on_main([] { + if (Messenger::InstancePointer()) { + Current().reattachTracks(); + } }); return true; } void ScheduleDetachFromDeviceSafe() { - base::TaskQueue::Main().Put([] { - Current().scheduleDetachFromDevice(); + crl::on_main([] { + if (Messenger::InstancePointer()) { + Current().scheduleDetachFromDevice(); + } }); } void ScheduleDetachIfNotUsedSafe() { - base::TaskQueue::Main().Put([] { - Current().scheduleDetachIfNotUsed(); + crl::on_main([] { + if (Messenger::InstancePointer()) { + Current().scheduleDetachIfNotUsed(); + } }); } void StopDetachIfNotUsedSafe() { - base::TaskQueue::Main().Put([] { - Current().stopDetachIfNotUsed(); + crl::on_main([] { + if (Messenger::InstancePointer()) { + Current().stopDetachIfNotUsed(); + } }); } diff --git a/Telegram/SourceFiles/mediaview.cpp b/Telegram/SourceFiles/mediaview.cpp index 88921ceeb..7e3ee86f8 100644 --- a/Telegram/SourceFiles/mediaview.cpp +++ b/Telegram/SourceFiles/mediaview.cpp @@ -36,7 +36,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "history/history_media_types.h" #include "window/themes/window_theme_preview.h" #include "window/window_peer_menu.h" -#include "base/task_queue.h" #include "observer_peer.h" #include "auth_session.h" #include "messenger.h" @@ -1708,38 +1707,43 @@ void MediaView::initThemePreview() { auto &location = _doc->location(); if (!location.isEmpty() && location.accessEnable()) { _themePreviewShown = true; - auto path = _doc->location().name(); - auto id = _themePreviewId = rand_value(); - auto ready = base::lambda_guarded(this, [this, id](std::unique_ptr result) { - if (id != _themePreviewId) { - return; - } - _themePreviewId = 0; - _themePreview = std::move(result); - if (_themePreview) { - _themeApply.create(this, langFactory(lng_theme_preview_apply), st::themePreviewApplyButton); - _themeApply->show(); - _themeApply->setClickedCallback([this] { - auto preview = std::move(_themePreview); - close(); - Window::Theme::Apply(std::move(preview)); - }); - _themeCancel.create(this, langFactory(lng_cancel), st::themePreviewCancelButton); - _themeCancel->show(); - _themeCancel->setClickedCallback([this] { close(); }); - updateControls(); - } - update(); - }); Window::Theme::CurrentData current; current.backgroundId = Window::Theme::Background()->id(); current.backgroundImage = Window::Theme::Background()->pixmap(); current.backgroundTiled = Window::Theme::Background()->tile(); + + const auto path = _doc->location().name(); + const auto id = _themePreviewId = rand_value(); + const auto weak = make_weak(this); crl::async([=] { auto preview = Window::Theme::GeneratePreview(path, current); - crl::on_main([ready, result = std::move(preview)]() mutable { - ready(std::move(result)); + crl::on_main(weak, [=, result = std::move(preview)]() mutable { + if (id != _themePreviewId) { + return; + } + _themePreviewId = 0; + _themePreview = std::move(result); + if (_themePreview) { + _themeApply.create( + this, + langFactory(lng_theme_preview_apply), + st::themePreviewApplyButton); + _themeApply->show(); + _themeApply->setClickedCallback([this] { + auto preview = std::move(_themePreview); + close(); + Window::Theme::Apply(std::move(preview)); + }); + _themeCancel.create( + this, + langFactory(lng_cancel), + st::themePreviewCancelButton); + _themeCancel->show(); + _themeCancel->setClickedCallback([this] { close(); }); + updateControls(); + } + update(); }); }); location.accessDisable(); diff --git a/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp b/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp index f29bb1f7b..561595d2a 100644 --- a/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp +++ b/Telegram/SourceFiles/platform/linux/notifications_manager_linux.cpp @@ -24,7 +24,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "platform/linux/linux_libnotify.h" #include "platform/linux/linux_libs.h" #include "lang/lang_keys.h" -#include "base/task_queue.h" namespace Platform { namespace Notifications { @@ -203,10 +202,9 @@ private: MsgId msgId = 0; }; static void performOnMainQueue(NotificationDataStruct *data, base::lambda_once task) { - base::TaskQueue::Main().Put([weak = data->weak, task = std::move(task)]() mutable { - if (auto strong = weak.lock()) { - task(*strong); - } + const auto weak = data->weak; + crl::on_main(weak, [=, task = std::move(task)]() mutable { + task(*weak.lock()); }); } static void notificationDataFree(gpointer data) { diff --git a/Telegram/SourceFiles/platform/mac/notifications_manager_mac.mm b/Telegram/SourceFiles/platform/mac/notifications_manager_mac.mm index 4c20192b8..55c9bc046 100644 --- a/Telegram/SourceFiles/platform/mac/notifications_manager_mac.mm +++ b/Telegram/SourceFiles/platform/mac/notifications_manager_mac.mm @@ -24,7 +24,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "platform/mac/mac_utilities.h" #include "styles/style_window.h" #include "mainwindow.h" -#include "base/task_queue.h" #include "base/variant.h" #include @@ -87,7 +86,7 @@ NSImage *qt_mac_create_nsimage(const QPixmap &pm); auto notificationManagerId = managerIdObject ? [managerIdObject unsignedLongLongValue] : 0ULL; DEBUG_LOG(("Received notification with instance %1, mine: %2").arg(notificationManagerId).arg(_managerId)); if (notificationManagerId != _managerId) { // other app instance notification - base::TaskQueue::Main().Put([] { + crl::on_main([] { // Usually we show and activate main window when the application // is activated (receives applicationDidBecomeActive: notification). // @@ -112,17 +111,15 @@ NSImage *qt_mac_create_nsimage(const QPixmap &pm); NSNumber *msgObject = [notificationUserInfo objectForKey:@"msgid"]; auto notificationMsgId = msgObject ? [msgObject intValue] : 0; if (notification.activationType == NSUserNotificationActivationTypeReplied) { - auto notificationReply = QString::fromUtf8([[[notification response] string] UTF8String]); - base::TaskQueue::Main().Put([manager = _manager, notificationPeerId, notificationMsgId, notificationReply] { - if (manager) { - manager->notificationReplied(notificationPeerId, notificationMsgId, notificationReply); - } + const auto notificationReply = QString::fromUtf8([[[notification response] string] UTF8String]); + const auto manager = _manager; + crl::on_main(manager, [=] { + manager->notificationReplied(notificationPeerId, notificationMsgId, notificationReply); }); } else if (notification.activationType == NSUserNotificationActivationTypeContentsClicked) { - base::TaskQueue::Main().Put([manager = _manager, notificationPeerId, notificationMsgId] { - if (manager) { - manager->notificationActivated(notificationPeerId, notificationMsgId); - } + const auto manager = _manager; + crl::on_main(manager, [=] { + manager->notificationActivated(notificationPeerId, notificationMsgId); }); } @@ -214,9 +211,9 @@ Manager::Private::Private(Manager *manager) subscribe(Global::RefWorkMode(), [this](DBIWorkMode mode) { // We need to update the delegate _after_ the tray icon change was done in Qt. // Because Qt resets the delegate. - base::TaskQueue::Main().Put(base::lambda_guarded(this, [this] { + crl::on_main(this, [=] { updateDelegate(); - })); + }); }); } diff --git a/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp b/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp index bf0525682..a04038a2c 100644 --- a/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp +++ b/Telegram/SourceFiles/platform/win/notifications_manager_win.cpp @@ -25,7 +25,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "platform/win/windows_event_filter.h" #include "platform/win/windows_dlls.h" #include "mainwindow.h" -#include "base/task_queue.h" #include #include @@ -226,10 +225,9 @@ public: ~ToastEventHandler() = default; void performOnMainQueue(base::lambda_once task) { - base::TaskQueue::Main().Put([weak = _weak, task = std::move(task)]() mutable { - if (auto strong = weak.lock()) { - task(*strong); - } + const auto weak = _weak; + crl::on_main(weak, [=, task = std::move(task)]() mutable { + task(*weak.lock()); }); } diff --git a/Telegram/SourceFiles/platform/win/specific_win.cpp b/Telegram/SourceFiles/platform/win/specific_win.cpp index 2bf662ec7..ed758fb35 100644 --- a/Telegram/SourceFiles/platform/win/specific_win.cpp +++ b/Telegram/SourceFiles/platform/win/specific_win.cpp @@ -31,7 +31,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "history/history_location_manager.h" #include "storage/localstorage.h" #include "passcodewidget.h" -#include "base/task_queue.h" #include "core/crash_reports.h" #include diff --git a/Telegram/SourceFiles/storage/storage_media_prepare.cpp b/Telegram/SourceFiles/storage/storage_media_prepare.cpp index 31d01d441..65c452bb6 100644 --- a/Telegram/SourceFiles/storage/storage_media_prepare.cpp +++ b/Telegram/SourceFiles/storage/storage_media_prepare.cpp @@ -21,7 +21,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "storage/storage_media_prepare.h" #include "platform/platform_file_utilities.h" -#include "base/task_queue.h" #include "storage/localimageloader.h" namespace Storage { @@ -58,8 +57,8 @@ bool PrepareAlbumMediaIsWaiting( QSemaphore &semaphore, PreparedFile &file, int previewWidth) { - // Use some special thread queue, like a separate QThreadPool. - base::TaskQueue::Normal().Put([&, previewWidth] { + // TODO: Use some special thread queue, like a separate QThreadPool. + crl::async([=, &semaphore, &file] { const auto guard = gsl::finally([&] { semaphore.release(); }); if (!file.path.isEmpty()) { file.mime = mimeTypeForFile(QFileInfo(file.path)).name(); diff --git a/Telegram/SourceFiles/storage/storage_shared_media.cpp b/Telegram/SourceFiles/storage/storage_shared_media.cpp index b03e6fb66..ecfbb5ad1 100644 --- a/Telegram/SourceFiles/storage/storage_shared_media.cpp +++ b/Telegram/SourceFiles/storage/storage_shared_media.cpp @@ -21,7 +21,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "storage/storage_shared_media.h" #include -#include "base/task_queue.h" namespace Storage { diff --git a/Telegram/SourceFiles/storage/storage_user_photos.cpp b/Telegram/SourceFiles/storage/storage_user_photos.cpp index e4a160964..3b4afc282 100644 --- a/Telegram/SourceFiles/storage/storage_user_photos.cpp +++ b/Telegram/SourceFiles/storage/storage_user_photos.cpp @@ -20,8 +20,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org */ #include "storage/storage_user_photos.h" -#include "base/task_queue.h" - namespace Storage { void UserPhotos::List::addNew(PhotoId photoId) { diff --git a/Telegram/SourceFiles/window/themes/window_theme_editor.cpp b/Telegram/SourceFiles/window/themes/window_theme_editor.cpp index 060e22d1a..fbe7adb9c 100644 --- a/Telegram/SourceFiles/window/themes/window_theme_editor.cpp +++ b/Telegram/SourceFiles/window/themes/window_theme_editor.cpp @@ -35,7 +35,6 @@ Copyright (c) 2014-2017 John Preston, https://desktop.telegram.org #include "ui/widgets/checkbox.h" #include "ui/widgets/multi_select.h" #include "base/parse_helper.h" -#include "base/task_queue.h" #include "base/zlib_help.h" #include "ui/toast/toast.h" #include "core/file_utilities.h" @@ -718,7 +717,9 @@ Editor::Editor(QWidget*, const QString &path) // This could be from inner->_context observable notification. // We should not destroy it while iterating in subscribers. - base::TaskQueue::Main().Put(base::lambda_guarded(this, [this] { closeEditor(); })); + crl::on_main(this, [=] { + closeEditor(); + }); }); _inner->setFocusCallback([this] { App::CallDelayed(2 * st::boxDuration, this, [this] { _select->setInnerFocus(); }); diff --git a/Telegram/ThirdParty/crl b/Telegram/ThirdParty/crl index 9e11a5c92..705a5fd61 160000 --- a/Telegram/ThirdParty/crl +++ b/Telegram/ThirdParty/crl @@ -1 +1 @@ -Subproject commit 9e11a5c9291760d03df559d03d81fa7afdd0a46d +Subproject commit 705a5fd6166fd577d6a95cef9d74f7aa0c4ec3ed diff --git a/Telegram/gyp/crl.gyp b/Telegram/gyp/crl.gyp index 8355e574c..0e599bd2c 100644 --- a/Telegram/gyp/crl.gyp +++ b/Telegram/gyp/crl.gyp @@ -52,6 +52,7 @@ '<(crl_src_loc)/common/crl_common_list.h', '<(crl_src_loc)/common/crl_common_on_main.cpp', '<(crl_src_loc)/common/crl_common_on_main.h', + '<(crl_src_loc)/common/crl_common_on_main_guarded.h', '<(crl_src_loc)/common/crl_common_queue.cpp', '<(crl_src_loc)/common/crl_common_queue.h', '<(crl_src_loc)/common/crl_common_sync.h', diff --git a/Telegram/gyp/telegram_sources.txt b/Telegram/gyp/telegram_sources.txt index 5d2f627ed..32317724f 100644 --- a/Telegram/gyp/telegram_sources.txt +++ b/Telegram/gyp/telegram_sources.txt @@ -22,8 +22,6 @@ <(src_loc)/base/qthelp_url.h <(src_loc)/base/runtime_composer.cpp <(src_loc)/base/runtime_composer.h -<(src_loc)/base/task_queue.cpp -<(src_loc)/base/task_queue.h <(src_loc)/base/timer.cpp <(src_loc)/base/timer.h <(src_loc)/base/type_traits.h