Skip to content

Commit

Permalink
fix(unity-collections): support unity collections version > 2.x.x
Browse files Browse the repository at this point in the history
update APIs in `NativeText` and `NativeList` extensions to allow unity collections version 2.x.x to
compile

fix #192
  • Loading branch information
jasonboukheir committed Feb 22, 2023
1 parent ebe81df commit 025a153
Show file tree
Hide file tree
Showing 20 changed files with 270 additions and 60 deletions.
24 changes: 10 additions & 14 deletions Runtime/Algorand.Unity.Collections/FixedStringParseExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -5,46 +5,43 @@ namespace Algorand.Unity.Collections
public static class FixedStringParseExtensions
{
internal static bool ParseUlongInternal<T>(ref T fs, ref int offset, out ulong value)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
int digitOffset = offset;
var digitOffset = offset;
value = 0;
var rune = fs.Peek(offset);
var c = (char)rune.value;
while (offset < fs.Length && Unicode.Rune.IsDigit(rune))
{
value *= 10;
value += (ulong)(fs.Read(ref offset).value - '0');
rune = fs.Peek(offset);
}

return digitOffset != offset;
}


public static ParseError Parse<T>(ref this T fs, ref int offset, ref long output)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
if (!FixedStringMethods.ParseLongInternal(ref fs, ref offset, out long value))
return ParseError.Syntax;
output = value;
return ParseError.None;
}


public static ParseError Parse<T>(ref this T fs, ref int offset, ref ulong output)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
if (!ParseUlongInternal(ref fs, ref offset, out ulong value))
return ParseError.Syntax;
output = value;
return ParseError.None;
}


public static bool Found<T>(ref this T fs, ref int offset, char a, char b, char c, char d)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
int old = offset;
var old = offset;
if ((fs.Read(ref offset).value | 32) == a
&& (fs.Read(ref offset).value | 32) == b
&& (fs.Read(ref offset).value | 32) == c
Expand All @@ -54,11 +51,10 @@ public static bool Found<T>(ref this T fs, ref int offset, char a, char b, char
return false;
}


public static bool Found<T>(ref this T fs, ref int offset, char a, char b, char c, char d, char e)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
int old = offset;
var old = offset;
if ((fs.Read(ref offset).value | 32) == a
&& (fs.Read(ref offset).value | 32) == b
&& (fs.Read(ref offset).value | 32) == c
Expand All @@ -69,4 +65,4 @@ public static bool Found<T>(ref this T fs, ref int offset, char a, char b, char
return false;
}
}
}
}
56 changes: 56 additions & 0 deletions Runtime/Algorand.Unity.Collections/NativeTextExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,5 +19,61 @@ public unsafe static NativeArray<byte> AsArray(this NativeText text)
#endif
return array;
}

internal static bool ParseUlongInternal(ref NativeText fs, ref int offset, out ulong value)
{
var digitOffset = offset;
value = 0;
var rune = fs.Peek(offset);
while (offset < fs.Length && Unicode.Rune.IsDigit(rune))
{
value *= 10;
value += (ulong)(fs.Read(ref offset).value - '0');
rune = fs.Peek(offset);
}

return digitOffset != offset;
}

public static ParseError Parse(ref this NativeText fs, ref int offset, ref long output)
{
if (!FixedStringMethods.ParseLongInternal(ref fs, ref offset, out long value))
return ParseError.Syntax;
output = value;
return ParseError.None;
}

public static ParseError Parse(ref this NativeText fs, ref int offset, ref ulong output)
{
if (!ParseUlongInternal(ref fs, ref offset, out ulong value))
return ParseError.Syntax;
output = value;
return ParseError.None;
}

public static bool Found(ref this NativeText fs, ref int offset, char a, char b, char c, char d)
{
var old = offset;
if ((fs.Read(ref offset).value | 32) == a
&& (fs.Read(ref offset).value | 32) == b
&& (fs.Read(ref offset).value | 32) == c
&& (fs.Read(ref offset).value | 32) == d)
return true;
offset = old;
return false;
}

public static bool Found(ref this NativeText fs, ref int offset, char a, char b, char c, char d, char e)
{
var old = offset;
if ((fs.Read(ref offset).value | 32) == a
&& (fs.Read(ref offset).value | 32) == b
&& (fs.Read(ref offset).value | 32) == c
&& (fs.Read(ref offset).value | 32) == d
&& (fs.Read(ref offset).value | 32) == e)
return true;
offset = old;
return false;
}
}
}
23 changes: 20 additions & 3 deletions Runtime/Algorand.Unity.Encoding/Base64Encoding.cs
Original file line number Diff line number Diff line change
Expand Up @@ -8,14 +8,31 @@ public static class Base64Encoding
{
public static void CopyToBase64<TBytes, T>(this TBytes bytes, ref T s)
where TBytes : struct, IArray<byte>
where T : struct, IUTF8Bytes, INativeList<byte>
where T : unmanaged, IUTF8Bytes, INativeList<byte>
{
s.CopyFrom(System.Convert.ToBase64String(bytes.ToArray()));
}

public static void CopyFromBase64<TByteArray, T>(ref this TByteArray bytes, T s, int maxLength = int.MaxValue)
where TByteArray : struct, IArray<byte>
where T : struct, IUTF8Bytes, INativeList<byte>
where T : unmanaged, IUTF8Bytes, INativeList<byte>
{
var managedString = s.ToString();
var byteArr = System.Convert.FromBase64String(managedString);
var length = math.min(maxLength, byteArr.Length);
for (var i = 0; i < length; i++)
bytes[i] = byteArr[i];
}

public static void CopyToBase64<TBytes>(this TBytes bytes, ref NativeText s)
where TBytes : struct, IArray<byte>
{
s.CopyFrom(System.Convert.ToBase64String(bytes.ToArray()));
}

public static void CopyFromBase64<TByteArray>(ref this TByteArray bytes, NativeText s,
int maxLength = int.MaxValue)
where TByteArray : struct, IArray<byte>
{
var managedString = s.ToString();
var byteArr = System.Convert.FromBase64String(managedString);
Expand Down Expand Up @@ -51,4 +68,4 @@ public static int BytesRequiredForBase64Encoding(int currentBytes)
return (currentBytes + 2) / 3 * 4;
}
}
}
}
59 changes: 45 additions & 14 deletions Runtime/Algorand.Unity.Encoding/Utf8StringExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,10 @@

