performance optimizations

This commit is contained in:
Christian Köllner 2020-02-09 13:49:21 +01:00
parent 47cb578057
commit 5e71ce69c5
16 changed files with 130 additions and 30 deletions

View File

@ -7,7 +7,7 @@
<ItemGroup> <ItemGroup>
<PackageReference Include="BenchmarkDotNet" Version="0.12.0" /> <PackageReference Include="BenchmarkDotNet" Version="0.12.0" />
<PackageReference Include="Capnp.Net.Runtime" Version="1.2.189" /> <PackageReference Include="Capnp.Net.Runtime" Version="1.3.22-g47cb578057" />
<PackageReference Include="CapnpC.CSharp.MsBuild.Generation" Version="1.2.138" /> <PackageReference Include="CapnpC.CSharp.MsBuild.Generation" Version="1.2.138" />
<PackageReference Include="Google.Protobuf" Version="3.11.3" /> <PackageReference Include="Google.Protobuf" Version="3.11.3" />
<PackageReference Include="Grpc.Net.Client" Version="2.27.0" /> <PackageReference Include="Grpc.Net.Client" Version="2.27.0" />

View File

@ -0,0 +1,25 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 16
VisualStudioVersion = 16.0.29728.190
MinimumVisualStudioVersion = 10.0.40219.1
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "CapnpProfile", "CapnpProfile\CapnpProfile.csproj", "{D2D3AE23-C19E-47C7-B758-E2259DC01B5A}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{D2D3AE23-C19E-47C7-B758-E2259DC01B5A}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{D2D3AE23-C19E-47C7-B758-E2259DC01B5A}.Debug|Any CPU.Build.0 = Debug|Any CPU
{D2D3AE23-C19E-47C7-B758-E2259DC01B5A}.Release|Any CPU.ActiveCfg = Release|Any CPU
{D2D3AE23-C19E-47C7-B758-E2259DC01B5A}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {F5DDDA09-394B-4A71-B6BE-C7103BCEF3A2}
EndGlobalSection
EndGlobal

View File

@ -0,0 +1,13 @@
<Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup>
<OutputType>Exe</OutputType>
<TargetFramework>netcoreapp3.1</TargetFramework>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Capnp.Net.Runtime" Version="1.3.22-g47cb578057" />
<PackageReference Include="CapnpC.CSharp.MsBuild.Generation" Version="1.3.0" />
</ItemGroup>
</Project>

View File

@ -0,0 +1,30 @@
using Capnp.Rpc;
using CapnpGen;
using CapnpProfile.Services;
using System;
using System.Net;
using System.Threading.Tasks;
namespace CapnpProfile
{
class Program
{
static async Task Main(string[] args)
{
using var server = new TcpRpcServer(IPAddress.Any, 5002);
server.Main = new CapnpEchoService();
using var client = new TcpRpcClient("localhost", 5002);
await client.WhenConnected;
using var echoer = client.GetMain<IEchoer>();
var payload = new byte[200000];
new Random().NextBytes(payload);
while (true)
{
var result = await echoer.Echo(payload);
if (result.Count != payload.Length)
throw new InvalidOperationException("Echo server malfunction");
}
}
}
}

View File

@ -0,0 +1,5 @@
@0x8c309c720de8cf7c;
interface Echoer {
echo @0 (input : Data) -> (output : Data);
}

View File

@ -0,0 +1,20 @@
using System;
using System.Collections.Generic;
using System.Text;
using System.Threading;
using System.Threading.Tasks;
namespace CapnpProfile.Services
{
public class CapnpEchoService : CapnpGen.IEchoer
{
public void Dispose()
{
}
public Task<IReadOnlyList<byte>> Echo(IReadOnlyList<byte> input, CancellationToken cancellationToken_ = default)
{
return Task.FromResult(input);
}
}
}

View File

