Der Versuch, Daten in ein Paket zu packen. Dieses Paket sollte 64 Bits sein. Ich habe dies:Bitfelder und Ausrichtung
typedef union {
uint64_t raw;
struct {
unsigned int magic : 8;
unsigned int parity : 1;
unsigned int stype : 8;
unsigned int sid : 8;
unsigned int mlength : 31;
unsigned int message : 8;
} spacket;
} packet_t;
Aber es scheint, dass die Ausrichtung nicht garantiert ist. Denn wenn ich laufen diese:
#include <strings.h>
#include <stdio.h>
#include <stddef.h>
#include <stdint.h>
const char *number_to_binary(uint64_t x)
{
static char b[65];
b[64] = '\0';
uint64_t z;
int w = 0;
for (z = 1; w < 64; z <<= 1, ++w)
{
b[w] = ((x & z) == z) ? '1' : '0';
}
return b;
}
int main(void)
{
packet_t ipacket;
bzero(&ipacket, sizeof(packet_t));
ipacket.spacket.magic = 255;
printf("%s\n", number_to_binary(ipacket.raw));
ipacket.spacket.parity = 1;
printf("%s\n", number_to_binary(ipacket.raw));
ipacket.spacket.stype = 255;
printf("%s\n", number_to_binary(ipacket.raw));
ipacket.spacket.sid = 255;
printf("%s\n", number_to_binary(ipacket.raw));
ipacket.spacket.mlength = 2147483647;
printf("%s\n", number_to_binary(ipacket.raw));
ipacket.spacket.message = 255;
printf("%s\n", number_to_binary(ipacket.raw));
}
ich (Big Endian):
1111111100000000000000000000000000000000000000000000000000000000
1111111110000000000000000000000000000000000000000000000000000000
1111111111111111100000000000000000000000000000000000000000000000
1111111111111111111111111000000000000000000000000000000000000000
1111111111111111111111111000000011111111111111111111111111111110
1111111111111111111111111000000011111111111111111111111111111110
Mein .mlength
Feld ist irgendwo auf dem rechten Teil verloren, obwohl es direkt neben dem .sid
Feld sein sollte.
This page bestätigt es: "Ausrichtung der Zuordnungseinheit, die ein Bitfeld enthält". Aber wenn das der Fall ist, wie verpacken Menschen Daten in Bitfelder, was ist ihr Zweck überhaupt?
24 Bits scheint die maximale Größe zu sein, die das Feld .mlength
einnehmen kann, bevor das Feld .message
hinausgeschmissen wird.
Im Allgemeinen können Sie sich nicht darauf verlassen, wie die Daten in einem Bitfeld ausgelegt sind.Wenn Sie mehrere Daten in ein Wort packen müssen, müssen Sie das Marshalling manuell durchführen. – fuz
Ihre Struktur ist 32 * 6 Bits ... Sie sollten stattdessen Zeichen verwenden. – xvan
Verlassen Sie sich nicht auf ein bestimmtes Speicherlayout für C-Datenstrukturen. Es gibt einfach zu viele implementierungsdefinierte und compilerspezifische Parameter. Wie @ FUZxxl schrieb, verwenden Sie ordnungsgemäßes Marshalling. Bei einem guten Compiler ist das nicht unbedingt langsamer. – Olaf