Trial By Error

Marshalling your data for Socket/IO? Maybe not.

By April 4, 2017 No Comments

Hi again!  Today I’ve been working on send variable sized data packets over from my client to server using the simple TCP components I mentioned in my TCP Socket Programming post.

I have a few different classes that I want to serialize to byte[]s and send over the wire.   After reading a few suggestions online, I decided to try Marshalling.

With marshaling, you can copy the bytes as they are stored in memory – which is exactly what I needed.


            //Serialize data

            int size = Marshal.SizeOf(data);

            byte[] dataArr = new byte[size];

            IntPtr ptr = Marshal.AllocHGlobal(size);

            Marshal.StructureToPtr(data, ptr, false);

            Marshal.Copy(ptr, dataArr, 0, size);


This copies the byte[] into dataArr.

Here’s Microsoft’s documentation


The only caveat with Marshalling is that you have to explicitly define the size of each property in your class.  And as I mentioned earlier, I was sending variable sized data packets.  Sometimes the property of my class would be quite large (ie. 500Kb) and other times really small (ie. 128 bytes).

[StructLayout(LayoutKind.Sequential, Pack = 1,CharSet = CharSet.Ansi)]
    public class HtsSenderPacket
        [MarshalAs(UnmanagedType.ByValArray, SizeConst = 300000)]
        public byte[] ScreenCapture;
        public HtsSenderPacket()
            ScreenCapture = new byte[300000];

So I defined my ScreenCapture property to be a very large byte[].  I didn’t fill it all most of the time, but  I still was forced to send 300000 bytes.  So marshalling isn’t really the way to go for this case.  However, if you do decide to go this route, be sure to include the attribute:

[MarshalAs(UnmanagedType.ByValArray, SizeConst = 300000)]

I forgot this at first and was only sending the address and not the value.

Since marshalling wasn’t going to work for me, I ended up writing my class where I include the size of the variable property.

public class HtsPacket

        private byte[] _screenCaptureSize = new byte[32];
        private byte[] _screenCapture; //variable size

        private int CLASS_SIZE { get { return 32 + _screenCapture.Length; } }
        public byte[] ScreenCapture { get { return _screenCapture; } }

        public HtsPacket(){

        public HtsPacket(byte[] screenCapture){
          _screenCaptureSize = HtsEncoding.GetBytes(screenCapture.Length);
          _screenCapture = screenCapture;

        public byte[] ToBytes(){ //Serializes class to bytes        
            byte[] arr = new byte[CLASS_SIZE];
            Array.Copy(_screenCaptureSize, 0, arr, 0, _screenCaptureSize.Length);
            Array.Copy(_screenCapture, 0, arr, 32, _screenCapture.Length);
            return arr;
Roshni Patel

Author Roshni Patel

Founder of HomeVision VR, a virtual reality solution for residential/commercial developers and architects.

More posts by Roshni Patel

Contact Us

HomeVision VR