El lenguaje C++ no tiene ningún concepto de una marca de transporte, por lo que hacer una envoltura de función intrínseca alrededor de la ADC
instruction es torpe. Sin embargo, Intel lo hizo de todos modos: unsigned char _addcarry_u32 (unsigned char c_in, unsigned a, unsigned b, unsigned * out);
. La última vez que lo verifiqué, gcc hizo un mal trabajo con esto (guardando el resultado de acarreo en un registro entero, en lugar de dejarlo en CF), pero espero que el propio compilador de Intel lo haga mejor.
Consulte también la wiki de la etiqueta x86 para la documentación de ensamblaje.
El compilador utilizará ADC para usted al agregar enteros más amplios que un solo registro, p. agregando int64_t
en código de 32 bits, o __int128_t
en código de 64bit.
#include <stdint.h>
#ifdef __x86_64__
__int128_t add128(__int128_t a, __int128_t b) { return a+b; }
#endif
# clang 3.8 -O3 for x86-64, SystemV ABI.
# __int128_t args passed in 2 regs each, and returned in rdx:rax
add rdi, rdx
adc rsi, rcx
mov rax, rdi
mov rdx, rsi
ret
asm salida del Godbolt compiler explorer. No es muy verosímil -fverbose-asm
de clang, pero gcc 5.3/6.1 desperdicia dos instrucciones mov
por lo que es menos legible.
cual de los procesadores? – Chubsdad
@Chubsdad: hice todo lo posible para agregar algo de información. Espero que sea suficiente –
¿Qué compilador? Para acceder al indicador de acarreo, debe incrustar el código de ensamblador en su código de C++. Cómo lo hace depende del compilador que está utilizando. – TonyK