Как заставить два процесса работать на одном процессоре?

Контекст:

Я программирую программную систему, состоящую из нескольких процессов. Он запрограммирован в C ++ под Linux. и они обмениваются данными между ними с использованием общей памяти Linux.

Как правило, при разработке программного обеспечения находится в завершающем этапе, когда выполняется оптимизация производительности. Здесь я столкнулся с большой проблемой. Программное обеспечение имеет высокие требования к производительности, но на машинах с 4 или 8 ядрами процессора (как правило, с несколькими процессорами) он мог использовать только 3 ядра, таким образом, тратя 25% мощности процессора в первых и больше, чем 60% – во втором. После многих исследований, отказавшись от мьютекса и блокировки, я узнал, что время тратится на вызовы shmdt / shmat (отсоединяется и присоединяется к сегментам разделяемой памяти). После нескольких исследований я узнал, что эти процессоры, которые обычно являются процессорами AMD Opteron и Intel Xeon, используют систему памяти NUMA, которая в основном означает, что каждый процессор имеет быструю «локальную память» и доступ к памяти от других процессоров дорого.

После выполнения некоторых тестов проблема заключается в том, что программное обеспечение сконструировано таким образом, что в принципе любой процесс может передавать сегменты разделяемой памяти в любой другой процесс и любой stream в них. Это, похоже, убивает производительность, поскольку процесс постоянно обращается к памяти из других процессов.

Вопрос:

Теперь вопрос в том, есть ли способ заставить пары процессов выполнить в одном CPU ?. Я не хочу заставлять их выполняться всегда в одном процессоре, так как мне все равно, в каком они исполняются, хотя это и сработало бы. В идеале, было бы способ рассказать kernel: если вы планируете этот процесс в одном процессоре, вы также должны запланировать этот «брат» процесс (который является процессом, с которым он обменивается через разделяемую память) в том же процессоре, так что производительность не наказывается.

Я думаю, что вы можете начать с этих страниц руководства:

$ apropos affinity sched_getaffinity (2) - set and get a process's CPU affinity mask sched_setaffinity (2) - set and get a process's CPU affinity mask taskset (1) - retrieve or set a process's CPU affinity $ 

в зависимости от того, хотите ли вы сделать это из исходного кода или оболочки. Библиотека pthread также имеет некоторую функцию.

В C то, что вы ищете, скорее всего, это системный вызов sched_setaffinity() .

Существует также утилита командной строки schedtool, если вы не хотите (или не можете) изменять свой код.

Написание приложений, поддерживающих NUMA, немного больше, чем просто «два процесса, выполняемые на одном процессоре». Знание NUMA пронизывает все: распределение памяти, завершение ввода-вывода, планирование streamов и т. Д.

Посмотрите на libnuma