Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Align with netty-4.1.55.Final #73

Draft
wants to merge 7 commits into
base: main
Choose a base branch
from
Draft
Changes from 1 commit
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Next Next commit
WIP
cuteant committed Jul 16, 2021
commit 02647e6a5bc2d996fa09c31563527730e090cfb6
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
@@ -17,7 +17,7 @@ This is a fork of [DotNetty](https://github.com/azure/dotnetty).
| .NET Netstandard (Windows) Unit Tests | [![Build status](https://ci.appveyor.com/api/projects/status/rvx3h1bmahad2giw/branch/main?svg=true)](https://ci.appveyor.com/project/cuteant/SpanNetty/branch/main) |

## Features
- Align with [Netty-4.1.51.Final](https://github.com/netty/netty/tree/netty-4.1.51.Final)
- Align with [Netty-4.1.52.Final](https://github.com/netty/netty/tree/netty-4.1.52.Final)
- ArrayPooledByteBuffer
- Support **Span<byte>** and **Memory<byte>** in Buffer/Common APIs
- Add support for IBufferWriter<byte> to the **IByteBuffer**
72 changes: 72 additions & 0 deletions src/DotNetty.Buffers/ISizeClassesMetric.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,72 @@
/*
* Copyright 2012 The Netty Project
*
* The Netty Project licenses this file to you under the Apache License,
* version 2.0 (the "License"); you may not use this file except in compliance
* with the License. You may obtain a copy of the License at:
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
* WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
* License for the specific language governing permissions and limitations
* under the License.
*
* Copyright (c) Microsoft. All rights reserved.
* Licensed under the MIT license. See LICENSE file in the project root for full license information.
*
* Copyright (c) 2020 The Dotnetty-Span-Fork Project (cuteant@outlook.com)
*
* https://github.com/cuteant/spannetty
*
* Licensed under the MIT license. See LICENSE file in the project root for full license information.
*/

namespace DotNetty.Buffers
{
/// <summary>Expose metrics for an SizeClasses.</summary>
public interface ISizeClassesMetric
{
/// <summary>Computes size from lookup table according to sizeIdx.</summary>
/// <param name="sizeIdx">TBD</param>
/// <returns>size</returns>
int SizeIdx2Size(int sizeIdx);

/// <summary>Computes size according to sizeIdx.</summary>
/// <param name="sizeIdx">TBD</param>
/// <returns>size</returns>
int SizeIdx2SizeCompute(int sizeIdx);

/// <summary>Computes size from lookup table according to pageIdx.</summary>
/// <param name="pageIdx">TBD</param>
/// <returns>size which is multiples of pageSize.</returns>
long PageIdx2Size(int pageIdx);

/// <summary>Computes size according to pageIdx.</summary>
/// <param name="pageIdx">TBD</param>
/// <returns>size which is multiples of pageSize</returns>
long PageIdx2SizeCompute(int pageIdx);

/// <summary>Normalizes request size up to the nearest size class.</summary>
/// <param name="size">request size</param>
/// <returns>sizeIdx of the size class</returns>
int Size2SizeIdx(int size);

/// <summary>Normalizes request size up to the nearest pageSize class.</summary>
/// <param name="pages">multiples of pageSizes</param>
/// <returns>pageIdx of the pageSize class</returns>
int Pages2PageIdx(int pages);

/// <summary>Normalizes request size down to the nearest pageSize class.</summary>
/// <param name="pages">multiples of pageSizes</param>
/// <returns>pageIdx of the pageSize class</returns>
int Pages2PageIdxFloor(int pages);

/// <summary>Normalizes usable size that would result from allocating an object with the
/// specified size and alignment.</summary>
/// <param name="size">request size</param>
/// <returns>normalized size</returns>
int NormalizeSize(int size);
}
}
2 changes: 1 addition & 1 deletion src/DotNetty.Buffers/PoolThreadCache.cs
Original file line number Diff line number Diff line change
@@ -185,7 +185,7 @@ static MemoryRegionCache[] CreateNormalCaches(

// val > 0
[MethodImpl(InlineMethod.AggressiveOptimization)]
private static int Log2(int val)
internal static int Log2(int val)
{
return s_integerSizeMinusOne - IntegerExtensions.NumberOfLeadingZeros(val);
}
480 changes: 480 additions & 0 deletions src/DotNetty.Buffers/SizeClasses.cs

Large diffs are not rendered by default.

Original file line number Diff line number Diff line change
@@ -82,20 +82,20 @@ sealed class GenericEventExecutorChooser : IEventExecutorChooser<TEventExecutor>
{
private readonly TEventExecutor[] _executors;
private readonly int _amount;
//private readonly bool _isSingle;
private int _idx;
// Use a 'long' counter to avoid non-round-robin behaviour at the 32-bit overflow boundary.
// The 64-bit long solves this by placing the overflow so far into the future, that no system
// will encounter this in practice.
private long _idx;

public GenericEventExecutorChooser(TEventExecutor[] executors)
{
_executors = executors;
_amount = executors.Length;
//_isSingle = 1u >= (uint)_amount; // 最小值为 1
}

public TEventExecutor GetNext()
{
//if (_isSingle) { return _executors[0]; }
return _executors[Math.Abs(Interlocked.Increment(ref _idx) % _amount)];
return _executors[(int)Math.Abs(Interlocked.Increment(ref _idx) % _amount)];
}
}
}
30 changes: 15 additions & 15 deletions src/DotNetty.Common/ResourceLeakDetector.cs
Original file line number Diff line number Diff line change
@@ -228,7 +228,7 @@ sealed class DefaultResourceLeak : IResourceLeakTracker
{
private readonly ResourceLeakDetector _owner;

private RecordEntry v_head;
private TraceRecord v_head;
private long _droppedRecords;
private readonly WeakReference<GCNotice> _gcNotice;

@@ -254,7 +254,7 @@ public DefaultResourceLeak(ResourceLeakDetector owner, object referent)
}
while (!gcNotice.Arm(this, owner, referent));
_gcNotice = new WeakReference<GCNotice>(gcNotice);
v_head = RecordEntry.Bottom;
v_head = TraceRecord.Bottom;
Record();
}

@@ -273,9 +273,9 @@ private void Record0(object hint)
StackTrace stackTrace = null;

var thisHead = Volatile.Read(ref v_head);
RecordEntry oldHead;
RecordEntry prevHead;
RecordEntry newHead;
TraceRecord oldHead;
TraceRecord prevHead;
TraceRecord newHead;
bool dropped;
do
{
@@ -299,7 +299,7 @@ private void Record0(object hint)
dropped = false;
}
stackTrace ??= new StackTrace(skipFrames: 3, fNeedFileInfo: true);
newHead = hint is object ? new RecordEntry(prevHead, stackTrace, hint) : new RecordEntry(prevHead, stackTrace);
newHead = hint is object ? new TraceRecord(prevHead, stackTrace, hint) : new TraceRecord(prevHead, stackTrace);
thisHead = Interlocked.CompareExchange(ref v_head, newHead, thisHead);
}
while (thisHead != oldHead);
@@ -334,7 +334,7 @@ internal void CloseFinal()

public string Dump()
{
RecordEntry oldHead = Interlocked.Exchange(ref v_head, null);
TraceRecord oldHead = Interlocked.Exchange(ref v_head, null);
if (oldHead is null)
{
// Already closed
@@ -352,12 +352,12 @@ public string Dump()

int i = 1;
var seen = new HashSet<string>(StringComparer.Ordinal);
for (; oldHead != RecordEntry.Bottom; oldHead = oldHead.Next)
for (; oldHead != TraceRecord.Bottom; oldHead = oldHead.Next)
{
string s = oldHead.ToString();
if (seen.Add(s))
{
if (oldHead.Next == RecordEntry.Bottom)
if (oldHead.Next == TraceRecord.Bottom)
{
_ = buf.Append("Created at:").Append(StringUtil.Newline).Append(s);
}
@@ -403,17 +403,17 @@ internal void Dispose()
}

// Record
sealed class RecordEntry
sealed class TraceRecord
{
internal static readonly RecordEntry Bottom = new RecordEntry();
internal static readonly TraceRecord Bottom = new TraceRecord();

internal readonly RecordEntry Next;
internal readonly TraceRecord Next;
internal readonly int Pos;

private readonly string _hintString;
private readonly StackTrace _stackTrace;

internal RecordEntry(RecordEntry next, StackTrace stackTrace, object hint)
internal TraceRecord(TraceRecord next, StackTrace stackTrace, object hint)
{
// This needs to be generated even if toString() is never called as it may change later on.
_hintString = hint is IResourceLeakHint leakHint ? leakHint.ToHintString() : null;
@@ -422,7 +422,7 @@ internal RecordEntry(RecordEntry next, StackTrace stackTrace, object hint)
_stackTrace = stackTrace;
}

internal RecordEntry(RecordEntry next, StackTrace stackTrace)
internal TraceRecord(TraceRecord next, StackTrace stackTrace)
{
_hintString = null;
Next = next;
@@ -431,7 +431,7 @@ internal RecordEntry(RecordEntry next, StackTrace stackTrace)
}

// Used to terminate the stack
RecordEntry()
TraceRecord()
{
_hintString = null;
Next = null;
9 changes: 5 additions & 4 deletions src/DotNetty.Transport.Libuv/EventLoopChooserFactory.cs
Original file line number Diff line number Diff line change
@@ -88,14 +88,15 @@ sealed class GenericEventExecutorChooser : IEventExecutorChooser<TEventLoop>
{
private readonly TEventLoop[] _eventLoops;
private readonly int _amount;
//private readonly bool _isSingle;
private int _idx;
// Use a 'long' counter to avoid non-round-robin behaviour at the 32-bit overflow boundary.
// The 64-bit long solves this by placing the overflow so far into the future, that no system
// will encounter this in practice.
private long _idx;

public GenericEventExecutorChooser(TEventLoop[] eventLoops)
{
_eventLoops = eventLoops;
_amount = eventLoops.Length;
//_isSingle = 1u >= (uint)_amount; // 最小值为 1
}

public TEventLoop GetNext()
@@ -114,7 +115,7 @@ public TEventLoop GetNext()
}
}

return _eventLoops[Math.Abs(Interlocked.Increment(ref _idx) % _amount)];
return _eventLoops[(int)Math.Abs(Interlocked.Increment(ref _idx) % _amount)];
}
}
}