Ignore OpenMP on machine that does not have it

后端 未结 5 1300
暖寄归人
暖寄归人 2021-02-03 20:21

I have a C++ program using OpenMP, which will run on several machines that may have or not have OpenMP installed.

How could I make my program know if a machine has no O

相关标签:
5条回答
  • 2021-02-03 21:02

    There is another approach that I like, borrowed from Bisqwit:

    #if defined(_OPENMP)
    #include <omp.h>
    extern const bool parallelism_enabled = true;
    #else
    extern const bool parallelism_enabled = false;
    #endif
    

    Then, start your OpenMP parallel for loops like this:

    #pragma omp parallel for if(parallelism_enabled)
    

    Note: there are valid reasons for not using pragma, which is non-standard, hence why Google and others do not support it.

    0 讨论(0)
  • 2021-02-03 21:08

    Compilers are supposed to ignore #pragma directives they don't understand; that's the whole point of the syntax. And the functions defined in openmp.h have simple well-defined meanings on a non-parallel system -- in particular, the header file will check for whether the compiler defines ENABLE_OPENMP and, if it's not enabled, provide the right fallbacks.

    So, all you need is a copy of openmp.h to link to. Here's one: http://cms.mcc.uiuc.edu/qmcdev/docs/html/OpenMP_8h-source.html .

    The relevant portion of the code, though, is just this:

    #if defined(ENABLE_OPENMP)
    #include <omp.h>
    #else
    typedef int omp_int_t;
    inline omp_int_t omp_get_thread_num() { return 0;}
    inline omp_int_t omp_get_max_threads() { return 1;}
    #endif
    

    At worst, you can just take those three lines and put them in a dummy openmp.h file, and use that. The rest will just work.

    0 讨论(0)
  • 2021-02-03 21:20

    OpenMP compilation adds the preprocessor definition "_OPENMP", so you can do:

    #if defined(_OPENMP)
       #pragma omp ...
    #endif
    

    For some examples, see http://bisqwit.iki.fi/story/howto/openmp/#Discussion and the code which follows.

    0 讨论(0)
  • 2021-02-03 21:22

    How could I make my program know if a machine has no OpenMP and ignore those #include <omp.h>, OpenMP directives (like #pragma omp parallel ...) and/or library functions (like tid = omp_get_thread_num();) ?

    Here's a late answer, but we just got a bug report due to use of #pragma omp simd on Microsoft compilers.

    According to OpenMP Specification, section 2.2:

    Conditional Compilation

    In implementations that support a preprocessor, the _OPENMP macro name is defined to have the decimal value yyyymm where yyyy and mm are the year and onth designations of the version of the OpenMP API that the implementation supports.

    It appears modern Microsoft compilers only support OpenMP from sometime between 2000 and 2005. I can only say "sometime between" because OpenMP 2.0 was released in 2000, and OpenMP 2.5 was released in 2005. But Microsoft advertises a version from 2002.

    Here are some _OPENMP numbers...

    • Visual Studio 2012 - OpenMP 200203
    • Visual Studio 2017 - OpenMP 200203
    • IBM XLC 13.01 - OpenMP 201107
    • Clang 7.0 - OpenMP 201107
    • GCC 4.8 - OpenMP 201107
    • GCC 8.2 - OpenMP 201511

    So if you want to use, say #pragma omp simd to guard a loop, and #pragma omp simd is available in OpenMP 4.0, then:

    #if _OPENMP >= 201307
        #pragma omp simd
        for (size_t i = 0; i < 16; ++i)
            data[i] += x[i];
    #else
        for (size_t i = 0; i < 16; ++i)
            data[i] += x[i];
    #endif
    

    which will run on several machines that may have or not have OpenMP installed.

    And to be clear, you probably need to build your program on each of those machines. The x86_64 ABI does not guarantee OpenMP is available on x86, x32 or x86_64 machines. And I have not read you can build on one machine, and then run on another machine.

    0 讨论(0)
  • 2021-02-03 21:24

    OpenMP is a compiler runtime thing and not a platform thing.

    ie. If you compile your app using Visual Studio 2005 or higher, then you always have OpenMP available as the runtime supports it. (and if the end-user doesn't have the Visual Studio C runtime installed, then your app won't work at all).

    So, you don't need to worry, if you can use it, it will always be there just like functions such as strcmp. To make sure they have the CRT, then you can install the visual studio redistributable.

    edit:

    ok, but GCC 4.1 will not be able to compile your openMP app, so the issue is not the target machine, but the target compiler. As all compilers have pre-defined macros giving their version, wrap your OpenMP calls with #ifdef blocks. for example, GCC uses 3 macros to identify the compiler version, __GNUC__, __GNUC_MINOR__ and __GNUC_PATCHLEVEL__

    0 讨论(0)
提交回复
热议问题