Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/mono/mono.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMartin Baulig <mabaul@microsoft.com>2019-09-19 15:46:29 +0300
committerAlexander Köplinger <alex.koeplinger@outlook.com>2019-09-19 15:46:29 +0300
commit1256d6c8cf149306032677fa8e060a8de9e69de2 (patch)
treeb9d2ae8c16e5dc979ea101dd014ce4d2408a8044 /mcs/class/System
parent12949cf2e65b02f7d67028187cc45f8d4bbc403e (diff)
Use `NetworkStream` from CoreFX. (#16889)
* Use `NetworkStream` from CoreFX. This brings the `NetworkStream` class and related tests from CoreFX. * `SocketAsyncEventArgs`: partially replace the following properties with the CoreFX version: `Buffer`, `BufferList`, `Offset`, `SetBuffer ()` as well as the internal `CopyBufferFrom ()`. * `SocketAsyncResult`: change `Buffer` from `byte[]` to `Memory<byte>`. * Add internal `Socket` overloads: - `Receive (Memory<byte> buffer, int, int, SocketFlags, out SocketError)` - `ReceiveFrom (Memory<byte>, int, int, SocketFlags, ref EndPoint, out SocketError)` - `SendTo (Memory<byte>, int, int, SocketFlags, EndPoint)` * Implement async task overloads from CoreFX (`Socket.Tasks.cs`) to `Socket`: - `int Read(Span<byte>)` - `Task<int> ReadAsync(byte[], int, int, CancellationToken)` - `ValueTask<int> ReadAsync(Memory<byte>, CancellationToken)` - `int ReadByte()` - `void Write(ReadOnlySpan<byte>)` - `Task WriteAsync(byte[], int, int, CancellationToken)` - `ValueTask WriteAsync(ReadOnlyMemory<byte>, CancellationToken)` - `void WriteByte(byte)` * remove internal unused `PooledStream` and `ConnectionPool` APIs. * bring new tests from CoreFX: - `System.Net.Sockets/tests/FunctionalTests/NetworkStreamTest.cs` - `System.Net.Sockets/tests/FunctionalTests/NetworkStreamTest.netcoreapp.cs` * corlib: add `System.IO.FileSystem` and `System.Net.Sockets` resources and update SR. * Update Socket.cs * [csproj] Update project files * Bump API snapshot submodule
Diffstat (limited to 'mcs/class/System')
-rw-r--r--mcs/class/System/System.Net.Sockets/Socket.cs112
-rw-r--r--mcs/class/System/System.Net.Sockets/SocketAsyncEventArgs.cs70
-rw-r--r--mcs/class/System/System.Net.Sockets/SocketAsyncResult.cs2
-rw-r--r--mcs/class/System/System.Net/ServicePoint.cs5
-rw-r--r--mcs/class/System/System.Net/ServicePoint.platformnotsupported.cs6
-rw-r--r--mcs/class/System/System.Net/WebConnection.cs16
-rw-r--r--mcs/class/System/System.csproj8
-rw-r--r--mcs/class/System/System_xtest.dll.sources3
-rw-r--r--mcs/class/System/common.sources10
-rw-r--r--mcs/class/System/corefx/NetworkStream.cs18
-rw-r--r--mcs/class/System/corefx/SocketAsyncEventArgs.cs169
11 files changed, 323 insertions, 96 deletions
diff --git a/mcs/class/System/System.Net.Sockets/Socket.cs b/mcs/class/System/System.Net.Sockets/Socket.cs
index b130853ff19..3c369158934 100644
--- a/mcs/class/System/System.Net.Sockets/Socket.cs
+++ b/mcs/class/System/System.Net.Sockets/Socket.cs
@@ -740,7 +740,7 @@ namespace System.Net.Sockets
sockares.CheckIfThrowDelayedException ();
- buffer = sockares.Buffer;
+ buffer = sockares.Buffer.ToArray ();
bytesTransferred = sockares.Total;
return sockares.AcceptedSocket;
@@ -1408,6 +1408,29 @@ namespace System.Net.Sockets
return ret;
}
+ int Receive (Memory<byte> buffer, int offset, int size, SocketFlags socketFlags, out SocketError errorCode)
+ {
+ ThrowIfDisposedAndClosed ();
+
+ int nativeError;
+ int ret;
+ unsafe {
+ using (var handle = buffer.Slice (offset, size).Pin ()) {
+ ret = Receive_internal (m_Handle, (byte*)handle.Pointer, size, socketFlags, out nativeError, is_blocking);
+ }
+ }
+
+ errorCode = (SocketError) nativeError;
+ if (errorCode != SocketError.Success && errorCode != SocketError.WouldBlock && errorCode != SocketError.InProgress) {
+ is_connected = false;
+ is_bound = false;
+ } else {
+ is_connected = true;
+ }
+
+ return ret;
+ }
+
[CLSCompliant (false)]
public int Receive (IList<ArraySegment<byte>> buffers, SocketFlags socketFlags, out SocketError errorCode)
{
@@ -1486,10 +1509,10 @@ namespace System.Net.Sockets
// LAME SPEC: the ArgumentException is never thrown, instead an NRE is
// thrown when e.Buffer and e.BufferList are null (works fine when one is
// set to a valid object)
- if (e.Buffer == null && e.BufferList == null)
+ if (e.MemoryBuffer.Equals (default) && e.BufferList == null)
throw new NullReferenceException ("Either e.Buffer or e.BufferList must be valid buffers.");
- if (e.Buffer == null) {
+ if (e.BufferList != null) {
InitSocketAsyncEventArgs (e, ReceiveAsyncCallback, e, SocketOperation.ReceiveGeneric);
e.socket_async_result.Buffers = e.BufferList;
@@ -1498,7 +1521,7 @@ namespace System.Net.Sockets
} else {
InitSocketAsyncEventArgs (e, ReceiveAsyncCallback, e, SocketOperation.Receive);
- e.socket_async_result.Buffer = e.Buffer;
+ e.socket_async_result.Buffer = e.MemoryBuffer;
e.socket_async_result.Offset = e.Offset;
e.socket_async_result.Size = e.Count;
@@ -1554,8 +1577,8 @@ namespace System.Net.Sockets
try {
unsafe {
- fixed (byte* pbuffer = sockares.Buffer) {
- total = Receive_internal (sockares.socket.m_Handle, &pbuffer[sockares.Offset], sockares.Size, sockares.SockFlags, out sockares.error, sockares.socket.is_blocking);
+ using (var pbuffer = sockares.Buffer.Slice (sockares.Offset, sockares.Size).Pin ()) {
+ total = Receive_internal (sockares.socket.m_Handle, (byte*)pbuffer.Pointer, sockares.Size, sockares.SockFlags, out sockares.error, sockares.socket.is_blocking);
}
}
} catch (Exception e) {
@@ -1709,6 +1732,44 @@ namespace System.Net.Sockets
return cnt;
}
+ int ReceiveFrom (Memory<byte> buffer, int offset, int size, SocketFlags socketFlags, ref EndPoint remoteEP, out SocketError errorCode)
+ {
+ SocketAddress sockaddr = remoteEP.Serialize();
+
+ int nativeError;
+ int cnt;
+ unsafe {
+ using (var handle = buffer.Slice (offset, size).Pin ()) {
+ cnt = ReceiveFrom_internal (m_Handle, (byte*)handle.Pointer, size, socketFlags, ref sockaddr, out nativeError, is_blocking);
+ }
+ }
+
+ errorCode = (SocketError) nativeError;
+ if (errorCode != SocketError.Success) {
+ if (errorCode != SocketError.WouldBlock && errorCode != SocketError.InProgress) {
+ is_connected = false;
+ } else if (errorCode == SocketError.WouldBlock && is_blocking) { // This might happen when ReceiveTimeout is set
+ errorCode = SocketError.TimedOut;
+ }
+
+ return 0;
+ }
+
+ is_connected = true;
+ is_bound = true;
+
+ /* If sockaddr is null then we're a connection oriented protocol and should ignore the
+ * remoteEP parameter (see MSDN documentation for Socket.ReceiveFrom(...) ) */
+ if (sockaddr != null) {
+ /* Stupidly, EndPoint.Create() is an instance method */
+ remoteEP = remoteEP.Create (sockaddr);
+ }
+
+ seed_endpoint = remoteEP;
+
+ return cnt;
+ }
+
public bool ReceiveFromAsync (SocketAsyncEventArgs e)
{
ThrowIfDisposedAndClosed ();
@@ -1989,10 +2050,10 @@ namespace System.Net.Sockets
ThrowIfDisposedAndClosed ();
- if (e.Buffer == null && e.BufferList == null)
+ if (e.MemoryBuffer.Equals (default) && e.BufferList == null)
throw new NullReferenceException ("Either e.Buffer or e.BufferList must be valid buffers.");
- if (e.Buffer == null) {
+ if (e.BufferList != null) {
InitSocketAsyncEventArgs (e, SendAsyncCallback, e, SocketOperation.SendGeneric);
e.socket_async_result.Buffers = e.BufferList;
@@ -2001,7 +2062,7 @@ namespace System.Net.Sockets
} else {
InitSocketAsyncEventArgs (e, SendAsyncCallback, e, SocketOperation.Send);
- e.socket_async_result.Buffer = e.Buffer;
+ e.socket_async_result.Buffer = e.MemoryBuffer;
e.socket_async_result.Offset = e.Offset;
e.socket_async_result.Size = e.Count;
@@ -2059,8 +2120,8 @@ namespace System.Net.Sockets
try {
unsafe {
- fixed (byte *pbuffer = sockares.Buffer) {
- total = Socket.Send_internal (sockares.socket.m_Handle, &pbuffer[sockares.Offset], sockares.Size, sockares.SockFlags, out sockares.error, false);
+ using (var pbuffer = sockares.Buffer.Slice (sockares.Offset, sockares.Size).Pin ()) {
+ total = Socket.Send_internal (sockares.socket.m_Handle, (byte*)pbuffer.Pointer, sockares.Size, sockares.SockFlags, out sockares.error, false);
}
}
} catch (Exception e) {
@@ -2211,6 +2272,35 @@ namespace System.Net.Sockets
return ret;
}
+ int SendTo (Memory<byte> buffer, int offset, int size, SocketFlags socketFlags, EndPoint remoteEP)
+ {
+ ThrowIfDisposedAndClosed ();
+
+ if (remoteEP == null)
+ throw new ArgumentNullException("remoteEP");
+
+ int error;
+ int ret;
+ unsafe {
+ using (var pbuffer = buffer.Slice (offset, size).Pin ()) {
+ ret = SendTo_internal (m_Handle, (byte*)pbuffer.Pointer, size, socketFlags, remoteEP.Serialize (), out error, is_blocking);
+ }
+ }
+
+ SocketError err = (SocketError) error;
+ if (err != 0) {
+ if (err != SocketError.WouldBlock && err != SocketError.InProgress)
+ is_connected = false;
+ throw new SocketException (error);
+ }
+
+ is_connected = true;
+ is_bound = true;
+ seed_endpoint = remoteEP;
+
+ return ret;
+ }
+
public bool SendToAsync (SocketAsyncEventArgs e)
{
// NO check is made whether e != null in MS.NET (NRE is thrown in such case)
diff --git a/mcs/class/System/System.Net.Sockets/SocketAsyncEventArgs.cs b/mcs/class/System/System.Net.Sockets/SocketAsyncEventArgs.cs
index def7c46d6f3..69510e35ebf 100644
--- a/mcs/class/System/System.Net.Sockets/SocketAsyncEventArgs.cs
+++ b/mcs/class/System/System.Net.Sockets/SocketAsyncEventArgs.cs
@@ -36,7 +36,7 @@ using System.Threading;
namespace System.Net.Sockets
{
- public class SocketAsyncEventArgs : EventArgs, IDisposable
+ public partial class SocketAsyncEventArgs : EventArgs, IDisposable
{
bool disposed;
@@ -56,33 +56,11 @@ namespace System.Net.Sockets
set;
}
- public byte[] Buffer {
- get;
- private set;
- }
-
- public Memory<byte> MemoryBuffer => Buffer;
-
- IList<ArraySegment<byte>> m_BufferList;
- public IList<ArraySegment<byte>> BufferList {
- get { return m_BufferList; }
- set {
- if (Buffer != null && value != null)
- throw new ArgumentException ("Buffer and BufferList properties cannot both be non-null.");
- m_BufferList = value;
- }
- }
-
public int BytesTransferred {
get;
private set;
}
- public int Count {
- get;
- private set;
- }
-
public bool DisconnectReuseSocket {
get;
set;
@@ -93,11 +71,6 @@ namespace System.Net.Sockets
private set;
}
- public int Offset {
- get;
- private set;
- }
-
public EndPoint RemoteEndPoint {
get { return remote_ep; }
set { remote_ep = value; }
@@ -157,6 +130,10 @@ namespace System.Net.Sockets
SendPacketsSendSize = -1;
}
+ internal SocketAsyncEventArgs (bool flowExecutionContext)
+ {
+ }
+
~SocketAsyncEventArgs ()
{
Dispose (false);
@@ -221,43 +198,6 @@ namespace System.Net.Sockets
handler (e.current_socket, e);
}
- internal void CopyBufferFrom (SocketAsyncEventArgs source)
- {
- Buffer = source.Buffer;
- Offset = source.Offset;
- Count = source.Count;
- }
-
- public void SetBuffer (int offset, int count)
- {
- SetBuffer (Buffer, offset, count);
- }
-
- public void SetBuffer (byte[] buffer, int offset, int count)
- {
- if (buffer != null) {
- if (BufferList != null)
- throw new ArgumentException ("Buffer and BufferList properties cannot both be non-null.");
-
- int buflen = buffer.Length;
- if (offset < 0 || (offset != 0 && offset >= buflen))
- throw new ArgumentOutOfRangeException ("offset");
-
- if (count < 0 || count > buflen - offset)
- throw new ArgumentOutOfRangeException ("count");
-
- Count = count;
- Offset = offset;
- }
-
- Buffer = buffer;
- }
-
- public void SetBuffer(Memory<byte> buffer)
- {
- SetBuffer(buffer.ToArray(), 0, buffer.Length);
- }
-
internal void StartOperationCommon (Socket socket)
{
current_socket = socket;
diff --git a/mcs/class/System/System.Net.Sockets/SocketAsyncResult.cs b/mcs/class/System/System.Net.Sockets/SocketAsyncResult.cs
index 4004e475854..99c940d4afe 100644
--- a/mcs/class/System/System.Net.Sockets/SocketAsyncResult.cs
+++ b/mcs/class/System/System.Net.Sockets/SocketAsyncResult.cs
@@ -43,7 +43,7 @@ namespace System.Net.Sockets
Exception DelayedException;
public EndPoint EndPoint; // Connect,ReceiveFrom,SendTo
- public byte [] Buffer; // Receive,ReceiveFrom,Send,SendTo
+ public Memory<byte> Buffer; // Receive,ReceiveFrom,Send,SendTo
public int Offset; // Receive,ReceiveFrom,Send,SendTo
public int Size; // Receive,ReceiveFrom,Send,SendTo
public SocketFlags SockFlags; // Receive,ReceiveFrom,Send,SendTo
diff --git a/mcs/class/System/System.Net/ServicePoint.cs b/mcs/class/System/System.Net/ServicePoint.cs
index 4e59aa35372..2a501abcf82 100644
--- a/mcs/class/System/System.Net/ServicePoint.cs
+++ b/mcs/class/System/System.Net/ServicePoint.cs
@@ -392,11 +392,6 @@ namespace System.Net
return true;
}
}
-
- internal Socket GetConnection(PooledStream PooledStream, object owner, bool async, out IPAddress address, ref Socket abortSocket, ref Socket abortSocket6)
- {
- throw new NotImplementedException ();
- }
}
}
diff --git a/mcs/class/System/System.Net/ServicePoint.platformnotsupported.cs b/mcs/class/System/System.Net/ServicePoint.platformnotsupported.cs
index d744a556442..3380a29c65b 100644
--- a/mcs/class/System/System.Net/ServicePoint.platformnotsupported.cs
+++ b/mcs/class/System/System.Net/ServicePoint.platformnotsupported.cs
@@ -117,11 +117,5 @@ namespace System.Net
public X509Certificate ClientCertificate {
get { throw new PlatformNotSupportedException (EXCEPTION_MESSAGE); }
}
-
- // For reference source
- internal Socket GetConnection(PooledStream PooledStream, object owner, bool async, out IPAddress address, ref Socket abortSocket, ref Socket abortSocket6)
- {
- throw new NotImplementedException ();
- }
}
}
diff --git a/mcs/class/System/System.Net/WebConnection.cs b/mcs/class/System/System.Net/WebConnection.cs
index 5fd7e013a90..a6e6daf20ae 100644
--- a/mcs/class/System/System.Net/WebConnection.cs
+++ b/mcs/class/System/System.Net/WebConnection.cs
@@ -166,7 +166,21 @@ namespace System.Net
} else {
try {
operation.ThrowIfDisposed (cancellationToken);
- await socket.ConnectAsync (remote).ConfigureAwait (false);
+
+ /*
+ * Socket.Tasks.cs from CoreFX introduces a new internal
+ * BeginConnect(EndPoint) overload, which will replace
+ * the one we're using from SocketTaskExtensions.cs.
+ *
+ * Our implementation of Socket.BeginConnect() does not
+ * invoke the callback when the request failed synchronously.
+ *
+ * Explicitly use our implementation from SocketTaskExtensions.cs here.
+ */
+ await Task.Factory.FromAsync (
+ (targetEndPoint, callback, state) => ((Socket)state).BeginConnect (targetEndPoint, callback, state),
+ asyncResult => ((Socket)asyncResult.AsyncState).EndConnect (asyncResult),
+ remote, socket).ConfigureAwait (false);
} catch (ObjectDisposedException) {
throw;
} catch (Exception exc) {
diff --git a/mcs/class/System/System.csproj b/mcs/class/System/System.csproj
index 6223dd758bb..725075883ab 100644
--- a/mcs/class/System/System.csproj
+++ b/mcs/class/System/System.csproj
@@ -154,6 +154,7 @@
<Compile Include="..\..\..\external\corefx\src\Common\src\System\Net\Mail\QuotedStringFormatReader.cs" />
<Compile Include="..\..\..\external\corefx\src\Common\src\System\Net\Mail\WhitespaceReader.cs" />
<Compile Include="..\..\..\external\corefx\src\Common\src\System\Net\NegotiationInfoClass.cs" />
+ <Compile Include="..\..\..\external\corefx\src\Common\src\System\Net\RangeValidationHelpers.cs" />
<Compile Include="..\..\..\external\corefx\src\Common\src\System\Net\SecurityProtocol.cs" />
<Compile Include="..\..\..\external\corefx\src\Common\src\System\Net\SecurityStatusPal.cs" />
<Compile Include="..\..\..\external\corefx\src\Common\src\System\Net\Security\CertificateHelper.cs" />
@@ -453,6 +454,8 @@
<Compile Include="..\..\..\external\corefx\src\System.Net.Primitives\src\System\Net\IPEndPoint.cs" />
<Compile Include="..\..\..\external\corefx\src\System.Net.ServicePoint\src\System\Net\SecurityProtocolType.cs" />
<Compile Include="..\..\..\external\corefx\src\System.Net.Sockets\src\System\Net\Sockets\MultipleConnectAsync.cs" />
+ <Compile Include="..\..\..\external\corefx\src\System.Net.Sockets\src\System\Net\Sockets\NetworkStream.cs" />
+ <Compile Include="..\..\..\external\corefx\src\System.Net.Sockets\src\System\Net\Sockets\Socket.Tasks.cs" />
<Compile Include="..\..\..\external\corefx\src\System.Net.WebClient\src\System\Net\WebClient.cs" />
<Compile Include="..\..\..\external\corefx\src\System.Net.WebSockets.Client\src\System\Net\WebSockets\ClientWebSocket.cs" />
<Compile Include="..\..\..\external\corefx\src\System.Net.WebSockets.Client\src\System\Net\WebSockets\ClientWebSocketOptions.cs" />
@@ -699,7 +702,6 @@
<Compile Include="..\referencesource\System\net\System\Net\Sockets\IPProtectionLevel.cs" />
<Compile Include="..\referencesource\System\net\System\Net\Sockets\LingerOption.cs" />
<Compile Include="..\referencesource\System\net\System\Net\Sockets\MulticastOption.cs" />
- <Compile Include="..\referencesource\System\net\System\Net\Sockets\NetworkStream.cs" />
<Compile Include="..\referencesource\System\net\System\Net\Sockets\ProtocolFamily.cs" />
<Compile Include="..\referencesource\System\net\System\Net\Sockets\ProtocolType.cs" />
<Compile Include="..\referencesource\System\net\System\Net\Sockets\SelectMode.cs" />
@@ -735,7 +737,6 @@
<Compile Include="..\referencesource\System\net\System\Net\_LazyAsyncResult.cs" />
<Compile Include="..\referencesource\System\net\System\Net\_LoggingObject.cs" />
<Compile Include="..\referencesource\System\net\System\Net\_NetRes.cs" />
- <Compile Include="..\referencesource\System\net\System\Net\_PooledStream.cs" />
<Compile Include="..\referencesource\System\net\System\Net\_ProxyChain.cs" />
<Compile Include="..\referencesource\System\net\System\Net\_ScatterGatherBuffers.cs" />
<Compile Include="..\referencesource\System\net\System\Net\_Semaphore.cs" />
@@ -743,7 +744,6 @@
<Compile Include="..\referencesource\System\net\System\Net\_TimerThread.cs" />
<Compile Include="..\referencesource\System\net\System\Net\_WebProxyDataBuilder.cs" />
<Compile Include="..\referencesource\System\net\System\Net\_emptywebproxy.cs" />
- <Compile Include="..\referencesource\System\net\System\Net\connectionpool.cs" />
<Compile Include="..\referencesource\System\net\System\Net\cookie.cs" />
<Compile Include="..\referencesource\System\net\System\Net\cookiecollection.cs" />
<Compile Include="..\referencesource\System\net\System\Net\cookiecontainer.cs" />
@@ -1014,6 +1014,8 @@
<Compile Include="System\UriTypeConverter.cs" />
<Compile Include="corefx\CertificateRequest.cs" />
<Compile Include="corefx\NameValueCollection.cs" />
+ <Compile Include="corefx\NetworkStream.cs" />
+ <Compile Include="corefx\SocketAsyncEventArgs.cs" />
<Compile Include="corefx\StringDictionary.cs" />
<Compile Include="corefx\X509SignatureGenerator.cs" />
<Compile Include="corefx\ZLibNative.cs" />
diff --git a/mcs/class/System/System_xtest.dll.sources b/mcs/class/System/System_xtest.dll.sources
index 737cc2e6d5b..b96253754d5 100644
--- a/mcs/class/System/System_xtest.dll.sources
+++ b/mcs/class/System/System_xtest.dll.sources
@@ -1,6 +1,7 @@
../test-helpers/Configuration.Http.cs
../test-helpers/Configuration.Certificates.cs
../test-helpers/TestConfiguration.cs
+../test-helpers/NetworkStreamHelper.cs
../../../external/corefx/src/Common/tests/System/Threading/Tasks/TaskTimeoutExtensions.cs
@@ -96,6 +97,8 @@ System/RemoteExecutorTests.cs
../../../external/corefx/src/Common/tests/System/Net/Sockets/SocketTestServerAPM.cs
../../../external/corefx/src/Common/tests/System/Net/Sockets/SocketTestServerAsync.cs
../../../external/corefx/src/Common/tests/System/Net/Sockets/TestSettings.cs
+../../../external/corefx/src/System.Net.Sockets/tests/FunctionalTests/NetworkStreamTest.cs
+../../../external/corefx/src/System.Net.Sockets/tests/FunctionalTests/NetworkStreamTest.netcoreapp.cs
#../../../external/corefx/src/System.Net.Sockets/tests/FunctionalTests/*.cs:NetworkStreamTest.netcoreapp.cs,SocketTestHelper.netcoreapp.cs,SendReceive.netcoreapp.cs,SocketAsyncEventArgsTest.cs,LoggingTest.cs,SendReceive.cs
# System.Net.Primitives
diff --git a/mcs/class/System/common.sources b/mcs/class/System/common.sources
index de785afbbe1..eda8e8cdf70 100644
--- a/mcs/class/System/common.sources
+++ b/mcs/class/System/common.sources
@@ -587,7 +587,6 @@ ReferenceSources/Win32Exception.cs
../referencesource/System/net/System/Net/_NetRes.cs
../referencesource/System/net/System/Net/_LazyAsyncResult.cs
../referencesource/System/net/System/Net/_LoggingObject.cs
-../referencesource/System/net/System/Net/_PooledStream.cs
../referencesource/System/net/System/Net/_ProxyChain.cs
../referencesource/System/net/System/Net/_ScatterGatherBuffers.cs
../referencesource/System/net/System/Net/_Semaphore.cs
@@ -602,7 +601,6 @@ ReferenceSources/Win32Exception.cs
../referencesource/System/net/System/Net/cookiecollection.cs
../referencesource/System/net/System/Net/cookiecontainer.cs
../referencesource/System/net/System/Net/cookieexception.cs
-../referencesource/System/net/System/Net/connectionpool.cs
../referencesource/System/net/System/Net/DnsEndPoint.cs
../referencesource/System/net/System/Net/EndPoint.cs
../referencesource/System/net/System/Net/FtpStatusCode.cs
@@ -663,18 +661,20 @@ ReferenceSources/Win32Exception.cs
../referencesource/System/net/System/Net/SecureProtocols/AuthenticatedStream.cs
../referencesource/System/net/System/Net/SecureProtocols/NegotiateEnumTypes.cs
-../../../external/corefx/src/System.Net.Sockets/src/System/Net/Sockets/MultipleConnectAsync.cs
../referencesource/System/net/System/Net/Sockets/AddressFamily.cs
../referencesource/System/net/System/Net/Sockets/IOControlCode.cs
../referencesource/System/net/System/Net/Sockets/IPPacketInformation.cs
../referencesource/System/net/System/Net/Sockets/IPProtectionLevel.cs
../referencesource/System/net/System/Net/Sockets/LingerOption.cs
+../../../external/corefx/src/System.Net.Sockets/src/System/Net/Sockets/MultipleConnectAsync.cs
../referencesource/System/net/System/Net/Sockets/MulticastOption.cs
-../referencesource/System/net/System/Net/Sockets/NetworkStream.cs
+# ../referencesource/System/net/System/Net/Sockets/NetworkStream.cs
+../../../external/corefx/src/System.Net.Sockets/src/System/Net/Sockets/NetworkStream.cs
../referencesource/System/net/System/Net/Sockets/ProtocolFamily.cs
../referencesource/System/net/System/Net/Sockets/ProtocolType.cs
../referencesource/System/net/System/Net/Sockets/SelectMode.cs
../referencesource/System/net/System/Net/Sockets/Socket.cs
+../../../external/corefx/src/System.Net.Sockets/src/System/Net/Sockets/Socket.Tasks.cs
../referencesource/System/net/System/Net/Sockets/SocketErrors.cs
../referencesource/System/net/System/Net/Sockets/SocketFlags.cs
../referencesource/System/net/System/Net/Sockets/SocketInformation.cs
@@ -810,6 +810,7 @@ ReferenceSources/Win32Exception.cs
../../../external/corefx/src/Common/src/System/Net/ExceptionCheck.cs
../../../external/corefx/src/Common/src/System/Net/HttpStatusDescription.cs
../../../external/corefx/src/Common/src/System/Net/NegotiationInfoClass.cs
+../../../external/corefx/src/Common/src/System/Net/RangeValidationHelpers.cs
../../../external/corefx/src/Common/src/System/Net/SecurityProtocol.cs
../../../external/corefx/src/Common/src/System/Net/SecurityStatusPal.cs
../../../external/corefx/src/Common/src/System/Net/UriScheme.cs
@@ -914,3 +915,4 @@ ReferenceSources/Win32Exception.cs
../../../external/corefx/src/System.Text.RegularExpressions/src/System/Collections/Generic/ValueListBuilder.Pop.cs
../../../external/corefx/src/System.Text.RegularExpressions/src/System/Collections/HashtableExtensions.cs
+
diff --git a/mcs/class/System/corefx/NetworkStream.cs b/mcs/class/System/corefx/NetworkStream.cs
new file mode 100644
index 00000000000..d18f8e51683
--- /dev/null
+++ b/mcs/class/System/corefx/NetworkStream.cs
@@ -0,0 +1,18 @@
+using System.Threading;
+using System.Threading.Tasks;
+
+namespace System.Net.Sockets
+{
+ partial class NetworkStream
+ {
+ internal Socket InternalSocket {
+ get {
+ Socket chkSocket = _streamSocket;
+ if (_cleanedUp || chkSocket == null)
+ throw new ObjectDisposedException (GetType ().FullName);
+
+ return chkSocket;
+ }
+ }
+ }
+}
diff --git a/mcs/class/System/corefx/SocketAsyncEventArgs.cs b/mcs/class/System/corefx/SocketAsyncEventArgs.cs
new file mode 100644
index 00000000000..ddc8793bbf8
--- /dev/null
+++ b/mcs/class/System/corefx/SocketAsyncEventArgs.cs
@@ -0,0 +1,169 @@
+using System;
+using System.Diagnostics;
+using System.Collections.Generic;
+using System.Runtime.InteropServices;
+using System.Reflection;
+using System.Security;
+using System.Threading;
+
+namespace System.Net.Sockets
+{
+ partial class SocketAsyncEventArgs
+ {
+ // Single buffer.
+ private Memory<byte> _buffer;
+ private int _offset;
+ private int _count;
+ private bool _bufferIsExplicitArray;
+
+ // BufferList property variables.
+ private IList<ArraySegment<byte>> _bufferList;
+ private List<ArraySegment<byte>> _bufferListInternal;
+
+ public byte[] Buffer
+ {
+ get
+ {
+ if (_bufferIsExplicitArray)
+ {
+ bool success = MemoryMarshal.TryGetArray(_buffer, out ArraySegment<byte> arraySegment);
+ Debug.Assert(success);
+ return arraySegment.Array;
+ }
+
+ return null;
+ }
+ }
+
+ public Memory<byte> MemoryBuffer => _buffer;
+
+ public int Offset => _offset;
+
+ public int Count => _count;
+
+ // NOTE: this property is mutually exclusive with Buffer.
+ // Setting this property with an existing non-null Buffer will throw.
+ public IList<ArraySegment<byte>> BufferList
+ {
+ get { return _bufferList; }
+ set
+ {
+ if (value != null)
+ {
+ if (!_buffer.Equals(default))
+ {
+ // Can't have both set
+ throw new ArgumentException(SR.Format(SR.net_ambiguousbuffers, nameof(Buffer)));
+ }
+
+ // Copy the user-provided list into our internal buffer list,
+ // so that we are not affected by subsequent changes to the list.
+ // We reuse the existing list so that we can avoid reallocation when possible.
+ int bufferCount = value.Count;
+ if (_bufferListInternal == null)
+ {
+ _bufferListInternal = new List<ArraySegment<byte>>(bufferCount);
+ }
+ else
+ {
+ _bufferListInternal.Clear();
+ }
+
+ for (int i = 0; i < bufferCount; i++)
+ {
+ ArraySegment<byte> buffer = value[i];
+ RangeValidationHelpers.ValidateSegment(buffer);
+ _bufferListInternal.Add(buffer);
+ }
+ }
+ else
+ {
+ _bufferListInternal?.Clear();
+ }
+
+ _bufferList = value;
+ }
+ }
+
+ public void SetBuffer(int offset, int count)
+ {
+ if (!_buffer.Equals(default))
+ {
+ if ((uint)offset > _buffer.Length)
+ {
+ throw new ArgumentOutOfRangeException(nameof(offset));
+ }
+ if ((uint)count > (_buffer.Length - offset))
+ {
+ throw new ArgumentOutOfRangeException(nameof(count));
+ }
+ if (!_bufferIsExplicitArray)
+ {
+ throw new InvalidOperationException(SR.InvalidOperation_BufferNotExplicitArray);
+ }
+
+ _offset = offset;
+ _count = count;
+ }
+ }
+
+ internal void CopyBufferFrom(SocketAsyncEventArgs source)
+ {
+ _buffer = source._buffer;
+ _offset = source._offset;
+ _count = source._count;
+ _bufferIsExplicitArray = source._bufferIsExplicitArray;
+ }
+
+ public void SetBuffer(byte[] buffer, int offset, int count)
+ {
+ if (buffer == null)
+ {
+ // Clear out existing buffer.
+ _buffer = default;
+ _offset = 0;
+ _count = 0;
+ _bufferIsExplicitArray = false;
+ }
+ else
+ {
+ // Can't have both Buffer and BufferList.
+ if (_bufferList != null)
+ {
+ throw new ArgumentException(SR.Format(SR.net_ambiguousbuffers, nameof(BufferList)));
+ }
+
+ // Offset and count can't be negative and the
+ // combination must be in bounds of the array.
+ if ((uint)offset > buffer.Length)
+ {
+ throw new ArgumentOutOfRangeException(nameof(offset));
+ }
+ if ((uint)count > (buffer.Length - offset))
+ {
+ throw new ArgumentOutOfRangeException(nameof(count));
+ }
+
+ _buffer = buffer;
+ _offset = offset;
+ _count = count;
+ _bufferIsExplicitArray = true;
+ }
+ }
+
+ public void SetBuffer(Memory<byte> buffer)
+ {
+ if (buffer.Length != 0 && _bufferList != null)
+ {
+ throw new ArgumentException(SR.Format(SR.net_ambiguousbuffers, nameof(BufferList)));
+ }
+
+ _buffer = buffer;
+ _offset = 0;
+ _count = buffer.Length;
+ _bufferIsExplicitArray = false;
+ }
+
+ internal bool HasMultipleBuffers => _bufferList != null;
+ }
+}