C/C++ Befehl time(NULL) falscher Wert?
bearbeitet von Der MartinMoin,
> Also der Befehl radio.write() erwartet void* als Daten.
und das bedeutet jetzt was genau - so zusammenhanglos?
> ~~~c
> time_t stamp2 = time(NULL);
>
> uint8_t stamp[4];
> stamp[0] = (stamp2 >> 0)& 0xFF;
> stamp[1] = (stamp2 >> 8)& 0xFF;
> stamp[2] = (stamp2 >> 16)& 0xFF;
> stamp[3] = (stamp2 >> 24)& 0xFF;
> ~~~
Okay, das geht natürlich. Ist quasi die Holzhammer-Narkose. Einen eleganteren Weg hatte ich dir [schon vorgeschlagen](https://forum.selfhtml.org/self/2016/mar/25/c-strich-c-plus-plus-befehl-time-null-falscher-wert/1664057#m1664057); ein anderer wäre eine union-Deklaration, so dass ein time_t und vier Bytes dieselben Adressen belegen:
~~~c
union
{ time_t t;
uint8 b[4];
} stamp;
~~~
So kannst du denselben Speicherplatz einmal mit stamp.t als time-Wert ansprechen, und einmal mit stamp.b als Byte-Array.
> ~~~c
> //Allerdings:
> cout << "stamp: " << (unsigned long) *stamp << endl; // nur das erste Byte
> cout << "stamp: " << (unsigned int) stamp << endl; // nur Adresse
> //Jetzt bekomm ich:
> radio.write( &stamp, 4); //sizeof(stamp)) ; // Also Adresse von stamp
> // nix gscheids
> ~~~
Nochmal: Der Ausdruck _(unsigned long) \*stamp_ nimmt die Basisadresse des Arrays als Zeiger auf uint8, dereferenziert diesen Zeiger und liest das erste Array-Element, und castet das dann nach unsigned long. Das ist dasselbe wie _(unsigned long) stamp[0]_.
Der Ausdruck _(unsigned int) stamp_ nimmt die Adresse des Arrays und castet die nach unsigned int. (Warum nimmst du hier nicht auch long?)
Und _&stamp_ ist wieder nur die Adresse des Arrays, wobei der Adress-Operator & hier überflüssig ist (aber auch nicht schädlich).
> ~~~c
> uint8_t stamp[4];
> *(unsigned long*)stamp = time(NULL);
> cout << "stamp: " << *(unsigned long*)stamp << endl;
> ~~~
>
> warning: dereferencing type-punned pointer will break strict-aliasing rules [-Wstrict-aliasing]
Prima: Der Compiler erkennt, dass du hier verschiedene Zeiger-Typen ineinander überführen willst und warnt, weil das meistens ein Fehler ist. Hier ist es dagegen Absicht.
> So richtig, wie ich an den Speicherbereich bei Linux ran muss, weiß ich noch nicht?
Es gibt keinen Unterschied zwischen Linux und beispielsweise Windows in diesen Beispielen.
> ~~~c
> data[x] = 0x01; x++;
> data[x] = analogValue & 0xFF; x++;
> data[x] = (analogValue >> 8) & 0xFF; x++;
> ~~~
Das geht noch etwas schöner, wenn man die Zuweisung und das Increment zusammenfasst:
~~~c
data[x++] = 0x01;
data[x++] = analogValue & 0xFF;
data[x++] = (analogValue >> 8) & 0xFF;
~~~
Schöne Ostern noch,
Martin