如何设置特定pthread的CPU亲和力?

56 cpu multithreading processor affinity

我想指定特定pthread的cpu-affinity.到目前为止,我发现的所有引用都涉及设置进程的cpu-affinity(pid_t)而不是线程(pthread_t).我尝试了一些传递pthread_t的实验,正如预期的那样,它们会失败.我想做一些不可能的事吗?如果没有,你能发一个指针吗?太感谢了.

Edu*_*rra 56

这是我为使我的生活更轻松而做的包装.它的作用是调用线程被"卡住"到具有id的核心core_id:

// core_id = 0, 1, ... n-1, where n is the system's number of cores

int stick_this_thread_to_core(int core_id) {
   int num_cores = sysconf(_SC_NPROCESSORS_ONLN);
   if (core_id < 0 || core_id >= num_cores)
      return EINVAL;

   cpu_set_t cpuset;
   CPU_ZERO(&cpuset);
   CPU_SET(core_id, &cpuset);

   pthread_t current_thread = pthread_self();    
   return pthread_setaffinity_np(current_thread, sizeof(cpu_set_t), &cpuset);
}
Run Code Online (Sandbox Code Playgroud)

  • 供将来参考:需要添加#define _GNU_SOURCE和#include <sched.h>来处理gcc 4.7.2.在linux上完美地工作,使用oprofile和pthread进行测试. (9认同)
  • 此外,使用`gcc 4.8.1` 的`sysconf` 需要`#include &lt;unistd.h&gt;`。 (2认同)

nos*_*nos 43

假设linux:

设置亲和力的界面是 - 正如您可能已经发现的那样:

int sched_setaffinity(pid_t pid,size_t cpusetsize,cpu_set_t *mask);
Run Code Online (Sandbox Code Playgroud)

传递0作为pid,它只适用于当前线程,或者让其他线程报告其内核pid与linux特定的调用pid_t gettid(void); 并将其作为pid传递.

引用手册页

关联掩码实际上是每线程属性,可以针对线程组中的每个线程独立调整.调用gettid(2)返回的值可以在参数pid中传递.将pid指定为0将设置调用线程的属性,并将从调用返回的值传递给getpid(2)将设置线程组的主线程的属性.(如果您使用的是POSIX线程API,则使用pthread_setaffinity_np(3)而不是sched_setaffinity().)

  • "如果您使用POSIX线程API,则使用pthread_setaffinity_np(3)而不是sched_setaffinity()".我怎么知道我是否使用POSIX API?如何选择使用`sched_setaffinity`或`pthread_setaffinity_np`? (2认同)

小智 19

//compilation: gcc -o affinity affinity.c -lpthread

#define _GNU_SOURCE
#include <sched.h>   //cpu_set_t , CPU_SET
#include <pthread.h> //pthread_t
#include <stdio.h>

void *th_func(void * arg); 

int main(void) {
  pthread_t thread; //the thread

  pthread_create(&thread,NULL,th_func,NULL); 

  pthread_join(thread,NULL);   

  return 0;
}


void *th_func(void * arg)
{  
  //we can set one or more bits here, each one representing a single CPU
  cpu_set_t cpuset; 

  //the CPU we whant to use
  int cpu = 2;

  CPU_ZERO(&cpuset);       //clears the cpuset
  CPU_SET( cpu , &cpuset); //set CPU 2 on cpuset


  /*
   * cpu affinity for the calling thread 
   * first parameter is the pid, 0 = calling thread
   * second parameter is the size of your cpuset
   * third param is the cpuset in which your thread will be
   * placed. Each bit represents a CPU
   */
  sched_setaffinity(0, sizeof(cpuset), &cpuset);

  while (1);
       ; //burns the CPU 2

  return 0;
}
Run Code Online (Sandbox Code Playgroud)

在POSIX环境中,您可以使用cpusets来控制进程或pthreads可以使用哪些CPU.这种类型的控制称为CPU亲和性.

函数'sched_setaffinity'接收pthread ID和cpuset作为参数.在第一个参数中使用0时,调用线程将受到影响