XOR-Verknüpfung Gleitkommawert & allgemeine Guss Frage Kompiliererausgabe

stimmen
0

Nun, beide Fragen sind besorgt in Richtung meiner Zusammenstellung ausgegeben, da ich versuche, alle Warnungen zu entfernen ..

Zur ersten Frage :
Ich bin XOR - Verknüpfung Float - Werte, Compiler Ausgabe: warning: dereferencing type-punned pointer will break strict-aliasing rules [-Wstrict-aliasing]

inline float ClassXY::GetFloat(void) const
{
    uint32_t xored = *(uint32_t*)&m_pParent->m_Value.m_fValue ^ (uint32_t)this; // compiler warning for this line
    return *(float*)&xored;
}

m_pParent ist ein Zeiger auf diese Klasse ClassXY *m_pParent;
m_Value ist eine var eines struct und m_fValue ist als Schwimmer innerhalb des struct definiert.

Jede Idee, wie um die Warnung zu bekommen? (Ich weiß, dass ich die Warnung deaktivieren kann, aber ich habe keine Ahnung, eine saubere Lösung, um es zu bekommen)

Meine zweite qustion wäre:
Das Szenario , obwohl fast das gleiche, nur mit int. Compiler spricht über Informationsverlust: warning: cast from ‘const ClassXY*’ to ‘uint32_t {aka unsigned int}’ loses precision [-fpermissive]
Ohne den -fpermissive Compiler - Flag, würde ich nicht in der Lage sein , zu kompilieren ..

inline int ClassXY::GetInt(void) const
{
    return (int)(m_pParent->m_Value.m_nValue ^ (int)this); // compiler warning for this line
}

Und wieder eine Idee, wie man dieses Problem beheben?
Oder ist es inpossible ohne Warnungen, was zu tun ich versuche?

Um Ihnen alle eine Vorstellung , worum es geht: auto example = g_pClassXY->FindVar(example_var);
Dann: float float_val = example->fValue; // direct access, value is wrong
Um den Wert richtig zu machen, der richtige Ansatz wäre:float float_val = example->GetFloat();

Danke im Voraus!

Veröffentlicht am 07/11/2018 um 23:52
quelle vom benutzer
In anderen Sprachen...                            


1 antworten

stimmen
2

Um eine strenge Aliasing Verletzung zu vermeiden, könnte der Code sein:

static_assert( sizeof(float) <= sizeof(uint32_t), "size problem" );
uint32_t xored{};
memcpy(&xored, &m_pParent->m_Value.m_fValue, sizeof xored);
xored ^= reinterpret_cast<uint32_t>(this);

float ret;
memcpy(&ret, &xored, sizeof ret);
return ret;

Allerdings gibt es noch einige Probleme:

  • Der Code wird auf einem System schlecht ausgebildet , in dem thisein 64-Bit - Zeiger.
  • Der Float - Wert beteiligt könnte ein ungültiger Bitmuster sein float, was nicht definiertes Verhalten.

Wenn Ihre Absicht einen Schwimmer zu „verschlüsseln“ ist, dann sollte der verschlüsselten Wert als gespeichert werden uint32_toder ein Byte - Array, nicht so float.

Der erste Aufzählungspunkt kann durch Erzeugen eine zufällige 32-Bit - Maske für jede Instanz adressiert werden, anstelle der Verwendung this; oder unter Verwendung uintptr_tstatt uint32_t.

Beantwortet am 08/11/2018 um 00:17
quelle vom benutzer

Cookies help us deliver our services. By using our services, you agree to our use of cookies. Learn more