Hi,
Of course, of course. Them are 32-bit aligned because of using 32-bit processor.Yes, but only in memory on 32-bit (and pseudo-64bit) machines
Another question. I'm compiling the program with Visual Studio 2003 .NET and when using GNU/Linux I will have to compile with GCC, will the behavior be different? I'm asking this because I don't know what "__attribute__((packed))" do.
Thanks,
Òscar Llarch i Galán
__attribute__((packed)) is a GCC extension, so it won't work with VS. Basicly it sets the packed attribute for given class, which tells the compiler not to align it. It's perfect when you want to sent your structure directly over the network or read/write it from/to a file, but it's also completely unportable.
VS probably has something different that will allow you to pack the structure. Since it's .NET, it might have a form of some annotation.
Hi,
Ok, so it's only important because of the data that will be sent becomes longer and it could be smaller. So if I force to not pack, send it, and recive to another program that loads the data into the struct, the struct will contain the same data.
But if forcing not to align the data, when using the variables in memory will produce TLB miss or a page faults (from the link of "Data structure alignment").
Thank you very much,
Òscar Llarch i Galán
It isn't about sending few bytes less, but about adhering to given protocol. If it requires you to send a one-byte field followed by two-byte one, you can't send 1B of data, 1B of garbage and then 2B of data. If you use some custom protocol and both sender and receiver follow the same rules of alignment, you don't have to worry about it, but if you want to implement Modbus, you have to follow its specification and there are no holes in Modbus messages.
Yes, some CPUs can't even fetch unaligned data from memory, so accesses to such structures might be split into several operations.
Hi,
Searching for the web I found this two helpful links (for Visual Studio compiler):
http://msdn2.microsoft.com/en-us/lib...65(VS.80).aspx
http://msdn2.microsoft.com/en-us/lib...y1(VS.80).aspx
The second one works for me:
Qt Code:
#pragma pack(1) struct MB_Request { uchar function_code; quint16 start_adr; quint16 quantity_regs; }; #pragma pack(1) struct MBAP_Header { quint16 transaction_id; quint16 protocol_id; quint16 len; uchar unit_id; }; #pragma pack(1) struct MB_Message { MBAP_Header mb_hdr; MB_Request mb_req; };To copy to clipboard, switch view to plain text mode
Then, executing your example code, the structs are unaligned as I need for Modbus protocol.
Could I use "#ifndef" statment to know wich compiler is used to then use "#pragma pack(1)" or "__attribute__((packed))" depending on compiler?
So when I use GCC on GNU/Linux(or windows also) it will pack the data unaligned as expected. Could use GCC with Visual Studio?
Thanks,
Thanks,
Òscar Llarch i Galán
Yes, but using __desclspec(align(1)) might be more cleaner, because you will need only two macros (depending on the compiler one of them will be empty), instead of ifdef before each structure.
AFAIR it's possible, but I don't use VS, so I can't help you with that.
Hi,
I've tryied this:Yes, but using __desclspec(align(1)) might be more cleaner
Qt Code:
__declspec(align(1)) struct MB_Request { uchar function_code; quint16 start_adr; quint16 quantity_regs; }; int main() { int iA1 = __alignof(MBAP_Header); // This returns "2" byte alignment and using #pragma pack(1) returns me "1" " byte alignment }To copy to clipboard, switch view to plain text mode
I've found that GCC also supports this #pragma for compatibility with Win32:instead of ifdef before each structure
http://gcc.gnu.org/onlinedocs/gcc/St...g-Pragmas.html
Thanks,
Òscar Llarch i Galán
Hi,
Yes:Have you placed __declspec before MBAP_Header too?
Qt Code:
//#pragma pack(1) __declspec(align(1)) struct MB_Request { uchar function_code; quint16 start_adr; quint16 quantity_regs; }; //#pragma pack(1) __declspec(align(1)) struct MBAP_Header { quint16 transaction_id; quint16 protocol_id; quint16 len; uchar unit_id; }; //#pragma pack(1) __declspec(align(1)) struct MB_Message { MBAP_Header mb_hdr; MB_Request mb_req; };To copy to clipboard, switch view to plain text mode
But
Returns always "2" for iA1, iA2 and iA3.Qt Code:
int iA1 = __alignof(MBAP_Header); int iA2 = __alignof(MB_Request); int iA3 = __alignof(MB_Message);To copy to clipboard, switch view to plain text mode
Don't worry about it, using "#pragma pack(1)" is going well.
Thanks for your time and your knowdelege.
Òscar Llarch i Galán
Bookmarks