/
githubmirror
/
aspnetcore
Обзор
Документация
Войти
/
githubmirror
/
aspnetcore
Код
Запросы
0
Пакеты
0
Релизы
0
Аналитика
Безопасность
main
src/Servers/Kestrel/perf/Microbenchmarks/HttpParserBenchmark.cs
151 строка
5 KB
Brennan
Remove array allocation from multi-span header parsing (#45044)
17 ноя 2022, 22:08
Не верифицирован
17 ноя 2022, 22:08
7d3b46d
Код
Авторство
О чём код?
// Licensed to the .NET Foundation under one or more agreements. // The .NET Foundation licenses this file to you under the MIT license. using System.Buffers; using System.IO.Pipelines; using BenchmarkDotNet.Attributes; using Microsoft.AspNetCore.Server.Kestrel.Core.Internal.Http; namespace Microsoft.AspNetCore.Server.Kestrel.Microbenchmarks; public class HttpParserBenchmark : IHttpRequestLineHandler, IHttpHeadersHandler { private readonly HttpParser<Adapter> _parser = new HttpParser<Adapter>(); private ReadOnlySequence<byte> _buffer; private ReadOnlySequence<byte> _multispanHeader; [GlobalSetup] public void Setup() { var segment = new BufferSegment(); var split = RequestParsingData.UnicodeRequest.Length / 2; segment.SetOwnedMemory(RequestParsingData.UnicodeRequest.AsSpan(0, split).ToArray()); segment.End = split; var next = new BufferSegment(); next.SetOwnedMemory(RequestParsingData.UnicodeRequest.AsSpan(split).ToArray()); next.End = split; segment.SetNext(next); _multispanHeader = new ReadOnlySequence<byte>(segment, 0, next, next.Memory.Length); } [Benchmark(Baseline = true, OperationsPerInvoke = RequestParsingData.InnerLoopCount)] public void PlaintextTechEmpower() { for (var i = 0; i < RequestParsingData.InnerLoopCount; i++) { InsertData(RequestParsingData.PlaintextTechEmpowerRequest); ParseData(); } } [Benchmark(OperationsPerInvoke = RequestParsingData.InnerLoopCount)] public void JsonTechEmpower() { for (var i = 0; i < RequestParsingData.InnerLoopCount; i++) { InsertData(RequestParsingData.JsonTechEmpowerRequest); ParseData(); } } [Benchmark(OperationsPerInvoke = RequestParsingData.InnerLoopCount)] public void LiveAspNet() { for (var i = 0; i < RequestParsingData.InnerLoopCount; i++) { InsertData(RequestParsingData.LiveaspnetRequest); ParseData(); } } [Benchmark(OperationsPerInvoke = RequestParsingData.InnerLoopCount)] public void Unicode() { for (var i = 0; i < RequestParsingData.InnerLoopCount; i++) { InsertData(RequestParsingData.UnicodeRequest); ParseData(); } } [Benchmark(OperationsPerInvoke = RequestParsingData.InnerLoopCount)] public void MultispanUnicodeHeader() { for (var i = 0; i < RequestParsingData.InnerLoopCount; i++) { _buffer = _multispanHeader; ParseData(); } } private void InsertData(byte[] data) { _buffer = new ReadOnlySequence<byte>(data); } private void ParseData() { var reader = new SequenceReader<byte>(_buffer); if (!_parser.ParseRequestLine(new Adapter(this), ref reader)) { ErrorUtilities.ThrowInvalidRequestHeaders(); } if (!_parser.ParseHeaders(new Adapter(this), ref reader)) { ErrorUtilities.ThrowInvalidRequestHeaders(); } } public void OnStartLine(HttpVersionAndMethod versionAndMethod, TargetOffsetPathLength targetPath, Span<byte> startLine) { } public void OnHeader(ReadOnlySpan<byte> name, ReadOnlySpan<byte> value) { } public void OnHeadersComplete(bool endStream) { } public void OnStaticIndexedHeader(int index) { throw new NotImplementedException(); } public void OnStaticIndexedHeader(int index, ReadOnlySpan<byte> value) { throw new NotImplementedException(); } private struct Adapter : IHttpRequestLineHandler, IHttpHeadersHandler { public HttpParserBenchmark RequestHandler; public Adapter(HttpParserBenchmark requestHandler) { RequestHandler = requestHandler; } public void OnHeader(ReadOnlySpan<byte> name, ReadOnlySpan<byte> value) => RequestHandler.OnHeader(name, value); public void OnHeadersComplete(bool endStream) => RequestHandler.OnHeadersComplete(endStream); public void OnStartLine(HttpVersionAndMethod versionAndMethod, TargetOffsetPathLength targetPath, Span<byte> startLine) => RequestHandler.OnStartLine(versionAndMethod, targetPath, startLine); public void OnStaticIndexedHeader(int index) { throw new NotImplementedException(); } public void OnStaticIndexedHeader(int index, ReadOnlySpan<byte> value) { throw new NotImplementedException(); } } }