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

Use BinaryPrimitives for ObjectDataBuilder primitive emit logic #102394

Merged
merged 9 commits into from
May 18, 2024
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
// The .NET Foundation licenses this file to you under the MIT license.

using System;
using System.Buffers.Binary;
using System.Collections.Generic;
using Internal.TypeSystem;

Expand Down Expand Up @@ -85,42 +86,27 @@ public void EmitByte(byte emit)

public void EmitShort(short emit)
{
EmitByte((byte)(emit & 0xFF));
EmitByte((byte)((emit >> 8) & 0xFF));
BinaryPrimitives.WriteInt16LittleEndian(_data.AppendSpan(sizeof(short)), emit);
}

public void EmitUShort(ushort emit)
{
EmitByte((byte)(emit & 0xFF));
EmitByte((byte)((emit >> 8) & 0xFF));
BinaryPrimitives.WriteUInt16LittleEndian(_data.AppendSpan(sizeof(ushort)), emit);
}

public void EmitInt(int emit)
{
EmitByte((byte)(emit & 0xFF));
EmitByte((byte)((emit >> 8) & 0xFF));
EmitByte((byte)((emit >> 16) & 0xFF));
EmitByte((byte)((emit >> 24) & 0xFF));
BinaryPrimitives.WriteInt32LittleEndian(_data.AppendSpan(sizeof(int)), emit);
}

public void EmitUInt(uint emit)
{
EmitByte((byte)(emit & 0xFF));
EmitByte((byte)((emit >> 8) & 0xFF));
EmitByte((byte)((emit >> 16) & 0xFF));
EmitByte((byte)((emit >> 24) & 0xFF));
BinaryPrimitives.WriteUInt32LittleEndian(_data.AppendSpan(sizeof(uint)), emit);
}

public void EmitLong(long emit)
{
EmitByte((byte)(emit & 0xFF));
EmitByte((byte)((emit >> 8) & 0xFF));
EmitByte((byte)((emit >> 16) & 0xFF));
EmitByte((byte)((emit >> 24) & 0xFF));
EmitByte((byte)((emit >> 32) & 0xFF));
EmitByte((byte)((emit >> 40) & 0xFF));
EmitByte((byte)((emit >> 48) & 0xFF));
EmitByte((byte)((emit >> 56) & 0xFF));
BinaryPrimitives.WriteInt64LittleEndian(_data.AppendSpan(sizeof(long)), emit);
}

public void EmitNaturalInt(int emit)
Expand Down Expand Up @@ -245,8 +231,7 @@ public Reservation ReserveShort()
public void EmitShort(Reservation reservation, short emit)
{
int offset = ReturnReservationTicket(reservation);
_data[offset] = (byte)(emit & 0xFF);
_data[offset + 1] = (byte)((emit >> 8) & 0xFF);
BinaryPrimitives.WriteInt16LittleEndian(_data.AsSpan(offset), emit);
}

public Reservation ReserveInt()
Expand All @@ -257,19 +242,13 @@ public Reservation ReserveInt()
public void EmitInt(Reservation reservation, int emit)
{
int offset = ReturnReservationTicket(reservation);
_data[offset] = (byte)(emit & 0xFF);
_data[offset + 1] = (byte)((emit >> 8) & 0xFF);
_data[offset + 2] = (byte)((emit >> 16) & 0xFF);
_data[offset + 3] = (byte)((emit >> 24) & 0xFF);
BinaryPrimitives.WriteInt32LittleEndian(_data.AsSpan(offset), emit);
}

public void EmitUInt(Reservation reservation, uint emit)
{
int offset = ReturnReservationTicket(reservation);
_data[offset] = (byte)(emit & 0xFF);
_data[offset + 1] = (byte)((emit >> 8) & 0xFF);
_data[offset + 2] = (byte)((emit >> 16) & 0xFF);
_data[offset + 3] = (byte)((emit >> 24) & 0xFF);
BinaryPrimitives.WriteUInt32LittleEndian(_data.AsSpan(offset), emit);
}

public void EmitReloc(ISymbolNode symbol, RelocType relocType, int delta = 0)
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
// Licensed to the .NET Foundation under one or more agreements.
// The .NET Foundation licenses this file to you under the MIT license.

using System.Runtime.CompilerServices;

using Debug = System.Diagnostics.Debug;

namespace System.Collections.Generic
Expand Down Expand Up @@ -29,6 +31,19 @@ public void Add(T item)
_items[_count++] = item;
}

#if NET
public readonly Span<T> AsSpan(int start) => _items.AsSpan(start);
PaulusParssinen marked this conversation as resolved.
Show resolved Hide resolved

public Span<T> AppendSpan(int length)
{
int origCount = _count;
EnsureCapacity(origCount + length);

_count = origCount + length;
return _items.AsSpan(origCount, length);
}
#endif

public void Append(T[] newItems)
{
Append(newItems, 0, newItems.Length);
Expand Down Expand Up @@ -67,32 +82,26 @@ public void EnsureCapacity(int requestedCapacity)
{
if (requestedCapacity > ((_items != null) ? _items.Length : 0))
{
int newCount = Math.Max(2 * _count + 1, requestedCapacity);
Array.Resize(ref _items, newCount);
Grow(requestedCapacity);
}
}

public int Count
[MethodImpl(MethodImplOptions.NoInlining)]
private void Grow(int requestedCapacity)
{
get
{
return _count;
}
int newCount = Math.Max(2 * _count + 1, requestedCapacity);
Array.Resize(ref _items, newCount);
}

public T this[int index]
public readonly int Count => _count;

public readonly T this[int index]
{
get
{
return _items[index];
}
set
{
_items[index] = value;
}
get => _items[index];
set => _items[index] = value;
}

public bool Contains(T t)
public readonly bool Contains(T t)
{
for (int i = 0; i < _count; i++)
{
Expand All @@ -105,7 +114,7 @@ public bool Contains(T t)
return false;
}

public bool Any(Func<T, bool> func)
public readonly bool Any(Func<T, bool> func)
{
for (int i = 0; i < _count; i++)
{
Expand Down