Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
S
StackExchange.Redis
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
tsai
StackExchange.Redis
Commits
c54c0671
Commit
c54c0671
authored
May 28, 2018
by
Nick Craver
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
PoC: Dropping netstandard1.x support
A demo of how much this saves in complexity.
parent
d7c72b05
Changes
32
Hide whitespace changes
Inline
Side-by-side
Showing
32 changed files
with
117 additions
and
588 deletions
+117
-588
BasicTest.csproj
BasicTest/BasicTest.csproj
+1
-5
Directory.build.props
Directory.build.props
+1
-1
NRediSearch.Test.csproj
NRediSearch.Test/NRediSearch.Test.csproj
+1
-1
StackExchange.Redis.StrongName.csproj
...ge.Redis.StrongName/StackExchange.Redis.StrongName.csproj
+2
-13
Config.cs
StackExchange.Redis.Tests/Booksleeve/Config.cs
+2
-6
Config.cs
StackExchange.Redis.Tests/Config.cs
+1
-5
Extensions.cs
StackExchange.Redis.Tests/Helpers/Extensions.cs
+0
-2
TestConfig.cs
StackExchange.Redis.Tests/Helpers/TestConfig.cs
+1
-4
MassiveOps.cs
StackExchange.Redis.Tests/MassiveOps.cs
+0
-10
Naming.cs
StackExchange.Redis.Tests/Naming.cs
+6
-49
Profiling.cs
StackExchange.Redis.Tests/Profiling.cs
+3
-6
PubSub.cs
StackExchange.Redis.Tests/PubSub.cs
+18
-30
StackExchange.Redis.Tests.csproj
StackExchange.Redis.Tests/StackExchange.Redis.Tests.csproj
+2
-11
TaskTests.cs
StackExchange.Redis.Tests/TaskTests.cs
+1
-5
TestBase.cs
StackExchange.Redis.Tests/TestBase.cs
+0
-13
StackExchange.Redis.csproj
StackExchange.Redis/StackExchange.Redis.csproj
+0
-11
BrowsableAttribute.cs
...ge.Redis/StackExchange/Redis/Compat/BrowsableAttribute.cs
+0
-15
ConvertHelper.cs
...xchange.Redis/StackExchange/Redis/Compat/ConvertHelper.cs
+0
-30
VolatileWrapper.cs
...hange.Redis/StackExchange/Redis/Compat/VolatileWrapper.cs
+0
-23
ConfigurationOptions.cs
...xchange.Redis/StackExchange/Redis/ConfigurationOptions.cs
+3
-12
ConnectionMultiplexer.cs
...change.Redis/StackExchange/Redis/ConnectionMultiplexer.cs
+3
-23
Exceptions.cs
StackExchange.Redis/StackExchange/Redis/Exceptions.cs
+48
-67
ExtensionMethods.cs
StackExchange.Redis/StackExchange/Redis/ExtensionMethods.cs
+1
-10
PhysicalBridge.cs
StackExchange.Redis/StackExchange/Redis/PhysicalBridge.cs
+1
-1
PhysicalConnection.cs
...kExchange.Redis/StackExchange/Redis/PhysicalConnection.cs
+9
-93
RedisResult.cs
StackExchange.Redis/StackExchange/Redis/RedisResult.cs
+8
-8
RedisValue.cs
StackExchange.Redis/StackExchange/Redis/RedisValue.cs
+3
-55
ResultBox.cs
StackExchange.Redis/StackExchange/Redis/ResultBox.cs
+0
-4
ScriptParameterMapper.cs
...change.Redis/StackExchange/Redis/ScriptParameterMapper.cs
+0
-12
ServerEndPoint.cs
StackExchange.Redis/StackExchange/Redis/ServerEndPoint.cs
+1
-1
SocketManager.cs
StackExchange.Redis/StackExchange/Redis/SocketManager.cs
+0
-53
TaskSource.cs
StackExchange.Redis/StackExchange/Redis/TaskSource.cs
+1
-9
No files found.
BasicTest/BasicTest.csproj
View file @
c54c0671
...
@@ -2,7 +2,7 @@
...
@@ -2,7 +2,7 @@
<PropertyGroup>
<PropertyGroup>
<Description>StackExchange.Redis.BasicTest .NET Core</Description>
<Description>StackExchange.Redis.BasicTest .NET Core</Description>
<TargetFrameworks>netcoreapp
1.1;netcoreapp
2.0</TargetFrameworks>
<TargetFrameworks>netcoreapp2.0</TargetFrameworks>
<AssemblyName>BasicTest</AssemblyName>
<AssemblyName>BasicTest</AssemblyName>
<OutputType>Exe</OutputType>
<OutputType>Exe</OutputType>
<PackageId>BasicTest</PackageId>
<PackageId>BasicTest</PackageId>
...
@@ -14,8 +14,4 @@
...
@@ -14,8 +14,4 @@
<ProjectReference Include="..\StackExchange.Redis\StackExchange.Redis.csproj" />
<ProjectReference Include="..\StackExchange.Redis\StackExchange.Redis.csproj" />
</ItemGroup>
</ItemGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'netcoreapp1.1' ">
<PackageReference Include="System.Console" Version="$(CoreFxVersion)" />
</ItemGroup>
</Project>
</Project>
Directory.build.props
View file @
c54c0671
...
@@ -22,7 +22,7 @@
...
@@ -22,7 +22,7 @@
<DefaultLanguage>en-US</DefaultLanguage>
<DefaultLanguage>en-US</DefaultLanguage>
<IncludeSymbols>false</IncludeSymbols>
<IncludeSymbols>false</IncludeSymbols>
<LibraryTargetFrameworks>net45;net46;netstandard
1.5;netstandard
2.0</LibraryTargetFrameworks>
<LibraryTargetFrameworks>net45;net46;netstandard2.0</LibraryTargetFrameworks>
<CoreFxVersion>4.3.0</CoreFxVersion>
<CoreFxVersion>4.3.0</CoreFxVersion>
<xUnitVersion>2.4.0-beta.2.build3981</xUnitVersion>
<xUnitVersion>2.4.0-beta.2.build3981</xUnitVersion>
</PropertyGroup>
</PropertyGroup>
...
...
NRediSearch.Test/NRediSearch.Test.csproj
View file @
c54c0671
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<PropertyGroup>
<OutputType>Library</OutputType>
<OutputType>Library</OutputType>
<TargetFrameworks>netcoreapp
1.1;netcoreapp
2.0</TargetFrameworks>
<TargetFrameworks>netcoreapp2.0</TargetFrameworks>
<GenerateDocumentationFile>false</GenerateDocumentationFile>
<GenerateDocumentationFile>false</GenerateDocumentationFile>
</PropertyGroup>
</PropertyGroup>
<ItemGroup>
<ItemGroup>
...
...
StackExchange.Redis.StrongName/StackExchange.Redis.StrongName.csproj
View file @
c54c0671
...
@@ -21,27 +21,16 @@
...
@@ -21,27 +21,16 @@
</ItemGroup>
</ItemGroup>
<PropertyGroup Condition=" '$(TargetFramework)' == 'net45' or '$(TargetFramework)' == 'net46'">
<PropertyGroup Condition=" '$(TargetFramework)' == 'net45' or '$(TargetFramework)' == 'net46'">
<DefineConstants>$(DefineConstants);FEATURE_S
ERIALIZATION;FEATURE_S
OCKET_MODE_POLL;FEATURE_PERFCOUNTER;FEATURE_THREADPOOL</DefineConstants>
<DefineConstants>$(DefineConstants);FEATURE_SOCKET_MODE_POLL;FEATURE_PERFCOUNTER;FEATURE_THREADPOOL</DefineConstants>
</PropertyGroup>
</PropertyGroup>
<ItemGroup>
<ItemGroup>
<PackageReference Include="System.IO.Compression" Version="$(CoreFxVersion)" />
<PackageReference Include="System.IO.Compression" Version="$(CoreFxVersion)" />
</ItemGroup>
</ItemGroup>
<PropertyGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' ">
<PropertyGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' ">
<DefineConstants>$(DefineConstants);FEATURE_
SERIALIZATION;FEATURE_
THREADPOOL</DefineConstants>
<DefineConstants>$(DefineConstants);FEATURE_THREADPOOL</DefineConstants>
</PropertyGroup>
</PropertyGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard1.5' ">
<PackageReference Include="System.Collections.NonGeneric" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Net.NameResolution" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Net.Security" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.Lightweight" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.TypeExtensions" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Threading.Thread" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Threading.ThreadPool" Version="$(CoreFxVersion)" />
</ItemGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' ">
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' ">
<PackageReference Include="System.Reflection.Emit.Lightweight" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.Lightweight" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.ILGeneration" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.ILGeneration" Version="$(CoreFxVersion)" />
...
...
StackExchange.Redis.Tests/Booksleeve/Config.cs
View file @
c54c0671
...
@@ -4,9 +4,7 @@
...
@@ -4,9 +4,7 @@
using
System.Threading.Tasks
;
using
System.Threading.Tasks
;
using
Xunit
;
using
Xunit
;
using
Xunit.Abstractions
;
using
Xunit.Abstractions
;
#if !NETCOREAPP1_0
using
System.Security.Authentication
;
using
System.Security.Authentication
;
#endif
namespace
StackExchange.Redis.Tests.Booksleeve
namespace
StackExchange.Redis.Tests.Booksleeve
{
{
...
@@ -106,8 +104,7 @@ public void CreateDisconnectedNonsenseConnection_DNS()
...
@@ -106,8 +104,7 @@ public void CreateDisconnectedNonsenseConnection_DNS()
Output
.
WriteLine
(
log
.
ToString
());
Output
.
WriteLine
(
log
.
ToString
());
}
}
}
}
#if !NETCOREAPP1_0
[
Fact
]
[
Fact
]
public
void
SslProtocols_SingleValue
()
public
void
SslProtocols_SingleValue
()
{
{
...
@@ -143,7 +140,6 @@ public void SslProtocols_InvalidValue()
...
@@ -143,7 +140,6 @@ public void SslProtocols_InvalidValue()
var
log
=
new
StringWriter
();
var
log
=
new
StringWriter
();
Assert
.
Throws
<
ArgumentOutOfRangeException
>(()
=>
ConfigurationOptions
.
Parse
(
"myhost,sslProtocols=InvalidSslProtocol"
));
Assert
.
Throws
<
ArgumentOutOfRangeException
>(()
=>
ConfigurationOptions
.
Parse
(
"myhost,sslProtocols=InvalidSslProtocol"
));
}
}
#endif
[
Fact
]
[
Fact
]
public
void
ConfigurationOptionsDefaultForAzure
()
public
void
ConfigurationOptionsDefaultForAzure
()
...
@@ -202,4 +198,4 @@ public void ConfigurationOptionsDefaultWhenNoEndpointsSpecifiedYet()
...
@@ -202,4 +198,4 @@ public void ConfigurationOptionsDefaultWhenNoEndpointsSpecifiedYet()
Assert
.
True
(
options
.
AbortOnConnectFail
);
Assert
.
True
(
options
.
AbortOnConnectFail
);
}
}
}
}
}
}
\ No newline at end of file
StackExchange.Redis.Tests/Config.cs
View file @
c54c0671
...
@@ -161,12 +161,8 @@ public void ReadConfig()
...
@@ -161,12 +161,8 @@ public void ReadConfig()
var
conn
=
GetAnyMaster
(
muxer
);
var
conn
=
GetAnyMaster
(
muxer
);
var
all
=
conn
.
ConfigGet
();
var
all
=
conn
.
ConfigGet
();
Assert
.
True
(
all
.
Length
>
0
,
"any"
);
Assert
.
True
(
all
.
Length
>
0
,
"any"
);
#if !NETCOREAPP1_0
var
pairs
=
all
.
ToDictionary
(
x
=>
(
string
)
x
.
Key
,
x
=>
(
string
)
x
.
Value
,
StringComparer
.
InvariantCultureIgnoreCase
);
var
pairs
=
all
.
ToDictionary
(
x
=>
(
string
)
x
.
Key
,
x
=>
(
string
)
x
.
Value
,
StringComparer
.
InvariantCultureIgnoreCase
);
#else
var
pairs
=
all
.
ToDictionary
(
x
=>
(
string
)
x
.
Key
,
x
=>
(
string
)
x
.
Value
,
StringComparer
.
OrdinalIgnoreCase
);
#endif
Assert
.
Equal
(
all
.
Length
,
pairs
.
Count
);
Assert
.
Equal
(
all
.
Length
,
pairs
.
Count
);
Assert
.
True
(
pairs
.
ContainsKey
(
"timeout"
),
"timeout"
);
Assert
.
True
(
pairs
.
ContainsKey
(
"timeout"
),
"timeout"
);
...
...
StackExchange.Redis.Tests/Helpers/Extensions.cs
View file @
c54c0671
...
@@ -12,8 +12,6 @@ static Extensions()
...
@@ -12,8 +12,6 @@ static Extensions()
{
{
#if NET462
#if NET462
VersionInfo
=
"Compiled under .NET 4.6.2"
;
VersionInfo
=
"Compiled under .NET 4.6.2"
;
#elif NETCOREAPP1_0
VersionInfo
=
"Compiled under .NETCoreApp1.0"
;
#elif NETCOREAPP2_0
#elif NETCOREAPP2_0
VersionInfo
=
"Compiled under .NETCoreApp2.0"
;
VersionInfo
=
"Compiled under .NETCoreApp2.0"
;
#else
#else
...
...
StackExchange.Redis.Tests/Helpers/TestConfig.cs
View file @
c54c0671
...
@@ -2,9 +2,6 @@
...
@@ -2,9 +2,6 @@
using
Jil
;
using
Jil
;
using
System
;
using
System
;
using
System.Collections.Generic
;
using
System.Collections.Generic
;
#if NETCOREAPP1_0
using
System.Reflection
;
#endif
namespace
StackExchange.Redis.Tests
namespace
StackExchange.Redis.Tests
{
{
...
@@ -19,7 +16,7 @@ static TestConfig()
...
@@ -19,7 +16,7 @@ static TestConfig()
Current
=
new
Config
();
Current
=
new
Config
();
try
try
{
{
using
(
var
stream
=
typeof
(
TestConfig
).
GetTypeInfo
().
Assembly
.
GetManifestResourceStream
(
"StackExchange.Redis.Tests."
+
FileName
))
using
(
var
stream
=
typeof
(
TestConfig
).
Assembly
.
GetManifestResourceStream
(
"StackExchange.Redis.Tests."
+
FileName
))
{
{
if
(
stream
!=
null
)
if
(
stream
!=
null
)
{
{
...
...
StackExchange.Redis.Tests/MassiveOps.cs
View file @
c54c0671
...
@@ -28,19 +28,9 @@ public async Task MassiveBulkOpsAsync(bool preserveOrder, bool withContinuation)
...
@@ -28,19 +28,9 @@ public async Task MassiveBulkOpsAsync(bool preserveOrder, bool withContinuation)
RedisKey
key
=
"MBOA"
;
RedisKey
key
=
"MBOA"
;
var
conn
=
muxer
.
GetDatabase
();
var
conn
=
muxer
.
GetDatabase
();
await
conn
.
PingAsync
().
ForAwait
();
await
conn
.
PingAsync
().
ForAwait
();
#if NETCOREAPP1_0
int
number
=
0
;
#endif
Action
<
Task
>
nonTrivial
=
delegate
Action
<
Task
>
nonTrivial
=
delegate
{
{
#if NETCOREAPP1_0
for
(
int
i
=
0
;
i
<
50
;
i
++)
{
number
++;
}
#else
Thread
.
SpinWait
(
5
);
Thread
.
SpinWait
(
5
);
#endif
};
};
var
watch
=
Stopwatch
.
StartNew
();
var
watch
=
Stopwatch
.
StartNew
();
for
(
int
i
=
0
;
i
<=
AsyncOpsQty
;
i
++)
for
(
int
i
=
0
;
i
<=
AsyncOpsQty
;
i
++)
...
...
StackExchange.Redis.Tests/Naming.cs
View file @
c54c0671
...
@@ -20,7 +20,7 @@ public class Naming
...
@@ -20,7 +20,7 @@ public class Naming
public
void
CheckSignatures
(
Type
type
,
bool
isAsync
)
public
void
CheckSignatures
(
Type
type
,
bool
isAsync
)
{
{
// check that all methods and interfaces look appropriate for their sync/async nature
// check that all methods and interfaces look appropriate for their sync/async nature
CheckName
(
type
.
GetTypeInfo
()
,
isAsync
);
CheckName
(
type
,
isAsync
);
var
members
=
type
.
GetMethods
(
BindingFlags
.
Public
|
BindingFlags
.
Instance
|
BindingFlags
.
Static
|
BindingFlags
.
DeclaredOnly
);
var
members
=
type
.
GetMethods
(
BindingFlags
.
Public
|
BindingFlags
.
Instance
|
BindingFlags
.
Static
|
BindingFlags
.
DeclaredOnly
);
foreach
(
var
member
in
members
)
foreach
(
var
member
in
members
)
{
{
...
@@ -32,9 +32,9 @@ public void CheckSignatures(Type type, bool isAsync)
...
@@ -32,9 +32,9 @@ public void CheckSignatures(Type type, bool isAsync)
[
Fact
]
[
Fact
]
public
void
ShowReadOnlyOperations
()
public
void
ShowReadOnlyOperations
()
{
{
var
msg
=
typeof
(
ConnectionMultiplexer
).
GetTypeInfo
().
Assembly
.
GetType
(
"StackExchange.Redis.Message"
);
var
msg
=
typeof
(
ConnectionMultiplexer
).
Assembly
.
GetType
(
"StackExchange.Redis.Message"
);
Assert
.
NotNull
(
msg
);
Assert
.
NotNull
(
msg
);
var
cmd
=
typeof
(
ConnectionMultiplexer
).
GetTypeInfo
().
Assembly
.
GetType
(
"StackExchange.Redis.RedisCommand"
);
var
cmd
=
typeof
(
ConnectionMultiplexer
).
Assembly
.
GetType
(
"StackExchange.Redis.RedisCommand"
);
Assert
.
NotNull
(
cmd
);
Assert
.
NotNull
(
cmd
);
var
masterOnlyMethod
=
msg
.
GetMethod
(
nameof
(
Message
.
IsMasterOnly
),
BindingFlags
.
Static
|
BindingFlags
.
NonPublic
|
BindingFlags
.
Public
);
var
masterOnlyMethod
=
msg
.
GetMethod
(
nameof
(
Message
.
IsMasterOnly
),
BindingFlags
.
Static
|
BindingFlags
.
NonPublic
|
BindingFlags
.
Public
);
Assert
.
NotNull
(
masterOnlyMethod
);
Assert
.
NotNull
(
masterOnlyMethod
);
...
@@ -103,7 +103,7 @@ private static bool UsesKey(Type type)
...
@@ -103,7 +103,7 @@ private static bool UsesKey(Type type)
{
{
if
(
UsesKey
(
type
.
GetElementType
()))
return
true
;
if
(
UsesKey
(
type
.
GetElementType
()))
return
true
;
}
}
if
(
type
.
GetTypeInfo
().
IsGenericType
)
// KVP, etc
if
(
type
.
IsGenericType
)
// KVP, etc
{
{
var
args
=
type
.
GetGenericArguments
();
var
args
=
type
.
GetGenericArguments
();
if
(
args
.
Any
(
UsesKey
))
return
true
;
if
(
args
.
Any
(
UsesKey
))
return
true
;
...
@@ -156,7 +156,7 @@ public void CheckSyncAsyncMethodsMatch(Type from, Type to)
...
@@ -156,7 +156,7 @@ public void CheckSyncAsyncMethodsMatch(Type from, Type to)
{
{
huntType
=
null
;
huntType
=
null
;
}
}
else
if
(
method
.
ReturnType
.
GetTypeInfo
().
IsSubclassOf
(
typeof
(
Task
)))
else
if
(
method
.
ReturnType
.
IsSubclassOf
(
typeof
(
Task
)))
{
{
huntType
=
method
.
ReturnType
.
GetGenericArguments
()[
0
];
huntType
=
method
.
ReturnType
.
GetGenericArguments
()[
0
];
}
}
...
@@ -168,12 +168,7 @@ public void CheckSyncAsyncMethodsMatch(Type from, Type to)
...
@@ -168,12 +168,7 @@ public void CheckSyncAsyncMethodsMatch(Type from, Type to)
Type
[]
args
=
pFrom
.
Select
(
x
=>
x
.
ParameterType
).
ToArray
();
Type
[]
args
=
pFrom
.
Select
(
x
=>
x
.
ParameterType
).
ToArray
();
Output
.
WriteLine
(
"Checking: {0}.{1}"
,
from
.
Name
,
method
.
Name
);
Output
.
WriteLine
(
"Checking: {0}.{1}"
,
from
.
Name
,
method
.
Name
);
Assert
.
Equal
(
typeof
(
CommandFlags
),
args
.
Last
());
Assert
.
Equal
(
typeof
(
CommandFlags
),
args
.
Last
());
#if !NETCOREAPP1_0
var
found
=
to
.
GetMethod
(
huntName
,
flags
,
null
,
method
.
CallingConvention
,
args
,
null
);
var
found
=
to
.
GetMethod
(
huntName
,
flags
,
null
,
method
.
CallingConvention
,
args
,
null
);
#else
var
found
=
to
.
GetMethods
(
flags
)
.
SingleOrDefault
(
m
=>
m
.
Name
==
huntName
&&
m
.
HasMatchingParameterTypes
(
args
));
#endif
Assert
.
NotNull
(
found
);
// "Found " + name + ", no " + huntName
Assert
.
NotNull
(
found
);
// "Found " + name + ", no " + huntName
var
pTo
=
found
.
GetParameters
();
var
pTo
=
found
.
GetParameters
();
...
@@ -188,22 +183,14 @@ public void CheckSyncAsyncMethodsMatch(Type from, Type to)
...
@@ -188,22 +183,14 @@ public void CheckSyncAsyncMethodsMatch(Type from, Type to)
Output
.
WriteLine
(
"Validated: {0} ({1} methods)"
,
from
.
Name
,
count
);
Output
.
WriteLine
(
"Validated: {0} ({1} methods)"
,
from
.
Name
,
count
);
}
}
private
static
readonly
Type
ignoreType
=
typeof
(
ConnectionMultiplexer
).
GetTypeInfo
().
Assembly
.
GetType
(
"StackExchange.Redis.IgnoreNamePrefixAttribute"
);
private
static
readonly
Type
ignoreType
=
typeof
(
ConnectionMultiplexer
).
Assembly
.
GetType
(
"StackExchange.Redis.IgnoreNamePrefixAttribute"
);
private
void
CheckMethod
(
MethodInfo
method
,
bool
isAsync
)
private
void
CheckMethod
(
MethodInfo
method
,
bool
isAsync
)
{
{
#if DEBUG
#if DEBUG
#if !NETCOREAPP1_0
bool
ignorePrefix
=
ignoreType
!=
null
&&
Attribute
.
IsDefined
(
method
,
ignoreType
);
bool
ignorePrefix
=
ignoreType
!=
null
&&
Attribute
.
IsDefined
(
method
,
ignoreType
);
#else
bool
ignorePrefix
=
ignoreType
!=
null
&&
method
.
IsDefined
(
ignoreType
);
#endif
if
(
ignorePrefix
)
if
(
ignorePrefix
)
{
{
#if !NETCOREAPP1_0
Attribute
attrib
=
Attribute
.
GetCustomAttribute
(
method
,
ignoreType
);
Attribute
attrib
=
Attribute
.
GetCustomAttribute
(
method
,
ignoreType
);
#else
Attribute
attrib
=
method
.
GetCustomAttribute
(
ignoreType
);
#endif
if
((
bool
)
attrib
.
GetType
().
GetProperty
(
"IgnoreEntireMethod"
).
GetValue
(
attrib
))
if
((
bool
)
attrib
.
GetType
().
GetProperty
(
"IgnoreEntireMethod"
).
GetValue
(
attrib
))
{
{
return
;
return
;
...
@@ -250,34 +237,4 @@ private void CheckName(MemberInfo member, bool isAsync)
...
@@ -250,34 +237,4 @@ private void CheckName(MemberInfo member, bool isAsync)
else
Assert
.
False
(
member
.
Name
.
EndsWith
(
"Async"
),
member
.
Name
+
":Name - don't end *Async"
);
else
Assert
.
False
(
member
.
Name
.
EndsWith
(
"Async"
),
member
.
Name
+
":Name - don't end *Async"
);
}
}
}
}
public
static
class
ReflectionExtensions
{
#if !NETCOREAPP1_0
public
static
Type
GetTypeInfo
(
this
Type
type
)
{
return
type
;
}
#else
public
static
bool
HasMatchingParameterTypes
(
this
MethodInfo
method
,
Type
[]
paramTypes
)
{
var
types
=
method
.
GetParameters
().
Select
(
pi
=>
pi
.
ParameterType
).
ToArray
();
if
(
types
.
Length
!=
paramTypes
.
Length
)
{
return
false
;
}
for
(
int
i
=
0
;
i
<
types
.
Length
;
i
++)
{
if
(
types
[
i
]
!=
paramTypes
[
i
])
{
return
false
;
}
}
return
true
;
}
#endif
}
}
}
StackExchange.Redis.Tests/Profiling.cs
View file @
c54c0671
using
System
;
using
System
;
using
System.Collections.Generic
;
using
System.Collections.Generic
;
using
System.Linq
;
using
System.Linq
;
#if NETCOREAPP1_0
using
System.Reflection
;
#endif
using
System.Threading.Tasks
;
using
System.Threading.Tasks
;
using
System.Threading
;
using
System.Threading
;
using
System.Collections.Concurrent
;
using
System.Collections.Concurrent
;
...
@@ -430,11 +427,11 @@ public void LowAllocationEnumerable()
...
@@ -430,11 +427,11 @@ public void LowAllocationEnumerable()
conn
.
WaitAll
(
allTasks
.
ToArray
());
conn
.
WaitAll
(
allTasks
.
ToArray
());
var
res
=
conn
.
FinishProfiling
(
profiler
.
MyContext
);
var
res
=
conn
.
FinishProfiling
(
profiler
.
MyContext
);
Assert
.
True
(
res
.
GetType
().
GetTypeInfo
().
IsValueType
);
Assert
.
True
(
res
.
GetType
().
IsValueType
);
using
(
var
e
=
res
.
GetEnumerator
())
using
(
var
e
=
res
.
GetEnumerator
())
{
{
Assert
.
True
(
e
.
GetType
().
GetTypeInfo
().
IsValueType
);
Assert
.
True
(
e
.
GetType
().
IsValueType
);
Assert
.
True
(
e
.
MoveNext
());
Assert
.
True
(
e
.
MoveNext
());
var
i
=
e
.
Current
;
var
i
=
e
.
Current
;
...
@@ -557,4 +554,4 @@ public void ProfilingMD_Ex2()
...
@@ -557,4 +554,4 @@ public void ProfilingMD_Ex2()
}
}
}
}
}
}
}
}
\ No newline at end of file
StackExchange.Redis.Tests/PubSub.cs
View file @
c54c0671
...
@@ -27,17 +27,17 @@ public void ExplicitPublishMode()
...
@@ -27,17 +27,17 @@ public void ExplicitPublishMode()
Thread
.
Sleep
(
1000
);
Thread
.
Sleep
(
1000
);
pub
.
Publish
(
"abcd"
,
"efg"
);
pub
.
Publish
(
"abcd"
,
"efg"
);
Thread
.
Sleep
(
500
);
Thread
.
Sleep
(
500
);
Assert
.
Equal
(
0
,
VolatileWrapper
.
Read
(
ref
a
));
Assert
.
Equal
(
0
,
Thread
.
Volatile
Read
(
ref
a
));
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
b
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
b
));
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
c
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
c
));
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
d
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
d
));
pub
.
Publish
(
"*bcd"
,
"efg"
);
pub
.
Publish
(
"*bcd"
,
"efg"
);
Thread
.
Sleep
(
500
);
Thread
.
Sleep
(
500
);
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
a
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
a
));
//Assert.Equal(1,
VolatileWrapper.
Read(ref b));
//Assert.Equal(1,
Thread.Volatile
Read(ref b));
//Assert.Equal(1,
VolatileWrapper.
Read(ref c));
//Assert.Equal(1,
Thread.Volatile
Read(ref c));
//Assert.Equal(1,
VolatileWrapper.
Read(ref d));
//Assert.Equal(1,
Thread.Volatile
Read(ref d));
}
}
}
}
...
@@ -89,7 +89,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
...
@@ -89,7 +89,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
{
{
Assert
.
Empty
(
received
);
Assert
.
Empty
(
received
);
}
}
Assert
.
Equal
(
0
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
0
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
var
count
=
sub
.
Publish
(
pubChannel
,
"def"
);
var
count
=
sub
.
Publish
(
pubChannel
,
"def"
);
Ping
(
muxer
,
pub
,
sub
,
3
);
Ping
(
muxer
,
pub
,
sub
,
3
);
...
@@ -98,7 +98,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
...
@@ -98,7 +98,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
{
{
Assert
.
Single
(
received
);
Assert
.
Single
(
received
);
}
}
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
// unsubscribe from first; should still see second
// unsubscribe from first; should still see second
sub
.
Unsubscribe
(
subChannel
,
handler1
);
sub
.
Unsubscribe
(
subChannel
,
handler1
);
...
@@ -108,7 +108,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
...
@@ -108,7 +108,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
{
{
Assert
.
Single
(
received
);
Assert
.
Single
(
received
);
}
}
Assert
.
Equal
(
2
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
2
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
Assert
.
Equal
(
1
,
count
);
Assert
.
Equal
(
1
,
count
);
// unsubscribe from second; should see nothing this time
// unsubscribe from second; should see nothing this time
...
@@ -119,7 +119,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
...
@@ -119,7 +119,7 @@ public void TestBasicPubSub(bool preserveOrder, string channelPrefix, bool wildC
{
{
Assert
.
Single
(
received
);
Assert
.
Single
(
received
);
}
}
Assert
.
Equal
(
2
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
2
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
Assert
.
Equal
(
0
,
count
);
Assert
.
Equal
(
0
,
count
);
}
}
}
}
...
@@ -156,7 +156,7 @@ public void TestBasicPubSubFireAndForget(bool preserveOrder)
...
@@ -156,7 +156,7 @@ public void TestBasicPubSubFireAndForget(bool preserveOrder)
{
{
Assert
.
Empty
(
received
);
Assert
.
Empty
(
received
);
}
}
Assert
.
Equal
(
0
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
0
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
Ping
(
muxer
,
pub
,
sub
);
Ping
(
muxer
,
pub
,
sub
);
var
count
=
sub
.
Publish
(
key
,
"def"
,
CommandFlags
.
FireAndForget
);
var
count
=
sub
.
Publish
(
key
,
"def"
,
CommandFlags
.
FireAndForget
);
Ping
(
muxer
,
pub
,
sub
);
Ping
(
muxer
,
pub
,
sub
);
...
@@ -165,7 +165,7 @@ public void TestBasicPubSubFireAndForget(bool preserveOrder)
...
@@ -165,7 +165,7 @@ public void TestBasicPubSubFireAndForget(bool preserveOrder)
{
{
Assert
.
Single
(
received
);
Assert
.
Single
(
received
);
}
}
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
sub
.
Unsubscribe
(
key
);
sub
.
Unsubscribe
(
key
);
count
=
sub
.
Publish
(
key
,
"ghi"
,
CommandFlags
.
FireAndForget
);
count
=
sub
.
Publish
(
key
,
"ghi"
,
CommandFlags
.
FireAndForget
);
...
@@ -228,7 +228,7 @@ public void TestPatternPubSub(bool preserveOrder)
...
@@ -228,7 +228,7 @@ public void TestPatternPubSub(bool preserveOrder)
{
{
Assert
.
Empty
(
received
);
Assert
.
Empty
(
received
);
}
}
Assert
.
Equal
(
0
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
0
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
var
count
=
sub
.
Publish
(
"abc"
,
"def"
);
var
count
=
sub
.
Publish
(
"abc"
,
"def"
);
Ping
(
muxer
,
pub
,
sub
);
Ping
(
muxer
,
pub
,
sub
);
...
@@ -237,7 +237,7 @@ public void TestPatternPubSub(bool preserveOrder)
...
@@ -237,7 +237,7 @@ public void TestPatternPubSub(bool preserveOrder)
{
{
Assert
.
Single
(
received
);
Assert
.
Single
(
received
);
}
}
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
secondHandler
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
secondHandler
));
sub
.
Unsubscribe
(
"a*c"
);
sub
.
Unsubscribe
(
"a*c"
);
count
=
sub
.
Publish
(
"abc"
,
"ghi"
);
count
=
sub
.
Publish
(
"abc"
,
"ghi"
);
...
@@ -268,7 +268,7 @@ public async Task SubscriptionsSurviveConnectionFailureAsync()
...
@@ -268,7 +268,7 @@ public async Task SubscriptionsSurviveConnectionFailureAsync()
await
sub
.
PublishAsync
(
channel
,
"abc"
).
ConfigureAwait
(
false
);
await
sub
.
PublishAsync
(
channel
,
"abc"
).
ConfigureAwait
(
false
);
sub
.
Ping
();
sub
.
Ping
();
await
Task
.
Delay
(
200
).
ConfigureAwait
(
false
);
await
Task
.
Delay
(
200
).
ConfigureAwait
(
false
);
Assert
.
Equal
(
1
,
VolatileWrapper
.
Read
(
ref
counter
));
Assert
.
Equal
(
1
,
Thread
.
Volatile
Read
(
ref
counter
));
var
server
=
GetServer
(
muxer
);
var
server
=
GetServer
(
muxer
);
Assert
.
Equal
(
1
,
server
.
GetCounters
().
Subscription
.
SocketCount
);
Assert
.
Equal
(
1
,
server
.
GetCounters
().
Subscription
.
SocketCount
);
...
@@ -280,21 +280,9 @@ public async Task SubscriptionsSurviveConnectionFailureAsync()
...
@@ -280,21 +280,9 @@ public async Task SubscriptionsSurviveConnectionFailureAsync()
await
sub
.
PublishAsync
(
channel
,
"abc"
).
ConfigureAwait
(
false
);
await
sub
.
PublishAsync
(
channel
,
"abc"
).
ConfigureAwait
(
false
);
await
Task
.
Delay
(
200
).
ConfigureAwait
(
false
);
await
Task
.
Delay
(
200
).
ConfigureAwait
(
false
);
sub
.
Ping
();
sub
.
Ping
();
Assert
.
Equal
(
2
,
VolatileWrapper
.
Read
(
ref
counter
));
Assert
.
Equal
(
2
,
Thread
.
Volatile
Read
(
ref
counter
));
}
}
}
}
#endif
#endif
}
}
internal
static
class
VolatileWrapper
{
public
static
int
Read
(
ref
int
location
)
{
#if !NETCOREAPP1_0
return
Thread
.
VolatileRead
(
ref
location
);
#else
return
Volatile
.
Read
(
ref
location
);
#endif
}
}
}
}
StackExchange.Redis.Tests/StackExchange.Redis.Tests.csproj
View file @
c54c0671
<Project Sdk="Microsoft.NET.Sdk">
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<PropertyGroup>
<Description>StackExchange.Redis.Tests</Description>
<Description>StackExchange.Redis.Tests</Description>
<TargetFrameworks>net462;netcoreapp
1.0;netcoreapp
2.0</TargetFrameworks>
<TargetFrameworks>net462;netcoreapp2.0</TargetFrameworks>
<AssemblyName>StackExchange.Redis.Tests</AssemblyName>
<AssemblyName>StackExchange.Redis.Tests</AssemblyName>
<GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
<GenerateRuntimeConfigurationFiles>true</GenerateRuntimeConfigurationFiles>
<GenerateDocumentationFile>false</GenerateDocumentationFile>
<GenerateDocumentationFile>false</GenerateDocumentationFile>
<DebugType>full</DebugType>
<DebugType>full</DebugType>
</PropertyGroup>
</PropertyGroup>
<ItemGroup>
<ItemGroup>
<None Update="*.json" CopyToOutputDirectory="Always" />
<None Update="*.json" CopyToOutputDirectory="Always" />
<EmbeddedResource Include="*Config.json" />
<EmbeddedResource Include="*Config.json" />
...
@@ -28,13 +28,4 @@
...
@@ -28,13 +28,4 @@
<ItemGroup Condition=" '$(TargetFramework)' == 'net462' ">
<ItemGroup Condition=" '$(TargetFramework)' == 'net462' ">
<Reference Include="Microsoft.CSharp" />
<Reference Include="Microsoft.CSharp" />
</ItemGroup>
</ItemGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'netcoreapp1.0' ">
<PackageReference Include="System.Console" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Diagnostics.Debug" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Linq.Expressions" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Extensions" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Runtime.InteropServices" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Threading.Tasks.Parallel" Version="$(CoreFxVersion)" />
<PackageReference Include="Microsoft.CSharp" Version="$(CoreFxVersion)" />
</ItemGroup>
</Project>
</Project>
StackExchange.Redis.Tests/TaskTests.cs
View file @
c54c0671
...
@@ -9,7 +9,6 @@ public class TaskTests
...
@@ -9,7 +9,6 @@ public class TaskTests
{
{
#if DEBUG
#if DEBUG
#if !PLAT_SAFE_CONTINUATIONS // IsSyncSafe doesn't exist if PLAT_SAFE_CONTINUATIONS is defined
[
Theory
]
[
Theory
]
[
InlineData
(
SourceOrign
.
NewTCS
)]
[
InlineData
(
SourceOrign
.
NewTCS
)]
[
InlineData
(
SourceOrign
.
Create
)]
[
InlineData
(
SourceOrign
.
Create
)]
...
@@ -20,13 +19,10 @@ public void VerifyIsSyncSafe(SourceOrign origin)
...
@@ -20,13 +19,10 @@ public void VerifyIsSyncSafe(SourceOrign origin)
// ...and if we're dropping NET45 support, we can just nuke it all.
// ...and if we're dropping NET45 support, we can just nuke it all.
#if NET462
#if NET462
Assert
.
True
(
TaskSource
.
IsSyncSafe
(
source
.
Task
));
Assert
.
True
(
TaskSource
.
IsSyncSafe
(
source
.
Task
));
#elif NETCOREAPP1_0
Assert
.
True
(
TaskSource
.
IsSyncSafe
(
source
.
Task
));
#elif NETCOREAPP2_0
#elif NETCOREAPP2_0
Assert
.
True
(
TaskSource
.
IsSyncSafe
(
source
.
Task
));
Assert
.
True
(
TaskSource
.
IsSyncSafe
(
source
.
Task
));
#endif
#endif
}
}
#endif
private
static
TaskCompletionSource
<
T
>
Create
<
T
>(
SourceOrign
origin
)
private
static
TaskCompletionSource
<
T
>
Create
<
T
>(
SourceOrign
origin
)
{
{
switch
(
origin
)
switch
(
origin
)
...
@@ -123,4 +119,4 @@ private async void DoAwait(Task task)
...
@@ -123,4 +119,4 @@ private async void DoAwait(Task task)
}
}
#endif
#endif
}
}
}
}
\ No newline at end of file
StackExchange.Redis.Tests/TestBase.cs
View file @
c54c0671
...
@@ -59,9 +59,6 @@ static TestBase()
...
@@ -59,9 +59,6 @@ static TestBase()
{
{
Console
.
WriteLine
(
"Unobserved: "
+
args
.
Exception
);
Console
.
WriteLine
(
"Unobserved: "
+
args
.
Exception
);
args
.
SetObserved
();
args
.
SetObserved
();
#if NETCOREAPP1_0
if
(
IgnorableExceptionPredicates
.
Any
(
predicate
=>
predicate
(
args
.
Exception
.
InnerException
)))
return
;
#endif
lock
(
sharedFailCount
)
lock
(
sharedFailCount
)
{
{
if
(
sharedFailCount
!=
null
)
if
(
sharedFailCount
!=
null
)
...
@@ -76,14 +73,6 @@ static TestBase()
...
@@ -76,14 +73,6 @@ static TestBase()
};
};
}
}
#if NETCOREAPP1_0
private
static
readonly
Func
<
Exception
,
bool
>[]
IgnorableExceptionPredicates
=
new
Func
<
Exception
,
bool
>[]
{
e
=>
e
!=
null
&&
e
is
ObjectDisposedException
&&
e
.
Message
.
Equals
(
"Cannot access a disposed object.\r\nObject name: 'System.Net.Sockets.NetworkStream'."
),
e
=>
e
!=
null
&&
e
is
IOException
&&
e
.
Message
.
StartsWith
(
"Unable to read data from the transport connection:"
)
};
#endif
protected
void
OnConnectionFailed
(
object
sender
,
ConnectionFailedEventArgs
e
)
protected
void
OnConnectionFailed
(
object
sender
,
ConnectionFailedEventArgs
e
)
{
{
Interlocked
.
Increment
(
ref
privateFailCount
);
Interlocked
.
Increment
(
ref
privateFailCount
);
...
@@ -318,13 +307,11 @@ protected static TimeSpan RunConcurrent(Action work, int threads, int timeout =
...
@@ -318,13 +307,11 @@ protected static TimeSpan RunConcurrent(Action work, int threads, int timeout =
}
}
if
(!
allDone
.
WaitOne
(
timeout
))
if
(!
allDone
.
WaitOne
(
timeout
))
{
{
#if !NETCOREAPP1_0
for
(
int
i
=
0
;
i
<
threads
;
i
++)
for
(
int
i
=
0
;
i
<
threads
;
i
++)
{
{
var
thd
=
threadArr
[
i
];
var
thd
=
threadArr
[
i
];
if
(
thd
.
IsAlive
)
thd
.
Abort
();
if
(
thd
.
IsAlive
)
thd
.
Abort
();
}
}
#endif
throw
new
TimeoutException
();
throw
new
TimeoutException
();
}
}
...
...
StackExchange.Redis/StackExchange.Redis.csproj
View file @
c54c0671
...
@@ -27,17 +27,6 @@
...
@@ -27,17 +27,6 @@
<DefineConstants>$(DefineConstants);FEATURE_SERIALIZATION;FEATURE_THREADPOOL</DefineConstants>
<DefineConstants>$(DefineConstants);FEATURE_SERIALIZATION;FEATURE_THREADPOOL</DefineConstants>
</PropertyGroup>
</PropertyGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard1.5' ">
<PackageReference Include="System.Collections.NonGeneric" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Net.NameResolution" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Net.Security" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.Lightweight" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.TypeExtensions" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Threading.Thread" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Threading.ThreadPool" Version="$(CoreFxVersion)" />
</ItemGroup>
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' ">
<ItemGroup Condition=" '$(TargetFramework)' == 'netstandard2.0' ">
<PackageReference Include="System.Reflection.Emit.Lightweight" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.Lightweight" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.ILGeneration" Version="$(CoreFxVersion)" />
<PackageReference Include="System.Reflection.Emit.ILGeneration" Version="$(CoreFxVersion)" />
...
...
StackExchange.Redis/StackExchange/Redis/Compat/BrowsableAttribute.cs
deleted
100644 → 0
View file @
d7c72b05
#
if
NETSTANDARD1_5
using
System
;
namespace
StackExchange.Redis
{
/// <summary>
/// Strictly for compat and less #if defs on netstandard1.5
/// </summary>
[
AttributeUsage
(
AttributeTargets
.
All
,
AllowMultiple
=
false
)]
internal
class
BrowsableAttribute
:
Attribute
{
public
BrowsableAttribute
(
bool
_
)
{
}
}
}
#
endif
\ No newline at end of file
StackExchange.Redis/StackExchange/Redis/Compat/ConvertHelper.cs
deleted
100644 → 0
View file @
d7c72b05
using
System
;
namespace
StackExchange.Redis
{
/// <summary>
/// Helper for Array.ConvertAll() as it's missing on .Net Core.
/// </summary>
public
static
class
ConvertHelper
{
/// <summary>
/// Converts array of one type to an array of another type.
/// </summary>
/// <typeparam name="TInput">Input type</typeparam>
/// <typeparam name="TOutput">Output type</typeparam>
/// <param name="source">source</param>
/// <param name="selector">selector</param>
/// <returns></returns>
public
static
TOutput
[]
ConvertAll
<
TInput
,
TOutput
>(
TInput
[]
source
,
Func
<
TInput
,
TOutput
>
selector
)
{
#if NETSTANDARD1_5
TOutput
[]
arr
=
new
TOutput
[
source
.
Length
];
for
(
int
i
=
0
;
i
<
arr
.
Length
;
i
++)
arr
[
i
]
=
selector
(
source
[
i
]);
return
arr
;
#else
return
Array
.
ConvertAll
(
source
,
item
=>
selector
(
item
));
#endif
}
}
}
StackExchange.Redis/StackExchange/Redis/Compat/VolatileWrapper.cs
deleted
100644 → 0
View file @
d7c72b05
namespace
StackExchange.Redis
{
internal
static
class
VolatileWrapper
{
public
static
int
Read
(
ref
int
location
)
{
#if NETSTANDARD1_5
return
System
.
Threading
.
Volatile
.
Read
(
ref
location
);
#else
return
System
.
Threading
.
Thread
.
VolatileRead
(
ref
location
);
#endif
}
public
static
void
Write
(
ref
int
address
,
int
value
)
{
#if NETSTANDARD1_5
System
.
Threading
.
Volatile
.
Write
(
ref
address
,
value
);
#else
System
.
Threading
.
Thread
.
VolatileWrite
(
ref
address
,
value
);
#endif
}
}
}
StackExchange.Redis/StackExchange/Redis/ConfigurationOptions.cs
View file @
c54c0671
...
@@ -14,10 +14,7 @@ namespace StackExchange.Redis
...
@@ -14,10 +14,7 @@ namespace StackExchange.Redis
/// <summary>
/// <summary>
/// The options relevant to a set of redis connections
/// The options relevant to a set of redis connections
/// </summary>
/// </summary>
public
sealed
class
ConfigurationOptions
public
sealed
class
ConfigurationOptions
:
ICloneable
#if !NETSTANDARD1_5
:
ICloneable
#endif
{
{
internal
const
string
DefaultTieBreaker
=
"__Booksleeve_TieBreak"
,
DefaultConfigurationChannel
=
"__Booksleeve_MasterChanged"
;
internal
const
string
DefaultTieBreaker
=
"__Booksleeve_TieBreak"
,
DefaultConfigurationChannel
=
"__Booksleeve_MasterChanged"
;
...
@@ -398,9 +395,7 @@ public ConfigurationOptions Clone()
...
@@ -398,9 +395,7 @@ public ConfigurationOptions Clone()
DefaultDatabase
=
DefaultDatabase
,
DefaultDatabase
=
DefaultDatabase
,
ReconnectRetryPolicy
=
reconnectRetryPolicy
,
ReconnectRetryPolicy
=
reconnectRetryPolicy
,
preserveAsyncOrder
=
preserveAsyncOrder
,
preserveAsyncOrder
=
preserveAsyncOrder
,
#if !NETSTANDARD1_5
SslProtocols
=
SslProtocols
,
SslProtocols
=
SslProtocols
,
#endif
};
};
foreach
(
var
item
in
EndPoints
)
foreach
(
var
item
in
EndPoints
)
options
.
EndPoints
.
Add
(
item
);
options
.
EndPoints
.
Add
(
item
);
...
@@ -547,9 +542,7 @@ private void Clear()
...
@@ -547,9 +542,7 @@ private void Clear()
SocketManager
=
null
;
SocketManager
=
null
;
}
}
#if !NETSTANDARD1_5
object
ICloneable
.
Clone
()
=>
Clone
();
object
ICloneable
.
Clone
()
{
return
Clone
();
}
#endif
private
void
DoParse
(
string
configuration
,
bool
ignoreUnknown
)
private
void
DoParse
(
string
configuration
,
bool
ignoreUnknown
)
{
{
...
@@ -652,11 +645,9 @@ private void DoParse(string configuration, bool ignoreUnknown)
...
@@ -652,11 +645,9 @@ private void DoParse(string configuration, bool ignoreUnknown)
case
OptionKeys
.
PreserveAsyncOrder
:
case
OptionKeys
.
PreserveAsyncOrder
:
PreserveAsyncOrder
=
OptionKeys
.
ParseBoolean
(
key
,
value
);
PreserveAsyncOrder
=
OptionKeys
.
ParseBoolean
(
key
,
value
);
break
;
break
;
#if !NETSTANDARD1_5
case
OptionKeys
.
SslProtocols
:
case
OptionKeys
.
SslProtocols
:
SslProtocols
=
OptionKeys
.
ParseSslProtocols
(
key
,
value
);
SslProtocols
=
OptionKeys
.
ParseSslProtocols
(
key
,
value
);
break
;
break
;
#endif
default
:
default
:
if
(!
string
.
IsNullOrEmpty
(
key
)
&&
key
[
0
]
==
'$'
)
if
(!
string
.
IsNullOrEmpty
(
key
)
&&
key
[
0
]
==
'$'
)
{
{
...
@@ -731,4 +722,4 @@ private string InferSslHostFromEndpoints()
...
@@ -731,4 +722,4 @@ private string InferSslHostFromEndpoints()
return
null
;
return
null
;
}
}
}
}
}
}
\ No newline at end of file
StackExchange.Redis/StackExchange/Redis/ConnectionMultiplexer.cs
View file @
c54c0671
...
@@ -69,9 +69,6 @@ private static string GetDefaultClientName()
...
@@ -69,9 +69,6 @@ private static string GetDefaultClientName()
/// </summary>
/// </summary>
internal
static
string
TryGetAzureRoleInstanceIdNoThrow
()
internal
static
string
TryGetAzureRoleInstanceIdNoThrow
()
{
{
#if NETSTANDARD1_5
return
null
;
#else
string
roleInstanceId
=
null
;
string
roleInstanceId
=
null
;
// TODO: CoreCLR port pending https://github.com/dotnet/coreclr/issues/919
// TODO: CoreCLR port pending https://github.com/dotnet/coreclr/issues/919
try
try
...
@@ -109,7 +106,6 @@ internal static string TryGetAzureRoleInstanceIdNoThrow()
...
@@ -109,7 +106,6 @@ internal static string TryGetAzureRoleInstanceIdNoThrow()
roleInstanceId
=
null
;
roleInstanceId
=
null
;
}
}
return
roleInstanceId
;
return
roleInstanceId
;
#endif
}
}
/// <summary>
/// <summary>
...
@@ -504,7 +500,7 @@ public EndPoint[] GetEndPoints(bool configuredOnly = false)
...
@@ -504,7 +500,7 @@ public EndPoint[] GetEndPoints(bool configuredOnly = false)
{
{
if
(
configuredOnly
)
return
configuration
.
EndPoints
.
ToArray
();
if
(
configuredOnly
)
return
configuration
.
EndPoints
.
ToArray
();
return
ConvertHelper
.
ConvertAll
(
serverSnapshot
,
x
=>
x
.
EndPoint
);
return
Array
.
ConvertAll
(
serverSnapshot
,
x
=>
x
.
EndPoint
);
}
}
private
readonly
ConfigurationOptions
configuration
;
private
readonly
ConfigurationOptions
configuration
;
...
@@ -581,7 +577,6 @@ private static bool WaitAllIgnoreErrors(Task[] tasks, int timeout)
...
@@ -581,7 +577,6 @@ private static bool WaitAllIgnoreErrors(Task[] tasks, int timeout)
return
false
;
return
false
;
}
}
#if FEATURE_THREADPOOL
private
void
LogLockedWithThreadPoolStats
(
TextWriter
log
,
string
message
,
out
int
busyWorkerCount
)
private
void
LogLockedWithThreadPoolStats
(
TextWriter
log
,
string
message
,
out
int
busyWorkerCount
)
{
{
busyWorkerCount
=
0
;
busyWorkerCount
=
0
;
...
@@ -594,7 +589,6 @@ private void LogLockedWithThreadPoolStats(TextWriter log, string message, out in
...
@@ -594,7 +589,6 @@ private void LogLockedWithThreadPoolStats(TextWriter log, string message, out in
LogLocked
(
log
,
sb
.
ToString
());
LogLocked
(
log
,
sb
.
ToString
());
}
}
}
}
#endif
private
static
bool
AllComplete
(
Task
[]
tasks
)
private
static
bool
AllComplete
(
Task
[]
tasks
)
{
{
...
@@ -623,27 +617,21 @@ private async Task<bool> WaitAllIgnoreErrorsAsync(Task[] tasks, int timeoutMilli
...
@@ -623,27 +617,21 @@ private async Task<bool> WaitAllIgnoreErrorsAsync(Task[] tasks, int timeoutMilli
}
}
var
watch
=
Stopwatch
.
StartNew
();
var
watch
=
Stopwatch
.
StartNew
();
#if FEATURE_THREADPOOL
LogLockedWithThreadPoolStats
(
log
,
"Awaiting task completion"
,
out
int
busyWorkerCount
);
LogLockedWithThreadPoolStats
(
log
,
"Awaiting task completion"
,
out
int
busyWorkerCount
);
#endif
try
try
{
{
// if none error, great
// if none error, great
var
remaining
=
timeoutMilliseconds
-
checked
((
int
)
watch
.
ElapsedMilliseconds
);
var
remaining
=
timeoutMilliseconds
-
checked
((
int
)
watch
.
ElapsedMilliseconds
);
if
(
remaining
<=
0
)
if
(
remaining
<=
0
)
{
{
#if FEATURE_THREADPOOL
LogLockedWithThreadPoolStats
(
log
,
"Timeout before awaiting for tasks"
,
out
busyWorkerCount
);
LogLockedWithThreadPoolStats
(
log
,
"Timeout before awaiting for tasks"
,
out
busyWorkerCount
);
#endif
return
false
;
return
false
;
}
}
var
allTasks
=
Task
.
WhenAll
(
tasks
).
ObserveErrors
();
var
allTasks
=
Task
.
WhenAll
(
tasks
).
ObserveErrors
();
var
any
=
Task
.
WhenAny
(
allTasks
,
Task
.
Delay
(
remaining
)).
ObserveErrors
();
var
any
=
Task
.
WhenAny
(
allTasks
,
Task
.
Delay
(
remaining
)).
ObserveErrors
();
bool
all
=
await
any
.
ForAwait
()
==
allTasks
;
bool
all
=
await
any
.
ForAwait
()
==
allTasks
;
#if FEATURE_THREADPOOL
LogLockedWithThreadPoolStats
(
log
,
all
?
"All tasks completed cleanly"
:
"Not all tasks completed cleanly"
,
out
busyWorkerCount
);
LogLockedWithThreadPoolStats
(
log
,
all
?
"All tasks completed cleanly"
:
"Not all tasks completed cleanly"
,
out
busyWorkerCount
);
#endif
return
all
;
return
all
;
}
}
catch
catch
...
@@ -659,9 +647,7 @@ private async Task<bool> WaitAllIgnoreErrorsAsync(Task[] tasks, int timeoutMilli
...
@@ -659,9 +647,7 @@ private async Task<bool> WaitAllIgnoreErrorsAsync(Task[] tasks, int timeoutMilli
var
remaining
=
timeoutMilliseconds
-
checked
((
int
)
watch
.
ElapsedMilliseconds
);
var
remaining
=
timeoutMilliseconds
-
checked
((
int
)
watch
.
ElapsedMilliseconds
);
if
(
remaining
<=
0
)
if
(
remaining
<=
0
)
{
{
#if FEATURE_THREADPOOL
LogLockedWithThreadPoolStats
(
log
,
"Timeout awaiting tasks"
,
out
busyWorkerCount
);
LogLockedWithThreadPoolStats
(
log
,
"Timeout awaiting tasks"
,
out
busyWorkerCount
);
#endif
return
false
;
return
false
;
}
}
try
try
...
@@ -672,9 +658,7 @@ private async Task<bool> WaitAllIgnoreErrorsAsync(Task[] tasks, int timeoutMilli
...
@@ -672,9 +658,7 @@ private async Task<bool> WaitAllIgnoreErrorsAsync(Task[] tasks, int timeoutMilli
{
}
{
}
}
}
}
}
#if FEATURE_THREADPOOL
LogLockedWithThreadPoolStats
(
log
,
"Finished awaiting tasks"
,
out
busyWorkerCount
);
LogLockedWithThreadPoolStats
(
log
,
"Finished awaiting tasks"
,
out
busyWorkerCount
);
#endif
return
false
;
return
false
;
}
}
...
@@ -978,13 +962,13 @@ internal long LastHeartbeatSecondsAgo
...
@@ -978,13 +962,13 @@ internal long LastHeartbeatSecondsAgo
get
get
{
{
if
(
pulse
==
null
)
return
-
1
;
if
(
pulse
==
null
)
return
-
1
;
return
unchecked
(
Environment
.
TickCount
-
VolatileWrapper
.
Read
(
ref
lastHeartbeatTicks
))
/
1000
;
return
unchecked
(
Environment
.
TickCount
-
Thread
.
Volatile
Read
(
ref
lastHeartbeatTicks
))
/
1000
;
}
}
}
}
internal
Exception
LastException
{
get
;
set
;
}
internal
Exception
LastException
{
get
;
set
;
}
internal
static
long
LastGlobalHeartbeatSecondsAgo
=>
unchecked
(
Environment
.
TickCount
-
VolatileWrapper
.
Read
(
ref
lastGlobalHeartbeatTicks
))
/
1000
;
internal
static
long
LastGlobalHeartbeatSecondsAgo
=>
unchecked
(
Environment
.
TickCount
-
Thread
.
Volatile
Read
(
ref
lastGlobalHeartbeatTicks
))
/
1000
;
internal
CompletionManager
UnprocessableCompletionManager
{
get
;
}
internal
CompletionManager
UnprocessableCompletionManager
{
get
;
}
...
@@ -2063,12 +2047,10 @@ void add(string lk, string sk, string v)
...
@@ -2063,12 +2047,10 @@ void add(string lk, string sk, string v)
{
{
add
(
"Key-HashSlot"
,
"keyHashSlot"
,
message
.
GetHashSlot
(
this
.
ServerSelectionStrategy
).
ToString
());
add
(
"Key-HashSlot"
,
"keyHashSlot"
,
message
.
GetHashSlot
(
this
.
ServerSelectionStrategy
).
ToString
());
}
}
#if FEATURE_THREADPOOL
int
busyWorkerCount
=
GetThreadPoolStats
(
out
string
iocp
,
out
string
worker
);
int
busyWorkerCount
=
GetThreadPoolStats
(
out
string
iocp
,
out
string
worker
);
add
(
"ThreadPool-IO-Completion"
,
"IOCP"
,
iocp
);
add
(
"ThreadPool-IO-Completion"
,
"IOCP"
,
iocp
);
add
(
"ThreadPool-Workers"
,
"WORKER"
,
worker
);
add
(
"ThreadPool-Workers"
,
"WORKER"
,
worker
);
data
.
Add
(
Tuple
.
Create
(
"Busy-Workers"
,
busyWorkerCount
.
ToString
()));
data
.
Add
(
Tuple
.
Create
(
"Busy-Workers"
,
busyWorkerCount
.
ToString
()));
#endif
#if FEATURE_PERFCOUNTER
#if FEATURE_PERFCOUNTER
if
(
IncludePerformanceCountersInExceptions
)
if
(
IncludePerformanceCountersInExceptions
)
{
{
...
@@ -2123,7 +2105,6 @@ private static string GetSystemCpuPercent()
...
@@ -2123,7 +2105,6 @@ private static string GetSystemCpuPercent()
:
"unavailable"
;
:
"unavailable"
;
}
}
#endif
#endif
#if FEATURE_THREADPOOL
private
static
int
GetThreadPoolStats
(
out
string
iocp
,
out
string
worker
)
private
static
int
GetThreadPoolStats
(
out
string
iocp
,
out
string
worker
)
{
{
ThreadPool
.
GetMaxThreads
(
out
int
maxWorkerThreads
,
out
int
maxIoThreads
);
ThreadPool
.
GetMaxThreads
(
out
int
maxWorkerThreads
,
out
int
maxIoThreads
);
...
@@ -2137,7 +2118,6 @@ private static int GetThreadPoolStats(out string iocp, out string worker)
...
@@ -2137,7 +2118,6 @@ private static int GetThreadPoolStats(out string iocp, out string worker)
worker
=
$"(Busy=
{
busyWorkerThreads
}
,Free=
{
freeWorkerThreads
}
,Min=
{
minWorkerThreads
}
,Max=
{
maxWorkerThreads
}
)"
;
worker
=
$"(Busy=
{
busyWorkerThreads
}
,Free=
{
freeWorkerThreads
}
,Min=
{
minWorkerThreads
}
,Max=
{
maxWorkerThreads
}
)"
;
return
busyWorkerThreads
;
return
busyWorkerThreads
;
}
}
#endif
/// <summary>
/// <summary>
/// Should exceptions include identifiable details? (key names, additional .Data annotations)
/// Should exceptions include identifiable details? (key names, additional .Data annotations)
...
...
StackExchange.Redis/StackExchange/Redis/Exceptions.cs
View file @
c54c0671
using
System
;
using
System
;
#if FEATURE_SERIALIZATION
using
System.Runtime.Serialization
;
using
System.Runtime.Serialization
;
#endif
#pragma warning disable RCS1194 // Implement exception constructors.
#pragma warning disable RCS1194 // Implement exception constructors.
namespace
StackExchange.Redis
namespace
StackExchange.Redis
{
{
#if FEATURE_SERIALIZATION
[
Serializable
]
public
sealed
partial
class
RedisCommandException
:
Exception
{
private
RedisCommandException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
}
}
[
Serializable
]
public
sealed
partial
class
RedisTimeoutException
:
TimeoutException
{
private
RedisTimeoutException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
Commandstatus
=
(
CommandStatus
)
info
.
GetValue
(
"commandStatus"
,
typeof
(
CommandStatus
));
}
/// <summary>
/// Serialization implementation; not intended for general usage
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Serialization context.</param>
public
override
void
GetObjectData
(
SerializationInfo
info
,
StreamingContext
context
)
{
base
.
GetObjectData
(
info
,
context
);
info
.
AddValue
(
"commandStatus"
,
Commandstatus
);
}
}
[
Serializable
]
public
sealed
partial
class
RedisConnectionException
:
RedisException
{
private
RedisConnectionException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
FailureType
=
(
ConnectionFailureType
)
info
.
GetInt32
(
"failureType"
);
CommandStatus
=
(
CommandStatus
)
info
.
GetValue
(
"commandStatus"
,
typeof
(
CommandStatus
));
}
/// <summary>
/// Serialization implementation; not intended for general usage
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Serialization context.</param>
public
override
void
GetObjectData
(
SerializationInfo
info
,
StreamingContext
context
)
{
base
.
GetObjectData
(
info
,
context
);
info
.
AddValue
(
"failureType"
,
(
int
)
FailureType
);
info
.
AddValue
(
"commandStatus"
,
CommandStatus
);
}
}
[
Serializable
]
public
partial
class
RedisException
:
Exception
{
/// <summary>
/// Deserialization constructor; not intended for general usage
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="ctx">Serialization context.</param>
protected
RedisException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
}
}
[
Serializable
]
public
sealed
partial
class
RedisServerException
:
RedisException
{
private
RedisServerException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
}
}
#endif
/// <summary>
/// <summary>
/// Indicates that a command was illegal and was not sent to the server
/// Indicates that a command was illegal and was not sent to the server
/// </summary>
/// </summary>
[
Serializable
]
public
sealed
partial
class
RedisCommandException
:
Exception
public
sealed
partial
class
RedisCommandException
:
Exception
{
{
/// <summary>
/// <summary>
...
@@ -88,11 +22,14 @@ public sealed partial class RedisCommandException : Exception
...
@@ -88,11 +22,14 @@ public sealed partial class RedisCommandException : Exception
/// <param name="message">The message for the exception.</param>
/// <param name="message">The message for the exception.</param>
/// <param name="innerException">The inner exception.</param>
/// <param name="innerException">The inner exception.</param>
public
RedisCommandException
(
string
message
,
Exception
innerException
)
:
base
(
message
,
innerException
)
{
}
public
RedisCommandException
(
string
message
,
Exception
innerException
)
:
base
(
message
,
innerException
)
{
}
private
RedisCommandException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
}
}
}
/// <summary>
/// <summary>
/// Indicates the time allotted for a command or operation has expired.
/// Indicates the time allotted for a command or operation has expired.
/// </summary>
/// </summary>
[
Serializable
]
public
sealed
partial
class
RedisTimeoutException
:
TimeoutException
public
sealed
partial
class
RedisTimeoutException
:
TimeoutException
{
{
/// <summary>
/// <summary>
...
@@ -109,11 +46,27 @@ public RedisTimeoutException(string message, CommandStatus commandStatus) : base
...
@@ -109,11 +46,27 @@ public RedisTimeoutException(string message, CommandStatus commandStatus) : base
/// status of the command while communicating with Redis
/// status of the command while communicating with Redis
/// </summary>
/// </summary>
public
CommandStatus
Commandstatus
{
get
;
}
public
CommandStatus
Commandstatus
{
get
;
}
private
RedisTimeoutException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
Commandstatus
=
(
CommandStatus
)
info
.
GetValue
(
"commandStatus"
,
typeof
(
CommandStatus
));
}
/// <summary>
/// Serialization implementation; not intended for general usage
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Serialization context.</param>
public
override
void
GetObjectData
(
SerializationInfo
info
,
StreamingContext
context
)
{
base
.
GetObjectData
(
info
,
context
);
info
.
AddValue
(
"commandStatus"
,
Commandstatus
);
}
}
}
/// <summary>
/// <summary>
/// Indicates a connection fault when communicating with redis
/// Indicates a connection fault when communicating with redis
/// </summary>
/// </summary>
[
Serializable
]
public
sealed
partial
class
RedisConnectionException
:
RedisException
public
sealed
partial
class
RedisConnectionException
:
RedisException
{
{
/// <summary>
/// <summary>
...
@@ -153,11 +106,29 @@ public RedisConnectionException(ConnectionFailureType failureType, string messag
...
@@ -153,11 +106,29 @@ public RedisConnectionException(ConnectionFailureType failureType, string messag
/// status of the command while communicating with Redis
/// status of the command while communicating with Redis
/// </summary>
/// </summary>
public
CommandStatus
CommandStatus
{
get
;
}
public
CommandStatus
CommandStatus
{
get
;
}
private
RedisConnectionException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
FailureType
=
(
ConnectionFailureType
)
info
.
GetInt32
(
"failureType"
);
CommandStatus
=
(
CommandStatus
)
info
.
GetValue
(
"commandStatus"
,
typeof
(
CommandStatus
));
}
/// <summary>
/// Serialization implementation; not intended for general usage
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="context">Serialization context.</param>
public
override
void
GetObjectData
(
SerializationInfo
info
,
StreamingContext
context
)
{
base
.
GetObjectData
(
info
,
context
);
info
.
AddValue
(
"failureType"
,
(
int
)
FailureType
);
info
.
AddValue
(
"commandStatus"
,
CommandStatus
);
}
}
}
/// <summary>
/// <summary>
/// Indicates an issue communicating with redis
/// Indicates an issue communicating with redis
/// </summary>
/// </summary>
[
Serializable
]
public
partial
class
RedisException
:
Exception
public
partial
class
RedisException
:
Exception
{
{
/// <summary>
/// <summary>
...
@@ -172,11 +143,19 @@ public partial class RedisException : Exception
...
@@ -172,11 +143,19 @@ public partial class RedisException : Exception
/// <param name="message">The message for the exception.</param>
/// <param name="message">The message for the exception.</param>
/// <param name="innerException">The inner exception.</param>
/// <param name="innerException">The inner exception.</param>
public
RedisException
(
string
message
,
Exception
innerException
)
:
base
(
message
,
innerException
)
{
}
public
RedisException
(
string
message
,
Exception
innerException
)
:
base
(
message
,
innerException
)
{
}
/// <summary>
/// Deserialization constructor; not intended for general usage
/// </summary>
/// <param name="info">Serialization info.</param>
/// <param name="ctx">Serialization context.</param>
protected
RedisException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
}
}
}
/// <summary>
/// <summary>
/// Indicates an exception raised by a redis server
/// Indicates an exception raised by a redis server
/// </summary>
/// </summary>
[
Serializable
]
public
sealed
partial
class
RedisServerException
:
RedisException
public
sealed
partial
class
RedisServerException
:
RedisException
{
{
/// <summary>
/// <summary>
...
@@ -184,5 +163,7 @@ public sealed partial class RedisServerException : RedisException
...
@@ -184,5 +163,7 @@ public sealed partial class RedisServerException : RedisException
/// </summary>
/// </summary>
/// <param name="message">The message for the exception.</param>
/// <param name="message">The message for the exception.</param>
public
RedisServerException
(
string
message
)
:
base
(
message
)
{
}
public
RedisServerException
(
string
message
)
:
base
(
message
)
{
}
private
RedisServerException
(
SerializationInfo
info
,
StreamingContext
ctx
)
:
base
(
info
,
ctx
)
{
}
}
}
}
}
StackExchange.Redis/StackExchange/Redis/ExtensionMethods.cs
View file @
c54c0671
...
@@ -131,7 +131,7 @@ public static string[] ToStringArray(this RedisValue[] values)
...
@@ -131,7 +131,7 @@ public static string[] ToStringArray(this RedisValue[] values)
{
{
if
(
values
==
null
)
return
null
;
if
(
values
==
null
)
return
null
;
if
(
values
.
Length
==
0
)
return
nix
;
if
(
values
.
Length
==
0
)
return
nix
;
return
ConvertHelper
.
ConvertAll
(
values
,
x
=>
(
string
)
x
);
return
Array
.
ConvertAll
(
values
,
x
=>
(
string
)
x
);
}
}
internal
static
void
AuthenticateAsClient
(
this
SslStream
ssl
,
string
host
,
SslProtocols
?
allowedProtocols
)
internal
static
void
AuthenticateAsClient
(
this
SslStream
ssl
,
string
host
,
SslProtocols
?
allowedProtocols
)
...
@@ -145,21 +145,12 @@ internal static void AuthenticateAsClient(this SslStream ssl, string host, SslPr
...
@@ -145,21 +145,12 @@ internal static void AuthenticateAsClient(this SslStream ssl, string host, SslPr
var
certificateCollection
=
new
X509CertificateCollection
();
var
certificateCollection
=
new
X509CertificateCollection
();
const
bool
checkCertRevocation
=
true
;
const
bool
checkCertRevocation
=
true
;
#if NETSTANDARD1_5
ssl
.
AuthenticateAsClientAsync
(
host
,
certificateCollection
,
allowedProtocols
.
Value
,
checkCertRevocation
)
.
GetAwaiter
().
GetResult
();
#else
ssl
.
AuthenticateAsClient
(
host
,
certificateCollection
,
allowedProtocols
.
Value
,
checkCertRevocation
);
ssl
.
AuthenticateAsClient
(
host
,
certificateCollection
,
allowedProtocols
.
Value
,
checkCertRevocation
);
#endif
}
}
private
static
void
AuthenticateAsClientUsingDefaultProtocols
(
SslStream
ssl
,
string
host
)
private
static
void
AuthenticateAsClientUsingDefaultProtocols
(
SslStream
ssl
,
string
host
)
{
{
#if NETSTANDARD1_5
ssl
.
AuthenticateAsClientAsync
(
host
).
GetAwaiter
().
GetResult
();
#else
ssl
.
AuthenticateAsClient
(
host
);
ssl
.
AuthenticateAsClient
(
host
);
#endif
}
}
}
}
}
}
StackExchange.Redis/StackExchange/Redis/PhysicalBridge.cs
View file @
c54c0671
...
@@ -377,7 +377,7 @@ internal void OnHeartbeat(bool ifConnectedOnly)
...
@@ -377,7 +377,7 @@ internal void OnHeartbeat(bool ifConnectedOnly)
switch
(
state
)
switch
(
state
)
{
{
case
(
int
)
State
.
Connecting
:
case
(
int
)
State
.
Connecting
:
int
connectTimeMilliseconds
=
unchecked
(
Environment
.
TickCount
-
VolatileWrapper
.
Read
(
ref
connectStartTicks
));
int
connectTimeMilliseconds
=
unchecked
(
Environment
.
TickCount
-
Thread
.
Volatile
Read
(
ref
connectStartTicks
));
bool
shouldRetry
=
Multiplexer
.
RawConfig
.
ReconnectRetryPolicy
.
ShouldRetry
(
Interlocked
.
Read
(
ref
connectTimeoutRetryCount
),
connectTimeMilliseconds
);
bool
shouldRetry
=
Multiplexer
.
RawConfig
.
ReconnectRetryPolicy
.
ShouldRetry
(
Interlocked
.
Read
(
ref
connectTimeoutRetryCount
),
connectTimeMilliseconds
);
if
(
shouldRetry
)
if
(
shouldRetry
)
{
{
...
...
StackExchange.Redis/StackExchange/Redis/PhysicalConnection.cs
View file @
c54c0671
...
@@ -10,9 +10,6 @@
...
@@ -10,9 +10,6 @@
using
System.Security.Cryptography.X509Certificates
;
using
System.Security.Cryptography.X509Certificates
;
using
System.Text
;
using
System.Text
;
using
System.Threading
;
using
System.Threading
;
#if NETSTANDARD1_5
using
System.Threading.Tasks
;
#endif
namespace
StackExchange.Redis
namespace
StackExchange.Redis
{
{
...
@@ -24,28 +21,6 @@ internal sealed partial class PhysicalConnection : IDisposable, ISocketCallback
...
@@ -24,28 +21,6 @@ internal sealed partial class PhysicalConnection : IDisposable, ISocketCallback
private
static
readonly
byte
[]
Crlf
=
Encoding
.
ASCII
.
GetBytes
(
"\r\n"
);
private
static
readonly
byte
[]
Crlf
=
Encoding
.
ASCII
.
GetBytes
(
"\r\n"
);
#if NETSTANDARD1_5
private
readonly
Action
<
Task
<
int
>>
endRead
;
private
static
Action
<
Task
<
int
>>
EndReadFactory
(
PhysicalConnection
physical
)
{
return
result
=>
{
// can't capture AsyncState on SocketRead, so we'll do it once per physical instead
if
(
result
.
IsFaulted
)
{
GC
.
KeepAlive
(
result
.
Exception
);
}
try
{
physical
.
Multiplexer
.
Trace
(
"Completed asynchronously: processing in callback"
,
physical
.
physicalName
);
if
(
physical
.
EndReading
(
result
))
physical
.
BeginReading
();
}
catch
(
Exception
ex
)
{
physical
.
RecordConnectionFailed
(
ConnectionFailureType
.
InternalFailure
,
ex
);
}
};
}
#else
private
static
readonly
AsyncCallback
endRead
=
result
=>
private
static
readonly
AsyncCallback
endRead
=
result
=>
{
{
PhysicalConnection
physical
;
PhysicalConnection
physical
;
...
@@ -60,7 +35,6 @@ private static Action<Task<int>> EndReadFactory(PhysicalConnection physical)
...
@@ -60,7 +35,6 @@ private static Action<Task<int>> EndReadFactory(PhysicalConnection physical)
physical
.
RecordConnectionFailed
(
ConnectionFailureType
.
InternalFailure
,
ex
);
physical
.
RecordConnectionFailed
(
ConnectionFailureType
.
InternalFailure
,
ex
);
}
}
};
};
#endif
private
static
readonly
byte
[]
message
=
Encoding
.
UTF8
.
GetBytes
(
"message"
),
pmessage
=
Encoding
.
UTF8
.
GetBytes
(
"pmessage"
);
private
static
readonly
byte
[]
message
=
Encoding
.
UTF8
.
GetBytes
(
"message"
),
pmessage
=
Encoding
.
UTF8
.
GetBytes
(
"pmessage"
);
...
@@ -108,15 +82,12 @@ public PhysicalConnection(PhysicalBridge bridge)
...
@@ -108,15 +82,12 @@ public PhysicalConnection(PhysicalBridge bridge)
var
endpoint
=
bridge
.
ServerEndPoint
.
EndPoint
;
var
endpoint
=
bridge
.
ServerEndPoint
.
EndPoint
;
physicalName
=
connectionType
+
"#"
+
Interlocked
.
Increment
(
ref
totalCount
)
+
"@"
+
Format
.
ToString
(
endpoint
);
physicalName
=
connectionType
+
"#"
+
Interlocked
.
Increment
(
ref
totalCount
)
+
"@"
+
Format
.
ToString
(
endpoint
);
Bridge
=
bridge
;
Bridge
=
bridge
;
#if NETSTANDARD1_5
endRead
=
EndReadFactory
(
this
);
#endif
OnCreateEcho
();
OnCreateEcho
();
}
}
public
void
BeginConnect
(
TextWriter
log
)
public
void
BeginConnect
(
TextWriter
log
)
{
{
VolatileWrapper
.
Write
(
ref
firstUnansweredWriteTickCount
,
0
);
Thread
.
Volatile
Write
(
ref
firstUnansweredWriteTickCount
,
0
);
var
endpoint
=
Bridge
.
ServerEndPoint
.
EndPoint
;
var
endpoint
=
Bridge
.
ServerEndPoint
.
EndPoint
;
Multiplexer
.
Trace
(
"Connecting..."
,
physicalName
);
Multiplexer
.
Trace
(
"Connecting..."
,
physicalName
);
...
@@ -132,7 +103,7 @@ private enum ReadMode : byte
...
@@ -132,7 +103,7 @@ private enum ReadMode : byte
public
PhysicalBridge
Bridge
{
get
;
}
public
PhysicalBridge
Bridge
{
get
;
}
public
long
LastWriteSecondsAgo
=>
unchecked
(
Environment
.
TickCount
-
VolatileWrapper
.
Read
(
ref
lastWriteTickCount
))
/
1000
;
public
long
LastWriteSecondsAgo
=>
unchecked
(
Environment
.
TickCount
-
Thread
.
Volatile
Read
(
ref
lastWriteTickCount
))
/
1000
;
public
ConnectionMultiplexer
Multiplexer
{
get
;
}
public
ConnectionMultiplexer
Multiplexer
{
get
;
}
...
@@ -145,17 +116,13 @@ public void Dispose()
...
@@ -145,17 +116,13 @@ public void Dispose()
if
(
outStream
!=
null
)
if
(
outStream
!=
null
)
{
{
Multiplexer
.
Trace
(
"Disconnecting..."
,
physicalName
);
Multiplexer
.
Trace
(
"Disconnecting..."
,
physicalName
);
#if !NETSTANDARD1_5
try
{
outStream
.
Close
();
}
catch
{
}
try
{
outStream
.
Close
();
}
catch
{
}
#endif
try
{
outStream
.
Dispose
();
}
catch
{
}
try
{
outStream
.
Dispose
();
}
catch
{
}
outStream
=
null
;
outStream
=
null
;
}
}
if
(
netStream
!=
null
)
if
(
netStream
!=
null
)
{
{
#if !NETSTANDARD1_5
try
{
netStream
.
Close
();
}
catch
{
}
try
{
netStream
.
Close
();
}
catch
{
}
#endif
try
{
netStream
.
Dispose
();
}
catch
{
}
try
{
netStream
.
Dispose
();
}
catch
{
}
netStream
=
null
;
netStream
=
null
;
}
}
...
@@ -209,9 +176,9 @@ public void RecordConnectionFailed(ConnectionFailureType failureType, ref Socket
...
@@ -209,9 +176,9 @@ public void RecordConnectionFailed(ConnectionFailureType failureType, ref Socket
if
(
isCurrent
&&
Interlocked
.
CompareExchange
(
ref
failureReported
,
1
,
0
)
==
0
)
if
(
isCurrent
&&
Interlocked
.
CompareExchange
(
ref
failureReported
,
1
,
0
)
==
0
)
{
{
managerState
=
SocketManager
.
ManagerState
.
RecordConnectionFailed_ReportFailure
;
managerState
=
SocketManager
.
ManagerState
.
RecordConnectionFailed_ReportFailure
;
int
now
=
Environment
.
TickCount
,
lastRead
=
VolatileWrapper
.
Read
(
ref
lastReadTickCount
),
lastWrite
=
VolatileWrapper
.
Read
(
ref
lastWriteTickCount
),
int
now
=
Environment
.
TickCount
,
lastRead
=
Thread
.
VolatileRead
(
ref
lastReadTickCount
),
lastWrite
=
Thread
.
Volatile
Read
(
ref
lastWriteTickCount
),
lastBeat
=
VolatileWrapper
.
Read
(
ref
lastBeatTickCount
);
lastBeat
=
Thread
.
Volatile
Read
(
ref
lastBeatTickCount
);
int
unansweredRead
=
VolatileWrapper
.
Read
(
ref
firstUnansweredWriteTickCount
);
int
unansweredRead
=
Thread
.
Volatile
Read
(
ref
firstUnansweredWriteTickCount
);
var
exMessage
=
new
StringBuilder
(
failureType
.
ToString
());
var
exMessage
=
new
StringBuilder
(
failureType
.
ToString
());
...
@@ -646,19 +613,6 @@ private unsafe void WriteRaw(Stream stream, string value, int encodedLength)
...
@@ -646,19 +613,6 @@ private unsafe void WriteRaw(Stream stream, string value, int encodedLength)
}
}
else
else
{
{
#if NETSTANDARD1_5
int
charsRemaining
=
value
.
Length
,
charOffset
=
0
,
bytesWritten
;
var
valueCharArray
=
value
.
ToCharArray
();
while
(
charsRemaining
>
Scratch_CharsPerBlock
)
{
bytesWritten
=
outEncoder
.
GetBytes
(
valueCharArray
,
charOffset
,
Scratch_CharsPerBlock
,
outScratch
,
0
,
false
);
stream
.
Write
(
outScratch
,
0
,
bytesWritten
);
charOffset
+=
Scratch_CharsPerBlock
;
charsRemaining
-=
Scratch_CharsPerBlock
;
}
bytesWritten
=
outEncoder
.
GetBytes
(
valueCharArray
,
charOffset
,
charsRemaining
,
outScratch
,
0
,
true
);
if
(
bytesWritten
!=
0
)
stream
.
Write
(
outScratch
,
0
,
bytesWritten
);
#else
fixed
(
char
*
c
=
value
)
fixed
(
char
*
c
=
value
)
fixed
(
byte
*
b
=
outScratch
)
fixed
(
byte
*
b
=
outScratch
)
{
{
...
@@ -673,7 +627,6 @@ private unsafe void WriteRaw(Stream stream, string value, int encodedLength)
...
@@ -673,7 +627,6 @@ private unsafe void WriteRaw(Stream stream, string value, int encodedLength)
bytesWritten
=
outEncoder
.
GetBytes
(
c
+
charOffset
,
charsRemaining
,
b
,
ScratchSize
,
true
);
bytesWritten
=
outEncoder
.
GetBytes
(
c
+
charOffset
,
charsRemaining
,
b
,
ScratchSize
,
true
);
if
(
bytesWritten
!=
0
)
stream
.
Write
(
outScratch
,
0
,
bytesWritten
);
if
(
bytesWritten
!=
0
)
stream
.
Write
(
outScratch
,
0
,
bytesWritten
);
}
}
#endif
}
}
}
}
...
@@ -721,36 +674,15 @@ private void BeginReading()
...
@@ -721,36 +674,15 @@ private void BeginReading()
keepReading
=
false
;
keepReading
=
false
;
int
space
=
EnsureSpaceAndComputeBytesToRead
();
int
space
=
EnsureSpaceAndComputeBytesToRead
();
Multiplexer
.
Trace
(
"Beginning async read..."
,
physicalName
);
Multiplexer
.
Trace
(
"Beginning async read..."
,
physicalName
);
#if NETSTANDARD1_5
var
result
=
netStream
.
ReadAsync
(
ioBuffer
,
ioBufferBytes
,
space
);
switch
(
result
.
Status
)
{
case
TaskStatus
.
RanToCompletion
:
case
TaskStatus
.
Faulted
:
Multiplexer
.
Trace
(
"Completed synchronously: processing immediately"
,
physicalName
);
keepReading
=
EndReading
(
result
);
break
;
default
:
result
.
ContinueWith
(
endRead
);
break
;
}
#else
var
result
=
netStream
.
BeginRead
(
ioBuffer
,
ioBufferBytes
,
space
,
endRead
,
this
);
var
result
=
netStream
.
BeginRead
(
ioBuffer
,
ioBufferBytes
,
space
,
endRead
,
this
);
if
(
result
.
CompletedSynchronously
)
if
(
result
.
CompletedSynchronously
)
{
{
Multiplexer
.
Trace
(
"Completed synchronously: processing immediately"
,
physicalName
);
Multiplexer
.
Trace
(
"Completed synchronously: processing immediately"
,
physicalName
);
keepReading
=
EndReading
(
result
);
keepReading
=
EndReading
(
result
);
}
}
#endif
}
while
(
keepReading
);
}
while
(
keepReading
);
}
}
#if NETSTANDARD1_5
catch
(
IOException
ex
)
catch
(
AggregateException
ex
)
{
throw
ex
.
InnerException
;
}
#endif
catch
(
System
.
IO
.
IOException
ex
)
{
{
Multiplexer
.
Trace
(
"Could not connect: "
+
ex
.
Message
,
physicalName
);
Multiplexer
.
Trace
(
"Could not connect: "
+
ex
.
Message
,
physicalName
);
}
}
...
@@ -846,22 +778,6 @@ SocketMode ISocketCallback.Connected(Stream stream, TextWriter log)
...
@@ -846,22 +778,6 @@ SocketMode ISocketCallback.Connected(Stream stream, TextWriter log)
}
}
}
}
#if NETSTANDARD1_5
private
bool
EndReading
(
Task
<
int
>
result
)
{
try
{
var
tmp
=
netStream
;
int
bytesRead
=
tmp
==
null
?
0
:
result
.
Result
;
// note we expect this to be completed
return
ProcessReadBytes
(
bytesRead
);
}
catch
(
Exception
ex
)
{
RecordConnectionFailed
(
ConnectionFailureType
.
InternalFailure
,
ex
);
return
false
;
}
}
#else
private
bool
EndReading
(
IAsyncResult
result
)
private
bool
EndReading
(
IAsyncResult
result
)
{
{
try
try
...
@@ -875,7 +791,7 @@ private bool EndReading(IAsyncResult result)
...
@@ -875,7 +791,7 @@ private bool EndReading(IAsyncResult result)
return
false
;
return
false
;
}
}
}
}
#endif
private
int
EnsureSpaceAndComputeBytesToRead
()
private
int
EnsureSpaceAndComputeBytesToRead
()
{
{
int
space
=
ioBuffer
.
Length
-
ioBufferBytes
;
int
space
=
ioBuffer
.
Length
-
ioBufferBytes
;
...
@@ -1007,7 +923,7 @@ private bool ProcessReadBytes(int bytesRead)
...
@@ -1007,7 +923,7 @@ private bool ProcessReadBytes(int bytesRead)
Interlocked
.
Exchange
(
ref
lastReadTickCount
,
Environment
.
TickCount
);
Interlocked
.
Exchange
(
ref
lastReadTickCount
,
Environment
.
TickCount
);
// reset unanswered write timestamp
// reset unanswered write timestamp
VolatileWrapper
.
Write
(
ref
firstUnansweredWriteTickCount
,
0
);
Thread
.
Volatile
Write
(
ref
firstUnansweredWriteTickCount
,
0
);
ioBufferBytes
+=
bytesRead
;
ioBufferBytes
+=
bytesRead
;
Multiplexer
.
Trace
(
"More bytes available: "
+
bytesRead
+
" ("
+
ioBufferBytes
+
")"
,
physicalName
);
Multiplexer
.
Trace
(
"More bytes available: "
+
bytesRead
+
" ("
+
ioBufferBytes
+
")"
,
physicalName
);
...
@@ -1168,7 +1084,7 @@ private RawResult TryParseResult(byte[] buffer, ref int offset, ref int count)
...
@@ -1168,7 +1084,7 @@ private RawResult TryParseResult(byte[] buffer, ref int offset, ref int count)
public
void
CheckForStaleConnection
(
ref
SocketManager
.
ManagerState
state
)
public
void
CheckForStaleConnection
(
ref
SocketManager
.
ManagerState
state
)
{
{
int
firstUnansweredWrite
=
VolatileWrapper
.
Read
(
ref
firstUnansweredWriteTickCount
);
int
firstUnansweredWrite
=
Thread
.
Volatile
Read
(
ref
firstUnansweredWriteTickCount
);
DebugEmulateStaleConnection
(
ref
firstUnansweredWrite
);
DebugEmulateStaleConnection
(
ref
firstUnansweredWrite
);
...
...
StackExchange.Redis/StackExchange/Redis/RedisResult.cs
View file @
c54c0671
...
@@ -198,7 +198,7 @@ internal override bool AsBoolean()
...
@@ -198,7 +198,7 @@ internal override bool AsBoolean()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
bool
[]
AsBooleanArray
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsBoolean
());
internal
override
bool
[]
AsBooleanArray
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsBoolean
());
internal
override
byte
[]
AsByteArray
()
internal
override
byte
[]
AsByteArray
()
{
{
...
@@ -206,7 +206,7 @@ internal override byte[] AsByteArray()
...
@@ -206,7 +206,7 @@ internal override byte[] AsByteArray()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
byte
[][]
AsByteArrayArray
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsByteArray
());
internal
override
byte
[][]
AsByteArrayArray
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsByteArray
());
internal
override
double
AsDouble
()
internal
override
double
AsDouble
()
{
{
...
@@ -214,7 +214,7 @@ internal override double AsDouble()
...
@@ -214,7 +214,7 @@ internal override double AsDouble()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
double
[]
AsDoubleArray
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsDouble
());
internal
override
double
[]
AsDoubleArray
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsDouble
());
internal
override
int
AsInt32
()
internal
override
int
AsInt32
()
{
{
...
@@ -222,7 +222,7 @@ internal override int AsInt32()
...
@@ -222,7 +222,7 @@ internal override int AsInt32()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
int
[]
AsInt32Array
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsInt32
());
internal
override
int
[]
AsInt32Array
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsInt32
());
internal
override
long
AsInt64
()
internal
override
long
AsInt64
()
{
{
...
@@ -230,7 +230,7 @@ internal override long AsInt64()
...
@@ -230,7 +230,7 @@ internal override long AsInt64()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
long
[]
AsInt64Array
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsInt64
());
internal
override
long
[]
AsInt64Array
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsInt64
());
internal
override
bool
?
AsNullableBoolean
()
internal
override
bool
?
AsNullableBoolean
()
{
{
...
@@ -262,7 +262,7 @@ internal override RedisKey AsRedisKey()
...
@@ -262,7 +262,7 @@ internal override RedisKey AsRedisKey()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
RedisKey
[]
AsRedisKeyArray
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsRedisKey
());
internal
override
RedisKey
[]
AsRedisKeyArray
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsRedisKey
());
internal
override
RedisResult
[]
AsRedisResultArray
()
=>
value
;
internal
override
RedisResult
[]
AsRedisResultArray
()
=>
value
;
...
@@ -272,7 +272,7 @@ internal override RedisValue AsRedisValue()
...
@@ -272,7 +272,7 @@ internal override RedisValue AsRedisValue()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
RedisValue
[]
AsRedisValueArray
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsRedisValue
());
internal
override
RedisValue
[]
AsRedisValueArray
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsRedisValue
());
internal
override
string
AsString
()
internal
override
string
AsString
()
{
{
...
@@ -280,7 +280,7 @@ internal override string AsString()
...
@@ -280,7 +280,7 @@ internal override string AsString()
throw
new
InvalidCastException
();
throw
new
InvalidCastException
();
}
}
internal
override
string
[]
AsStringArray
()
=>
ConvertHelper
.
ConvertAll
(
value
,
x
=>
x
.
AsString
());
internal
override
string
[]
AsStringArray
()
=>
Array
.
ConvertAll
(
value
,
x
=>
x
.
AsString
());
}
}
private
sealed
class
ErrorRedisResult
:
RedisResult
private
sealed
class
ErrorRedisResult
:
RedisResult
...
...
StackExchange.Redis/StackExchange/Redis/RedisValue.cs
View file @
c54c0671
using
System
;
using
System
;
#if NETSTANDARD1_5
using
System.Collections.Generic
;
using
System.Reflection
;
#endif
using
System.Text
;
using
System.Text
;
namespace
StackExchange.Redis
namespace
StackExchange.Redis
...
@@ -295,12 +291,7 @@ public int CompareTo(RedisValue other)
...
@@ -295,12 +291,7 @@ public int CompareTo(RedisValue other)
if
(
otherType
==
CompareType
.
Double
)
return
thisDouble
.
CompareTo
(
otherDouble
);
if
(
otherType
==
CompareType
.
Double
)
return
thisDouble
.
CompareTo
(
otherDouble
);
}
}
// otherwise, compare as strings
// otherwise, compare as strings
#if NETSTANDARD1_5
var
compareInfo
=
System
.
Globalization
.
CultureInfo
.
InvariantCulture
.
CompareInfo
;
return
compareInfo
.
Compare
((
string
)
this
,
(
string
)
other
,
System
.
Globalization
.
CompareOptions
.
Ordinal
);
#else
return
StringComparer
.
InvariantCulture
.
Compare
((
string
)
this
,
(
string
)
other
);
return
StringComparer
.
InvariantCulture
.
Compare
((
string
)
this
,
(
string
)
other
);
#endif
}
}
catch
(
Exception
ex
)
catch
(
Exception
ex
)
{
{
...
@@ -575,7 +566,7 @@ object IConvertible.ToType(Type conversionType, IFormatProvider provider)
...
@@ -575,7 +566,7 @@ object IConvertible.ToType(Type conversionType, IFormatProvider provider)
if
(
conversionType
==
null
)
throw
new
ArgumentNullException
(
nameof
(
conversionType
));
if
(
conversionType
==
null
)
throw
new
ArgumentNullException
(
nameof
(
conversionType
));
if
(
conversionType
==
typeof
(
byte
[]))
return
(
byte
[])
this
;
if
(
conversionType
==
typeof
(
byte
[]))
return
(
byte
[])
this
;
if
(
conversionType
==
typeof
(
RedisValue
))
return
this
;
if
(
conversionType
==
typeof
(
RedisValue
))
return
this
;
switch
(
conversionType
.
GetTypeCode
(
))
switch
(
Type
.
GetTypeCode
(
conversionType
))
{
{
case
TypeCode
.
Boolean
:
return
(
bool
)
this
;
case
TypeCode
.
Boolean
:
return
(
bool
)
this
;
case
TypeCode
.
Byte
:
return
(
byte
)
this
;
case
TypeCode
.
Byte
:
return
(
byte
)
this
;
...
@@ -669,47 +660,4 @@ public bool TryParse(out double val)
...
@@ -669,47 +660,4 @@ public bool TryParse(out double val)
return
TryParseDouble
(
blob
,
out
val
);
return
TryParseDouble
(
blob
,
out
val
);
}
}
}
}
}
internal
static
class
ReflectionExtensions
{
#if NETSTANDARD1_5
internal
static
TypeCode
GetTypeCode
(
this
Type
type
)
{
if
(
type
==
null
)
return
TypeCode
.
Empty
;
if
(
typeCodeLookup
.
TryGetValue
(
type
,
out
TypeCode
result
))
return
result
;
if
(
type
.
GetTypeInfo
().
IsEnum
)
{
type
=
Enum
.
GetUnderlyingType
(
type
);
if
(
typeCodeLookup
.
TryGetValue
(
type
,
out
result
))
return
result
;
}
return
TypeCode
.
Object
;
}
private
static
readonly
Dictionary
<
Type
,
TypeCode
>
typeCodeLookup
=
new
Dictionary
<
Type
,
TypeCode
>
{
{
typeof
(
bool
),
TypeCode
.
Boolean
},
{
typeof
(
byte
),
TypeCode
.
Byte
},
{
typeof
(
char
),
TypeCode
.
Char
},
{
typeof
(
DateTime
),
TypeCode
.
DateTime
},
{
typeof
(
decimal
),
TypeCode
.
Decimal
},
{
typeof
(
double
),
TypeCode
.
Double
},
{
typeof
(
short
),
TypeCode
.
Int16
},
{
typeof
(
int
),
TypeCode
.
Int32
},
{
typeof
(
long
),
TypeCode
.
Int64
},
{
typeof
(
object
),
TypeCode
.
Object
},
{
typeof
(
sbyte
),
TypeCode
.
SByte
},
{
typeof
(
float
),
TypeCode
.
Single
},
{
typeof
(
string
),
TypeCode
.
String
},
{
typeof
(
ushort
),
TypeCode
.
UInt16
},
{
typeof
(
uint
),
TypeCode
.
UInt32
},
{
typeof
(
ulong
),
TypeCode
.
UInt64
},
};
#else
internal
static
TypeCode
GetTypeCode
(
this
Type
type
)
{
return
Type
.
GetTypeCode
(
type
);
}
#endif
}
}
\ No newline at end of file
StackExchange.Redis/StackExchange/Redis/ResultBox.cs
View file @
c54c0671
...
@@ -97,9 +97,7 @@ public override bool TryComplete(bool isAsync)
...
@@ -97,9 +97,7 @@ public override bool TryComplete(bool isAsync)
{
{
if
(
stateOrCompletionSource
is
TaskCompletionSource
<
T
>
tcs
)
if
(
stateOrCompletionSource
is
TaskCompletionSource
<
T
>
tcs
)
{
{
#if !PLAT_SAFE_CONTINUATIONS // we don't need to check in this scenario
if
(
isAsync
||
TaskSource
.
IsSyncSafe
(
tcs
.
Task
))
if
(
isAsync
||
TaskSource
.
IsSyncSafe
(
tcs
.
Task
))
#endif
{
{
UnwrapAndRecycle
(
this
,
true
,
out
T
val
,
out
Exception
ex
);
UnwrapAndRecycle
(
this
,
true
,
out
T
val
,
out
Exception
ex
);
...
@@ -117,12 +115,10 @@ public override bool TryComplete(bool isAsync)
...
@@ -117,12 +115,10 @@ public override bool TryComplete(bool isAsync)
}
}
return
true
;
return
true
;
}
}
#if !PLAT_SAFE_CONTINUATIONS
else
else
{
// looks like continuations; push to async to preserve the reader thread
{
// looks like continuations; push to async to preserve the reader thread
return
false
;
return
false
;
}
}
#endif
}
}
else
else
{
{
...
...
StackExchange.Redis/StackExchange/Redis/ScriptParameterMapper.cs
View file @
c54c0671
...
@@ -316,11 +316,7 @@ private static void PrefixIfNeeded(ILGenerator il, LocalBuilder needsPrefixBool,
...
@@ -316,11 +316,7 @@ private static void PrefixIfNeeded(ILGenerator il, LocalBuilder needsPrefixBool,
LocalBuilder
redisKeyLoc
=
null
;
LocalBuilder
redisKeyLoc
=
null
;
var
loc
=
il
.
DeclareLocal
(
t
);
var
loc
=
il
.
DeclareLocal
(
t
);
il
.
Emit
(
OpCodes
.
Ldarg_0
);
// object
il
.
Emit
(
OpCodes
.
Ldarg_0
);
// object
#if NETSTANDARD1_5
if
(
t
.
GetTypeInfo
().
IsValueType
)
#else
if
(
t
.
IsValueType
)
if
(
t
.
IsValueType
)
#endif
{
{
il
.
Emit
(
OpCodes
.
Unbox_Any
,
t
);
// T
il
.
Emit
(
OpCodes
.
Unbox_Any
,
t
);
// T
}
}
...
@@ -351,11 +347,7 @@ private static void PrefixIfNeeded(ILGenerator il, LocalBuilder needsPrefixBool,
...
@@ -351,11 +347,7 @@ private static void PrefixIfNeeded(ILGenerator il, LocalBuilder needsPrefixBool,
{
{
il
.
Emit
(
OpCodes
.
Dup
);
// RedisKey[] RedisKey[]
il
.
Emit
(
OpCodes
.
Dup
);
// RedisKey[] RedisKey[]
il
.
Emit
(
OpCodes
.
Ldc_I4
,
i
);
// RedisKey[] RedisKey[] int
il
.
Emit
(
OpCodes
.
Ldc_I4
,
i
);
// RedisKey[] RedisKey[] int
#if NETSTANDARD1_5
if
(
t
.
GetTypeInfo
().
IsValueType
)
#else
if
(
t
.
IsValueType
)
if
(
t
.
IsValueType
)
#endif
{
{
il
.
Emit
(
OpCodes
.
Ldloca
,
loc
);
// RedisKey[] RedisKey[] int T*
il
.
Emit
(
OpCodes
.
Ldloca
,
loc
);
// RedisKey[] RedisKey[] int T*
}
}
...
@@ -383,11 +375,7 @@ private static void PrefixIfNeeded(ILGenerator il, LocalBuilder needsPrefixBool,
...
@@ -383,11 +375,7 @@ private static void PrefixIfNeeded(ILGenerator il, LocalBuilder needsPrefixBool,
{
{
il
.
Emit
(
OpCodes
.
Dup
);
// RedisKey[] RedisValue[] RedisValue[]
il
.
Emit
(
OpCodes
.
Dup
);
// RedisKey[] RedisValue[] RedisValue[]
il
.
Emit
(
OpCodes
.
Ldc_I4
,
i
);
// RedisKey[] RedisValue[] RedisValue[] int
il
.
Emit
(
OpCodes
.
Ldc_I4
,
i
);
// RedisKey[] RedisValue[] RedisValue[] int
#if NETSTANDARD1_5
if
(
t
.
GetTypeInfo
().
IsValueType
)
#else
if
(
t
.
IsValueType
)
if
(
t
.
IsValueType
)
#endif
{
{
il
.
Emit
(
OpCodes
.
Ldloca
,
loc
);
// RedisKey[] RedisValue[] RedisValue[] int T*
il
.
Emit
(
OpCodes
.
Ldloca
,
loc
);
// RedisKey[] RedisValue[] RedisValue[] int T*
}
}
...
...
StackExchange.Redis/StackExchange/Redis/ServerEndPoint.cs
View file @
c54c0671
...
@@ -483,7 +483,7 @@ internal void OnFullyEstablished(PhysicalConnection connection)
...
@@ -483,7 +483,7 @@ internal void OnFullyEstablished(PhysicalConnection connection)
internal
int
LastInfoReplicationCheckSecondsAgo
internal
int
LastInfoReplicationCheckSecondsAgo
{
{
get
{
return
unchecked
(
Environment
.
TickCount
-
VolatileWrapper
.
Read
(
ref
lastInfoReplicationCheckTicks
))
/
1000
;
}
get
{
return
unchecked
(
Environment
.
TickCount
-
Thread
.
Volatile
Read
(
ref
lastInfoReplicationCheckTicks
))
/
1000
;
}
}
}
private
EndPoint
masterEndPoint
;
private
EndPoint
masterEndPoint
;
...
...
StackExchange.Redis/StackExchange/Redis/SocketManager.cs
View file @
c54c0671
...
@@ -4,10 +4,6 @@
...
@@ -4,10 +4,6 @@
using
System.Net
;
using
System.Net
;
using
System.Net.Sockets
;
using
System.Net.Sockets
;
using
System.Threading
;
using
System.Threading
;
#if NETSTANDARD1_5
using
System.Runtime.InteropServices
;
using
System.Threading.Tasks
;
#endif
namespace
StackExchange.Redis
namespace
StackExchange.Redis
{
{
...
@@ -146,12 +142,8 @@ public SocketManager(string name, bool useHighPrioritySocketThreads)
...
@@ -146,12 +142,8 @@ public SocketManager(string name, bool useHighPrioritySocketThreads)
// we need a dedicated writer, because when under heavy ambient load
// we need a dedicated writer, because when under heavy ambient load
// (a busy asp.net site, for example), workers are not reliable enough
// (a busy asp.net site, for example), workers are not reliable enough
#if NETSTANDARD1_5
var
dedicatedWriter
=
new
Thread
(
writeAllQueues
);
#else
var
dedicatedWriter
=
new
Thread
(
writeAllQueues
,
32
*
1024
);
// don't need a huge stack;
var
dedicatedWriter
=
new
Thread
(
writeAllQueues
,
32
*
1024
);
// don't need a huge stack;
dedicatedWriter
.
Priority
=
useHighPrioritySocketThreads
?
ThreadPriority
.
AboveNormal
:
ThreadPriority
.
Normal
;
dedicatedWriter
.
Priority
=
useHighPrioritySocketThreads
?
ThreadPriority
.
AboveNormal
:
ThreadPriority
.
Normal
;
#endif
dedicatedWriter
.
Name
=
name
+
":Write"
;
dedicatedWriter
.
Name
=
name
+
":Write"
;
dedicatedWriter
.
IsBackground
=
true
;
// should not keep process alive
dedicatedWriter
.
IsBackground
=
true
;
// should not keep process alive
dedicatedWriter
.
Start
(
this
);
// will self-exit when disposed
dedicatedWriter
.
Start
(
this
);
// will self-exit when disposed
...
@@ -179,7 +171,6 @@ public void Dispose()
...
@@ -179,7 +171,6 @@ public void Dispose()
internal
SocketToken
BeginConnect
(
EndPoint
endpoint
,
ISocketCallback
callback
,
ConnectionMultiplexer
multiplexer
,
TextWriter
log
)
internal
SocketToken
BeginConnect
(
EndPoint
endpoint
,
ISocketCallback
callback
,
ConnectionMultiplexer
multiplexer
,
TextWriter
log
)
{
{
#if !NETSTANDARD1_5
void
RunWithCompletionType
(
Func
<
AsyncCallback
,
IAsyncResult
>
beginAsync
,
AsyncCallback
asyncCallback
)
void
RunWithCompletionType
(
Func
<
AsyncCallback
,
IAsyncResult
>
beginAsync
,
AsyncCallback
asyncCallback
)
{
{
void
proxyCallback
(
IAsyncResult
ar
)
void
proxyCallback
(
IAsyncResult
ar
)
...
@@ -197,7 +188,6 @@ void proxyCallback(IAsyncResult ar)
...
@@ -197,7 +188,6 @@ void proxyCallback(IAsyncResult ar)
asyncCallback
(
result
);
asyncCallback
(
result
);
}
}
}
}
#endif
var
addressFamily
=
endpoint
.
AddressFamily
==
AddressFamily
.
Unspecified
?
AddressFamily
.
InterNetwork
:
endpoint
.
AddressFamily
;
var
addressFamily
=
endpoint
.
AddressFamily
==
AddressFamily
.
Unspecified
?
AddressFamily
.
InterNetwork
:
endpoint
.
AddressFamily
;
var
socket
=
new
Socket
(
addressFamily
,
SocketType
.
Stream
,
ProtocolType
.
Tcp
);
var
socket
=
new
Socket
(
addressFamily
,
SocketType
.
Stream
,
ProtocolType
.
Tcp
);
...
@@ -211,14 +201,6 @@ void proxyCallback(IAsyncResult ar)
...
@@ -211,14 +201,6 @@ void proxyCallback(IAsyncResult ar)
// A work-around for a Mono bug in BeginConnect(EndPoint endpoint, AsyncCallback callback, object state)
// A work-around for a Mono bug in BeginConnect(EndPoint endpoint, AsyncCallback callback, object state)
if
(
endpoint
is
DnsEndPoint
dnsEndpoint
)
if
(
endpoint
is
DnsEndPoint
dnsEndpoint
)
{
{
#if NETSTANDARD1_5 // No BeginConnect there, because everything was an Async push...we should drop this
socket
.
ConnectAsync
(
dnsEndpoint
.
Host
,
dnsEndpoint
.
Port
).
ContinueWith
(
t
=>
{
multiplexer
.
LogLocked
(
log
,
"EndConnect: {0}"
,
formattedEndpoint
);
EndConnectImpl
(
t
,
multiplexer
,
log
,
tuple
);
multiplexer
.
LogLocked
(
log
,
"Connect complete: {0}"
,
formattedEndpoint
);
});
#else
RunWithCompletionType
(
RunWithCompletionType
(
cb
=>
socket
.
BeginConnect
(
dnsEndpoint
.
Host
,
dnsEndpoint
.
Port
,
cb
,
tuple
),
cb
=>
socket
.
BeginConnect
(
dnsEndpoint
.
Host
,
dnsEndpoint
.
Port
,
cb
,
tuple
),
ar
=>
{
ar
=>
{
...
@@ -226,17 +208,9 @@ void proxyCallback(IAsyncResult ar)
...
@@ -226,17 +208,9 @@ void proxyCallback(IAsyncResult ar)
EndConnectImpl
(
ar
,
multiplexer
,
log
,
tuple
);
EndConnectImpl
(
ar
,
multiplexer
,
log
,
tuple
);
multiplexer
.
LogLocked
(
log
,
"Connect complete: {0}"
,
formattedEndpoint
);
multiplexer
.
LogLocked
(
log
,
"Connect complete: {0}"
,
formattedEndpoint
);
});
});
#endif
}
}
else
else
{
{
#if NETSTANDARD1_5 // No BeginConnect there, because everything was an Async push...we should drop this
socket
.
ConnectAsync
(
endpoint
).
ContinueWith
(
t
=>
{
multiplexer
.
LogLocked
(
log
,
"EndConnect: {0}"
,
formattedEndpoint
);
EndConnectImpl
(
t
,
multiplexer
,
log
,
tuple
);
});
#else
RunWithCompletionType
(
RunWithCompletionType
(
cb
=>
socket
.
BeginConnect
(
endpoint
,
cb
,
tuple
),
cb
=>
socket
.
BeginConnect
(
endpoint
,
cb
,
tuple
),
ar
=>
{
ar
=>
{
...
@@ -244,7 +218,6 @@ void proxyCallback(IAsyncResult ar)
...
@@ -244,7 +218,6 @@ void proxyCallback(IAsyncResult ar)
EndConnectImpl
(
ar
,
multiplexer
,
log
,
tuple
);
EndConnectImpl
(
ar
,
multiplexer
,
log
,
tuple
);
multiplexer
.
LogLocked
(
log
,
"Connect complete: {0}"
,
formattedEndpoint
);
multiplexer
.
LogLocked
(
log
,
"Connect complete: {0}"
,
formattedEndpoint
);
});
});
#endif
}
}
}
}
catch
(
NotImplementedException
ex
)
catch
(
NotImplementedException
ex
)
...
@@ -266,25 +239,6 @@ internal void SetFastLoopbackOption(Socket socket)
...
@@ -266,25 +239,6 @@ internal void SetFastLoopbackOption(Socket socket)
// or will be subject to WFP filtering.
// or will be subject to WFP filtering.
const
int
SIO_LOOPBACK_FAST_PATH
=
-
1744830448
;
const
int
SIO_LOOPBACK_FAST_PATH
=
-
1744830448
;
#if NETSTANDARD1_5
try
{
// Ioctl is not supported on other platforms at the moment
if
(
RuntimeInformation
.
IsOSPlatform
(
OSPlatform
.
Windows
))
{
byte
[]
optionInValue
=
BitConverter
.
GetBytes
(
1
);
socket
.
IOControl
(
SIO_LOOPBACK_FAST_PATH
,
optionInValue
,
null
);
}
}
catch
(
SocketException
)
{
}
catch
(
PlatformNotSupportedException
)
{
// Fix for https://github.com/StackExchange/StackExchange.Redis/issues/582
// Checking the platform can fail on some platforms. However, we don't
// care if the platform check fails because this is for a Windows
// optimization, and checking the platform will not fail on Windows.
}
#else
// windows only
// windows only
if
(
Environment
.
OSVersion
.
Platform
==
PlatformID
.
Win32NT
)
if
(
Environment
.
OSVersion
.
Platform
==
PlatformID
.
Win32NT
)
{
{
...
@@ -296,7 +250,6 @@ internal void SetFastLoopbackOption(Socket socket)
...
@@ -296,7 +250,6 @@ internal void SetFastLoopbackOption(Socket socket)
socket
.
IOControl
(
SIO_LOOPBACK_FAST_PATH
,
optionInValue
,
null
);
socket
.
IOControl
(
SIO_LOOPBACK_FAST_PATH
,
optionInValue
,
null
);
}
}
}
}
#endif
}
}
internal
void
RequestWrite
(
PhysicalBridge
bridge
,
bool
forced
)
internal
void
RequestWrite
(
PhysicalBridge
bridge
,
bool
forced
)
...
@@ -332,11 +285,7 @@ private void EndConnectImpl(IAsyncResult ar, ConnectionMultiplexer multiplexer,
...
@@ -332,11 +285,7 @@ private void EndConnectImpl(IAsyncResult ar, ConnectionMultiplexer multiplexer,
if
(
ignoreConnect
)
return
;
if
(
ignoreConnect
)
return
;
var
socket
=
tuple
.
Item1
;
var
socket
=
tuple
.
Item1
;
var
callback
=
tuple
.
Item2
;
var
callback
=
tuple
.
Item2
;
#if NETSTANDARD1_5
multiplexer
.
Wait
((
Task
)
ar
);
// make it explode if invalid (note: already complete at this point)
#else
socket
.
EndConnect
(
ar
);
socket
.
EndConnect
(
ar
);
#endif
var
netStream
=
new
NetworkStream
(
socket
,
false
);
var
netStream
=
new
NetworkStream
(
socket
,
false
);
var
socketMode
=
callback
?.
Connected
(
netStream
,
log
)
??
SocketMode
.
Abort
;
var
socketMode
=
callback
?.
Connected
(
netStream
,
log
)
??
SocketMode
.
Abort
;
switch
(
socketMode
)
switch
(
socketMode
)
...
@@ -401,9 +350,7 @@ private void Shutdown(Socket socket)
...
@@ -401,9 +350,7 @@ private void Shutdown(Socket socket)
{
{
OnShutdown
(
socket
);
OnShutdown
(
socket
);
try
{
socket
.
Shutdown
(
SocketShutdown
.
Both
);
}
catch
{
}
try
{
socket
.
Shutdown
(
SocketShutdown
.
Both
);
}
catch
{
}
#if !NETSTANDARD1_5
try
{
socket
.
Close
();
}
catch
{
}
try
{
socket
.
Close
();
}
catch
{
}
#endif
try
{
socket
.
Dispose
();
}
catch
{
}
try
{
socket
.
Dispose
();
}
catch
{
}
}
}
}
}
...
...
StackExchange.Redis/StackExchange/Redis/TaskSource.cs
View file @
c54c0671
using
System.Threading.Tasks
;
using
System.Threading.Tasks
;
#if !PLAT_SAFE_CONTINUATIONS
using
System
;
using
System
;
using
System.Diagnostics
;
using
System.Reflection
;
using
System.Reflection
;
using
System.Reflection.Emit
;
using
System.Reflection.Emit
;
#endif
namespace
StackExchange.Redis
namespace
StackExchange.Redis
{
{
...
@@ -15,7 +12,6 @@ namespace StackExchange.Redis
...
@@ -15,7 +12,6 @@ namespace StackExchange.Redis
/// </summary>
/// </summary>
internal
static
class
TaskSource
internal
static
class
TaskSource
{
{
#if !PLAT_SAFE_CONTINUATIONS
// on .NET < 4.6, it was possible to have threads hijacked; this is no longer a problem in 4.6 and core-clr 5,
// on .NET < 4.6, it was possible to have threads hijacked; this is no longer a problem in 4.6 and core-clr 5,
// thanks to the new TaskCreationOptions.RunContinuationsAsynchronously, however we still need to be a little
// thanks to the new TaskCreationOptions.RunContinuationsAsynchronously, however we still need to be a little
// "test and react", as we could be targeting 4.5 but running on a 4.6 machine, in which case *it can still
// "test and react", as we could be targeting 4.5 but running on a 4.6 machine, in which case *it can still
...
@@ -80,7 +76,7 @@ static TaskSource()
...
@@ -80,7 +76,7 @@ static TaskSource()
IsSyncSafe
=
_
=>
false
;
// assume: not
IsSyncSafe
=
_
=>
false
;
// assume: not
}
}
}
}
#endif
/// <summary>
/// <summary>
/// Create a new TaskCompletion source
/// Create a new TaskCompletion source
/// </summary>
/// </summary>
...
@@ -88,11 +84,7 @@ static TaskSource()
...
@@ -88,11 +84,7 @@ static TaskSource()
/// <param name="asyncState">The state for the created <see cref="TaskCompletionSource{TResult}"/>.</param>
/// <param name="asyncState">The state for the created <see cref="TaskCompletionSource{TResult}"/>.</param>
public
static
TaskCompletionSource
<
T
>
Create
<
T
>(
object
asyncState
)
public
static
TaskCompletionSource
<
T
>
Create
<
T
>(
object
asyncState
)
{
{
#if PLAT_SAFE_CONTINUATIONS
return
new
TaskCompletionSource
<
T
>(
asyncState
,
TaskCreationOptions
.
RunContinuationsAsynchronously
);
#else
return
new
TaskCompletionSource
<
T
>(
asyncState
,
TaskCreationOptions
.
None
);
return
new
TaskCompletionSource
<
T
>(
asyncState
,
TaskCreationOptions
.
None
);
#endif
}
}
}
}
}
}
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment