Browse Source

Check array bounds in expression indexer.

pull/242/merge
Steven Kirk 11 years ago
parent
commit
12c1127f06
  1. 27
      src/Markup/Perspex.Markup/Binding/IndexerNode.cs
  2. 30
      tests/Perspex.Markup.UnitTests/Binding/ExpressionObserverTests_Indexer.cs

27
src/Markup/Perspex.Markup/Binding/IndexerNode.cs

@ -90,7 +90,12 @@ namespace Perspex.Markup.Binding
if (typeInfo.IsArray && _intArgs != null) if (typeInfo.IsArray && _intArgs != null)
{ {
return ((Array)target).GetValue(_intArgs); var array = (Array)target;
if (InBounds(_intArgs, array))
{
return array.GetValue(_intArgs);
}
} }
else if (target is IList && _intArgs?.Length == 1) else if (target is IList && _intArgs?.Length == 1)
{ {
@ -102,5 +107,25 @@ namespace Perspex.Markup.Binding
return PerspexProperty.UnsetValue; return PerspexProperty.UnsetValue;
} }
private bool InBounds(int[] args, Array array)
{
if (args.Length == array.Rank)
{
for (var i = 0; i < args.Length; ++i)
{
if (args[i] >= array.GetLength(i))
{
return false;
}
}
return true;
}
else
{
return false;
}
}
} }
} }

30
tests/Perspex.Markup.UnitTests/Binding/ExpressionObserverTests_Indexer.cs

@ -32,6 +32,36 @@ namespace Perspex.Markup.UnitTests.Binding
Assert.Equal("qux", result); Assert.Equal("qux", result);
} }
[Fact]
public async void Array_Out_Of_Bounds_Should_Return_UnsetValue()
{
var data = new { Foo = new[] { "foo", "bar" } };
var target = new ExpressionObserver(data, "Foo[2]");
var result = await target.Take(1);
Assert.Equal(PerspexProperty.UnsetValue, result);
}
[Fact]
public async void Array_With_Wrong_Dimensions_Should_Return_UnsetValue()
{
var data = new { Foo = new[] { "foo", "bar" } };
var target = new ExpressionObserver(data, "Foo[1,2]");
var result = await target.Take(1);
Assert.Equal(PerspexProperty.UnsetValue, result);
}
[Fact]
public async void List_Out_Of_Bounds_Should_Return_UnsetValue()
{
var data = new { Foo = new List<string> { "foo", "bar" } };
var target = new ExpressionObserver(data, "Foo[2]");
var result = await target.Take(1);
Assert.Equal(PerspexProperty.UnsetValue, result);
}
[Fact] [Fact]
public async void Should_Get_List_Value() public async void Should_Get_List_Value()
{ {

Loading…
Cancel
Save