Annotate System.Net.WebSockets for nullable reference types (#31875)
authorStephen Toub <stoub@microsoft.com>
Fri, 7 Feb 2020 11:16:59 +0000 (06:16 -0500)
committerGitHub <noreply@github.com>
Fri, 7 Feb 2020 11:16:59 +0000 (06:16 -0500)
13 files changed:
src/libraries/Common/src/System/Net/WebSockets/ManagedWebSocket.cs
src/libraries/Common/src/System/Net/WebSockets/WebSocketValidate.cs
src/libraries/System.Net.HttpListener/src/System.Net.HttpListener.csproj
src/libraries/System.Net.WebSockets.Client/src/System.Net.WebSockets.Client.csproj
src/libraries/System.Net.WebSockets.WebSocketProtocol/src/System.Net.WebSockets.WebSocketProtocol.csproj
src/libraries/System.Net.WebSockets/ref/System.Net.WebSockets.cs
src/libraries/System.Net.WebSockets/ref/System.Net.WebSockets.csproj
src/libraries/System.Net.WebSockets/src/System.Net.WebSockets.csproj
src/libraries/System.Net.WebSockets/src/System/Net/WebSockets/ManagedWebSocket.netcoreapp.cs
src/libraries/System.Net.WebSockets/src/System/Net/WebSockets/WebSocket.cs
src/libraries/System.Net.WebSockets/src/System/Net/WebSockets/WebSocketContext.cs
src/libraries/System.Net.WebSockets/src/System/Net/WebSockets/WebSocketException.cs
src/libraries/System.Net.WebSockets/src/System/Net/WebSockets/WebSocketReceiveResult.cs

index 9c76f6f..437c6ea 100644 (file)
@@ -33,7 +33,7 @@ namespace System.Net.WebSockets
         /// <param name="keepAliveInterval">The interval to use for keep-alive pings.</param>
         /// <returns>The created <see cref="ManagedWebSocket"/> instance.</returns>
         public static ManagedWebSocket CreateFromConnectedStream(
-            Stream stream, bool isServer, string subprotocol, TimeSpan keepAliveInterval)
+            Stream stream, bool isServer, string? subprotocol, TimeSpan keepAliveInterval)
         {
             return new ManagedWebSocket(stream, isServer, subprotocol, keepAliveInterval);
         }
@@ -74,9 +74,9 @@ namespace System.Net.WebSockets
         /// </summary>
         private readonly bool _isServer = false;
         /// <summary>The agreed upon subprotocol with the server.</summary>
-        private readonly string _subprotocol;
+        private readonly string? _subprotocol;
         /// <summary>Timer used to send periodic pings to the server, at the interval specified</summary>
-        private readonly Timer _keepAliveTimer;
+        private readonly Timer? _keepAliveTimer;
         /// <summary>CancellationTokenSource used to abort all current and future operations when anything is canceled or any error occurs.</summary>
         private readonly CancellationTokenSource _abortSource = new CancellationTokenSource();
         /// <summary>Buffer used for reading data from the network.</summary>
@@ -106,7 +106,7 @@ namespace System.Net.WebSockets
         /// <summary>The reason for the close, as sent by the server, or null if not yet closed.</summary>
         private WebSocketCloseStatus? _closeStatus = null;
         /// <summary>A description of the close reason as sent by the server, or null if not yet closed.</summary>
-        private string _closeStatusDescription = null;
+        private string? _closeStatusDescription = null;
 
         /// <summary>
         /// The last header received in a ReceiveAsync.  If ReceiveAsync got a header but then
@@ -133,7 +133,7 @@ namespace System.Net.WebSockets
         /// field to minimize needing to pass it around and to avoid it becoming a field on
         /// various async state machine objects.
         /// </summary>
-        private byte[] _sendBuffer;
+        private byte[]? _sendBuffer;
         /// <summary>
         /// Whether the last SendAsync had endOfMessage==false. We need to track this so that we
         /// can send the subsequent message with a continuation opcode if the last message was a fragment.
@@ -159,7 +159,7 @@ namespace System.Net.WebSockets
         /// <param name="isServer">true if this is the server-side of the connection; false if this is the client-side of the connection.</param>
         /// <param name="subprotocol">The agreed upon subprotocol for the connection.</param>
         /// <param name="keepAliveInterval">The interval to use for keep-alive pings.</param>
