MSVC и ICC поддерживают встроенные _addcarry_u64
и _addcarryx_u64
.
В соответствии с Intel Intrinsic Guide и белая бумага должен отображаться на adcx
и adox
соответственно. Однако, посмотрев на сгенерированную сборку, ясно, что они сопоставляются с adc
и adcx
соответственно, и нет никакого внутреннего, который отображается на adox
.
Кроме того, сообщая компилятору о включении AVX2 с
Я не уверен, как включить ADX с MSVC и ICC./arch:AVX2
в MSVC или -march=core-avx2
с ICC на Linux, не имеет значения.
Документация для MSVC содержит список _addcarryx_u64
с технологией ADX, тогда как _addcarry_u64
не имеет перечисленных технологий. Тем не менее, ссылка в документации MSVC для этих встроенных функций напрямую связана с руководством Intel Intrinsic, которое противоречит собственно документации MSVC и сгенерированной сборке.
Из этого я пришел к выводу, что Intel Intrinsic guide и белая бумага ошибочны.
Это означает, что MSVC считает, что он не позволяет встроенную сборку, он должен предоставить способ использования adc
, который он выполняет с помощью _addcarry_u64
.
Одним из больших преимуществ adcx
и adox
является то, что они работают с разными флагами (переносят CF
и overflow OF
), что позволяет использовать две независимые параллельные цепи переноса. Однако, поскольку для adox
нет неотъемлемой возможности, как это возможно? С ICC по крайней мере можно использовать встроенную сборку, но это невозможно с MSVC в 64-битном режиме.
Документация Microsoft и Intel (как белая бумага, так и встроенный гид онлайн) соглашаются теперь.
Внутренняя документация _addcarry_u64
говорит только о adc
. Внутренний _addcarryx_u64
может создавать либо adcx
, либо adox
. Однако с MSVC 2013 и 2015, _addcarryx_u64
создает adcx
. ICC производит оба.