dlinyj: (Default)
[personal profile] dlinyj
Статьи на русском по многопоточному программированию пишут какие-то наркоманы, нихрена непонятно.


Фак мой моск...

Стоит примитивная задача, при определённом событии заблокировать поток (или функцию хотя бы), и после второго события разрешить ей работу. При чём события могут происходить в разных местах.

Начал читать, и утонул во мьютексах, спин блокировках и т.п. Жесть, как она есть.

З.Ы. Хотя многопоточное программирование - это ништяк.

Date: 2014-01-27 08:22 pm (UTC)
From: [identity profile] vp.livejournal.com
Картинка знатная! Она вообще ко всему подходит

Date: 2014-01-27 08:28 pm (UTC)
From: [identity profile] sevasat.livejournal.com
Рисунок похож на иллюстрацию из какой-то размноженной на ксероксе брошюрки с антинаучной хуйней из 90-х, типа "биополе человека и его влияние на жопную чакру" или "торсионные поля в народной медицине среднего поволжья. метод Чебурана Моисеевича".

Date: 2014-01-27 08:32 pm (UTC)
From: [identity profile] vp.livejournal.com
Что вы такое говорите! Может еще и поиск геоаномальных энергетических зон с помощью двух карандашей отрицаете!?

Date: 2014-01-27 08:50 pm (UTC)
From: [identity profile] sevasat.livejournal.com
Посоны говорят нужны карандаши из структурированного графита, обычные не годятся..

Date: 2014-01-28 02:42 am (UTC)
From: [identity profile] sinclair-sc.livejournal.com
Из графитовых нанотрубок пойдут?

Date: 2014-01-27 09:02 pm (UTC)
From: [identity profile] arush-damage.livejournal.com
Ересь!
Искать нужно используя лозу!
Ну или на крайняк - вогнутую проволоку! %))

Date: 2014-01-27 09:05 pm (UTC)
From: [identity profile] arush-damage.livejournal.com
В смысле?
В определённом месте проверить событие и стопнуться или тормознуть исполнение невзирая на то что сейчас выполняется?
Если второе - это сигналы смотреть нужно.

А вообще нужно больше деталей чтобы понять что и как делать.
Edited Date: 2014-01-27 09:07 pm (UTC)

Date: 2014-01-27 09:20 pm (UTC)
From: [identity profile] dlinyj.livejournal.com
Сигналы не канают, т.к. нужно чтобы основной поток продолжал работать. Есть некоторая функция, которая шлёт данные на дисплей по таймеру. Если мы ловим события в основной программе, то нужно стопануть функцию показать менюшку, если юзер всё сделал, то продолжить слать данные. Функция посылки была сначала сделана алармом по таймеру, сейчас отдельный поток с задержкой

Date: 2014-01-27 09:27 pm (UTC)
From: [identity profile] arush-damage.livejournal.com
А, так тут атомарных операций должно хватить - в одном месте атомарного ставим флаги , в другом атомарного читаем.
Ну или, сделать тоже самое с помощью блокировок.

Date: 2014-01-28 04:38 am (UTC)
From: [identity profile] dlinyj.livejournal.com
Это всё понятно, КАК это сделать? Пример кода? Интересует блокировка

Date: 2014-01-28 06:08 pm (UTC)
From: [identity profile] arush-damage.livejournal.com
Ниже уже написали.

Ну или если код примерно такой:

while(true)
{
sleep(T);
send_data();
}

То достаточно send_data внутрь блокировки взять:

while(true)
{
sleep(T);
mutex_lock()
send_data()
mutex_unlock();
}

А в обработчике события тоже самое:
{
mutex_lock();
show_and_work_with_menu();
mutex_unlock();
}

