Skip to content

Commit

Permalink
Merge pull request #34 from RevolveNTNU/feature/support-half-aka-float16
Browse files Browse the repository at this point in the history
Talian asked nicely. Will test now with embedded, will revert if if it doesn't work.
  • Loading branch information
jkguttormsen authored Feb 11, 2024
2 parents be8b55e + 45b5d5d commit 58c86c6
Show file tree
Hide file tree
Showing 8 changed files with 74 additions and 8 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/build_and_test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -16,7 +16,7 @@ jobs:
- name: Setup .NET
uses: actions/setup-dotnet@v1
with:
dotnet-version: 3.1.x
dotnet-version: 6.0.x
- name: Restore dependencies
run: dotnet restore
- name: Build
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/pack_and_release.yml
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,7 @@ jobs:
- name: Setup dotnet
uses: actions/setup-dotnet@v1
with:
dotnet-version: 3.1.x
dotnet-version: 6.0.x

- name: Restore dependencies
run: dotnet restore
Expand Down
7 changes: 7 additions & 0 deletions RevolveUavcan/Properties/launchSettings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"profiles": {
"Profile 1": {
"commandName": "Executable"
}
}
}
2 changes: 1 addition & 1 deletion RevolveUavcan/RevolveUavcan.csproj
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<TargetFramework>net6.0</TargetFramework>
<LangVersion>8.0</LangVersion>
<PackageId>RevolveUavcan</PackageId>
<Version>0.0.0</Version>
Expand Down
32 changes: 29 additions & 3 deletions RevolveUavcan/Tools/BitArrayTools.cs
Original file line number Diff line number Diff line change
Expand Up @@ -114,6 +114,27 @@ private static BitArray FillBitArrayWithMSB(this BitArray bitArray, int finalSiz
return template;
}

/// <summary>
/// Calculate the ulong value of a BitArray
/// </summary>
/// <param name="bitArray">The BitArray we want to calculate the corresponding ulong value for</param>
/// <returns>An integer representation of the BitArray</returns>
public static ulong GetULongFromBitArray(this BitArray bitArray)
{
if (bitArray.Length > 64)
{
throw new ArgumentException("BitArray length cannot be greater than 64 bits.");
}

// Initialize bitArrayWithMsb with values from bitArray and fill it with MSB
BitArray bitArrayWithMsb = FillBitArrayWithMSB(bitArray, 64);

// Find and return corresponding integer value from bitArrayWithMsb
int[] array = new int[2];
bitArrayWithMsb.CopyTo(array, 0);
return (uint)array[0] + ((ulong)(uint)array[1] << 32);
}

/// <summary>
/// Calculate the long value of a BitArray
/// </summary>
Expand All @@ -137,16 +158,21 @@ public static long GetLongFromBitArray(this BitArray bitArray)

public static double GetFloatFromBitArray(this BitArray dataBits)
{
if (dataBits.Length != 64 && dataBits.Length != 32)
if (dataBits.Length != 64 && dataBits.Length != 32 && dataBits.Length != 16)
{
throw new ArgumentException("Invalid bit length.");
}

byte[] bytes = new byte[dataBits.Length / 8];

dataBits.CopyTo(bytes, 0);

return dataBits.Length == 64 ? BitConverter.ToDouble(bytes, 0) : BitConverter.ToSingle(bytes, 0);

if(dataBits.Length == 16)
return (double) BitConverter.ToHalf(bytes, 0);
else if(dataBits.Length == 32)
return BitConverter.ToSingle(bytes, 0);
else
return BitConverter.ToDouble(bytes, 0);
}

public static byte[] GetByteArrayFromBitArray(this BitArray bitArray)
Expand Down
2 changes: 1 addition & 1 deletion RevolveUavcan/Uavcan/UavcanParser.cs
Original file line number Diff line number Diff line change
Expand Up @@ -134,7 +134,7 @@ private double ParseUavcanChannel(BitArray frameData, UavcanChannel channel, int
result = channel.Basetype switch
{
BaseType.SIGNED_INT => dataBits.GetLongFromBitArray(),
BaseType.UNSIGNED_INT => dataBits.GetUIntFromBitArray(),
BaseType.UNSIGNED_INT => dataBits.GetULongFromBitArray(),
BaseType.BOOLEAN => dataBits.Get(0) ? 1D : 0D,
BaseType.FLOAT => dataBits.GetFloatFromBitArray(),
_ => result
Expand Down
2 changes: 1 addition & 1 deletion RevolveUavcanTest/RevolveUavcanTest.csproj
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>netcoreapp3.1</TargetFramework>
<TargetFramework>net6.0</TargetFramework>

<IsPackable>false</IsPackable>
</PropertyGroup>
Expand Down
33 changes: 33 additions & 0 deletions RevolveUavcanTest/Tools/BitArrayToolsGetValueTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -126,6 +126,8 @@ public void GetFloatAndDoubleValidArgsTest(BitArray bitArray, double expectedRes

public static IEnumerable<object[]> GetFloatAndDoubleValidData()
{
yield return new object[] { new BitArray(BitConverter.GetBytes((Half) 128)), 128 };
yield return new object[] { new BitArray(BitConverter.GetBytes((Half) (-128))), -128 };
yield return new object[] { new BitArray(BitConverter.GetBytes(128D)), 128D };
yield return new object[] { new BitArray(BitConverter.GetBytes(-128D)), -128D };
yield return new object[] { new BitArray(BitConverter.GetBytes(-128F)), -128F };
Expand All @@ -142,8 +144,39 @@ public void GetFloatAndDoubleInvalidArgsTest(BitArray bitArray)

public static IEnumerable<object[]> GetFloatAndDoubleInvalidData()
{
yield return new object[] { new BitArray(8) };
yield return new object[] { new BitArray(42) };
yield return new object[] { new BitArray(69) };
}


[DataTestMethod]
[DynamicData(nameof(GetULongValidData), DynamicDataSourceType.Method)]
public void GetULongValidArgsTest(BitArray bitArray, ulong expectedResult)
{
var result = bitArray.GetULongFromBitArray();
Assert.AreEqual(expectedResult, result);
}

public static IEnumerable<object[]> GetULongValidData()
{
yield return new object[] { new BitArray(BitConverter.GetBytes((ulong) 12)), (ulong) 12 };
yield return new object[] { new BitArray(BitConverter.GetBytes((ulong) 17)), (ulong ) 17 };
yield return new object[] { new BitArray(BitConverter.GetBytes((ulong) 128)), (ulong) 128 };
yield return new object[] { new BitArray(BitConverter.GetBytes((ulong) 12_000)), (ulong) 12_000 };
yield return new object[] { new BitArray(BitConverter.GetBytes((ulong) 3_000_000_000)), (ulong) 3_000_000_000 };
}

[TestMethod]
[DynamicData(nameof(GetULongInvalidData), DynamicDataSourceType.Method)]
public void GetULongInvalidArgsTest(BitArray bitArray)
{
Assert.ThrowsException<ArgumentException>(() => bitArray.GetULongFromBitArray());
}

public static IEnumerable<object[]> GetULongInvalidData()
{
yield return new object[] { new BitArray(69) };
}
}
}

0 comments on commit 58c86c6

Please sign in to comment.