@ -1,4 +1,4 @@
<Project Sdk="Microsoft.NET.Sdk"> <Project Sdk="Microsoft.NET.Sdk">
<PropertyGroup> <PropertyGroup>
<OutputType>Exe</OutputType> <OutputType>Exe</OutputType>
@ -6,7 +6,7 @@
</PropertyGroup> </PropertyGroup>
<ItemGroup> <ItemGroup>
<PackageReference Include="Capnp.Net.Runtime" Version="1.2.189" /> <PackageReference Include="Capnp.Net.Runtime" Version="1.3.22-g47cb578057" />
<PackageReference Include="CapnpC.CSharp.MsBuild.Generation" Version="1.2.138" /> <PackageReference Include="CapnpC.CSharp.MsBuild.Generation" Version="1.2.138" />
</ItemGroup> </ItemGroup>

10
Benchmarking/nuget.config Normal file
View File

@ -0,0 +1,10 @@
<?xml version="1.0" encoding="utf-8"?>
<configuration>
<config>
<add key="repositoryPath" value="..\packages" />
<add key="globalPackagesFolder" value="..\globalPackages" />
</config>
<packageSources>
<add key="CapnpRuntimeSource" value="..\GeneratedNuGetPackages\Release" />
</packageSources>
</configuration>

View File

