Search
Module:
Directory

   Desktop Functions:

   Smart Device Functions:


Show Recent Changes
Subscribe (RSS)
Misc. Pages
Comments
FAQ
Helpful Tools
Playground
Suggested Reading
Website TODO List
Download Visual Studio Add-In

SOCKADDR (Structures)
 
.
Summary
TODO - a short description

C# Definition:

// WinsockSockAddr takes an IPAddress of IPEndpoint on creation, then provides a
// pinned PSOCKADDR to be used for async PInvoke calls.  The owner and pending
// async calls may reference the same instance at the same time, and have
// different independent needs with regards to the lifetime of the pinned
// PSOCKADDR.  So WinsockSockAddr guarantees the pinned copy is available so
// long as the WinsockSockAddr instance owning that pinned copy is referenced.

// NOTENOTE:  System.Net.Endpoint.Serialize will provide a System.Net.SocketAddress
// which mostly fulfills the same use as the class below.  It does not pin the
// result though.  Consider passing the result of System.Net.Endpoint.Serialize()
// as X to GCHandle.Alloc(X, GCHandleType.Pinned) instead of picking up the
// entire class below.

[StructLayout(LayoutKind.Sequential)]

    public struct sockaddr_in
    {
        public ADDRESS_FAMILIES sin_family;
        public ushort sin_port;
        public in_addr sin_addr;
        [MarshalAs(UnmanagedType.ByValArray, SizeConst = 8)]
        public byte[] sin_zero;
    }

[StructLayout(LayoutKind.Explicit, Size = 4)]

    public struct in_addr
    {
        [FieldOffset(0)]
        public byte s_b1;
        [FieldOffset(1)]
        public byte s_b2;
        [FieldOffset(2)]
        public byte s_b3;
        [FieldOffset(3)]
        public byte s_b4;

        [FieldOffset(0)]
        public ushort s_w1;
        [FieldOffset(2)]
        public ushort s_w2;

        [FieldOffset(0)]
        public uint S_addr;

        /// <summary>
        /// can be used for most tcp & ip code
        /// </summary>
        public uint s_addr { get { return S_addr; } }

        /// <summary>
        /// host on imp
        /// </summary>
        public byte s_host { get { return s_b2; } }

        /// <summary>
        /// network
        /// </summary>
        public byte s_net { get { return s_b1; } }

        /// <summary>
        /// imp
        /// </summary>
        public ushort s_imp { get { return s_w2; } }

        /// <summary>
        /// imp #
        /// </summary>
        public byte s_impno { get { return s_b4; } }

        /// <summary>
        /// logical host
        /// </summary>
        public byte s_lh { get { return s_b3; } }
    }

class WinsockSockAddr
{
     const Int16 AF_INET = 2;
     const Int16 AF_INET6 = 23;

     [StructLayout(LayoutKind.Sequential)]
     struct SOCKADDR_IN
     {
     public Int16 _family;
     public Int16 _port;
     public Byte _addr0;
     public Byte _addr1;
     public Byte _addr2;
     public Byte _addr3;
     public Int32 _nothing;
     }

     static readonly int SIZEOF_SOCKADDR_IN = Marshal.SizeOf(typeof(SOCKADDR_IN));

     [StructLayout(LayoutKind.Sequential)]
     struct SOCKADDR_IN6
     {
     public Int16 _family;
     public Int16 _port;
     public Int32 _flowInfo;
     public Byte _addr0;
     public Byte _addr1;
     public Byte _addr2;
     public Byte _addr3;
     public Byte _addr4;
     public Byte _addr5;
     public Byte _addr6;
     public Byte _addr7;
     public Byte _addr8;
     public Byte _addr9;
     public Byte _addr10;
     public Byte _addr11;
     public Byte _addr12;
     public Byte _addr13;
     public Byte _addr14;
     public Byte _addr15;
     public Int32 _scopeID;
     }

     static readonly int SIZEOF_SOCKADDR_IN6 = Marshal.SizeOf(typeof(SOCKADDR_IN6));

     // Depending on the family type of address represented, either a SOCKADDR_IN
     // or a SOCKADDR_IN6 will be referenced by _addr.  We'll pin the same object
     // to _pinAddr, and finally keep a IntPtr to the alloc.
     object _addr;
     GCHandle _pinAddr;
     IntPtr _pAddr;

     public WinsockSockAddr(IPEndPoint source)
     : this(source.Address, (short)source.Port)
     {
     }

     public WinsockSockAddr(IPAddress source)
     : this(source, 0)
     {
     }

     public WinsockSockAddr(IPAddress source, short port)
     {
     _pAddr = (IntPtr)0;

     if (source.AddressFamily == AddressFamily.InterNetwork)
     {
         SOCKADDR_IN a;
         Byte[] addr = source.GetAddressBytes();
         Debug.Assert(addr.Length == 4);

         a._family = AF_INET;
         a._port = IPAddress.HostToNetworkOrder(port);
         a._addr0 = addr[0];
         a._addr1 = addr[1];
         a._addr2 = addr[2];
         a._addr3 = addr[3];
         a._nothing = 0;

         _addr = a;
     }
     else if (source.AddressFamily == AddressFamily.InterNetworkV6)
     {
         SOCKADDR_IN6 a;
         Byte[] addr = source.GetAddressBytes();
         Debug.Assert(addr.Length == 16);

         a._family = AF_INET6;
         a._port = IPAddress.HostToNetworkOrder(port);
         a._flowInfo = 0;
         a._addr0 = addr[0];
         a._addr1 = addr[1];
         a._addr2 = addr[2];
         a._addr3 = addr[3];
         a._addr4 = addr[4];
         a._addr5 = addr[5];
         a._addr6 = addr[6];
         a._addr7 = addr[7];
         a._addr8 = addr[8];
         a._addr9 = addr[9];
         a._addr10 = addr[10];
         a._addr11 = addr[11];
         a._addr12 = addr[12];
         a._addr13 = addr[13];
         a._addr14 = addr[14];
         a._addr15 = addr[15];
         a._scopeID = (Int32)source.ScopeId;

         _addr = a;
     }
     else
     {
         throw new ArgumentException();
     }

     _pinAddr = GCHandle.Alloc(_addr, GCHandleType.Pinned);
     _pAddr = _pinAddr.AddrOfPinnedObject();
     }


     void Close()
     {
     if (_pinAddr.IsAllocated)
     {
         _pinAddr.Free();
     }

     _addr = null;
     _pAddr = (IntPtr)0;
     }

     ~WinsockSockAddr()
     {
     Close();
     }

     public IntPtr PinnedSockAddr
     { get { return _pAddr; } }
}

Notes:

None.

This sample code also shows how to work with this structure in C#: http://dotnetcodebox.blogspot.com/2012/01/how-to-use-umanaged-sockaddr-structure.html .

Documentation
SOCKADDR on MSDN

Please edit this page!

Do you have...

  • helpful tips?
  • corrections to the existing content?
  • alternate definitions?
  • additional languages you want to include?

Select "Edit This Page" on the right hand toolbar and edit it! Or add new pages containing any supporting types needed.

 
Access PInvoke.net directly from VS:
Terms of Use
Find References
Show Printable Version
Revisions