#testing #x86 #avx #instruction-set #avx2
# #тестирование #x86 #avx #набор инструкций #avx2
Вопрос:
У меня есть приложение, для корректной работы которого требуется AVX2. Была реализована проверка для проверки во время запуска приложения, имеет ли процессор инструкцию AVX2. Я хотел бы проверить, правильно ли он работает, но у меня есть только процессор с AVX2. Есть ли способ временно отключить его для целей тестирования? Или как-то эмулировать другой процессор?
Комментарии:
1. Если решение Питера не работает для вас, некоторые BIOS также позволяют отключить AVX2.
Ответ №1:
Да, используйте уровень «эмуляции» (или динамической перекомпиляции), такой как эмулятор разработки программного обеспечения Intel (SDE) или, возможно, QEMU.
SDE является бесплатной программой с закрытым исходным кодом и очень удобна как для тестирования кода AVX512 на старых процессорах, так и для имитации старых процессоров, чтобы убедиться, что вы случайно не выполняете слишком новые инструкции.
Пример: у меня оказался двоичный файл, который безоговорочно использует vpmovzxwq
инструкцию загрузки AVX2 (для функции, которую я тестировал). Он отлично работает на моем процессоре Skylake изначально, но у SDE есть -snb
возможность эмулировать Sandybridge как в CPUID, так и в фактической проверке каждой инструкции.
$ sde64 -snb -- ./mask
TID 0 SDE-ERROR: Executed instruction not valid for specified chip (SANDYBRIDGE): 0x401005: vpmovzxwq ymm2, qword ptr [rip 0xff2]
Image: /tmp/mask 0x5 (in multi-region image, region# 1)
Instruction bytes are: c4 e2 7d 34 15 f2 0f 00 00
Есть варианты эмуляции процессоров, таких старых, как -quark
, -p4
(SSE2) или Core 2 Merom ( -mrm
), до таких новых, как IceLake-Server ( -icx
) или Tremont ( -tnt
). (И процессоры Xeon Phi, такие как KNL и KNM.)
Он работает довольно быстро, используя динамическую перекомпиляцию (JIT), поэтому я думаю, что код, использующий только те инструкции, которые поддерживаются изначально, может работать с практически собственной скоростью.
Он также имеет опции инструментирования (например -mix
, для сброса набора команд) и опции для более тщательного управления JIT. Я думаю, вы могли бы заставить его не сообщать AVX2 в CPUID, но все же позволить инструкциям AVX2 выполняться без сбоев.
Или, возможно, эмулировать процессор, который поддерживает AVX2, но не FMA (к сожалению, у Via есть такой реальный процессор). Или комбинации, которых нет ни у одного реального процессора, например, AVX2, но нет popcnt
, или BMI1 / BMI2, но не AVX. Но я не изучал, как это сделать.
Базовые sde -help
параметры позволяют настроить его только для определенных процессоров Intel и для проверки потенциально медленных переходов SSE / AVX (без правильного использования vzeroupper). И еще кое-что.
Один важный тестовый пример, в котором отсутствует SDE, — это AVX FMA без AVX2 (AMD Piledriver / Steamroller, то есть большинство процессоров AMD серии FX). Легко забыть и использовать перемешивание AVX2 в коде, который должен быть AVX1 FMA3, и некоторые компиляторы (например, MSVC) не поймают это во время компиляции, как gcc -march=bdver2
это было бы. (У Bulldozer есть только AVX FMA4, а не FMA3, потому что Intel изменила свои планы после того, как AMD было слишком поздно перепроектировать.)
Если вы просто хотите, чтобы CPUID не сообщал о наличии AVX2 (и FMA?), Поэтому ваш код использует его AVX1 или не AVX версии функций, вы можете сделать это с большинством виртуальных машин.
Чтобы инструкции AVX выполнялись без сбоев, необходимо установить бит в управляющем регистре. (Таким образом, это работает как обещание ОС, что оно правильно сохранит / восстановит новое архитектурное состояние верхних половин YMM). Таким образом, отключение AVX в CPUID даст вам экземпляр виртуальной машины, в котором ошибка инструкций AVX. (По крайней мере, 256-битные инструкции? Я не пробовал это, чтобы узнать, могут ли 128-битные инструкции AVX по-прежнему выполняться в этом состоянии на HW, который поддерживает AVX.)