namespace Algorand.Unity
{
public unsafe static class Utf8StringExtensions
public static unsafe class Utf8StringExtensions
{
public static FormatError Append<T>(ref this T fs, ulong input)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
const int maximumDigits = 20;
var temp = stackalloc byte[maximumDigits];
Expand All @@ -16,33 +16,64 @@ public static FormatError Append<T>(ref this T fs, ulong input)
var digit = (byte)(input % 10);
temp[--offset] = (byte)('0' + digit);
input /= 10;
}
while (input != 0);
} while (input != 0);

return fs.Append(temp + offset, maximumDigits - offset);
}

public static FormatError Append<T>(ref this T fs, bool input)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
return input
? fs.Append("true")
: fs.Append("false")
? fs.Append("true")
: fs.Append("false")
;
}

public static byte[] ToByteArray<T>(this T text)
where T : struct, IUTF8Bytes, INativeList<byte>
where T : unmanaged, IUTF8Bytes, INativeList<byte>
{
var bytes = new byte[text.Length];
fixed (byte* b = &bytes[0])
{
UnsafeUtility.MemCpy(b, text.GetUnsafePtr(), text.Length);
}

return bytes;
}

public static FormatError Append(ref this NativeText fs, ulong input)
{
const int maximumDigits = 20;
var temp = stackalloc byte[maximumDigits];
int offset = maximumDigits;
do
{
var digit = (byte)(input % 10);
temp[--offset] = (byte)('0' + digit);
input /= 10;
} while (input != 0);

return fs.Append(temp + offset, maximumDigits - offset);
}

public static FormatError Append(ref this NativeText fs, bool input)
{
return input
? fs.Append("true")
: fs.Append("false")
;
}

public static byte[] ToByteArray(this NativeText text)
{
var bytes = new byte[text.Length];
unsafe
fixed (byte* b = &bytes[0])
{
fixed (byte* b = &bytes[0])
{
UnsafeUtility.MemCpy(b, text.GetUnsafePtr(), text.Length);
}
UnsafeUtility.MemCpy(b, text.GetUnsafePtr(), text.Length);
}

return bytes;
}
}
}
}
37 changes: 36 additions & 1 deletion Runtime/Algorand.Unity.Json/JsonReader/JsonReader.String.cs
Original file line number Diff line number Diff line change
Expand Up @@ -19,8 +19,43 @@ public JsonReadError ReadString(out string value)
}
}

public JsonReadError ReadString(ref NativeText value)
{
value.Clear();
var resetOffset = offset;
var t = Read();
if (t != JsonToken.String)
{
offset = resetOffset;
return JsonReadError.IncorrectType;
}
while (offset < text.Length)
{
var r = text.Read(ref offset);
t = r.ToJsonToken();
if (t == JsonToken.String)
break;
if (t == JsonToken.EscapeChar)
{
if (offset >= text.Length)
{
offset = resetOffset;
return JsonReadError.IncorrectFormat;
}
r = text.Read(ref offset);
}
value.Append(r);
}
if (t != JsonToken.String)
{
offset = resetOffset;
return JsonReadError.Overflow;
}
return JsonReadError.None;
}

public JsonReadError ReadString<T>(ref T value)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
value.Clear();
var resetOffset = offset;
Expand Down
17 changes: 16 additions & 1 deletion Runtime/Algorand.Unity.Json/JsonReader/JsonReader.cs
Original file line number Diff line number Diff line change
Expand Up @@ -63,7 +63,22 @@ public JsonReadError Skip()
}

public JsonReadError ReadRaw<T>(ref T value)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
value.Clear();
var startOffset = offset;
var skipErr = Skip();
if (skipErr != JsonReadError.None)
{
offset = startOffset;
return skipErr;
}
while (startOffset < offset)
value.Append(text.Read(ref startOffset));
return JsonReadError.None;
}

public JsonReadError ReadRaw(ref NativeText value)
{
value.Clear();
var startOffset = offset;
Expand Down
28 changes: 26 additions & 2 deletions Runtime/Algorand.Unity.Json/JsonWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,24 @@ public JsonWriter WriteString(string s)
}

public JsonWriter WriteString<T>(T fs)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
WriteChar('"');
int index = 0;
var rune = fs.Read(ref index);
while (!rune.Equals(Unicode.BadRune))
{
var c = rune.ToChar();
if (c == '"')
text.Append('\\'.ToRune());
text.Append(rune);
rune = fs.Read(ref index);
}
WriteChar('"');
return this;
}

public JsonWriter WriteString(NativeText fs)
{
WriteChar('"');
int index = 0;
Expand Down Expand Up @@ -101,7 +118,14 @@ public JsonWriter WriteNull()
}

public JsonWriter WriteObjectKey<T>(T fs)
where T : struct, INativeList<byte>, IUTF8Bytes
where T : unmanaged, INativeList<byte>, IUTF8Bytes
{
WriteString(fs);
WriteChar(':');
return this;
}

public JsonWriter WriteObjectKey(NativeText fs)
{
WriteString(fs);
WriteChar(':');
Expand Down
Loading

0 comments on commit 025a153

Please sign in to comment.