-        private ManagedWebSocket(Stream stream, bool isServer, string subprotocol, TimeSpan keepAliveInterval)
+        private ManagedWebSocket(Stream stream, bool isServer, string? subprotocol, TimeSpan keepAliveInterval)
         {
             Debug.Assert(StateUpdateLock != null, $"Expected {nameof(StateUpdateLock)} to be non-null");
             Debug.Assert(ReceiveAsyncLock != null, $"Expected {nameof(ReceiveAsyncLock)} to be non-null");
@@ -185,7 +185,7 @@ namespace System.Net.WebSockets
             // the CancellationTokenSource, and the lifetime of that CTS matches the lifetime of the registration.
             _abortSource.Token.UnsafeRegister(s =>
             {
-                var thisRef = (ManagedWebSocket)s;
+                var thisRef = (ManagedWebSocket)s!;
 
                 lock (thisRef.StateUpdateLock)
                 {
@@ -206,8 +206,8 @@ namespace System.Net.WebSockets
             {
                 _keepAliveTimer = new Timer(s =>
                 {
-                    var wr = (WeakReference<ManagedWebSocket>)s;
-                    if (wr.TryGetTarget(out ManagedWebSocket thisRef))
+                    var wr = (WeakReference<ManagedWebSocket>)s!;
+                    if (wr.TryGetTarget(out ManagedWebSocket? thisRef))
                     {
                         thisRef.SendKeepAliveFrameAsync();
                     }
@@ -240,11 +240,11 @@ namespace System.Net.WebSockets
 
         public override WebSocketCloseStatus? CloseStatus => _closeStatus;
 
-        public override string CloseStatusDescription => _closeStatusDescription;
+        public override string? CloseStatusDescription => _closeStatusDescription;
 
         public override WebSocketState State => _state;
 
-        public override string SubProtocol => _subprotocol;
+        public override string? SubProtocol => _subprotocol;
 
         public override Task SendAsync(ArraySegment<byte> buffer, WebSocketMessageType messageType, bool endOfMessage, CancellationToken cancellationToken)
         {
@@ -258,7 +258,7 @@ namespace System.Net.WebSockets
 
             WebSocketValidate.ValidateArraySegment(buffer, nameof(buffer));
 
-            return SendPrivateAsync((ReadOnlyMemory<byte>)buffer, messageType, endOfMessage, cancellationToken).AsTask();
+            return SendPrivateAsync(buffer, messageType, endOfMessage, cancellationToken).AsTask();
         }
 
         private ValueTask SendPrivateAsync(ReadOnlyMemory<byte> buffer, WebSocketMessageType messageType, bool endOfMessage, CancellationToken cancellationToken)
@@ -313,7 +313,7 @@ namespace System.Net.WebSockets
             }
         }
 
-        public override Task CloseAsync(WebSocketCloseStatus closeStatus, string statusDescription, CancellationToken cancellationToken)
+        public override Task CloseAsync(WebSocketCloseStatus closeStatus, string? statusDescription, CancellationToken cancellationToken)
         {
             WebSocketValidate.ValidateCloseStatus(closeStatus, statusDescription);
 
@@ -329,13 +329,13 @@ namespace System.Net.WebSockets
             return CloseAsyncPrivate(closeStatus, statusDescription, cancellationToken);
         }
 
-        public override Task CloseOutputAsync(WebSocketCloseStatus closeStatus, string statusDescription, CancellationToken cancellationToken)
+        public override Task CloseOutputAsync(WebSocketCloseStatus closeStatus, string? statusDescription, CancellationToken cancellationToken)
         {
             WebSocketValidate.ValidateCloseStatus(closeStatus, statusDescription);
             return CloseOutputAsyncCore(closeStatus, statusDescription, cancellationToken);
         }
 
-        private async Task CloseOutputAsyncCore(WebSocketCloseStatus closeStatus, string statusDescription, CancellationToken cancellationToken)
+        private async Task CloseOutputAsyncCore(WebSocketCloseStatus closeStatus, string? statusDescription, CancellationToken cancellationToken)
         {
             WebSocketValidate.ThrowIfInvalidState(_state, _disposed, s_validCloseOutputStates);
 
@@ -449,7 +449,7 @@ namespace System.Net.WebSockets
             try
             {
                 int sendBytes = WriteFrameToSendBuffer(opcode, endOfMessage, payloadBuffer.Span);
-                using (cancellationToken.Register(s => ((ManagedWebSocket)s).Abort(), this))
+                using (cancellationToken.Register(s => ((ManagedWebSocket)s!).Abort(), this))
                 {
                     await _stream.WriteAsync(new ReadOnlyMemory<byte>(_sendBuffer, 0, sendBytes), cancellationToken).ConfigureAwait(false);
                 }
@@ -472,6 +472,7 @@ namespace System.Net.WebSockets
         {
             // Ensure we have a _sendBuffer.
             AllocateSendBuffer(payloadBuffer.Length + MaxMessageHeaderLength);
+            Debug.Assert(_sendBuffer != null);
 
             // Write the message header data to the buffer.
             int headerLength;
@@ -632,7 +633,7 @@ namespace System.Net.WebSockets
             // those to be much less frequent (e.g. we should only get one close per websocket), and thus we can afford to pay
             // a bit more for readability and maintainability.
 
-            CancellationTokenRegistration registration = cancellationToken.Register(s => ((ManagedWebSocket)s).Abort(), this);
+            CancellationTokenRegistration registration = cancellationToken.Register(s => ((ManagedWebSocket)s!).Abort(), this);
             try
             {
                 while (true) // in case we get control frames that should be ignored from the user's perspective
@@ -666,7 +667,7 @@ namespace System.Net.WebSockets
                             }
                         }
 
-                        string headerErrorMessage = TryParseMessageHeaderFromReceiveBuffer(out header);
+                        string? headerErrorMessage = TryParseMessageHeaderFromReceiveBuffer(out header);
                         if (headerErrorMessage != null)
                         {
                             await CloseWithReceiveErrorAndThrowAsync(WebSocketCloseStatus.ProtocolError, WebSocketError.Faulted, headerErrorMessage).ConfigureAwait(false);
@@ -866,7 +867,7 @@ namespace System.Net.WebSockets
             {
                 const int WaitForCloseTimeoutMs = 1_000; // arbitrary amount of time to give the server (same as netfx)
                 using (var finalCts = new CancellationTokenSource(WaitForCloseTimeoutMs))
-                using (finalCts.Token.Register(s => ((ManagedWebSocket)s).Abort(), this))
+                using (finalCts.Token.Register(s => ((ManagedWebSocket)s!).Abort(), this))
                 {
                     try
                     {
@@ -957,7 +958,7 @@ namespace System.Net.WebSockets
         /// <param name="errorMessage">An optional error message to include in the thrown exception.</param>
         /// <param name="innerException">An optional inner exception to include in the thrown exception.</param>
         private async ValueTask CloseWithReceiveErrorAndThrowAsync(
-            WebSocketCloseStatus closeStatus, WebSocketError error, string errorMessage = null, Exception innerException = null)
+            WebSocketCloseStatus closeStatus, WebSocketError error, string? errorMessage = null, Exception? innerException = null)
         {
             // Close the connection if it hasn't already been closed
             if (!_sentCloseFrame)
@@ -977,7 +978,7 @@ namespace System.Net.WebSockets
         /// <summary>Parses a message header from the buffer.  This assumes the header is in the buffer.</summary>
         /// <param name="resultHeader">The read header.</param>
         /// <returns>null if a valid header was read; non-null containing the string error message to use if the header was invalid.</returns>
-        private string TryParseMessageHeaderFromReceiveBuffer(out MessageHeader resultHeader)
+        private string? TryParseMessageHeaderFromReceiveBuffer(out MessageHeader resultHeader)
         {
             Debug.Assert(_receiveBufferCount >= 2, $"Expected to at least have the first two bytes of the header.");
 
@@ -1078,7 +1079,7 @@ namespace System.Net.WebSockets
         /// <param name="closeStatus">The close status to send.</param>
         /// <param name="statusDescription">The close status description to send.</param>
         /// <param name="cancellationToken">The CancellationToken to use to cancel the websocket.</param>
-        private async Task CloseAsyncPrivate(WebSocketCloseStatus closeStatus, string statusDescription, CancellationToken cancellationToken)
+        private async Task CloseAsyncPrivate(WebSocketCloseStatus closeStatus, string? statusDescription, CancellationToken cancellationToken)
         {
             // Send the close message.  Skip sending a close frame if we're currently in a CloseSent state,
             // for example having just done a CloseOutputAsync.
@@ -1150,11 +1151,11 @@ namespace System.Net.WebSockets
         /// <param name="closeStatus">The close status to send.</param>
         /// <param name="closeStatusDescription">The close status description to send.</param>
         /// <param name="cancellationToken">The CancellationToken to use to cancel the websocket.</param>
-        private async ValueTask SendCloseFrameAsync(WebSocketCloseStatus closeStatus, string closeStatusDescription, CancellationToken cancellationToken)
+        private async ValueTask SendCloseFrameAsync(WebSocketCloseStatus closeStatus, string? closeStatusDescription, CancellationToken cancellationToken)
         {
             // Close payload is two bytes containing the close status followed by a UTF8-encoding of the status description, if it exists.
 
-            byte[] buffer = null;
+            byte[]? buffer = null;
             try
             {
                 int count = 2;
@@ -1266,7 +1267,7 @@ namespace System.Net.WebSockets
         /// <summary>Releases the send buffer to the pool.</summary>
         private void ReleaseSendBuffer()
         {
-            byte[] old = _sendBuffer;
+            byte[]? old = _sendBuffer;
             if (old != null)
             {
                 _sendBuffer = null;
@@ -1370,7 +1371,7 @@ namespace System.Net.WebSockets
         }
 
         /// <summary>Aborts the websocket and throws an exception if an existing operation is in progress.</summary>
-        private void ThrowIfOperationInProgress(bool operationCompleted, [CallerMemberName] string methodName = null)
+        private void ThrowIfOperationInProgress(bool operationCompleted, [CallerMemberName] string? methodName = null)
         {
             if (!operationCompleted)
             {
@@ -1379,7 +1380,7 @@ namespace System.Net.WebSockets
             }
         }
 
-        private void ThrowOperationInProgress(string methodName) => throw new InvalidOperationException(SR.Format(SR.net_Websockets_AlreadyOneOutstandingOperation, methodName));
+        private void ThrowOperationInProgress(string? methodName) => throw new InvalidOperationException(SR.Format(SR.net_Websockets_AlreadyOneOutstandingOperation, methodName));
 
         /// <summary>Creates an OperationCanceledException instance, using a default message and the specified inner exception and token.</summary>
         private static Exception CreateOperationCanceledException(Exception innerException, CancellationToken cancellationToken = default(CancellationToken))
@@ -1514,13 +1515,13 @@ namespace System.Net.WebSockets
         /// <typeparam name="TResult">The type of the result</typeparam>
         private interface IWebSocketReceiveResultGetter<TResult>
         {
-            TResult GetResult(int count, WebSocketMessageType messageType, bool endOfMessage, WebSocketCloseStatus? closeStatus, string closeDescription);
+            TResult GetResult(int count, WebSocketMessageType messageType, bool endOfMessage, WebSocketCloseStatus? closeStatus, string? closeDescription);
         }
 
         /// <summary><see cref="IWebSocketReceiveResultGetter{TResult}"/> implementation for <see cref="WebSocketReceiveResult"/>.</summary>
         private readonly struct WebSocketReceiveResultGetter : IWebSocketReceiveResultGetter<WebSocketReceiveResult>
         {
-            public WebSocketReceiveResult GetResult(int count, WebSocketMessageType messageType, bool endOfMessage, WebSocketCloseStatus? closeStatus, string closeDescription) =>
+            public WebSocketReceiveResult GetResult(int count, WebSocketMessageType messageType, bool endOfMessage, WebSocketCloseStatus? closeStatus, string? closeDescription) =>
                 new WebSocketReceiveResult(count, messageType, endOfMessage, closeStatus, closeDescription);
         }
     }
index 5dec3c0..aabc25c 100644 (file)
@@ -52,7 +52,7 @@ namespace System.Net.WebSockets
                 throw new ArgumentException(SR.net_WebSockets_InvalidEmptySubProtocol, nameof(subProtocol));
             }
 
-            string invalidChar = null;
+            string? invalidChar = null;
             int i = 0;
             while (i < subProtocol.Length)
             {
@@ -79,7 +79,7 @@ namespace System.Net.WebSockets
             }
         }
 
-        internal static void ValidateCloseStatus(WebSocketCloseStatus closeStatus, string statusDescription)
+        internal static void ValidateCloseStatus(WebSocketCloseStatus closeStatus, string? statusDescription)
         {
             if (closeStatus == WebSocketCloseStatus.Empty && !string.IsNullOrEmpty(statusDescription))
             {
index 88ad375..d88ccb1 100644 (file)
@@ -3,6 +3,7 @@
     <AllowUnsafeBlocks>true</AllowUnsafeBlocks>
     <ForceManagedImplementation>false</ForceManagedImplementation>
     <TargetFrameworks>$(NetCoreAppCurrent)-Windows_NT;$(NetCoreAppCurrent)-Unix</TargetFrameworks>
+    <Nullable>annotations</Nullable>
   </PropertyGroup>
   <ItemGroup>
     <Reference Include="Microsoft.Win32.Primitives" />
index cda0e92..d30e94f 100644 (file)
@@ -3,6 +3,7 @@
     <AllowUnsafeBlocks>True</AllowUnsafeBlocks>
     <NoWarn>$(NoWarn);CS1573</NoWarn>
     <TargetFrameworks>$(NetCoreAppCurrent)-Unix;$(NetCoreAppCurrent)-Windows_NT</TargetFrameworks>
+    <Nullable>annotations</Nullable>
   </PropertyGroup>
   <ItemGroup>
     <Compile Include="System\Net\WebSockets\ClientWebSocket.cs" />
index b52987f..34e3482 100644 (file)
@@ -5,6 +5,7 @@
     <NoWarn>$(NoWarn);CS1573</NoWarn>
     <TargetFrameworks>netstandard2.0;netcoreapp2.1;$(NetCoreAppCurrent)</TargetFrameworks>
     <ExcludeCurrentNetCoreApp>true</ExcludeCurrentNetCoreApp>
+    <Nullable>annotations</Nullable>
   </PropertyGroup>
   <ItemGroup>
     <Compile Include="$(CommonPath)System\Net\WebSockets\ManagedWebSocket.cs">
index 3d8d700..3d62936 100644 (file)
@@ -19,17 +19,17 @@ namespace System.Net.WebSockets
     {
         protected WebSocket() { }
         public abstract System.Net.WebSockets.WebSocketCloseStatus? CloseStatus { get; }
-        public abstract string CloseStatusDescription { get; }
+        public abstract string? CloseStatusDescription { get; }
         public static System.TimeSpan DefaultKeepAliveInterval { get { throw null; } }
         public abstract System.Net.WebSockets.WebSocketState State { get; }
-        public abstract string SubProtocol { get; }
+        public abstract string? SubProtocol { get; }
         public abstract void Abort();
-        public abstract System.Threading.Tasks.Task CloseAsync(System.Net.WebSockets.WebSocketCloseStatus closeStatus, string statusDescription, System.Threading.CancellationToken cancellationToken);
-        public abstract System.Threading.Tasks.Task CloseOutputAsync(System.Net.WebSockets.WebSocketCloseStatus closeStatus, string statusDescription, System.Threading.CancellationToken cancellationToken);
+        public abstract System.Threading.Tasks.Task CloseAsync(System.Net.WebSockets.WebSocketCloseStatus closeStatus, string? statusDescription, System.Threading.CancellationToken cancellationToken);
+        public abstract System.Threading.Tasks.Task CloseOutputAsync(System.Net.WebSockets.WebSocketCloseStatus closeStatus, string? statusDescription, System.Threading.CancellationToken cancellationToken);
         public static System.ArraySegment<byte> CreateClientBuffer(int receiveBufferSize, int sendBufferSize) { throw null; }
         [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Never)]
         public static System.Net.WebSockets.WebSocket CreateClientWebSocket(System.IO.Stream innerStream, string subProtocol, int receiveBufferSize, int sendBufferSize, System.TimeSpan keepAliveInterval, bool useZeroMaskingKey, System.ArraySegment<byte> internalBuffer) { throw null; }
-        public static System.Net.WebSockets.WebSocket CreateFromStream(System.IO.Stream stream, bool isServer, string subProtocol, System.TimeSpan keepAliveInterval) { throw null; }
+        public static System.Net.WebSockets.WebSocket CreateFromStream(System.IO.Stream stream, bool isServer, string? subProtocol, System.TimeSpan keepAliveInterval) { throw null; }
         public static System.ArraySegment<byte> CreateServerBuffer(int receiveBufferSize) { throw null; }
         public abstract void Dispose();
         [System.ComponentModel.EditorBrowsableAttribute(System.ComponentModel.EditorBrowsableState.Never)]
@@ -70,7 +70,7 @@ namespace System.Net.WebSockets
         public abstract string SecWebSocketKey { get; }
         public abstract System.Collections.Generic.IEnumerable<string> SecWebSocketProtocols { get; }
         public abstract string SecWebSocketVersion { get; }
-        public abstract System.Security.Principal.IPrincipal User { get; }
+        public abstract System.Security.Principal.IPrincipal? User { get; }
         public abstract System.Net.WebSockets.WebSocket WebSocket { get; }
     }
     public enum WebSocketError
@@ -90,18 +90,18 @@ namespace System.Net.WebSockets
     {
         public WebSocketException() { }
         public WebSocketException(int nativeError) { }
-        public WebSocketException(int nativeError, System.Exception innerException) { }
-        public WebSocketException(int nativeError, string message) { }
+        public WebSocketException(int nativeError, System.Exception? innerException) { }
+        public WebSocketException(int nativeError, string? message) { }
         public WebSocketException(System.Net.WebSockets.WebSocketError error) { }
-        public WebSocketException(System.Net.WebSockets.WebSocketError error, System.Exception innerException) { }
+        public WebSocketException(System.Net.WebSockets.WebSocketError error, System.Exception? innerException) { }
         public WebSocketException(System.Net.WebSockets.WebSocketError error, int nativeError) { }
-        public WebSocketException(System.Net.WebSockets.WebSocketError error, int nativeError, System.Exception innerException) { }
-        public WebSocketException(System.Net.WebSockets.WebSocketError error, int nativeError, string message) { }
-        public WebSocketException(System.Net.WebSockets.WebSocketError error, int nativeError, string message, System.Exception innerException) { }
-        public WebSocketException(System.Net.WebSockets.WebSocketError error, string message) { }
-        public WebSocketException(System.Net.WebSockets.WebSocketError error, string message, System.Exception innerException) { }
-        public WebSocketException(string message) { }
-        public WebSocketException(string message, System.Exception innerException) { }
+        public WebSocketException(System.Net.WebSockets.WebSocketError error, int nativeError, System.Exception? innerException) { }
+        public WebSocketException(System.Net.WebSockets.WebSocketError error, int nativeError, string? message) { }
+        public WebSocketException(System.Net.WebSockets.WebSocketError error, int nativeError, string? message, System.Exception? innerException) { }
+        public WebSocketException(System.Net.WebSockets.WebSocketError error, string? message) { }
+        public WebSocketException(System.Net.WebSockets.WebSocketError error, string? message, System.Exception? innerException) { }
+        public WebSocketException(string? message) { }
+        public WebSocketException(string? message, System.Exception? innerException) { }
         public override int ErrorCode { get { throw null; } }
         public System.Net.WebSockets.WebSocketError WebSocketErrorCode { get { throw null; } }
         public override void GetObjectData(System.Runtime.Serialization.SerializationInfo info, System.Runtime.Serialization.StreamingContext context) { }
@@ -117,7 +117,7 @@ namespace System.Net.WebSockets
         public WebSocketReceiveResult(int count, System.Net.WebSockets.WebSocketMessageType messageType, bool endOfMessage) { }
         public WebSocketReceiveResult(int count, System.Net.WebSockets.WebSocketMessageType messageType, bool endOfMessage, System.Net.WebSockets.WebSocketCloseStatus? closeStatus, string closeStatusDescription) { }
         public System.Net.WebSockets.WebSocketCloseStatus? CloseStatus { get { throw null; } }
-        public string CloseStatusDescription { get { throw null; } }
+        public string? CloseStatusDescription { get { throw null; } }
         public int Count { get { throw null; } }
         public bool EndOfMessage { get { throw null; } }
         public System.Net.WebSockets.WebSocketMessageType MessageType { get { throw null; } }
index b6bbab0..134ea19 100644 (file)
@@ -1,6 +1,7 @@
 <Project Sdk="Microsoft.NET.Sdk">
   <PropertyGroup>
     <TargetFrameworks>$(NetCoreAppCurrent)</TargetFrameworks>
+    <Nullable>enable</Nullable>
   </PropertyGroup>
   <ItemGroup>
     <Compile Include="System.Net.WebSockets.cs" />
index f5a7375..06f9a2c 100644 (file)
@@ -4,6 +4,7 @@
     <AllowUnsafeBlocks>True</AllowUnsafeBlocks>
     <NoWarn>$(NoWarn);CS1573</NoWarn>
     <TargetFrameworks>$(NetCoreAppCurrent)</TargetFrameworks>
+    <Nullable>enable</Nullable>
   </PropertyGroup>
   <ItemGroup>
     <Compile Include="System\Net\WebSockets\ManagedWebSocket.netcoreapp.cs" />
index e923c94..8b0e680 100644 (file)
@@ -67,7 +67,7 @@ namespace System.Net.WebSockets
         /// <summary><see cref="IWebSocketReceiveResultGetter{TResult}"/> implementation for <see cref="ValueWebSocketReceiveResult"/>.</summary>
         private readonly struct ValueWebSocketReceiveResultGetter : IWebSocketReceiveResultGetter<ValueWebSocketReceiveResult>
         {
-            public ValueWebSocketReceiveResult GetResult(int count, WebSocketMessageType messageType, bool endOfMessage, WebSocketCloseStatus? closeStatus, string closeDescription) =>
+            public ValueWebSocketReceiveResult GetResult(int count, WebSocketMessageType messageType, bool endOfMessage, WebSocketCloseStatus? closeStatus, string? closeDescription) =>
                 new ValueWebSocketReceiveResult(count, messageType, endOfMessage); // closeStatus/closeDescription are ignored
         }
     }
index 16bcbca..04873fb 100644 (file)
@@ -14,16 +14,16 @@ namespace System.Net.WebSockets
     public abstract class WebSocket : IDisposable
     {
         public abstract WebSocketCloseStatus? CloseStatus { get; }
-        public abstract string CloseStatusDescription { get; }
-        public abstract string SubProtocol { get; }
+        public abstract string? CloseStatusDescription { get; }
+        public abstract string? SubProtocol { get; }
         public abstract WebSocketState State { get; }
 
         public abstract void Abort();
         public abstract Task CloseAsync(WebSocketCloseStatus closeStatus,
-            string statusDescription,
+            string? statusDescription,
             CancellationToken cancellationToken);
         public abstract Task CloseOutputAsync(WebSocketCloseStatus closeStatus,
-            string statusDescription,
+            string? statusDescription,
             CancellationToken cancellationToken);
         public abstract void Dispose();
         public abstract Task<WebSocketReceiveResult> ReceiveAsync(ArraySegment<byte> buffer,
@@ -134,7 +134,7 @@ namespace System.Net.WebSockets
         /// <param name="subProtocol">The agreed upon sub-protocol that was used when creating the connection.</param>
         /// <param name="keepAliveInterval">The keep-alive interval to use, or <see cref="Timeout.InfiniteTimeSpan"/> to disable keep-alives.</param>
         /// <returns>The created <see cref="WebSocket"/>.</returns>
-        public static WebSocket CreateFromStream(Stream stream, bool isServer, string subProtocol, TimeSpan keepAliveInterval)
+        public static WebSocket CreateFromStream(Stream stream, bool isServer, string? subProtocol, TimeSpan keepAliveInterval)
         {
             if (stream == null)
             {
@@ -175,7 +175,7 @@ namespace System.Net.WebSockets
 
         [EditorBrowsable(EditorBrowsableState.Never)]
         public static WebSocket CreateClientWebSocket(Stream innerStream,
-            string subProtocol, int receiveBufferSize, int sendBufferSize,
+            string? subProtocol, int receiveBufferSize, int sendBufferSize,
             TimeSpan keepAliveInterval, bool useZeroMaskingKey, ArraySegment<byte> internalBuffer)
         {
             if (innerStream == null)
index 7f21d26..4c4d58b 100644 (file)
@@ -17,7 +17,7 @@ namespace System.Net.WebSockets
         public abstract string SecWebSocketVersion { get; }
         public abstract string SecWebSocketKey { get; }
         public abstract CookieCollection CookieCollection { get; }
-        public abstract IPrincipal User { get; }
+        public abstract IPrincipal? User { get; }
         public abstract bool IsAuthenticated { get; }
         public abstract bool IsLocal { get; }
         public abstract bool IsSecureConnection { get; }
index e6838f3..7fe5265 100644 (file)
@@ -31,21 +31,21 @@ namespace System.Net.WebSockets
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(WebSocketError error, string message) : base(message)
+        public WebSocketException(WebSocketError error, string? message) : base(message)
         {
             _webSocketErrorCode = error;
         }
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(WebSocketError error, Exception innerException)
+        public WebSocketException(WebSocketError error, Exception? innerException)
             : this(error, GetErrorMessage(error), innerException)
         {
         }
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(WebSocketError error, string message, Exception innerException)
+        public WebSocketException(WebSocketError error, string? message, Exception? innerException)
             : base(message, innerException)
         {
             _webSocketErrorCode = error;
@@ -62,7 +62,7 @@ namespace System.Net.WebSockets
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(int nativeError, string message)
+        public WebSocketException(int nativeError, string? message)
             : base(nativeError, message)
         {
             _webSocketErrorCode = !Succeeded(nativeError) ? WebSocketError.NativeError : WebSocketError.Success;
@@ -71,7 +71,7 @@ namespace System.Net.WebSockets
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(int nativeError, Exception innerException)
+        public WebSocketException(int nativeError, Exception? innerException)
             : base(SR.net_WebSockets_Generic, innerException)
         {
             _webSocketErrorCode = !Succeeded(nativeError) ? WebSocketError.NativeError : WebSocketError.Success;
@@ -87,7 +87,7 @@ namespace System.Net.WebSockets
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(WebSocketError error, int nativeError, string message)
+        public WebSocketException(WebSocketError error, int nativeError, string? message)
             : base(message)
         {
             _webSocketErrorCode = error;
@@ -96,14 +96,14 @@ namespace System.Net.WebSockets
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(WebSocketError error, int nativeError, Exception innerException)
+        public WebSocketException(WebSocketError error, int nativeError, Exception? innerException)
             : this(error, nativeError, GetErrorMessage(error), innerException)
         {
         }
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(WebSocketError error, int nativeError, string message, Exception innerException)
+        public WebSocketException(WebSocketError error, int nativeError, string? message, Exception? innerException)
             : base(message, innerException)
         {
             _webSocketErrorCode = error;
@@ -112,14 +112,14 @@ namespace System.Net.WebSockets
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(string message)
+        public WebSocketException(string? message)
             : base(message)
         {
         }
 
         [SuppressMessage("Microsoft.Security", "CA2122:DoNotIndirectlyExposeMethodsWithLinkDemands",
             Justification = "This ctor is harmless, because it does not pass arbitrary data into the native code.")]
-        public WebSocketException(string message, Exception innerException)
+        public WebSocketException(string? message, Exception? innerException)
             : base(message, innerException)
         {
         }
index 2ce8955..ab1bf2a 100644 (file)
@@ -17,7 +17,7 @@ namespace System.Net.WebSockets
             WebSocketMessageType messageType,
             bool endOfMessage,
             WebSocketCloseStatus? closeStatus,
-            string closeStatusDescription)
+            string? closeStatusDescription)
         {
             if (count < 0)
             {
@@ -35,6 +35,6 @@ namespace System.Net.WebSockets
         public bool EndOfMessage { get; }
         public WebSocketMessageType MessageType { get; }
         public WebSocketCloseStatus? CloseStatus { get; }
-        public string CloseStatusDescription { get; }
+        public string? CloseStatusDescription { get; }
     }
 }