ЗЫ. Вроде ж в литературе все есть? Взять например "Теренс Чан - Системное программирование на C++ в Unix" вполне понятно написано как по мне. Или вот Стивенс У. UNIX. Профессиональное программирование. (http://padabum.com/d.php?id=16369) Вторая пожалуй даже получше будет.
Edited Date: 2014-01-28 06:10 pm (UTC)

Date: 2014-01-28 07:38 pm (UTC)
From: [identity profile] dlinyj.livejournal.com
По сути так и сделал, вот код:
void *show_current_track() {
	while (1) {
		pthread_mutex_lock(&mutex);
.... Некий код, который нельзя прерывать ...
		pthread_mutex_unlock(&mutex);
		usleep (500000);
	}

...

И далее в другой функции делаю так:

void tuning_action() {

....
	pthread_mutex_lock(&mutex);
       тут код, который исполнится когда у нас будет пауза

Date: 2014-01-29 03:48 am (UTC)
From: [identity profile] mbr.livejournal.com
Тут надо бить по рукам. Мьютексы нельзя использовать для обработки длительных событий - только для критического кода. Для остальных случаев - event, semaphore, message и т.п.

Критическая ошибка в том, что при использовании мьютексов приоритет работающего процесса поднимается до ожидающего, чтобы минимизировать его простой. Поэтому очень легко можно получить много сюрпризов многопоточности от снижения эффективности всей системы до deadlock. Ошибки подобного рода потом крайне трудно отладить.

Date: 2014-01-31 09:42 pm (UTC)
From: [identity profile] dlinyj.livejournal.com
Только добрался до ЖЖ. Можно не ругаться, а дать пример как надо делать? И объяснить почему так...

В данном случае я гонюсь не за скоростью, мне просто нравится гибкость многопоточного программирования. Тут выигрыш в удобстве реализации.

Date: 2014-02-01 09:30 am (UTC)
From: [identity profile] mbr.livejournal.com
Пример я написал раньше.

Вот хорошая статья про мьютексы: http://www.smxrtos.com/articles/techppr/mutex.htm

Начинать с раздела "Problems with Priority Inheritance".

Резюме такое: мьютексы можно использовать для кратковременной блокировки общих ресурсов. Сами процессы блокировать нельзя - от побочных эффектов развалится вся система, не только два блокирующих процесса.

В твоем случае можно использовать очередь сообщений (если позволяет ОС), либо семафор + мьютекс. Семафор показывает факт наличия события, которое нужно обработать, мьютекс гарантирует, что в момент обращения общий ресурс (команда для выполнения) будет использоваться только одним процессом.

Date: 2014-01-28 05:17 am (UTC)
From: [identity profile] mbr.livejournal.com
Не так. У тебя логика шиворот навыворот. Останавливать процесс неправильно. Нужно, чтобы сам рабочий процесс принимал решение - читать данные или выводить меню, исходя из семафоров.

Как вариант - отрисовка меню - в критической секции, окружаем ее мьютексами. Пока рабочий процесс занимается отрисовкой, управляющие не может слать данные. Т.е., грубо говоря, я это так вижу, в метокоде:

sem dataSend;
mutex dataInProcess;

управляющий:

mutex.lock(dataInProcess);
(...send to buf...)
mutex.unlock(dataInProcess);
sem.signal();

рабочий:

for (;;)
{
...if (sem.acquire(timeout)
...{
......mutex.lock(dataInProcess);
......(...read from buf...)
......mutex.unlock(dataInProcess);
...}
...(...draw...)
}

upd. жежешечка табуляцию порезала, но, я думаю, суть ясна
Edited Date: 2014-01-28 05:36 am (UTC)

Date: 2014-01-28 07:39 pm (UTC)
From: [identity profile] dlinyj.livejournal.com
Тег <pre> и его закрытие. Спасибо, я примерно так и сделал http://dlinyj.livejournal.com/640648.html?thread=8363656#t8363656 . Пытался написать тебе на мыло, ругается гмайл...
Edited Date: 2014-01-28 07:39 pm (UTC)

Date: 2014-01-29 03:50 am (UTC)
From: [identity profile] mbr.livejournal.com
Спасибо, про тег не знал.

alexeyk13 на яндекс.ру

Date: 2014-01-27 09:10 pm (UTC)
From: [identity profile] di-halt.livejournal.com
Почитай русский перевод документации по Salvo Rtos там писали не наркоманы. Еще книгу "Современные операционные системы" Танненбаума рекомендую.

Date: 2014-01-27 09:21 pm (UTC)
From: [identity profile] dlinyj.livejournal.com
Мне надо чтобы api линукса было, нафига мне ртос?

Date: 2014-01-27 09:26 pm (UTC)
From: [identity profile] di-halt.livejournal.com
Так тебе принцип не понятен или конкретная реализация?

Date: 2014-01-28 05:01 am (UTC)
From: [identity profile] dlinyj.livejournal.com
Реализация

Date: 2014-02-08 06:39 pm (UTC)
From: [identity profile] belbes.livejournal.com
Вообще нынче модно использовать TBB или трэды из C++11 :)

January 2026

S M T W T F S
    123
456 78910
11121314151617
18192021222324
25262728293031

Most Popular Tags

Style Credit

Expand Cut Tags

No cut tags
Page generated Jan. 22nd, 2026 07:00 pm
Powered by Dreamwidth Studios