Ist das Verschieben von mehr als 32 Bit einer uint64_t-Ganzzahl auf einem x86-Computer ein undefiniertes Verhalten?

Lesezeit: 2 Minuten

Abhijits Benutzeravatar
Abhijit

Ich lernte auf die harte Tour und versuchte, a nach links zu verschieben long long und uint64_t zu mehr als 32 Bit auf einem x86-Rechner führte 0. Ich erinnere mich vage, irgendwo gelesen zu haben, dass Schichtoperatoren auf einer 32-Bit-Maschine nur mit den ersten 32 Bit arbeiten, mich aber nicht an die Quelle erinnern können. Ich würde gerne wissen, ob das Verschieben von mehr als 32 Bit einer uint64_t-Ganzzahl auf einem x86-Computer ein undefiniertes Verhalten ist?

  • Sollte nicht sein. Welchen Compiler verwendest du?

    – Jonathan Grynspan

    8. Mai 2012 um 13:01 Uhr

  • Bitte klären Sie, was Sie mit “m/c” meinen.

    – Stefan Kanon

    8. Mai 2012 um 13:13 Uhr

  • Ich habe noch nie von “m/c” gehört. In meiner Branche würde MC höchstwahrscheinlich für Mikrocontroller oder weniger wahrscheinlich für einen integrierten Schaltkreis von Motorola/Freescale stehen. Stellen Sie sich vor, wie viel einfacher es wäre, als Programmierer zu arbeiten, wenn niemand seltsame Akronyme verwenden würde!

    – Ludin

    8. Mai 2012 um 13:27 Uhr

  • Sie haben wahrscheinlich so etwas wie verwendet uint64_t x = 1 << 33 und jetzt den Compiler beschuldigen (der Sie wahrscheinlich gewarnt hätte, wenn Sie jemals Warnungen aktiviert hätten)

    – Günther Piez

    8. Mai 2012 um 13:32 Uhr


  • Sie würden mehr Klarheit darüber bekommen, was hier tatsächlich passiert ist, wenn Sie den Code posten würden, der sich für Sie schlecht benommen hat.

    – Steve Townsend

    8. Mai 2012 um 13:51 Uhr

  • +1. So sollte es sein. Ein kompatibler Compiler muss dem C-Standard folgen.

    – ArjunShankar

    8. Mai 2012 um 13:17 Uhr

  • @drhirsch wies darauf hin, was das wahrscheinliche Problem ist: so etwas wie uint64_t x = 1 << 33

    – Namen53

    8. Mai 2012 um 16:05 Uhr

  • Gute Veranschaulichung dessen, was vor sich geht. ich persönlich mag die nicht PRIX64 Makro. ich bevorzuge printf("%2d: %#.016lx\n", i, (x << i));

    – dturvene

    16. März 2021 um 21:12 Uhr

  • Da es sich jedoch um ein undefiniertes Verhalten handelt, hat der Compiler möglicherweise entschieden, dass die tatsächliche Verschiebung NICHT stattfinden kann, und daher würde möglicherweise nicht einmal eine Assembler-Anweisung ausgegeben. Es macht also keinen Sinn, sich weiter anzusehen, was der Assembler tun würde.

    – hmjail

    22. März 2016 um 20:44 Uhr


  • Ein Compiler verwendet shr für vorzeichenlose Rechtsverschiebungen. sar (Arithmetik Verschiebung nach rechts) würde das MSB duplizieren und die C-Semantik für Fälle verletzen, die nicht UB sind.

    – Peter Cordes

    8. März 2019 um 22:40 Uhr

  • Compiler wissen, dass Verschiebungen die Zählung maskieren &31 oder &63wird also tatsächlich optimiert value >> (count&31) zu einem einzigen shr oder shrx Anweisung, weil sie die implementiert &31 sowie die Verschiebung.

    – Peter Cordes

    8. März 2019 um 22:41 Uhr

1432810cookie-checkIst das Verschieben von mehr als 32 Bit einer uint64_t-Ganzzahl auf einem x86-Computer ein undefiniertes Verhalten?

This website is using cookies to improve the user-friendliness. You agree by using the website further.

Privacy policy