![]() |
Здравствуйте, гость ( Вход | Регистрация )
![]() ![]() |
![]() |
mezmay |
![]()
Сообщение
#11
|
![]() Активный участник ![]() ![]() ![]() Группа: Участник Сообщений: 272 Регистрация: 13.7.2009 Из: Ростов-на-Дону Пользователь №: 904 Спасибо сказали: 16 раз(а) Репутация: ![]() ![]() ![]() |
Вопрос в том как сделать этот поток B. Jack работает и вызывает коллбэки в своем потоке, но как мне зауправлять этим потоком?
|
|
|
lanz |
![]()
Сообщение
#12
|
![]() Старейший участник ![]() ![]() ![]() ![]() Группа: Участник Сообщений: 690 Регистрация: 28.12.2012 Пользователь №: 3660 Спасибо сказали: 113 раз(а) Репутация: ![]() ![]() ![]() |
Не надо им управлять, вам нужно просто передавать в коллбэк правильные данные
Вроде
Цитата int jack_client_create_thread ( jack_client_t * client, jack_native_thread_t * thread, int priority, int realtime, void *(*)(void *) start_routine, void * arg <- Сюда передайте указатель на структуру данных с QAtomicInt например для синхронизации В коллбэке arg примет то же значение что вы передали, если я все правильно понял(обычно так работает) В начале коллбэка лочите структуру(например используя testAndSet на QAtomicInt) или ждете пока она освободится, затем читаете данные, разлочиваете. В GUI треде лочите структуру или ждете пока она освободится, записываете данные, разлочиваете. Для отладки попробуйте сначала то же самое с мутексами, если будет тормозить, переходите на atomic. Можно будет поиграть и с разными барьерами, чтобы улучшить быстродействие. Пока структура залочена, вы просто ничего с ней не делаете. |
|
|
mezmay |
![]()
Сообщение
#13
|
![]() Активный участник ![]() ![]() ![]() Группа: Участник Сообщений: 272 Регистрация: 13.7.2009 Из: Ростов-на-Дону Пользователь №: 904 Спасибо сказали: 16 раз(а) Репутация: ![]() ![]() ![]() |
Цитата лочите структуру(например используя testAndSet на QAtomicInt) или ждете пока она освободится Это можете подробнее объяснить? |
|
|
lanz |
![]()
Сообщение
#14
|
![]() Старейший участник ![]() ![]() ![]() ![]() Группа: Участник Сообщений: 690 Регистрация: 28.12.2012 Пользователь №: 3660 Спасибо сказали: 113 раз(а) Репутация: ![]() ![]() ![]() |
Ну во первых, можно использовать обычный QMutex, я не думаю что он будет сильно хуже самопального.
Во вторых, заводите два значения например(это упрощенный мутекс)
Потом лочите структуру
В третьих можно использовать две одинаковых структуры и один QAtomicPointer, суть такая - меняем структуру на которую не указывает указатель в данный момент, и с тех пор больше не трогаем структуру, это в принципе упрощенный вариант того, что предложила Iron Bug, т.е. кольцевой буфер из двух элементов, возможно потребуется завести два буфера - один для входящих данных, один для исходящих. |
|
|
mezmay |
![]()
Сообщение
#15
|
![]() Активный участник ![]() ![]() ![]() Группа: Участник Сообщений: 272 Регистрация: 13.7.2009 Из: Ростов-на-Дону Пользователь №: 904 Спасибо сказали: 16 раз(а) Репутация: ![]() ![]() ![]() |
Я правильно понимаю что эта функция просто присваивает значение (ну и возвращает которое было)? Она в любом случает сделает присваивание за 1 раз, цикл не нужен? |
|
|
lanz |
![]()
Сообщение
#16
|
![]() Старейший участник ![]() ![]() ![]() ![]() Группа: Участник Сообщений: 690 Регистрация: 28.12.2012 Пользователь №: 3660 Спасибо сказали: 113 раз(а) Репутация: ![]() ![]() ![]() |
Да, она просто перезаписывает.
|
|
|
Iron Bug |
![]()
Сообщение
#17
|
![]() Профессионал ![]() ![]() ![]() ![]() ![]() Группа: Модератор Сообщений: 1611 Регистрация: 6.2.2009 Из: Yekaterinburg Пользователь №: 533 Спасибо сказали: 219 раз(а) Репутация: ![]() ![]() ![]() |
это упрощенный мутекс это не мьютекс, это спинлок (spinlock). там используется специальная ассемблерная синхронизация (fence), которая гарантирует, что весь код, описанный выше "забора" будет выполнен до его вызова - отсюда наименование "ordered" в имени функции, это идёт из типов ассемблерной синхронизации работы конвейера по выборке и распараллеливании выполнения инструкций. и эта синхронизация касается, в том числе, внутренних очередей выборки команд у разных ядер процессора. спинлок отличается от мьютекса тем, что при залоченном ресурсе поток будет долбиться в него, пока не получит доступ, не уступая процессорное время другим потокам. спинлок шустрее мьютекса (за счёт отсутствия загрузки контекстов спящих потоков при переключении), но больше грузит проц. обрати внимание, что на одноядерном проце или на машине с одним простым процессором спинлок сожрёт всё процессорное время и, скорее всего, завесит машину. так что его использовать можно, но если ты уверен, что у тебя не возникнет проблем с залочиванием потоков. да, про циклические буферы я говорила не в смысле синхронизации, а в смысле передачи данных между потоками. синхронизация доступа потоков к очередям или буферам может быть какая угодно. можно по-разному реализовать обмен, но чем шустрее будут работать связанные с работой железа callback'и - тем правильнее. железяка (или неуправляемый входящий поток) не может ожидать и получаемые данные всегда имеют приоритет. отдавать их можно и с задержкой, а принимать надо по мере поступления. |
|
|
mezmay |
![]()
Сообщение
#18
|
![]() Активный участник ![]() ![]() ![]() Группа: Участник Сообщений: 272 Регистрация: 13.7.2009 Из: Ростов-на-Дону Пользователь №: 904 Спасибо сказали: 16 раз(а) Репутация: ![]() ![]() ![]() |
это спинлок (spinlock) синхронизация доступа потоков к очередям или буферам может быть какая угодно какие еще есть варианты (не через мьютексы и семафоры)?...не уступая процессорное время другим потокам разве потокам не поочередно предоставляются отрезки времени?
Сообщение отредактировал mezmay - 13.1.2015, 12:26 |
|
|
lanz |
![]()
Сообщение
#19
|
![]() Старейший участник ![]() ![]() ![]() ![]() Группа: Участник Сообщений: 690 Регистрация: 28.12.2012 Пользователь №: 3660 Спасибо сказали: 113 раз(а) Репутация: ![]() ![]() ![]() |
это не мьютекс, это спинлок (spinlock) Технически, мьютекс это семафор с одним ресурсом, так что тут нет противоречий. Спинлок это деталь реализации именно операции захвата семафора. Но это все непринципиально ![]() Цитата спинлок отличается от мьютекса тем, что при залоченном ресурсе поток будет долбиться в него Технически ![]() обрати внимание, что на одноядерном проце или на машине с одним простым процессором спинлок сожрёт всё процессорное время и, скорее всего, завесит машину Если нет ОС, которая переключает потоки, тогда да. Но если ОС не переключает потоки, зачем синхронизация? Про завесит тоже не понял. Цитата какие еще есть варианты (не через мьютексы и семафоры)? Мьютекс и семафор это абстрактные понятия, реализации их могут быть разные(см. выше), но я знаю только через объекты ОС и через атомарные операции/volatile переменные. Цитата разве потокам не поочередно предоставляются отрезки времени? Да, но можно отказаться от своего отрезка и засуспендить поток до наступления определенного события, ОС разбудит. Обычно этот способ предпочтительный, потому что не использует процессорное время для ожидания освобождения ресурса. Но соответственно он и медленнее. |
|
|
Iron Bug |
![]()
Сообщение
#20
|
![]() Профессионал ![]() ![]() ![]() ![]() ![]() Группа: Модератор Сообщений: 1611 Регистрация: 6.2.2009 Из: Yekaterinburg Пользователь №: 533 Спасибо сказали: 219 раз(а) Репутация: ![]() ![]() ![]() |
Технически, мьютекс это семафор с одним ресурсом, так что тут нет противоречий. Спинлок это деталь реализации именно операции захвата семафора. Но это все непринципиально это как раз принципиально. потому что базируется на разной реализации и используется для разных целей. упрощённо разницу я пояснила. если углубляться, нужно ковырять до ассемблерных вызовов и принципов работы очередей команд и синхронизации обращений к памяти. просто из имени этой функции очевидно, что она базируется на ассемблерной синхронизации. иначе такое странное название не придумать: оно просто отражает смысл конкретного вида синхронизации. в последних версиях GCC все виды синхронизации стали функциями стандартной библиотеки, до этого всё делалось вручную, на ассемблере. и ОС тут ни при чём, это архитектура процессора. если хочешь понять разницу - читай про реализацию мьютексов и спинлоков. можно, например, здесь: http://stackoverflow.com/questions/5869825...nstead-of-mutex там не подробно, но понятно и доступно написано в первом ответе. |
|
|
![]() ![]() ![]() |
![]() |
|
Текстовая версия | Сейчас: 16.5.2025, 4:28 |