using System; using UnitTestSharp; namespace Amphora.UnitTests { public class ByteViewTests : TestFixture { public static byte[] Counting(int length) { byte[] returnMe = new byte[length]; for (int i = 0; i < length; ++i) { returnMe[i] = (byte)i; } return returnMe; } public class CtorTests : TestFixture { public void Range_ViewsFromStartUpToEnd() { ByteView view = new ByteView(Counting(10), startIndex: 2, endIndex: 5); CheckEqual(2, view.StartIndex); CheckEqual(5, view.EndIndex); CheckEqual(3, view.Length); } public void Range_AllowsAnEmptyRunAtTheEnd() { CheckEqual(0, new ByteView(Counting(10), startIndex: 10, endIndex: 10).Length); } public void Range_NullArray_Throws() { CheckThrow(typeof(ArgumentNullException)); new ByteView(null, startIndex: 0, endIndex: 0); } public void Range_NegativeStart_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); new ByteView(Counting(10), startIndex: -1, endIndex: 3); } public void Range_StartPastTheEnd_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); new ByteView(Counting(10), startIndex: 11, endIndex: 11); } public void Range_NegativeEnd_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); new ByteView(Counting(10), startIndex: 0, endIndex: -1); } public void Range_EndPastTheEnd_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); new ByteView(Counting(10), startIndex: 0, endIndex: 11); } public void Range_EndBeforeStart_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); new ByteView(Counting(10), startIndex: 5, endIndex: 4); } public void WholeArray_ViewsEveryByte() { ByteView view = new ByteView(Counting(10)); CheckEqual(0, view.StartIndex); CheckEqual(10, view.EndIndex); } public void WholeArray_NullArray_Throws() { CheckThrow(typeof(ArgumentNullException)); new ByteView(null); } } public class LengthTests : TestFixture { public void Default_IsZero() { CheckEqual(0, default(ByteView).Length); } } public class EmptyTests : TestFixture { public void Default_IsEmpty() { CheckTrue(default(ByteView).Empty); } public void EmptyRun_IsEmpty() { CheckTrue(new ByteView(Counting(10), startIndex: 4, endIndex: 4).Empty); } public void NonEmptyRun_IsNotEmpty() { CheckFalse(new ByteView(Counting(10), startIndex: 4, endIndex: 5).Empty); } } public class IsDefaultTests : TestFixture { public void Default_IsDefault() { CheckTrue(default(ByteView).IsDefault); } public void EmptyRunOfAnArray_IsNotDefault() { CheckFalse(new ByteView(new byte[0]).IsDefault); } } public class IsOverTests : TestFixture { public void TheArrayItViews_IsTrue() { byte[] bytes = Counting(10); CheckTrue(new ByteView(bytes, startIndex: 2, endIndex: 5).IsOver(bytes)); } public void AnArrayHoldingTheSameBytes_IsFalse() { CheckFalse(new ByteView(Counting(10)).IsOver(Counting(10))); } public void Default_IsFalseEvenForNull() { CheckFalse(default(ByteView).IsOver(null)); } } public class GetPinnableReferenceTests : TestFixture { public unsafe void PinsTheFirstByteOfTheView() { ByteView view = new ByteView(Counting(10), startIndex: 3, endIndex: 6); fixed (byte* pointer = view) { CheckEqual(3, pointer[0]); CheckEqual(5, pointer[2]); } } public unsafe void WritesThroughThePointerReachTheArray() { byte[] bytes = Counting(10); ByteView view = new ByteView(bytes, startIndex: 3, endIndex: 6); fixed (byte* pointer = view) { pointer[1] = 200; } CheckEqual(200, bytes[4]); } public unsafe void EmptyView_PinsWithoutThrowing() { ByteView view = new ByteView(Counting(10), startIndex: 10, endIndex: 10); fixed (byte* pointer = view) { CheckTrue(pointer != null); } } public unsafe void DefaultView_PinsWithoutThrowing() { fixed (byte* pointer = default(ByteView)) { CheckTrue(pointer != null); } } } public class IndexerTests : TestFixture { public void ReadsFromTheStartOfTheView() { ByteView view = new ByteView(Counting(10), startIndex: 3, endIndex: 6); CheckEqual(3, view[0]); CheckEqual(5, view[2]); } public void WritesReachTheArray() { byte[] bytes = Counting(10); ByteView view = new ByteView(bytes, startIndex: 3, endIndex: 6); view[1] = 200; CheckEqual(200, bytes[4]); } public void SeesLaterChangesToTheArray() { byte[] bytes = Counting(10); ByteView view = new ByteView(bytes, startIndex: 3, endIndex: 6); bytes[3] = 99; CheckEqual(99, view[0]); } public void NegativeIndex_Throws() { ByteView view = new ByteView(Counting(10), startIndex: 3, endIndex: 6); CheckThrow(typeof(ArgumentOutOfRangeException)); byte unused = view[-1]; } public void IndexAtTheEndOfTheView_Throws() { ByteView view = new ByteView(Counting(10), startIndex: 3, endIndex: 6); CheckThrow(typeof(ArgumentOutOfRangeException)); byte unused = view[3]; } public void Default_Throws() { CheckThrow(typeof(ArgumentOutOfRangeException)); byte unused = default(ByteView)[0]; } } public class SliceTests : TestFixture { public void CountsIndicesFromTheStartOfTheView() { ByteView slice = new ByteView(Counting(10), startIndex: 2, endIndex: 8)[1, 4]; CheckEqual(3, slice.StartIndex); CheckEqual(6, slice.EndIndex); } public void ViewsTheSameArray() { byte[] bytes = Counting(10); CheckTrue(new ByteView(bytes, startIndex: 2, endIndex: 8)[1, 4].IsOver(bytes)); } public void WholeRange_GivesTheSameWindow() { ByteView slice = new ByteView(Counting(10), startIndex: 2, endIndex: 8)[0, 6]; CheckEqual(2, slice.StartIndex); CheckEqual(8, slice.EndIndex); } public void EmptyRunAtTheEnd_IsAllowed() { CheckEqual(0, new ByteView(Counting(10), startIndex: 2, endIndex: 8)[6, 6].Length); } public void NegativeLeft_Throws() { ByteView view = new ByteView(Counting(10), startIndex: 2, endIndex: 8); CheckThrow(typeof(ArgumentOutOfRangeException)); ByteView unused = view[-1, 3]; } public void LeftPastTheEnd_Throws() { ByteView view = new ByteView(Counting(10), startIndex: 2, endIndex: 8); CheckThrow(typeof(ArgumentOutOfRangeException)); ByteView unused = view[7, 7]; } public void NegativeRight_Throws() { ByteView view = new ByteView(Counting(10), startIndex: 2, endIndex: 8); CheckThrow(typeof(ArgumentOutOfRangeException)); ByteView unused = view[0, -1]; } public void RightPastTheEnd_Throws() { ByteView view = new ByteView(Counting(10), startIndex: 2, endIndex: 8); CheckThrow(typeof(ArgumentOutOfRangeException)); ByteView unused = view[0, 7]; } public void RightBeforeLeft_Throws() { ByteView view = new ByteView(Counting(10), startIndex: 2, endIndex: 8); CheckThrow(typeof(ArgumentOutOfRangeException)); ByteView unused = view[4, 3]; } } public class CopyToTests : TestFixture { public void CopiesTheViewsBytesFromTheDestinationIndex() { byte[] destination = new byte[6]; new ByteView(Counting(10), startIndex: 3, endIndex: 6).CopyTo(destination, destinationIndex: 2); CheckEqual(new byte[] { 0, 0, 3, 4, 5, 0 }, destination); } public void EmptyView_CopiesNothing() { byte[] destination = new byte[3]; new ByteView(Counting(10), startIndex: 4, endIndex: 4).CopyTo(destination, destinationIndex: 3); CheckEqual(new byte[3], destination); } public void Default_CopiesNothing() { byte[] destination = new byte[3]; default(ByteView).CopyTo(destination, destinationIndex: 0); CheckEqual(new byte[3], destination); } public void DestinationTooSmall_Throws() { CheckThrow(typeof(ArgumentException)); new ByteView(Counting(10)).CopyTo(new byte[4], destinationIndex: 0); } } public class CopyToViewTests : TestFixture { public void CopiesTheViewsBytesToTheStartOfTheDestinationView() { byte[] destination = new byte[8]; new ByteView(Counting(10), startIndex: 3, endIndex: 6).CopyTo( new ByteView(destination, startIndex: 2, endIndex: 7)); CheckEqual(new byte[] { 0, 0, 3, 4, 5, 0, 0, 0 }, destination); } public void ADestinationOfExactlyTheLength_Fits() { byte[] destination = new byte[3]; new ByteView(Counting(10), startIndex: 3, endIndex: 6).CopyTo(new ByteView(destination)); CheckEqual(new byte[] { 3, 4, 5 }, destination); } public void EmptyView_CopiesNothing() { byte[] destination = new byte[3]; new ByteView(Counting(10), startIndex: 4, endIndex: 4).CopyTo(new ByteView(destination)); CheckEqual(new byte[3], destination); } public void Default_CopiesNothingToADefaultDestination() { default(ByteView).CopyTo(default(ByteView)); } public void ADestinationTooSmall_Throws() { CheckThrow(typeof(ArgumentException)); new ByteView(Counting(10)).CopyTo(new ByteView(new byte[4])); } public void OverlappingViewsOfOneArray_CopyAsIfThroughATemporary() { byte[] bytes = Counting(6); new ByteView(bytes, startIndex: 0, endIndex: 4).CopyTo(new ByteView(bytes, startIndex: 2, endIndex: 6)); CheckEqual(new byte[] { 0, 1, 0, 1, 2, 3 }, bytes); } } } }