@ -516,28 +516,28 @@ namespace Capnp
switch (Kind) switch (Kind)
{ {
case ObjectKind.ListOfBits: case ObjectKind.ListOfBits:
return new ListOfBitsDeserializer(ref this, false); return new ListOfBitsDeserializer(this, false);
case ObjectKind.ListOfBytes: case ObjectKind.ListOfBytes:
return new ListOfPrimitivesDeserializer<byte>(ref this, ListKind.ListOfBytes); return new ListOfPrimitivesDeserializer<byte>(this, ListKind.ListOfBytes);
case ObjectKind.ListOfEmpty: case ObjectKind.ListOfEmpty:
return new ListOfEmptyDeserializer(ref this); return new ListOfEmptyDeserializer(this);
case ObjectKind.ListOfInts: case ObjectKind.ListOfInts:
return new ListOfPrimitivesDeserializer<int>(ref this, ListKind.ListOfInts); return new ListOfPrimitivesDeserializer<int>(this, ListKind.ListOfInts);
case ObjectKind.ListOfLongs: case ObjectKind.ListOfLongs:
return new ListOfPrimitivesDeserializer<long>(ref this, ListKind.ListOfLongs); return new ListOfPrimitivesDeserializer<long>(this, ListKind.ListOfLongs);
case ObjectKind.ListOfPointers: case ObjectKind.ListOfPointers:
return new ListOfPointersDeserializer(ref this); return new ListOfPointersDeserializer(this);
case ObjectKind.ListOfShorts: case ObjectKind.ListOfShorts:
return new ListOfPrimitivesDeserializer<short>(ref this, ListKind.ListOfShorts); return new ListOfPrimitivesDeserializer<short>(this, ListKind.ListOfShorts);
case ObjectKind.ListOfStructs: case ObjectKind.ListOfStructs:
return new ListOfStructsDeserializer(ref this); return new ListOfStructsDeserializer(this);
case ObjectKind.Nil: case ObjectKind.Nil:
return new EmptyListDeserializer(); return new EmptyListDeserializer();
@ -557,7 +557,7 @@ namespace Capnp
switch (Kind) switch (Kind)
{ {
case ObjectKind.ListOfPointers: case ObjectKind.ListOfPointers:
return new ListOfCapsDeserializer<T>(ref this); return new ListOfCapsDeserializer<T>(this);
default: default:
throw new DeserializationException("Cannot deserialize this object as capability list"); throw new DeserializationException("Cannot deserialize this object as capability list");

View File

@ -34,7 +34,7 @@ namespace Capnp
/// </summary> /// </summary>
protected readonly DeserializerState State; protected readonly DeserializerState State;
internal ListDeserializer(ref DeserializerState state) internal ListDeserializer(in DeserializerState state)
{ {
State = state; State = state;
} }

View File

@ -11,8 +11,8 @@ namespace Capnp
{ {
readonly bool _defaultValue; readonly bool _defaultValue;
internal ListOfBitsDeserializer(ref DeserializerState context, bool defaultValue) : internal ListOfBitsDeserializer(in DeserializerState context, bool defaultValue) :
base(ref context) base(context)
{ {
_defaultValue = defaultValue; _defaultValue = defaultValue;
} }

View File

@ -11,7 +11,7 @@ namespace Capnp
public class ListOfCapsDeserializer<T> : ListDeserializer, IReadOnlyList<T> public class ListOfCapsDeserializer<T> : ListDeserializer, IReadOnlyList<T>
where T: class where T: class
{ {
internal ListOfCapsDeserializer(ref DeserializerState state) : base(ref state) internal ListOfCapsDeserializer(in DeserializerState state) : base(state)
{ {
Rpc.CapabilityReflection.ValidateCapabilityInterface(typeof(T)); Rpc.CapabilityReflection.ValidateCapabilityInterface(typeof(T));
} }

View File

@ -10,8 +10,8 @@ namespace Capnp
/// </summary> /// </summary>
public class ListOfEmptyDeserializer : ListDeserializer, IReadOnlyList<DeserializerState> public class ListOfEmptyDeserializer : ListDeserializer, IReadOnlyList<DeserializerState>
{ {
internal ListOfEmptyDeserializer(ref DeserializerState state) : internal ListOfEmptyDeserializer(in DeserializerState state) :
base(ref state) base(state)
{ {
} }

View File

@ -9,8 +9,8 @@ namespace Capnp
/// </summary> /// </summary>
public class ListOfPointersDeserializer: ListDeserializer, IReadOnlyList<DeserializerState> public class ListOfPointersDeserializer: ListDeserializer, IReadOnlyList<DeserializerState>
{ {
internal ListOfPointersDeserializer(ref DeserializerState state) : internal ListOfPointersDeserializer(in DeserializerState state) :
base(ref state) base(state)
{ {
} }

View File

@ -11,7 +11,7 @@ namespace Capnp
/// </summary> /// </summary>
/// <typeparam name="T">List element type</typeparam> /// <typeparam name="T">List element type</typeparam>
public class ListOfPrimitivesDeserializer<T>: ListDeserializer, IReadOnlyList<T> public class ListOfPrimitivesDeserializer<T>: ListDeserializer, IReadOnlyList<T>
where T: struct where T: unmanaged
{ {
class ListOfULongAsStructView<U> : IReadOnlyList<U> class ListOfULongAsStructView<U> : IReadOnlyList<U>
{ {
@ -73,12 +73,10 @@ namespace Capnp
readonly ListKind _kind; readonly ListKind _kind;
internal ListOfPrimitivesDeserializer(ref DeserializerState state, ListKind kind) : internal ListOfPrimitivesDeserializer(in DeserializerState state, ListKind kind) :
base(ref state) base(state)
{ {
_kind = kind; _kind = kind;
var binCoder = PrimitiveCoder.Get<T>();
} }
/// <summary> /// <summary>
@ -96,13 +94,12 @@ namespace Capnp
/// <exception cref="IndexOutOfRangeException"><paramref name="index"/> is out of range.</exception> /// <exception cref="IndexOutOfRangeException"><paramref name="index"/> is out of range.</exception>
public T this[int index] => Data[index]; public T this[int index] => Data[index];
ListOfPrimitivesDeserializer<U> PrimitiveCast<U>() where U: struct ListOfPrimitivesDeserializer<U> PrimitiveCast<U>() where U: unmanaged
{ {
if (Marshal.SizeOf<U>() != Marshal.SizeOf<T>()) if (Marshal.SizeOf<U>() != Marshal.SizeOf<T>())
throw new NotSupportedException("Source and target types have different sizes, cannot cast"); throw new NotSupportedException("Source and target types have different sizes, cannot cast");
var stateCopy = State; return new ListOfPrimitivesDeserializer<U>(State, Kind);
return new ListOfPrimitivesDeserializer<U>(ref stateCopy, Kind);
} }
/// <summary> /// <summary>

View File

@ -9,8 +9,8 @@ namespace Capnp
/// </summary> /// </summary>
public class ListOfStructsDeserializer: ListDeserializer, IReadOnlyList<DeserializerState> public class ListOfStructsDeserializer: ListDeserializer, IReadOnlyList<DeserializerState>
{ {
internal ListOfStructsDeserializer(ref DeserializerState context): internal ListOfStructsDeserializer(in DeserializerState context):
base(ref context) base(context)
{ {
} }