Skip to content

Commit

Permalink
[1.6>1.7] [MERGE #3459 @sigatrev] fix crashes with cross site typed v…
Browse files Browse the repository at this point in the history
…irtual arrays

Merge pull request #3459 from sigatrev:CrossSiteVirtualTypedArrays

If an object has type CrossSiteObject\<T> then VirtualTableInfo\<T>::HasVirtualTable() will always return false. In the case of CrossSiteObject virtual typed arrays, the vtable check for the virtual array type was returning false, so they were assumed to be non-virtual arrays which is incorrect.

Since no action was performed for the CrossSiteObject arrays anyway, this commit adds specific checks for the non-cross site, non-virtual array types, and removes the redundant CrossSite checks.
  • Loading branch information
sigatrev committed Aug 1, 2017
2 parents 79c13b4 + bc4f4ed commit 12da674
Show file tree
Hide file tree
Showing 3 changed files with 67 additions and 91 deletions.
130 changes: 39 additions & 91 deletions lib/Runtime/Language/JavascriptOperators.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -3514,15 +3514,15 @@ namespace Js
if (VirtualTableInfo<Int8VirtualArray>::HasVirtualTable(instance))
{
Int8VirtualArray* int8Array = Int8VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int8Array) && indexInt >= 0)
if (indexInt >= 0)
{
return int8Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Int8Array>::HasVirtualTable(instance))
{
Int8Array* int8Array = Int8Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int8Array) && indexInt >= 0)
if (indexInt >= 0)
{
return int8Array->DirectGetItem(indexInt);
}
Expand All @@ -3537,15 +3537,15 @@ namespace Js
if (VirtualTableInfo<Uint8VirtualArray>::HasVirtualTable(instance))
{
Uint8VirtualArray* uint8Array = Uint8VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8Array) && indexInt >= 0)
if (indexInt >= 0)
{
return uint8Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Uint8Array>::HasVirtualTable(instance))
{
Uint8Array* uint8Array = Uint8Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8Array) && indexInt >= 0)
if (indexInt >= 0)
{
return uint8Array->DirectGetItem(indexInt);
}
Expand All @@ -3560,15 +3560,15 @@ namespace Js
if (VirtualTableInfo<Uint8ClampedVirtualArray>::HasVirtualTable(instance))
{
Uint8ClampedVirtualArray* uint8ClampedArray = Uint8ClampedVirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8ClampedArray) && indexInt >= 0)
if (indexInt >= 0)
{
return uint8ClampedArray->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Uint8ClampedArray>::HasVirtualTable(instance))
{
Uint8ClampedArray* uint8ClampedArray = Uint8ClampedArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8ClampedArray) && indexInt >= 0)
if (indexInt >= 0)
{
return uint8ClampedArray->DirectGetItem(indexInt);
}
Expand All @@ -3584,15 +3584,15 @@ namespace Js
if (VirtualTableInfo<Int16VirtualArray>::HasVirtualTable(instance))
{
Int16VirtualArray* int16Array = Int16VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int16Array) && indexInt >= 0)
if (indexInt >= 0)
{
return int16Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Int16Array>::HasVirtualTable(instance))
{
Int16Array* int16Array = Int16Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int16Array) && indexInt >= 0)
if (indexInt >= 0)
{
return int16Array->DirectGetItem(indexInt);
}
Expand All @@ -3608,15 +3608,15 @@ namespace Js
if (VirtualTableInfo<Uint16VirtualArray>::HasVirtualTable(instance))
{
Uint16VirtualArray* uint16Array = Uint16VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint16Array) && indexInt >= 0)
if (indexInt >= 0)
{
return uint16Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Uint16Array>::HasVirtualTable(instance))
{
Uint16Array* uint16Array = Uint16Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint16Array) && indexInt >= 0)
if (indexInt >= 0)
{
return uint16Array->DirectGetItem(indexInt);
}
Expand All @@ -3630,15 +3630,15 @@ namespace Js
if (VirtualTableInfo<Int32VirtualArray>::HasVirtualTable(instance))
{
Int32VirtualArray* int32Array = Int32VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int32Array) && indexInt >= 0)
if (indexInt >= 0)
{
return int32Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Int32Array>::HasVirtualTable(instance))
{
Int32Array* int32Array = Int32Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int32Array) && indexInt >= 0)
if (indexInt >= 0)
{
return int32Array->DirectGetItem(indexInt);
}
Expand All @@ -3653,15 +3653,15 @@ namespace Js
if (VirtualTableInfo<Uint32VirtualArray>::HasVirtualTable(instance))
{
Uint32VirtualArray* uint32Array = Uint32VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint32Array) && indexInt >= 0)
if (indexInt >= 0)
{
return uint32Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Uint32Array>::HasVirtualTable(instance))
{
Uint32Array* uint32Array = Uint32Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint32Array) && indexInt >= 0)
if (indexInt >= 0)
{
return uint32Array->DirectGetItem(indexInt);
}
Expand All @@ -3676,15 +3676,15 @@ namespace Js
if (VirtualTableInfo<Float32VirtualArray>::HasVirtualTable(instance))
{
Float32VirtualArray* float32Array = Float32VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float32Array) && indexInt >= 0)
if (indexInt >= 0)
{
return float32Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Float32Array>::HasVirtualTable(instance))
{
Float32Array* float32Array = Float32Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float32Array) && indexInt >= 0)
if (indexInt >= 0)
{
return float32Array->DirectGetItem(indexInt);
}
Expand All @@ -3698,15 +3698,15 @@ namespace Js
if (VirtualTableInfo<Float64VirtualArray>::HasVirtualTable(instance))
{
Float64VirtualArray* float64Array = Float64VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float64Array) && indexInt >= 0)
if (indexInt >= 0)
{
return float64Array->DirectGetItem(indexInt);
}
}
else
else if (VirtualTableInfo<Float64Array>::HasVirtualTable(instance))
{
Float64Array* float64Array = Float64Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float64Array) && indexInt >= 0)
if (indexInt >= 0)
{
return float64Array->DirectGetItem(indexInt);
}
Expand Down Expand Up @@ -4172,6 +4172,9 @@ namespace Js
{
BOOL returnValue = FALSE;
bool isNumericIndex = false;

// CrossSite types will go down the slow path.

switch (instanceType)
{
case TypeIds_Int8Array:
Expand All @@ -4181,19 +4184,13 @@ namespace Js
if (VirtualTableInfo<Int8VirtualArray>::HasVirtualTable(instance))
{
Int8VirtualArray* int8Array = Int8VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int8Array))
{
returnValue = int8Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if( VirtualTableInfo<Int8Array>::HasVirtualTable(instance))
{
Int8Array* int8Array = Int8Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int8Array))
{
returnValue = int8Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}

Expand All @@ -4203,19 +4200,13 @@ namespace Js
if (VirtualTableInfo<Uint8VirtualArray>::HasVirtualTable(instance))
{
Uint8VirtualArray* uint8Array = Uint8VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8Array))
{
returnValue = uint8Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if (VirtualTableInfo<Uint8Array>::HasVirtualTable(instance))
{
Uint8Array* uint8Array = Uint8Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8Array))
{
returnValue = uint8Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}

