File: portable_cpuid.h

package info (click to toggle)
intel-graphics-compiler 1.0.12504.6-1%2Bdeb12u1
  • links: PTS, VCS
  • area: main
  • in suites: bookworm
  • size: 83,912 kB
  • sloc: cpp: 910,147; lisp: 202,655; ansic: 15,197; python: 4,025; yacc: 2,241; lex: 1,570; pascal: 244; sh: 104; makefile: 25
file content (84 lines) | stat: -rw-r--r-- 2,906 bytes parent folder | download | duplicates (3)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
/*========================== begin_copyright_notice ============================

Copyright (C) 2019-2021 Intel Corporation

SPDX-License-Identifier: MIT

============================= end_copyright_notice ===========================*/

/**
 *  This file provides portable implementation of CPUID functions:
 *
 *  void __cpuid(int info[4], int function_id);
 *  void __cpuidex(int info[4], int function_id, int subfunction_id);
 *  int __get_cpuid(unsigned level, unsigned *eax, unsigned *ebx, unsigned *ecx, unsigned *edx);
 */

#ifndef UFO_PORTABLE_CPUID_H
#define UFO_PORTABLE_CPUID_H

#if defined(_MSC_VER) || defined(_WIN32)

    #if defined (_WIN64) && defined (_In_)
        // NOTE: <math.h> is not necessary here.
        // This is only an ugly workaround for a VS2008 bug that causes the compilation
        // issue on 64-bit DEBUG configuration.
        // Including "math.h" before "intrin.h" helps to get rid of the following warning:
        // warning C4985: 'ceil': attributes not present on previous declaration.
        #include <math.h>
        #include <smmintrin.h>
    #else
        #include <intrin.h>
    #endif

    #if (_MSC_VER >= 1500)
        #pragma intrinsic (__cpuid)
    #endif

    #if defined(__cplusplus) && (_MSC_VER >= 1900)
        // __get_cpuid as lambda
        #define __get_cpuid(_level, _peax, _pebx, _pecx, _pedx) \
            [](unsigned level, unsigned *peax, unsigned *pebx, unsigned *pecx, unsigned *pedx) { \
                int tmp[4] = { 0 }; \
                __cpuid(tmp, level); \
                *(peax) = static_cast<unsigned>(tmp[0]); \
                *(pebx) = static_cast<unsigned>(tmp[1]); \
                *(pecx) = static_cast<unsigned>(tmp[2]); \
                *(pedx) = static_cast<unsigned>(tmp[3]); \
                return 1; \
            } (_level, _peax, _pebx, _pecx, _pedx)
    #else
        static __forceinline
        int __get_cpuid(unsigned level, unsigned *peax, unsigned *pebx, unsigned *pecx, unsigned *pedx)
        {
            int tmp[4] = { 0 };
            __cpuid(tmp, level);
            *(peax) = (unsigned)tmp[0];
            *(pebx) = (unsigned)tmp[1];
            *(pecx) = (unsigned)tmp[2];
            *(pedx) = (unsigned)tmp[3];
            return 1;
        }
    #endif

#elif defined (__GNUC__) || defined(__clang__)

    #include <cpuid.h>
    #undef __cpuid // drop internal definition from cpuid.h

    #define __cpuid(info, function) \
        (void)__get_cpuid((function), \
                          (unsigned *)(info)+0, (unsigned *)(info)+1, \
                          (unsigned *)(info)+2, (unsigned *)(info)+3)

    #define __cpuidex(info, function, sub_function) \
        do { \
            __cpuid_count((function), (sub_function), (info)[0], (info)[1], (info)[2], (info)[3]); \
        } while(0)
#else

    #error "FIXME unknown compiler"

#endif

#endif /* UFO_PORTABLE_CPUID_H */