1# 2# W A R N I N G 3# ------------- 4# 5# This file is not part of the Qt API. It exists purely as an 6# implementation detail. It may change from version to version 7# without notice, or even be removed. 8# 9# We mean it. 10# 11 12# Get the SIMD flags 13load(qt_build_config) 14 15# Set QT_CPU_FEATURES for convenience 16QT_CPU_FEATURES = $$eval(QT_CPU_FEATURES.$$QT_ARCH) 17 18# 19# Set up compilers for SIMD (SSE/AVX, NEON etc) 20# 21defineTest(addSimdCompiler) { 22 name = $$1 23 upname = $$upper($$name) 24 headers_var = $${upname}_HEADERS 25 sources_var = $${upname}_SOURCES 26 csources_var = $${upname}_C_SOURCES 27 asm_var = $${upname}_ASM 28 29 CONFIG($$1) { 30 cflags = $$eval(QMAKE_CFLAGS_$${upname}) 31 ltcg: cflags += $$QMAKE_CFLAGS_DISABLE_LTCG 32 contains(QT_CPU_FEATURES, $$name) { 33 # Default compiler settings include this feature, so just add to SOURCES 34 SOURCES += $$eval($$sources_var) 35 export(SOURCES) 36 } else { 37 # We need special compiler flags 38 39 # Split C and C++ sources 40 $$csources_var = $$find($$sources_var, ".*\\.c$") 41 $$sources_var -= $$eval($$csources_var) 42 export($$csources_var) 43 export($$sources_var) 44 45 # Add C++ compiler 46 $${name}_compiler.commands = $$QMAKE_CXX -c $(CXXFLAGS) $$cflags $(INCPATH) ${QMAKE_FILE_IN} 47 msvc: $${name}_compiler.commands += -Fo${QMAKE_FILE_OUT} 48 else: $${name}_compiler.commands += -o ${QMAKE_FILE_OUT} 49 50 $${name}_compiler.dependency_type = TYPE_C 51 $${name}_compiler.output = ${QMAKE_VAR_OBJECTS_DIR}${QMAKE_FILE_BASE}$${first(QMAKE_EXT_OBJ)} 52 $${name}_compiler.input = $$sources_var 53 $${name}_compiler.variable_out = OBJECTS 54 $${name}_compiler.name = compiling[$${name}] ${QMAKE_FILE_IN} 55 silent: $${name}_compiler.commands = @echo compiling[$${name}] ${QMAKE_FILE_IN} && $$eval($${name}_compiler.commands) 56 QMAKE_EXTRA_COMPILERS += $${name}_compiler 57 58 export($${name}_compiler.commands) 59 export($${name}_compiler.dependency_type) 60 export($${name}_compiler.output) 61 export($${name}_compiler.input) 62 export($${name}_compiler.variable_out) 63 export($${name}_compiler.name) 64 65 # Add a C compiler 66 $${name}_c_compiler.commands = $$QMAKE_CC -c $(CFLAGS) $$cflags $(INCPATH) ${QMAKE_FILE_IN} 67 msvc: $${name}_c_compiler.commands += -Fo${QMAKE_FILE_OUT} 68 else: $${name}_c_compiler.commands += -o ${QMAKE_FILE_OUT} 69 70 $${name}_c_compiler.dependency_type = TYPE_C 71 $${name}_c_compiler.output = ${QMAKE_VAR_OBJECTS_DIR}${QMAKE_FILE_BASE}$${first(QMAKE_EXT_OBJ)} 72 $${name}_c_compiler.input = $$csources_var 73 $${name}_c_compiler.variable_out = OBJECTS 74 $${name}_c_compiler.name = compiling[$${name}] ${QMAKE_FILE_IN} 75 silent: $${name}_c_compiler.commands = @echo compiling[$${name}] ${QMAKE_FILE_IN} && $$eval($${name}_c_compiler.commands) 76 QMAKE_EXTRA_COMPILERS += $${name}_c_compiler 77 78 export($${name}_c_compiler.commands) 79 export($${name}_c_compiler.dependency_type) 80 export($${name}_c_compiler.output) 81 export($${name}_c_compiler.input) 82 export($${name}_c_compiler.variable_out) 83 export($${name}_c_compiler.name) 84 } 85 86 # We always need an assembler (need to run the C compiler and without precompiled headers) 87 msvc { 88 # Don't know how to run MSVC's assembler... 89 !isEmpty($$asm_var): error("Sorry, not implemented: assembling $$upname for MSVC.") 90 } else: false { 91 # This is just for the IDE 92 SOURCES += $$eval($$asm_var) 93 export(SOURCES) 94 } else { 95 $${name}_assembler.commands = $$QMAKE_CC -c $(CFLAGS) 96 !contains(QT_CPU_FEATURES, $${name}): $${name}_assembler.commands += $$cflags 97 clang:no_clang_integrated_as: $${name}_assembler.commands += -fno-integrated-as 98 $${name}_assembler.commands += $(INCPATH) ${QMAKE_FILE_IN} -o ${QMAKE_FILE_OUT} 99 $${name}_assembler.dependency_type = TYPE_C 100 $${name}_assembler.output = ${QMAKE_VAR_OBJECTS_DIR}${QMAKE_FILE_BASE}$${first(QMAKE_EXT_OBJ)} 101 $${name}_assembler.input = $$asm_var 102 $${name}_assembler.variable_out = OBJECTS 103 $${name}_assembler.name = assembling[$${name}] ${QMAKE_FILE_IN} 104 silent: $${name}_assembler.commands = @echo assembling[$${name}] ${QMAKE_FILE_IN} && $$eval($${name}_assembler.commands) 105 QMAKE_EXTRA_COMPILERS += $${name}_assembler 106 107 export($${name}_assembler.commands) 108 export($${name}_assembler.dependency_type) 109 export($${name}_assembler.output) 110 export($${name}_assembler.input) 111 export($${name}_assembler.variable_out) 112 export($${name}_assembler.name) 113 } 114 115 HEADERS += $$eval($$headers_var) 116 export(HEADERS) 117 export(QMAKE_EXTRA_COMPILERS) 118 } 119} 120addSimdCompiler(sse2) 121addSimdCompiler(sse3) 122addSimdCompiler(ssse3) 123addSimdCompiler(sse4_1) 124addSimdCompiler(sse4_2) 125addSimdCompiler(aesni) 126addSimdCompiler(shani) 127addSimdCompiler(vaes) 128addSimdCompiler(avx) 129addSimdCompiler(avx2) 130addSimdCompiler(avx512f) 131addSimdCompiler(avx512cd) 132addSimdCompiler(avx512er) 133addSimdCompiler(avx512pf) 134addSimdCompiler(avx512dq) 135addSimdCompiler(avx512bw) 136addSimdCompiler(avx512vl) 137addSimdCompiler(avx512vnni) 138addSimdCompiler(avx512ifma) 139addSimdCompiler(avx512vbmi) 140addSimdCompiler(avx512vbmi2) 141addSimdCompiler(avx512bitalg) 142addSimdCompiler(avx512vpopcntd) 143addSimdCompiler(f16c) 144addSimdCompiler(rdrnd) 145addSimdCompiler(rdseed) 146addSimdCompiler(neon) 147addSimdCompiler(mips_dsp) 148addSimdCompiler(mips_dspr2) 149 150# Haswell sub-architecture 151defineTest(addSimdArch) { 152 name = arch_$$1 153 dependencies = $$2 154 upname = $$upper($$name) 155 156 cpu_features_missing = 157 for(part, dependencies) { 158 !contains(QT_CPU_FEATURES, $$part): cpu_features_missing = 1 159 } 160 161 CONFIG += $$name 162 isEmpty(cpu_features_missing): QT_CPU_FEATURES += $$name 163 164 export(QT_CPU_FEATURES) 165 export(CONFIG) 166 addSimdCompiler($$name) 167} 168 169isEmpty(QMAKE_CFLAGS_ARCH_HASWELL): QMAKE_CFLAGS_ARCH_HASWELL = $$QMAKE_CFLAGS_AVX2 170avx2: addSimdArch(haswell, avx2 bmi bmi2 f16c fma lzcnt popcnt) 171 172# Follow the Intel compiler's lead and define profiles of AVX512 instructions 173defineTest(addAvx512Profile) { 174 name = $$1 175 dependencies = $$2 176 upname = $$upper($$name) 177 varname = QMAKE_CFLAGS_$$upname 178 179 cpu_features_missing = 180 cflags = $$QMAKE_CFLAGS_ARCH_HASWELL $$QMAKE_CFLAGS_AVX512F 181 for(part, dependencies) { 182 !CONFIG($$part): return() # Profile isn't supported by the compiler 183 184 uppart = $$upper($$part) 185 cflags *= $$eval(QMAKE_CFLAGS_$${uppart}) 186 !contains(QT_CPU_FEATURES, $$uppart): cpu_features_missing += $$uppart 187 } 188 189 CONFIG += $$name 190 isEmpty(cpu_features_missing): QT_CPU_FEATURES += $$name 191 $$varname = $$cflags 192 193 export(QT_CPU_FEATURES) 194 export(CONFIG) 195 export($$varname) 196 addSimdCompiler($$name) 197} 198addAvx512Profile(avx512common, avx512cd) 199addAvx512Profile(avx512core, avx512cd avx512bw avx512dq avx512vl) 200