64-Bit-Integers auf 32-Bit-Windows



  • SeppJ schrieb:

    hustbaer schrieb:

    Man könnte vermutlich SSE oder SSE2 oder sowas verwenden - da gibt's ja ausreichend grosse Register.
    Tun die Compiler aber glaube ich nicht, nichtmal wenn man SSE/SSE2 Support explizit aufdreht.

    SSE1, was es auch in reinen 32-Bit Prozessoren gibt, kann nur mit 32-Bit Zahlen rechnen. Kann man von 32-Bit Code aus SSE2 und höher benutzen?

    Nein, laut

    http://en.wikipedia.org/wiki/SSE2 schrieb:

    AMD's implementation of SSE2 on the AMD64 (x86-64) platform includes an additional eight registers, doubling the total number to 16 (XMM0 through XMM15). These additional registers are only visible when running in 64-bit mode.



  • Die zusätzlichen acht Register sind im 32-Bit-Modus nicht nutzbar. Die acht ursprünglichen m.W. durchaus.



  • Caligulaminus schrieb:

    Die zusätzlichen acht Register sind im 32-Bit-Modus nicht nutzbar. Die acht ursprünglichen m.W. durchaus.

    Heute ist nicht mein Tag, geh auf Tauchstation *blubblub*



  • @SeppJ:
    Naja... nachdem der 32 Bit Compiler vom MSVC nen /arch:SSE2 Switch hat, gehe ich mal davon aus dass es auch auf 32 Bit CPUs funktioniert.

    Und 64 Bit Integer Befehle gibt's bei SSE2 laut MSDN wohl auch.
    Müsste man fast doch mal ausprobieren was MSVC mit /arch:SSE2 für Code ausspuckt...

    EDIT: OK, erster schneller Test negativ: MSVC 2008/2010 verwenden trotz /arch:SSE2 Switch statt SSE2 lieber 32 Bit Registerpaare und die dadurch nötigen mit-der-Kirche-ums-Kreuz Multiplikationen und Divisionen.



  • Hab ein wenig rumgebastelt und eine Schleife mit SSE-Funktion und eine normale verwendet:

    for(int i=0;i<20000000;i++){
    	f[i] = _mm_andnot_si128(d[i],e);	
    }
    for(int i=0;i<20000000;i++){
    	c[i] = a[i] & (!b);
    	c2[i] = a2[i] & (!b2);
    }
    

    Eigentlich sollte die obere Schleife deutlich schneller sein, aber mit aktivierter Codeoptimierung ist sogar die untere schneller.
    Auch ändert sich nichts, wenn ich SSE2 aktiviere/deaktiviere



  • Müsste das nicht eher so heissen?

    for(int i=0;i<20000000;i++){
        c[i] = (~a[i]) & b;
        c2[i] = (~a2[i]) & b2;
    }
    


  • Danke hustbaer, so ist´s besser. Muss mich wieder an die Bitoperatoren gewöhnen 😉

    Am Ergebnis hat das aber nicht wahnsinnig viel geändert, statt ~10% langsamer ist die SSE-Version jetzt ~10% schneller. Das ist immer noch nicht das, was ich mir erwartet habe.


  • Mod

    Deswegen sag ich ja: Erwarte nicht zu viel. Die Compiler sind in der Regel schon ziemlich gut. Falls du z.B. das obige Programm für 64-Bit compiliert hast, dann werden möglicherweise auch automatisch SSE2-Befehle erzeugt (hier dürfte der Compiler erkennen, dass sich das lohnen könnte), da alle 64-Bit Prozessoren SSE2 können.



  • Heißt das jetzt, die SSE2-Befehle sind nicht viele schneller oder sie werden vom Compiler einfach nicht erzeugt?
    Falls zweiteres, wieso kann ich dann in Visual C++ SSE2 aktivieren, wenn es nicht verwendet wird?
    Von SSE2-Unterstützung kann ich bei meinem Programm sowieso ausgehen, da ich auch das wesentlich jüngere OpenGL 3 benötige.



  • Senfti schrieb:

    Heißt das jetzt, die SSE2-Befehle sind nicht viele schneller oder sie werden vom Compiler einfach nicht erzeugt?

    Die sind je nach Anwendungsfall ordentlich schneller, und werden auch erzeugt. Nur dass MSVC eben nicht perfekt ist, und viele Fälle wo man SSE2 (sinnvoll) anwenden könnte nicht "kann".

    Von SSE2-Unterstützung kann ich bei meinem Programm sowieso ausgehen, da ich auch das wesentlich jüngere OpenGL 3 benötige.

    Naja... OGL 3 Support ist abhängig von der Grafikkarte und deren Treiber, SSE2 ist abhängig von der CPU.
    Das eine hängt also nicht (direkt) mit dem anderen zusammen.

    Wobei die Chance einen z.B. Pentium III (letzter Pentium ohne SSE2) in Kombination mit einer OGL 3 fähigen Grafikkarte anzutreffen wohl relativ kein sein wird.


Anmelden zum Antworten