endianness bestimmen


  • Mod

    Das ist vollkommen egal, da das Lesen des nicht aktiven Unionmembers sowieso UB ist.

    Das ist (pauschal) offensichtlich falsch.

    Lesen ist aber mindestens implementation-defined, wenn nicht ebenfalls UB.

    Welches Lesen?



  • osdt schrieb:

    Nathan schrieb:

    Das ist vollkommen egal, da das Lesen des nicht aktiven Unionmembers sowieso UB ist.

    Das bezieht sich meines Wissens nur auf nicht-triviale Typen, deren Konstuktor explizit aufgerufen werden muss. Nur in diesem Zusmmenhang macht der Term 'aktiver Member' überhaupt Sinn. Ich lasse mich natürlich gern eines Besseren belehren.

    Arcoth schrieb:

    Das ist vollkommen egal, da das Lesen des nicht aktiven Unionmembers sowieso UB ist.

    Das ist (pauschal) offensichtlich falsch.

    type-punning via union verletzt die strict aliasing rule (§3.10/10), das ist UB.

    Lesen ist aber mindestens implementation-defined, wenn nicht ebenfalls UB.

    Welches Lesen?

    In dem verlinktem Code:

    bool isLittleEndian()
    {
        short int number = 0x1;
        char *numPtr = (char*)&number;
        return (numPtr[0] == 1); // hier
    }
    

    Aliasing via char* ist erlaubt, aber wenn man das dann als char liest, ist das Ergebnis definitiv nicht portabel.


  • Mod

    Aliasing via char* ist erlaubt, aber wenn man das dann als char liest, ist das Ergebnis definitiv nicht portabel.

    Ja, die value representation ist implementation-defined. UB ist es aber definitiv nicht, sondern explizit erlaubt.

    type-punning via union verletzt die strict aliasing rule (§3.10/10), das ist UB.

    Kleiner Tipp: Die Member einer Union müssen nicht alle von völlig unterschiedlichem Typ sein. 😉



  • Arcoth schrieb:

    Aliasing via char* ist erlaubt, aber wenn man das dann als char liest, ist das Ergebnis definitiv nicht portabel.

    Ja, die value representation ist implementation-defined. UB ist es aber definitiv nicht, sondern explizit erlaubt.

    Ja, deshalb schrieb ich das ja.

    type-punning via union verletzt die strict aliasing rule (§3.10/10), das ist UB.

    Kleiner Tipp: Die Member einer Union müssen nicht alle von völlig unterschiedlichem Typ sein. 😉

    *sigh*
    Ja, dann verletzt es nicht die strict aliasing rule. Garantiert das man den selben Wert bekommt, den man rein gesteckt hat ist das aber glaub ich immer noch nicht. 😉


  • Mod

    osdt schrieb:

    coder007 schrieb:

    kann man endianness zur compile time bestimmen?

    Sollte funktionieren:

    constexpr bool is_little_endian()
    {
        union helper {
            int i;
            char c;
        };
        return helper{1}.c;
    }
    

    Edit: garantiert der Standard, dass helper::c im 1. Byte von helper liegt? Ansonsten wäre char c[sizeof(int)] und helper{1}.c[0] wohl ehr Standardkonform.

    Sollte nicht funktionieren.

    2 A conditional-expression e is a core constant expression unless the evaluation of e, following the rules of the
    abstract machine (1.9), would evaluate one of the following expressions:
    [...]
    — an lvalue-to-rvalue conversion (4.1) or modification (5.17, 5.2.6, 5.3.2) that is applied to a glvalue that
    refers to a non-active member of a union or a subobject thereof;

    Das Standardkomitee hat solche Konstrukte ganz bewusst nicht konstant gemacht um die Implementation u.a. von cross-Compilern nicht zu erschweren.



  • LOL, Extrapunkte für osdt, weil er ein Konstrukt geschrieben hat, dass explicit vom Standard verboten ist. Respekt.



  • was ist nun die eine moegliche loesung? 🙂



  • Nathan schrieb:

    LOL, Extrapunkte für osdt, weil er ein Konstrukt geschrieben hat, dass explicit vom Standard verboten ist. Respekt.

    Da kannst du mal sehen was mit etwas gutem Willen alles möglich ist 😃 GCC (4.9.1) compiliert das ohne Murren und ich hab gedacht 'wird schon passen'.

    Leider musste ich eben feststellen, dass clang (3.5) anderer Meinung ist:

    prog.cc:10:22: note: read of member 'c' of union with active member 'i' is not allowed in a constant expression
    

    Tja, dumm gelaufen. Ich nehme alles zurück und gelobe Besserung.



  • coder007 schrieb:

    vorbereitung coding interview...

    Wie kommst du eigentlich gerade auf diese Frage?

    coder007 schrieb:

    was ist nun die eine moegliche loesung? 🙂

    Mögliche Lösung: In C++ gibt es keine Endianness.



  • Whenever I see code that asks what the native byte order is, it's almost certain the code is either wrong or misguided.



  • @pike: as i said its a coding interview question...


Anmelden zum Antworten