LINUX.ORG.RU

SpinLock в Shared memory

 , , ,


1

4

Добрый день! В приложении используется Shared Memory. Для того, чтобы разные процессы не меняли данные одновременно используется spinlock в виде переменной, лежащей в той-же Shared Memory. Проблема в том, что при большом количестве заблокированных процессов, они начинают слишком много времени тратить в цикле спинлока. Сейчас есть идея сделать счетчик процеесов, коорые ждут лока и если их больше количества ядер-1, то сразу вызвать sleep вместо цикла спинлока. Может есть другие решения? Где про это все хорошо написано?

★★★

Ответ на: комментарий от vasily_pupkin

Фактически там мютекс на основе спинлока.

static void rx_shm_spinlock(rx_shm_lock_t *lock, const char* file, int line) {
    int count = 0;
    rx_shm_atomic_inc64(&lock->lock_count);
    while (!rx_trylock_(&lock->mutex)) {
        count++;
        if (count < SPINLOK_INITIAL_SPIN) continue;
        if (count == SPINLOK_INITIAL_SPIN) {
            rx_shm_atomic_inc64(&lock->yield_count);
            sched_yield();
            continue;
        }
        rx_shm_atomic_inc64(&lock->sleep_count);
        rx_minimal_sleep();
        if ((count % SPINLOK_CHECK_PID) == 0) {
            rx_shm_atomic_inc64(&lock->check_pid_count);
            if (rx_check_dead_pid(lock->pid) == RX_TRUE) {
                rx_log_write(RX_LOG_DEBUG, "Process with pid %d died without unlocking(%s). Lock count=%d. Unlock by pid %d (%s:%d)", lock->pid, lock->at, lock->mutex, getpid(), file, line);
                rx_unlock(lock);
            }
        }
    }
}

vromanov ★★★
() автор топика
Ответ на: комментарий от vasily_pupkin

Семафоры это с однйо стороны несколько больше, чем нам надо. С другой стороны, это неудобно. Например, представте себе, что в разделяемой памяти лежит массив из 1000 элементов. И к каждому надо иметь свою блокировку. Сейчас все просто - в начале каждого элемента лежит его лок. И для начала арботы с этой стркутурой надо просто открыть shared memory. В случае использования именованных семафоров, каждому процессу придется хранить дополнительно масиив таких семафоров, инициализировать их итд. А семафоры в количестве ограничены, придется еще и их количество в операционке увеличивать.

vromanov ★★★
() автор топика
Ответ на: комментарий от vasily_pupkin

Работает это так, при начале работы с памятью вызвается lock, после конца unlock. Просблемв том, что под большой нагрузкой иногда возникают пикаи потребления ЦПУ. Подозрение, что слишком много потоков ждет разблокировки, и они на этом выжирают ЦПУ, которого в свою очередь не хватает процессу который держит блокировку, чтобы быстро ее освободить.

vromanov ★★★
() автор топика
Ответ на: комментарий от nerdogeek

Пул семафоров не сделает их быстрее

vromanov ★★★
() автор топика

Вам срочно нужно коммитить в ядро.

anonymous
()
Ответ на: комментарий от vasily_pupkin

Perf не помогает, т.к. проблема может возникнуть один раз за несколько часов и под большой нагрузкой, типа 12000 тысяч запросов в секунду. Т.е. за счет усреднения результатов мы ничего не увидим.

vromanov ★★★
() автор топика

В Стивенсе про это хорошо написано. «UNIX: взаимодействие процессов». Книжка хоть и старенькая, но за это время IPC сильно не изменилось

anonymous
()

Ну хоть какую-нибудь книжку по concurrency прочитать не судьба? От этого, кхм, «кода» кровь из глаз течет.

anonymous
()

Пролетал слушок, что при большой конкуренции (concurrency) спинлоки сосут, как Саша Грей, и их юзают только законченные оригиналы.

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

Например, если у тебя много читателей и мало/один пейсателей - r/w lock в руки.

Pavval ★★★★★
()
Последнее исправление: Pavval (всего исправлений: 1)
Ответ на: комментарий от vromanov

Автор, дай нормальное описание задачи, сколько потоков у вас? 1000 штук? сколько нужно семафоров? Что такое 12 тысяч запросов? Что делает система и ваше приложение? Realtime ли у вас?

pulo
()
Ответ на: комментарий от pulo

