LayoutKind.Explicit breaks service install

  • Thread starter Thread starter Dave
  • Start date Start date
D

Dave

I have a structure declared as:

[StructLayout(LayoutKind.Explicit, Size=6)]
private struct StandardFrame
{
[FieldOffset(0)] public byte [] frame;
[FieldOffset(0)] public UInt32 integrityCheck;
[FieldOffset(2)] public UInt32 sequenceNo;
[FieldOffset(4)] public UInt32 dataLength;
}

This is part of a Windows Service C# app. I've added an installer and
setup project but the install fails with "Unable to get installer types
in the <name of executable> --> one or more of the types in the
assembly unable to load."

I've narrowed the problem down to this struct. If I make the struct
LayoutKind.Sequential and remove the FieldOffset values the service
installs no problem. Obviously this is not what I want, the struct is
to be used as a union. This has really got me stumped, I can work
around it but I would prefer to use this approach.

Any clues gratefully accepted.
 
I've narrowed the problem down to this struct. If I make the struct
LayoutKind.Sequential and remove the FieldOffset values the service
installs no problem. Obviously this is not what I want, the struct is
to be used as a union. This has really got me stumped, I can work
around it but I would prefer to use this approach.

The struct is invalid. You can't overlap a reference type such as
byte[] with a uint value.


Mattias
 
Thanks Mattias, ignoring the other problem with the offsets not
matching the datatypes, is there a simple way to achieve what I
originally intended which was to convert between a six byte array and 3
UInt16's?
 
Thanks for taking the time to reply Mattias. I've now discovered
Buffer.BlockCopy which I think will provide what I'm looking for.

Dave
 
Dave said:
I have a structure declared as:

[StructLayout(LayoutKind.Explicit, Size=6)]
private struct StandardFrame
{
[FieldOffset(0)] public byte [] frame;
[FieldOffset(0)] public UInt32 integrityCheck;
[FieldOffset(2)] public UInt32 sequenceNo;
[FieldOffset(4)] public UInt32 dataLength;
}
Wow. Ignoring for a second what the other guy said, is that layout
right?

[ ][ ][ ][ ][ ][ ]
[integrityCheck ]
[sequenceNo ]
[dataLength ]

I'm surprised it would let you have that. Surely a write to dataLength
would overflow the boundary of the object?

Damien
 
Well, this was kind of my first attempt at a union and frankly it
hasn't worked out very well. The compiler didn't complain about it so I
assumed it was the way it was supposed to work. I specified the size of
the structure in the StructLayout attribute and assumed any overflow
would be trapped and an exception thrown based on the struct size, and
yes someone has already pointed out that my data types inside the
struct are incorrect. I had intended to use UInt16 rather than UInt32,
my bad. Of course it would have been nice if the compiler was able to
tell me that "Size=6" is at odds with the size of the declared struct
but that's just sour grapes.

My next good idea is to use Buffer.BlockCopy to do the conversion which
seems less intuitive to me. Thanks for your response.
 
Back
Top