Skip to content

Remove some #ifdefs with System.Memory #1434

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

Merged
merged 1 commit into from
Jul 5, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
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
60 changes: 0 additions & 60 deletions src/Renci.SshNet/Common/Extensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -235,29 +235,7 @@ public static bool IsEqualTo(this byte[] left, byte[] right)
throw new ArgumentNullException(nameof(right));
}

if (left == right)
{
return true;
}

#if NETSTANDARD2_1_OR_GREATER || NET6_0_OR_GREATER
return left.AsSpan().SequenceEqual(right);
#else
if (left.Length != right.Length)
{
return false;
}

for (var i = 0; i < left.Length; i++)
{
if (left[i] != right[i])
{
return false;
}
}

return true;
#endif
}

/// <summary>
Expand Down Expand Up @@ -297,44 +275,6 @@ public static byte[] TrimLeadingZeros(this byte[] value)
return value;
}

#if NETFRAMEWORK || NETSTANDARD2_0
public static int IndexOf(this byte[] array, byte[] value, int startIndex, int count)
{
if (value.Length > count)
{
return -1;
}

if (value.Length == 0)
{
return 0;
}

for (var i = startIndex; i < startIndex + count - value.Length + 1; i++)
{
if (MatchesAtIndex(i))
{
return i - startIndex;
}
}

return -1;

bool MatchesAtIndex(int i)
{
for (var j = 0; j < value.Length; j++)
{
if (array[i + j] != value[j])
{
return false;
}
}

return true;
}
}
#endif

/// <summary>
/// Pads with leading zeros if needed.
/// </summary>
Expand Down
Original file line number Diff line number Diff line change
@@ -1,8 +1,6 @@
using System;
#if NETSTANDARD2_1_OR_GREATER || NET6_0_OR_GREATER
using System.Buffers.Binary;
using System.Numerics;
#endif
using System.Security.Cryptography;

namespace Renci.SshNet.Security.Cryptography.Ciphers
Expand All @@ -15,13 +13,8 @@ private sealed class CtrImpl : BlockCipher, IDisposable

private readonly ICryptoTransform _encryptor;

#if NETSTANDARD2_1_OR_GREATER || NET6_0_OR_GREATER
private ulong _ivUpper; // The upper 64 bits of the IV
private ulong _ivLower; // The lower 64 bits of the IV
#else
// The same on netfx
private readonly uint[] _packedIV;
#endif

public CtrImpl(
byte[] key,
Expand All @@ -35,12 +28,8 @@ public CtrImpl(
_aes = aes;
_encryptor = aes.CreateEncryptor();

#if NETSTANDARD2_1_OR_GREATER || NET6_0_OR_GREATER
_ivLower = BinaryPrimitives.ReadUInt64BigEndian(iv.AsSpan(8));
_ivUpper = BinaryPrimitives.ReadUInt64BigEndian(iv);
#else
_packedIV = GetPackedIV(iv);
#endif
}

public override byte[] Encrypt(byte[] input, int offset, int length)
Expand Down Expand Up @@ -85,8 +74,6 @@ private byte[] CTREncryptDecrypt(byte[] data, int offset, int length)
return buffer;
}

#if NETSTANDARD2_1_OR_GREATER || NET6_0_OR_GREATER

// creates the Counter array filled with incrementing copies of IV
private void CTRCreateCounterArray(byte[] buffer)
{
Expand Down Expand Up @@ -118,87 +105,6 @@ private static void ArrayXOR(byte[] buffer, byte[] data, int offset, int length)
}
}

#else
// creates the Counter array filled with incrementing copies of IV
private void CTRCreateCounterArray(byte[] buffer)
{
// fill array with IV, increment by 1 for each copy
var words = buffer.Length / 4;
var counter = new uint[words];
for (var i = 0; i < words; i += 4)
{
// write IV to buffer (big endian)
counter[i] = _packedIV[0];
counter[i + 1] = _packedIV[1];
counter[i + 2] = _packedIV[2];
counter[i + 3] = _packedIV[3];

// increment IV (little endian)
if (_packedIV[3] < 0xFF000000u)
{
_packedIV[3] += 0x01000000u;
}
else
{
var j = 3;
do
{
_packedIV[j] = SwapEndianness(SwapEndianness(_packedIV[j]) + 1);
}
while (_packedIV[j] == 0 && --j >= 0);
}
}

// copy uint[] to byte[]
Buffer.BlockCopy(counter, 0, buffer, 0, buffer.Length);
}

