// SetUnmanagedStructures // // Fills in overlapped Structures used in an async overlapped Winsock call. // These calls are outside the runtime and are unmanaged code, so we need // to prepare specific structures and ints that lie in unmanaged memory // since the overlapped calls may complete asynchronously. internal void SetUnmanagedStructures(byte[] buffer, int offset, int size, Internals.SocketAddress socketAddress, SocketFlags socketFlags) { _messageBuffer = new byte[s_wsaMsgSize]; _wsaBufferArray = new byte[s_wsaBufferSize]; bool ipv4, ipv6; Socket.GetIPProtocolInformation(((Socket)AsyncObject).AddressFamily, socketAddress, out ipv4, out ipv6); // Prepare control buffer. if (ipv4) { _controlBuffer = new byte[s_controlDataSize]; } else if (ipv6) { _controlBuffer = new byte[s_controlDataIPv6Size]; } // Pin buffers. object[] objectsToPin = new object[(_controlBuffer != null) ? 5 : 4]; objectsToPin[0] = buffer; objectsToPin[1] = _messageBuffer; objectsToPin[2] = _wsaBufferArray; // Prepare socketaddress buffer. _socketAddress = socketAddress; _socketAddress.CopyAddressSizeIntoBuffer(); objectsToPin[3] = _socketAddress.Buffer; if (_controlBuffer != null) { objectsToPin[4] = _controlBuffer; } base.SetUnmanagedStructures(objectsToPin); // Prepare data buffer. _wsaBuffer = (WSABuffer *)Marshal.UnsafeAddrOfPinnedArrayElement(_wsaBufferArray, 0); _wsaBuffer->Length = size; _wsaBuffer->Pointer = Marshal.UnsafeAddrOfPinnedArrayElement(buffer, offset); // Setup structure. _message = (Interop.Winsock.WSAMsg *)Marshal.UnsafeAddrOfPinnedArrayElement(_messageBuffer, 0); _message->socketAddress = Marshal.UnsafeAddrOfPinnedArrayElement(_socketAddress.Buffer, 0); _message->addressLength = (uint)_socketAddress.Size; _message->buffers = Marshal.UnsafeAddrOfPinnedArrayElement(_wsaBufferArray, 0); _message->count = 1; if (_controlBuffer != null) { _message->controlBuffer.Pointer = Marshal.UnsafeAddrOfPinnedArrayElement(_controlBuffer, 0); _message->controlBuffer.Length = _controlBuffer.Length; } _message->flags = socketFlags; }
// SetUnmanagedStructures // // Fills in overlapped Structures used in an async overlapped Winsock call. // These calls are outside the runtime and are unmanaged code, so we need // to prepare specific structures and ints that lie in unmanaged memory // since the overlapped calls may complete asynchronously. internal void SetUnmanagedStructures(byte[] buffer, int offset, int size, Internals.SocketAddress socketAddress, SocketFlags socketFlags) { _messageBuffer = new byte[s_wsaMsgSize]; _wsaBufferArray = new byte[s_wsaBufferSize]; bool ipv4, ipv6; Socket.GetIPProtocolInformation(((Socket)AsyncObject).AddressFamily, socketAddress, out ipv4, out ipv6); // Prepare control buffer. if (ipv4) { _controlBuffer = new byte[s_controlDataSize]; } else if (ipv6) { _controlBuffer = new byte[s_controlDataIPv6Size]; } // Pin buffers. object[] objectsToPin = new object[(_controlBuffer != null) ? 5 : 4]; objectsToPin[0] = buffer; objectsToPin[1] = _messageBuffer; objectsToPin[2] = _wsaBufferArray; // Prepare socketaddress buffer. _socketAddress = socketAddress; _socketAddress.CopyAddressSizeIntoBuffer(); objectsToPin[3] = _socketAddress.Buffer; if (_controlBuffer != null) { objectsToPin[4] = _controlBuffer; } base.SetUnmanagedStructures(objectsToPin); // Prepare data buffer. _wsaBuffer = (WSABuffer*)Marshal.UnsafeAddrOfPinnedArrayElement(_wsaBufferArray, 0); _wsaBuffer->Length = size; _wsaBuffer->Pointer = Marshal.UnsafeAddrOfPinnedArrayElement(buffer, offset); // Setup structure. _message = (Interop.Winsock.WSAMsg*)Marshal.UnsafeAddrOfPinnedArrayElement(_messageBuffer, 0); _message->socketAddress = Marshal.UnsafeAddrOfPinnedArrayElement(_socketAddress.Buffer, 0); _message->addressLength = (uint)_socketAddress.Size; _message->buffers = Marshal.UnsafeAddrOfPinnedArrayElement(_wsaBufferArray, 0); _message->count = 1; if (_controlBuffer != null) { _message->controlBuffer.Pointer = Marshal.UnsafeAddrOfPinnedArrayElement(_controlBuffer, 0); _message->controlBuffer.Length = _controlBuffer.Length; } _message->flags = socketFlags; }