У меня есть сервер с 4 узлами numa, каждый из которых имеет 8 ядер с гиперпоточностью. Итак, у меня 64 логических процессора.
У меня есть несколько программ, производящих данные, и другие программы, использующие данные. Эти программы написаны на c ++ (11). Я хочу запустить ряд производителей и ряд потребительских программ.
Чтобы максимизировать производительность, мне нравится контролировать, где выполняются экземпляры программы. Другими словами, потребительская программа должна находиться на том же узле numa, что и соответствующий производитель.
В конце мне нужно контролировать, на каком ядре работает программа.
Я использую C ++ (11).
Как я могу контролировать способ распространения программ?
РЕДАКТИРОВАТЬ: Может быть, я должен добавить, что сервер работает под управлением Linux. Было бы неплохо решение для Linux, но решение, поддерживающее как Linux, так и Windows, было бы еще лучше.
Этот код должен заставить ваш поток работать на определенном ядре или подмножестве ядер — ядро 17 и 18 в этом примере;
cpu_set_t cpuset;
CPU_ZERO(&cpuset);
CPU_SET(17, &cpuset);
CPU_SET(18, &cpuset);
if (pthread_setaffinity_np(thread[0], sizeof(cpu_set_t), &cpuset) != 0)
throw error"Failed to set affinity for thread");
Вы можете разрешить вашему потоку иметь сходство с несколькими ядрами, поэтому вы можете настроить маску таким образом, чтобы любое ядро в одном процессоре было допустимым, или повозиться с допустимым набором для максимальной производительности кэша L2 / L3.
Вы можете написать свою собственную логику вокруг этого фрагмента, чтобы разрешить оставшиеся потоки на других ядрах.
Это по-прежнему работает, если у вас есть несколько процессов, которыми вы хотите управлять, а не несколько потоков, однако вам нужно будет либо заранее определить распределение ядра, либо создать внешнюю службу, которую каждая программа может запросить, какой набор ядра будет быть допустимым.