I'm testing on older OS X 10.8 with older SSE4 hardware from about 2010. I've got updated gear from MacPorts and it includes GCC and Clang. GCC is the compiler, and Clang is the assembler. We perform a compile/link on a test file to ensure an ISA is supported by the toolchain. If an ISA is available then we compile a source file to the ISA. Then, we guard the higher ISAs at runtime to avoid SIGILLs. It worked well until we added AVX2. At AVX2 we see this as expected: $ CXX=/opt/local/bin/clang++-mp-5.0 make /opt/local/bin/clang++-mp-5.0 ... -c chacha.cpp /opt/local/bin/clang++-mp-5.0 ... -mavx2 -c chacha_avx.cpp /opt/local/bin/clang++-mp-5.0 ... -msse2 -c chacha_simd.cpp At runtime we catch a SIGILL due to chacha_avx.cpp as shown below. It looks like global constructors are using instructions from AVX (vxorps ), which is beyond what the machine can support. How do we tell GCC to use the base ISA for global constructors? Thanks in advance. ========== (lldb) r v ... * thread #1: tid = 0x19f83aa, 0x000000010016ec49 cryptest.exe`_GLOBAL__sub_I_chacha_avx.cpp at string:1322, queue = 'com.apple.main-thread', stop reason = EXC_BAD_INSTRUCTION (code=EXC_I386_INVOP, subcode=0x0) frame #0: 0x000000010016ec49 cryptest.exe`_GLOBAL__sub_I_chacha_avx.cpp at string:1322 1319 { 1320 size_type (&__a)[__n_words] = __r_.first().__r.__words; 1321 for (unsigned __i = 0; __i < __n_words; ++__i) -> 1322 __a[__i] = 0; 1323 } 1324 1325 template <size_type __a> static And: (lldb) disass cryptest.exe`_GLOBAL__sub_I_chacha_avx.cpp at chacha_avx.cpp: 0x10016ec30: pushq %rbp 0x10016ec31: movq %rsp, %rbp 0x10016ec34: pushq %r14 0x10016ec36: pushq %rbx 0x10016ec37: movq 0x24cf8a(%rip), %rax ; (void *)0x00000001003e69f0: vtable for CryptoPP::NullNameValuePairs 0x10016ec3e: addq $0x10, %rax 0x10016ec42: movq %rax, 0x2dfb6f(%rip) ; CryptoPP::s_nullNameValuePairs -> 0x10016ec49: vxorps %xmm0, %xmm0, %xmm0 0x10016ec4d: vmovups %xmm0, 0x2dfb6b(%rip) ; CryptoPP::DEFAULT_CHANNEL 0x10016ec55: movq $0x0, 0x2dfb70(%rip) ; CryptoPP::DEFAULT_CHANNEL + 12 0x10016ec60: leaq 0x2dfb59(%rip), %rsi ; CryptoPP::DEFAULT_CHANNEL 0x10016ec67: movq 0x24ba52(%rip), %rbx ; (void *)0x00007fff8f09321e: std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> >::~basic_string() 0x10016ec6e: leaq -0x16ec75(%rip), %r14 ; _mh_execute_header ...