Expand All @@ -4225,19 +4216,13 @@ namespace Js
if (VirtualTableInfo<Uint8ClampedVirtualArray>::HasVirtualTable(instance))
{
Uint8ClampedVirtualArray* uint8ClampedArray = Uint8ClampedVirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8ClampedArray))
{
returnValue = uint8ClampedArray->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if(VirtualTableInfo<Uint8ClampedArray>::HasVirtualTable(instance))
{
Uint8ClampedArray* uint8ClampedArray = Uint8ClampedArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint8ClampedArray))
{
returnValue = uint8ClampedArray->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}

Expand All @@ -4247,19 +4232,13 @@ namespace Js
if (VirtualTableInfo<Int16VirtualArray>::HasVirtualTable(instance))
{
Int16VirtualArray* int16Array = Int16VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int16Array))
{
returnValue = int16Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if (VirtualTableInfo<Int16Array>::HasVirtualTable(instance))
{
Int16Array* int16Array = Int16Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int16Array))
{
returnValue = int16Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}

Expand All @@ -4270,19 +4249,13 @@ namespace Js
if (VirtualTableInfo<Uint16VirtualArray>::HasVirtualTable(instance))
{
Uint16VirtualArray* uint16Array = Uint16VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint16Array))
{
returnValue = uint16Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if (VirtualTableInfo<Uint16Array>::HasVirtualTable(instance))
{
Uint16Array* uint16Array = Uint16Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint16Array))
{
returnValue = uint16Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}
case TypeIds_Int32Array:
Expand All @@ -4291,19 +4264,13 @@ namespace Js
if (VirtualTableInfo<Int32VirtualArray>::HasVirtualTable(instance))
{
Int32VirtualArray* int32Array = Int32VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int32Array))
{
returnValue = int32Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if(VirtualTableInfo<Int32Array>::HasVirtualTable(instance))
{
Int32Array* int32Array = Int32Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(int32Array))
{
returnValue = int32Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}
case TypeIds_Uint32Array:
Expand All @@ -4313,19 +4280,13 @@ namespace Js
if (VirtualTableInfo<Uint32VirtualArray>::HasVirtualTable(instance))
{
Uint32VirtualArray* uint32Array = Uint32VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint32Array))
{
returnValue = uint32Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if (VirtualTableInfo<Uint32Array>::HasVirtualTable(instance))
{
Uint32Array* uint32Array = Uint32Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(uint32Array))
{
returnValue = uint32Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}
case TypeIds_Float32Array:
Expand All @@ -4334,41 +4295,28 @@ namespace Js
if (VirtualTableInfo<Float32VirtualArray>::HasVirtualTable(instance))
{
Float32VirtualArray* float32Array = Float32VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float32Array))
{
returnValue = float32Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if (VirtualTableInfo<Float32Array>::HasVirtualTable(instance))
{
Float32Array* float32Array = Float32Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float32Array))
{
returnValue = float32Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}
case TypeIds_Float64Array:
{
// The type array will deal with all possible values for the index

if (VirtualTableInfo<Float64VirtualArray>::HasVirtualTable(instance))
{
Float64VirtualArray* float64Array = Float64VirtualArray::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float64Array))
{
returnValue = float64Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
else
else if (VirtualTableInfo<Float64Array>::HasVirtualTable(instance))
{
Float64Array* float64Array = Float64Array::FromVar(instance);
if (!CrossSite::IsCrossSiteObjectTyped(float64Array))
{
returnValue = float64Array->ValidateIndexAndDirectSetItem(index, value, &isNumericIndex);
}
}
break;
}
}
Expand Down
23 changes: 23 additions & 0 deletions test/typedarray/CrossSiteVirtual.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
//-------------------------------------------------------------------------------------------------------
// Copyright (C) Microsoft. All rights reserved.
// Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
//-------------------------------------------------------------------------------------------------------

function foo( type )
{
var g = WScript.LoadScript("a = new " + type + "(16777216);", "samethread");
g.a[0] = 0;
g.a[0];
}

foo("Int8Array");
foo("Uint8Array");
foo("Uint8ClampedArray");
foo("Int16Array");
foo("Uint16Array");
foo("Int32Array");
foo("Uint32Array");
foo("Float32Array");
foo("Float64Array");

WScript.Echo("PASSED");
Loading

0 comments on commit 12da674

Please sign in to comment.