내 프로젝트는 Windows와 Linux 모두에서 32 비트 용으로 컴파일됩니다. 이것은 그러나하지 않습니다x86-32 용 MSVC++로 작은 구조체를 초기화하기위한 효율적인 asm을 얻는 방법은 무엇입니까?
#define NULL_VALUE_LITERAL {0, {0L}};
static const Value NULL_VALUE = NULL_VALUE_LITERAL;
// example of clearing a value
var = NULL_VALUE;
: 나는과 같이 수행 구조체를 제로로 할 필요가 많은 장소에서
struct Value {
unsigned char type;
union { // 4 bytes
unsigned long ref;
float num;
}
};
: 난 그냥 사방에 사용되는 8 바이트 구조체를 모든 최적화가 설정된 상태에서도 Visual Studio 2013에서 가장 효율적인 코드로 컴파일 할 수 있습니다. 어셈블리에서 볼 수있는 것은 NULL_VALUE에 대한 메모리 위치를 읽은 다음 var에 쓴다는 것입니다. 결과적으로 두 개의 메모리 읽기와 두 개의 메모리 쓰기가 수행됩니다. 그러나 이러한 정리 작업은 시간에 민감한 루틴에서도 많이 발생하며 최적화를 위해 찾고 있습니다.
값을 NULL_VALUE_LITERAL로 설정하면 상황이 더 나 빠집니다. 다시 모두 0 인 리터럴 데이터는 임시 스택 값으로 복사 된 다음 변수가 스택에있는 경우에도 변수에 복사됩니다. 그래서 그건 터무니없는 일입니다.
일반적인 상황이 이렇게도있다 :
*pd->v1 = NULL_VALUE;
그것은 위의 VAR = NULL_VALUE 유사 어셈블리 코드를 가지고 있지만, 그것이 내가 그 길을가는 것을 선택해야 내가 인라인 어셈블리 최적화 할 수있는 일입니다. 내 연구에서
이 같은 것 메모리를 지우려면 매우 빠른 방법 : 구조체의 정렬이 데이터 유형 후 3 바이트 단지 쓰레기가 있다는 뜻하기 때문에, 더 나은 여전히
xor eax, eax
mov byte ptr [var], al
mov dword ptr [var+4], eax
또는 :
xor eax, eax
mov dword ptr [var], eax
mov dword ptr [var+4], eax
당신은 내가 메모리가 완전히 불필요한 것을 읽어 방지하기 위해 최적화 된 것과 유사한 코드를 얻을 수있는 방법을 생각할 수 있는가?
두 가지 주소에 32 비트 0 리터럴을 쓰는 코드가 과도하게 많이 생성되는 것으로 끝내는 몇 가지 다른 방법을 시도했지만 IIRC는 메모리에 리터럴을 쓰는 것이 여전히 레지스터 작성만큼 빠르지 않습니다. 메모리로. 나는 내가 얻을 수있는 여분의 성과를 내기 위해 찾고있다.
이상적인 결과는 매우 유용 할 것입니다. 귀하의 도움을 주시면 감사하겠습니다.
"메모리에 리터럴을 쓰는 것이 여전히 메모리에 기록하는 것만 큼 빠릅니다 *"- 사실이 아닙니다. 그리고'memset'을 시도해 보셨습니까? – rustyx
'* ((long long *) & var) = 0LL;은 어떻게됩니까? – xs0
@ xs0 - 이것은 플랫폼 및 할당 방법에 따라 정렬에 문제가 발생할 수 있습니다 ... – immortal