Commit 6af1811b authored by Marc Gravell's avatar Marc Gravell

all of the outbound changes

parent 5c31bb25
......@@ -7,7 +7,7 @@
<AssemblyOriginatorKeyFile>../StackExchange.Redis.snk</AssemblyOriginatorKeyFile>
<PackageId>$(AssemblyName)</PackageId>
<Authors>Stack Exchange, Inc.; marc.gravell</Authors>
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
<AllowUnsafeBlocks>true</AllowUnsafeBlocks>
<PackageReleaseNotes>https://stackexchange.github.io/StackExchange.Redis/ReleaseNotes</PackageReleaseNotes>
<PackageProjectUrl>https://github.com/StackExchange/StackExchange.Redis/</PackageProjectUrl>
......@@ -21,7 +21,7 @@
<DefaultLanguage>en-US</DefaultLanguage>
<IncludeSymbols>false</IncludeSymbols>
<LibraryTargetFrameworks>net45;net46;netstandard2.0</LibraryTargetFrameworks>
<LibraryTargetFrameworks>net46;netstandard2.0</LibraryTargetFrameworks>
<CoreFxVersion>4.5.0</CoreFxVersion>
<xUnitVersion>2.4.0-beta.2.build3981</xUnitVersion>
</PropertyGroup>
......
......@@ -18,7 +18,7 @@
</ItemGroup>
<PropertyGroup Condition=" '$(TargetFramework)' == 'net45' or '$(TargetFramework)' == 'net46'">
<DefineConstants>$(DefineConstants);FEATURE_SOCKET_MODE_POLL;FEATURE_PERFCOUNTER;</DefineConstants>
<DefineConstants>$(DefineConstants);FEATURE_PERFCOUNTER;</DefineConstants>
</PropertyGroup>
<ItemGroup>
......@@ -27,9 +27,9 @@
<PackageReference Include="System.Reflection.Emit.ILGeneration" Version="4.3.0" />
<PackageReference Include="System.Reflection.Emit.Lightweight" Version="4.3.0" />
<!--<PackageReference Include="System.Memory" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Memory" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Buffers" Version="$(CoreFxVersion)" />
<PackageReference Include="System.IO.Pipelines" Version="$(CoreFxVersion)" />
<PackageReference Include="Pipelines.Sockets.Unofficial" Version="0.2.0-alpha-001" />-->
<PackageReference Include="Pipelines.Sockets.Unofficial" Version="0.2.0-alpha-004" />
</ItemGroup>
</Project>
\ No newline at end of file
......@@ -5,6 +5,7 @@
using System.Runtime.CompilerServices;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
namespace StackExchange.Redis
{
......@@ -267,21 +268,19 @@ internal void KeepAlive()
}
}
internal void OnConnected(PhysicalConnection connection, TextWriter log)
internal async Task OnConnectedAsync(PhysicalConnection connection, TextWriter log)
{
Trace("OnConnected");
if (physical == connection && !isDisposed && ChangeState(State.Connecting, State.ConnectedEstablishing))
{
ServerEndPoint.OnEstablishing(connection, log);
await ServerEndPoint.OnEstablishingAsync(connection, log);
}
else
{
try
{
connection.Dispose();
}
catch
{ }
} catch { }
}
}
......@@ -552,7 +551,10 @@ internal bool WriteMessageDirect(PhysicalConnection tmp, Message next)
}
}
internal WriteResult WriteQueue(int maxWork)
[MethodImpl(MethodImplOptions.AggressiveInlining)]
static ValueTask<T> AsResult<T>(T value) => new ValueTask<T>(value);
internal async ValueTask<WriteResult> WriteQueueAsync(int maxWork)
{
bool weAreWriter = false;
PhysicalConnection conn = null;
......@@ -585,7 +587,7 @@ internal WriteResult WriteQueue(int maxWork)
Trace("Nothing to write; exiting");
if(count == 0)
{
conn.Flush(); // only flush on an empty run
await conn.FlushAsync(); // only flush on an empty run
return WriteResult.NothingToDo;
}
return WriteResult.QueueEmptyAfterWrite;
......@@ -604,7 +606,7 @@ internal WriteResult WriteQueue(int maxWork)
{
Trace("Work limit; exiting");
Trace(last != null, "Flushed up to: " + last);
conn.Flush();
await conn.FlushAsync();
break;
}
}
......
using System;
//using System;
namespace StackExchange.Redis
{
internal static class PlatformHelper
{
public static bool IsMono { get; } = Type.GetType("Mono.Runtime") != null;
//namespace StackExchange.Redis
//{
// internal static class PlatformHelper
// {
// public static bool IsMono { get; } = Type.GetType("Mono.Runtime") != null;
public static bool IsUnix { get; } = (int)Environment.OSVersion.Platform == 4
|| (int)Environment.OSVersion.Platform == 6
|| (int)Environment.OSVersion.Platform == 128;
// public static bool IsUnix { get; } = (int)Environment.OSVersion.Platform == 4
// || (int)Environment.OSVersion.Platform == 6
// || (int)Environment.OSVersion.Platform == 128;
public static SocketMode DefaultSocketMode = IsMono && IsUnix ? SocketMode.Async : SocketMode.Poll;
}
}
// public static SocketMode DefaultSocketMode = IsMono && IsUnix ? SocketMode.Async : SocketMode.Poll;
// }
//}
......@@ -2521,6 +2521,7 @@ public ScriptEvalMessage(int db, CommandFlags flags, byte[] hash, RedisKey[] key
: this(db, flags, RedisCommand.EVAL, null, hash, keys, values)
{
if (hash == null) throw new ArgumentNullException(nameof(hash));
if (hash.Length != ResultProcessor.ScriptLoadProcessor.Sha1HashLength) throw new ArgumentOutOfRangeException(nameof(hash), "Invalid hash length");
}
private ScriptEvalMessage(int db, CommandFlags flags, RedisCommand command, string script, byte[] hexHash, RedisKey[] keys, RedisValue[] values)
......@@ -2571,7 +2572,7 @@ internal override void WriteImpl(PhysicalConnection physical)
if (hexHash != null)
{
physical.WriteHeader(RedisCommand.EVALSHA, 2 + keys.Length + values.Length);
physical.WriteAsHex(hexHash);
physical.WriteSha1AsHex(hexHash);
}
else if (asciiHash != null)
{
......
using System;
using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;
......@@ -250,7 +250,7 @@ public IEnumerable<Message> GetMessages(PhysicalConnection connection)
{
// need to get those sent ASAP; if they are stuck in the buffers, we die
multiplexer.Trace("Flushing and waiting for precondition responses");
connection.Flush();
connection.FlushAsync().Wait();
if (Monitor.Wait(lastBox, multiplexer.TimeoutMilliseconds))
{
if (!AreAllConditionsSatisfied(multiplexer))
......@@ -297,7 +297,7 @@ public IEnumerable<Message> GetMessages(PhysicalConnection connection)
if (explicitCheckForQueued && lastBox != null)
{
multiplexer.Trace("Flushing and waiting for precondition+queued responses");
connection.Flush(); // make sure they get sent, so we can check for QUEUED (and the pre-conditions if necessary)
connection.FlushAsync().Wait(); // make sure they get sent, so we can check for QUEUED (and the pre-conditions if necessary)
if (Monitor.Wait(lastBox, multiplexer.TimeoutMilliseconds))
{
if (!AreAllConditionsSatisfied(multiplexer))
......@@ -475,4 +475,4 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
// return ExecuteTransactionAsync(flags);
// }
//}
}
\ No newline at end of file
}
......@@ -393,11 +393,13 @@ internal static bool IsSHA1(string script)
return script != null && sha1.IsMatch(script);
}
internal const int Sha1HashLength = 20;
internal static byte[] ParseSHA1(byte[] value)
{
if (value?.Length == 40)
if (value?.Length == Sha1HashLength * 2)
{
var tmp = new byte[20];
var tmp = new byte[Sha1HashLength];
int charIndex = 0;
for (int i = 0; i < tmp.Length; i++)
{
......@@ -412,9 +414,9 @@ internal static byte[] ParseSHA1(byte[] value)
internal static byte[] ParseSHA1(string value)
{
if (value?.Length == 40 && sha1.IsMatch(value))
if (value?.Length == (Sha1HashLength * 2) && sha1.IsMatch(value))
{
var tmp = new byte[20];
var tmp = new byte[Sha1HashLength];
int charIndex = 0;
for (int i = 0; i < tmp.Length; i++)
{
......@@ -442,7 +444,7 @@ protected override bool SetResultCore(PhysicalConnection connection, Message mes
{
case ResultType.BulkString:
var asciiHash = result.GetBlob();
if (asciiHash == null || asciiHash.Length != 40) return false;
if (asciiHash == null || asciiHash.Length != (Sha1HashLength * 2)) return false;
byte[] hash = null;
if (!message.IsInternalCall)
......
......@@ -450,19 +450,33 @@ internal bool IsSelectable(RedisCommand command)
return bridge?.IsConnected == true;
}
internal void OnEstablishing(PhysicalConnection connection, TextWriter log)
internal Task OnEstablishingAsync(PhysicalConnection connection, TextWriter log)
{
try
{
if (connection == null) return;
Handshake(connection, log);
if (connection == null) return Task.CompletedTask;
var handshake = HandshakeAsync(connection, log);
if (handshake.Status != TaskStatus.RanToCompletion)
return OnEstablishingAsyncAwaited(connection, handshake);
}
catch (Exception ex)
{
connection.RecordConnectionFailed(ConnectionFailureType.InternalFailure, ex);
}
return Task.CompletedTask;
}
async Task OnEstablishingAsyncAwaited(PhysicalConnection connection, Task handshake)
{
try
{
await handshake;
}
catch (Exception ex)
{
connection.RecordConnectionFailed(ConnectionFailureType.InternalFailure, ex);
}
}
internal void OnFullyEstablished(PhysicalConnection connection)
{
try
......@@ -627,13 +641,13 @@ private PhysicalBridge CreateBridge(ConnectionType type, TextWriter log)
return bridge;
}
private void Handshake(PhysicalConnection connection, TextWriter log)
private Task HandshakeAsync(PhysicalConnection connection, TextWriter log)
{
Multiplexer.LogLocked(log, "Server handshake");
if (connection == null)
{
Multiplexer.Trace("No connection!?");
return;
return Task.CompletedTask;
}
Message msg;
string password = Multiplexer.RawConfig.Password;
......@@ -684,7 +698,7 @@ private void Handshake(PhysicalConnection connection, TextWriter log)
}
}
Multiplexer.LogLocked(log, "Flushing outbound buffer");
connection.Flush();
return connection.FlushAsync();
}
private void SetConfig<T>(ref T field, T value, [CallerMemberName] string caller = null)
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment