Wie kann man Funktionsrückgabewerte in C und C ++ auf x86-64 optimieren?

Das x86-64 ABI gibt zwei Rückgaberegister an:rax undrdx, beide 64-Bit (8 Byte) groß.

Angenommen, x86-64 ist die einzige Plattform, auf die abgezielt wird, und welche dieser beiden Funktionen:

uint64_t f(uint64_t * const secondReturnValue) {
    /* Calculate a and b. */
    *secondReturnValue = b;
    return a;
}

std::pair<uint64_t, uint64_t> g() {
    /* Calculate a and b, same as in f() above. */
    return { a, b };
}

würde angesichts des aktuellen Status von C / C ++ - Compilern, die auf x86-64 abzielen, eine bessere Leistung erzielen? Gibt es leistungsbezogene Probleme bei der Verwendung der einen oder anderen Version? Können Compiler (GCC, Clang) das @ immer optimierestd::pair wird in @ zurückgegebrax undrdx?

AKTUALISIEREN Im Allgemeinen ist die Rückgabe eines Paares schneller, wenn der Compiler das @ optimierstd::pair Methoden (Beispiele für Binärausgabe mitGCC 5.3.0 undClang 3.8.0). Obf() ist nicht inline, der Compiler muss Code generieren, um einen Wert in den Speicher zu schreiben, z. B .:

movq b, (%rdi)
movq a, %rax
retq

Aber im Falle vong() es genügt für den Compiler zu tun:

movq a, %rax
movq b, %rdx
retq

Da Anweisungen zum Schreiben von Werten in den Speicher im Allgemeinen langsamer sind als Anweisungen zum Schreiben von Werten in Register, sollte die zweite Version schneller sein.

Antworten auf die Frage(2)

Ihre Antwort auf die Frage