Byte order in structure

I am a little confused about how bytes are ordered in a struct .

Let's say I have the following structure:

 struct container { int myint; short myshort; long mylong; }; 

Now I want to initialize a variable of type struct container in the same way as the next, except that I want to do this with an array.

 struct container container1 = {.myint = 0x12345678, .myshort = 0xABCD, .mylong = 0x12345678}; 

Assume sizeof int and long 4 , and << 28> - 2 .

Assume no indentation.

How then would a 10 bytes struct layout be?

Does it depend on continent?

It would be like this:

 0x12345678 ABCD 12345678 

or how:

 0x78563412 CDAB 78563412 

What I want to do: I have the following char array:

 char buffer[10] = {0}; 

I want to manually populate this array with data, and then memcpy on a struct .

Should I do [1] :

 buffer[0] = 0x12345678 & 0xFF; buffer[1] = 0x12345678 >> 8 & 0xFF; buffer[2] = 0x12345678 >> 16 & 0xFF; buffer[3] = 0x12345678 >> 24 & 0xFF; ... buffer[9] = 0x12345678 >> 24 & 0xFF; 

or should be [2] :

 buffer[0] = 0x12345678 >> 24 & 0xFF; buffer[1] = 0x12345678 >> 16 & 0xFF; buffer[2] = 0x12345678 >> 8 & 0xFF; buffer[3] = 0x12345678 & 0xFF; ... buffer[9] = 0x12345678 & 0xFF; 

before i do my memcpy like:

 memcpy(&container1, buffer, sizeof(container1); 

And if I write to an array and copy it to a struct , is it transported across systems, especially regarding the statement?

EDIT : Does [1] work on a small end machine and [2] on a large endian?

+5
source share
2 answers

Does it depend on continent?

Yes, it depends on the accuracy of the machine. Thus, your logic will change depending on the finiteness of the machine.

There is no portable path * , because of the addition of a structure. Although different compilers provide customizable ways to disable structure debugging. Check Force C ++ struct so that it is not byte aligned .

  • You can add static_assert (C11 support required) to make sure your code does not compile if your structure is not tightly packed. You won't have a portable code, but you can still be sure that if your code compiles, it will behave correctly.

     static_assert(sizeof(container) == sizeof(int) + sizeof(short) + sizeof(long)); 
+2
source

There is another problem: aligning elements within your structure.

Your structure has spaces for alignment. The real layout, as if you did:

 struct container { int myint; short myshort; char __pad__[2]; // padding to align mylong to 4/8 byte boundary long mylong; }; 

How about using union :

 union { struct container vals; char buf[10]; }; 

But why do you want to do this? For almost any scenario I can think of, there may be a cleaner way to get the effect.

When you say an array, do you mean that you want to initialize an array of your structures? It can be done:

 struct container conts[3] = { { .myint = 1, .myshort = 2, .mylong = 3 }, { .myint = 4, .myshort = 5, .mylong = 6 }, { .myint = 7, .myshort = 8, .mylong = 9 } }; 

By the way, there is a way to make static_assert in C:

 // compile time assertion -- if the assertion fails, we will get two case 0:'s // which will cause the compiler to flag this #define static_assert(_assert) \ do { \ switch (0) { \ case (_assert): \ break; case 0: \ break; \ } \ } while (0) 
+1
source

Source: https://habr.com/ru/post/1234990/


All Articles