Open b0bh00d opened 1 year ago
I've iterated my way to what appears to be a functional approach that works right now:
final buffer = datagram.buffer;
final bytes = ByteData.view(buffer);
final int magic = bytes.getInt32(0, Endian.little);
final int sender = bytes.getInt32(4, Endian.little);
final Action action = Action.values[bytes.getInt32(8, Endian.little)];
final int payloadSize = bytes.getInt32(12, Endian.little);
final payloadBuffer = bytes.buffer;
final payload = payloadBuffer.asUint8List(16, payloadSize);
However, I'll hold this open for somebody to tell me if this is the best I can do. Thanks.
How is the memory layout of the datagram defined? Does it correspond to the memory layout of a struct in C? (For example, if you have a single byte field and then a large int, does it insert padding in between?)
If the datagram follows the C ABI struct memory layout, we could consider making a constructor on Struct
subtypes that takes a typed data as argument.
If the datagram does not follow the C ABI struct memory layout, the solution that you have come up with is the best we can do I believe, because you have to reason about the offsets according to what the sender defined as offsets and padding.
Yes, the data is compliant with the C ABI. The struct is 17 bytes in size, but the data being received is 20 (plus the payload), so the struct on the C/C++ side is indeed begin padded.
Using the ByteData.view()
approach above, I'm functional, but it would be a nice language feature to able to define a Struct
and then overlay it onto binary data (as one can in C/C++). I realized after posting that it would probably not be simple, as I had to specify Endian.lilttle
to properly decode the integers, and that would somehow have to be designated/handled in the Struct
.
Since I have a functional work-around, I guess this can be considered more of a feature request. :)
Thanks for a great language! I really love Dart/Flutter.
Apologies if this is somehow self-evident (or if this is not the appropriate place to ask such questions), but I could not find a single example that demonstrates this.
I have received a UDP datagram from a desktop C++ application that corresponds to the following C struct:
I have defined a Struct to mirror it in Dart:
Can I cast the Uint8List datagram binary data into an instance of this Struct (e.g.,
Pointer<Packet>
)? Or should I instead be using more primitive functions that crawl offsets, like:Thanks in advance for any assistance.