Hi there... That's not the problem...
I've got a code written in C# and works fine but I call a lot of API
functions so I decided to write the low-level stuff in C++. My problem is
(not about __pin cuz I already try that). I have a struct which is
responsible for storing packet's IP Header. It's defined like this...
[StructLayout(LayoutKind::Explicit)]
__value struct IPHeader {
[FieldOffset(0)] Byte verlen; // IP Version & IP Header
length
[FieldOffset(1)] Byte tos; // Type of service
[FieldOffset(2)] UInt16 length; // Packet's total length
[FieldOffset(4)] UInt16 id; // Unique identifier
[FieldOffset(6)] UInt16 offset; // Flags & Offset
[FieldOffset(8)] Byte ttl; // Time To Live
[FieldOffset(9)] Byte protocol; // Protocol (TCP, UDP, any
other)
[FieldOffset(10)] UInt16 checksum; // IP Header checksum
[FieldOffset(12)] Int64 source; // Source address
[FieldOffset(16)] Int64 destination; // Destination address
};
What I want to do (like I did in C# code) is... Fill all of the structs
fields by using a pointer... In C# I have this code
protected virtual unsafe object[] ParseIPHeader(byte[] packet, int length)
{
short src_port = 0, dst_port = 0;
object[] retval = new object[6];
fixed(byte* packetdata = packet) {
CCommon.IPHeader* ipheader = (CCommon.IPHeader*) packetdata;
// Rest of code goes here...
}
As you can see I fix my pointer and it's initialized with packet's address.
In C# I don't have to use the & operator for an operation like the one shown
above. My problem is that... I want to get the same result in C++.
Object* CRawSocket::ParseIPHeader(Byte packet[], int length)[] {
short src_port = 0, dst_port = 0;
System::Text::StringBuilder *src_address, *dst_address;
Object *retval[] = new Object*[6];
src_address = new System::Text::StringBuilder();
dst_address = new System::Text::StringBuilder();
Byte *packeddata = __try_cast< Byte *>(&packet[0]) ;
CCommon::IPHeader *ipheader = (CCommon::IPHeader *) &packeddata;
// Rest of code goes here...
}
I open two instances of VS Debugger (C# & C++ projects). The ipheader points
to packeddata which in turn points to the first element of the array
packet. This works perfectly in C# but it doesn't seem to work in C++. When
I compare both structures (C# & C++) the information contaned in them is
totally different when the data received from the socket is the same.
TIA
> > fixed(byte* packetdata = &packet) // wrong!
> >
[quoted text clipped - 10 lines]
>
> hth
Ben Schwehn - 13 Sep 2004 22:33 GMT
I would either use __pin to get an raw pointer and then use an unmanaged
native c++ struct (not a __value class) to reinterpret_cast to, or use
Marshal::PtrToStructure to get a managed struct. Don't know if this
helps you at all, sorry if it does not.