OpenMP线程在同一个cpu核心上执行

Gri*_*zly 7 c++ linux virtualbox openmp

我目前正在使用openmp在4核phenom2上并行化程序.但是我注意到我的并行化对性能没有任何作用.当然我以为我错过了一些东西(falsesharing,通过锁定序列化......),但是我无法找到类似的东西.此外,从CPU利用率来看,程序似乎只在一个核心上执行.从我发现的sched_getcpu()应该给我核心的Id,执行调用的线程当前安排在.所以我写了以下测试程序:

#include <iostream>
#include <sstream>
#include <omp.h>
#include <utmpx.h>
#include <random>
int main(){
    #pragma omp parallel
    {
        std::default_random_engine rand;
        int num = 0;
    #pragma omp for
        for(size_t i = 0; i < 1000000000; ++i) num += rand();
    auto cpu = sched_getcpu();
    std::ostringstream os;
        os<<"\nThread "<<omp_get_thread_num()<<" on cpu "<<sched_getcpu()<<std::endl;
        std::cout<<os.str()<<std::flush;
    std::cout<<num;
    }
}
Run Code Online (Sandbox Code Playgroud)

在我的机器上,这给出了以下输出(随机数当然会有所不同):

Thread 2 on cpu 0 num 127392776
Thread 0 on cpu 0 num 1980891664
Thread 3 on cpu 0 num 431821313
Thread 1 on cpu 0 num -1976497224
Run Code Online (Sandbox Code Playgroud)

由此我假设所有线程都在同一个核心(id为0的核心)上执行.更确切地说,我也尝试了这个答案的方法.结果在哪里相同.另外使用#pragma omp parallel num_threads(1)并没有使执行速度变慢(实际上稍微快一些),这使得所有线程使用相同cpu的理论具有可信度,但是cpu总是显示的事实0让我有点怀疑.另外我检查了GOMP_CPU_AFFINITY哪个最初未设置,所以我尝试将其设置为0 1 2 3,这应该将每个线程绑定到我理解的不同核心.然而,这并没有什么不同.

自从在Windows系统上开发以来,我在virtualbox中使用linux进行开发.所以我认为虚拟系统可能无法访问所有核心.然而,检查virtualbox的设置显示虚拟机应该获得所有4个内核并且同时执行我的测试程序4次似乎使用所有4个内核判断从cpu利用率(以及系统变得非常无响应的事实) .

所以我的问题基本上就是这里究竟发生了什么.更重要的是: 我推断所有线程是否正确使用相同的核心?如果是,那可能是什么原因?

Gri*_*zly 6

经过一些实验,我发现问题在于我是从eclipse IDE中启动我的程序,这似乎设置了仅使用一个核心的亲和力.我认为从IDE外部启动时遇到了同样的问题,但重复测试显示程序运行正常,从终端启动而不是从ide内部启动.