Потоков у нас нет. Только процессы (воркеры). Процессов немного 8-20. Семафоров надо относительно много 1000-5000. Приложение работетприблизительно так, ожин компоненет получает запросы по сети, складывает их в очередь. Насколько воркеров другого вынимает запросы из очереди, обрабатывает их, и раскладывает ответы по другим очередям. Первое отправляет ответы. Кроме всего прочего, подсчитывается общая статистика, пишутся логи (тоже через очередь). В осном блокируются очереди сообщений и логирования, а также статистика.

Сообщения - это сообщения по протоколу DIAMETER (Gx)

Вообще приложение лежит вот тут http://freepcrf.com

Я скорее всего сделаю тестовое приложение, которое протестирует различные варианты блокировок.

vromanov ★★★
() автор топика

а почему ты пытаешься угадать? запрофилируй хоть тем же vtune и увидишь точную картину мира

а смена типа лока по количеству процессов - не лучшая идея, может у тебя на системе уже 100500 процессов крутится, которые и без твоего велосипеда приложения цпу выжрали, интуиция - далеко не всегда верная помощница

EugeneBas ★★
()
Ответ на: комментарий от EugeneBas

Сервер ТОЛЬКО наш. Процессы за исключением минимальной системы только наши. Вот представь себе сервер крутится 10 часов. ВДРУГ в каком-то месте возникает затык на 5 секунд. Т.е. если снимать среднее время нахождения в какой-то функции это будет увеличение на совсем чуть-чуть.. Т.е. на самом деле надо снимать не среднее время, а максимальное время. Сейчас мы в коде подсичтываем сколько раз брался лок, сколько раз пришлось вызвать shed_yeld, сколько раз пришлось засыпать. Думаю добавить еще замер времени.

vromanov ★★★
() автор топика
Ответ на: комментарий от vromanov

Извиняюсь что влезаю, а готовые реализации очередей чем не устроили? Неужели какой-нить posix message queues сильно медленный?

true_admin ★★★★★
()
Ответ на: комментарий от unfo

ZeroMQ же

Хотел посоветовать, но для локального IPC под нужды ТС (подозреваю что 12тыщ запросов создаст в разы большее кол-во сообщений) это будет не очень хорошее решение.

true_admin ★★★★★
()
Ответ на: комментарий от true_admin

Каюсь, до 12 тыщ запросов я тред не дочитал :(

Но все же стоит протестировать производительность, благо прототип реализовать совсем недолго (заодно и для message queues).

И уж в крайнем случае мьютексы-семафоры с явными блокировками-разблокировками.

unfo ★★★★★
()
Ответ на: комментарий от vromanov

ок, согласен, пиковую нагрузку трудно замерить профилировщиком, трассировка - верный путь, добавь время того, сколько процесс сидит на локе и постараться скоррелировать данные с разных процессов по временной шкале

возможно еще стоит дампить сами сообщения, может оказаться, что там тоже какая-то закономерность наблюдается

EugeneBas ★★
()

по тс-у фскн просто рыдает

почитай про adaptive mutex и больше не пиши такой код. а лучше вообще не пиши.

можешь не благодарить.

anonymous
()
Ответ на: комментарий от vromanov

Вот именно. Т.е. эффективность вашего кода в лучшем случае сомнительна, а в худшем - намного уступает ядерному.

tailgunner ★★★★★
()
Ответ на: комментарий от vromanov

мало что регистрант, там ещё и неосилятор

anonymous
()
Ответ на: комментарий от vromanov

семафор/футекс все равно вызовет что-то подобное внутри себя.

Вообще-то нет. Он не будет делать busy wait, а переведёт процесс в состояние TASK_INTERRUPTABLE.

DELIRIUM ☆☆☆☆☆
()

Итого тесты показали следующий результат

Тип                  | Время ожидания лока
---------------------+--------------------
Наколенная релизация | 116.4
Семафоры             |  41.5
Mutex                |  37.5
Adaptive Mutex       |  11.6

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

vromanov ★★★
() автор топика
Ответ на: комментарий от vromanov

Внедрили в приложение. Стало получше, но все равно случаются затыки на бльшой нагрузке и при большом количестве процессов. Хорошо упало среднее время ответа. Занимался уменьшением количества блокировок, но все равно от всех не уйти :(. В приложении используется много разных очередей, с которыми рабоатают много программ. В следующей версии попробуем разбить очередь на несколько паралельных.

vromanov ★★★
() автор топика
Вы не можете добавлять комментарии в эту тему. Тема перемещена в архив.