// XOR 2 arrays using Uint[] and blockcopy
private static void ArrayXOR(byte[] buffer, byte[] data, int offset, int length)
{
var words = length / 4;
if (length % 4 != 0)
{
words++;
}

// convert original data to words
var datawords = new uint[words];
Buffer.BlockCopy(data, offset, datawords, 0, length);

// convert encrypted IV counter to words
var bufferwords = new uint[words];
Buffer.BlockCopy(buffer, 0, bufferwords, 0, length);

// XOR encrypted Counter with input data
for (var i = 0; i < words; i++)
{
bufferwords[i] = bufferwords[i] ^ datawords[i];
}

// copy uint[] to byte[]
Buffer.BlockCopy(bufferwords, 0, buffer, 0, length);
}

// pack the IV into an array of uint[4]
private static uint[] GetPackedIV(byte[] iv)
{
var packedIV = new uint[4];
packedIV[0] = BitConverter.ToUInt32(iv, 0);
packedIV[1] = BitConverter.ToUInt32(iv, 4);
packedIV[2] = BitConverter.ToUInt32(iv, 8);
packedIV[3] = BitConverter.ToUInt32(iv, 12);

return packedIV;
}

private static uint SwapEndianness(uint x)
{
x = (x >> 16) | (x << 16);
return ((x & 0xFF00FF00) >> 8) | ((x & 0x00FF00FF) << 8);
}
#endif

private void Dispose(bool disposing)
{
if (disposing)
Expand Down
23 changes: 4 additions & 19 deletions src/Renci.SshNet/ShellStream.cs
Original file line number Diff line number Diff line change
Expand Up @@ -393,11 +393,7 @@ public void Expect(TimeSpan timeout, int lookback, params ExpectAction[] expectA

Debug.Assert(_readHead <= searchHead && searchHead <= _readTail);

#if NETFRAMEWORK || NETSTANDARD2_0
var indexOfMatch = _readBuffer.IndexOf(expectBytes, searchHead, _readTail - searchHead);
#else
var indexOfMatch = _readBuffer.AsSpan(searchHead, _readTail - searchHead).IndexOf(expectBytes);
#endif

if (indexOfMatch >= 0)
{
Expand All @@ -417,7 +413,7 @@ public void Expect(TimeSpan timeout, int lookback, params ExpectAction[] expectA

if (timeout == Timeout.InfiniteTimeSpan)
{
Monitor.Wait(_sync);
_ = Monitor.Wait(_sync);
}
else
{
Expand Down Expand Up @@ -665,24 +661,16 @@ public IAsyncResult BeginExpect(TimeSpan timeout, int lookback, AsyncCallback? c
{
AssertValid();

#if NETFRAMEWORK || NETSTANDARD2_0
var indexOfCr = _readBuffer.IndexOf(_carriageReturnBytes, _readHead, _readTail - _readHead);
#else
var indexOfCr = _readBuffer.AsSpan(_readHead, _readTail - _readHead).IndexOf(_carriageReturnBytes);
#endif

if (indexOfCr >= 0)
{
// We have found \r. We only need to search for \n up to and just after the \r
// (in order to consume \r\n if we can).
#if NETFRAMEWORK || NETSTANDARD2_0
var indexOfLf = indexOfCr + _carriageReturnBytes.Length + _lineFeedBytes.Length <= _readTail - _readHead
? _readBuffer.IndexOf(_lineFeedBytes, _readHead, indexOfCr + _carriageReturnBytes.Length + _lineFeedBytes.Length)
: _readBuffer.IndexOf(_lineFeedBytes, _readHead, indexOfCr);
#else
var indexOfLf = indexOfCr + _carriageReturnBytes.Length + _lineFeedBytes.Length <= _readTail - _readHead
? _readBuffer.AsSpan(_readHead, indexOfCr + _carriageReturnBytes.Length + _lineFeedBytes.Length).IndexOf(_lineFeedBytes)
: _readBuffer.AsSpan(_readHead, indexOfCr).IndexOf(_lineFeedBytes);
#endif

if (indexOfLf >= 0 && indexOfLf < indexOfCr)
{
// If there is \n before the \r, then return up to the \n
Expand Down Expand Up @@ -720,11 +708,8 @@ public IAsyncResult BeginExpect(TimeSpan timeout, int lookback, AsyncCallback? c
else
{
// There is no \r. What about \n?
#if NETFRAMEWORK || NETSTANDARD2_0
var indexOfLf = _readBuffer.IndexOf(_lineFeedBytes, _readHead, _readTail - _readHead);
#else
var indexOfLf = _readBuffer.AsSpan(_readHead, _readTail - _readHead).IndexOf(_lineFeedBytes);
#endif

if (indexOfLf >= 0)
{
var returnText = _encoding.GetString(_readBuffer, _readHead, indexOfLf);
Expand Down