@@ -2696,7 +2696,8 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
2696
2696
// stack traces.
2697
2697
std::vector<Name> functionStack;
2698
2698
2699
- std::unordered_set<Name> droppedSegments;
2699
+ std::unordered_set<Name> droppedDataSegments;
2700
+ std::unordered_set<Name> droppedElementSegments;
2700
2701
2701
2702
struct TableInterfaceInfo {
2702
2703
// The external interface in which the table is defined.
@@ -2746,6 +2747,8 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
2746
2747
Flow ret = self ()->visit (segment->data [i]);
2747
2748
extInterface->tableStore (tableName, offset + i, ret.getSingleValue ());
2748
2749
}
2750
+
2751
+ droppedElementSegments.insert (segment->name );
2749
2752
});
2750
2753
}
2751
2754
@@ -3630,7 +3633,7 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
3630
3633
Address offsetVal (uint32_t (offset.getSingleValue ().geti32 ()));
3631
3634
Address sizeVal (uint32_t (size.getSingleValue ().geti32 ()));
3632
3635
3633
- if (offsetVal + sizeVal > 0 && droppedSegments .count (curr->segment )) {
3636
+ if (offsetVal + sizeVal > 0 && droppedDataSegments .count (curr->segment )) {
3634
3637
trap (" out of bounds segment access in memory.init" );
3635
3638
}
3636
3639
if ((uint64_t )offsetVal + sizeVal > segment->data .size ()) {
@@ -3652,7 +3655,7 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
3652
3655
}
3653
3656
Flow visitDataDrop (DataDrop* curr) {
3654
3657
NOTE_ENTER (" DataDrop" );
3655
- droppedSegments .insert (curr->segment );
3658
+ droppedDataSegments .insert (curr->segment );
3656
3659
return {};
3657
3660
}
3658
3661
Flow visitMemoryCopy (MemoryCopy* curr) {
@@ -3768,7 +3771,7 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
3768
3771
const auto & seg = *wasm.getDataSegment (curr->segment );
3769
3772
auto elemBytes = element.getByteSize ();
3770
3773
auto end = offset + size * elemBytes;
3771
- if ((size != 0ull && droppedSegments .count (curr->segment )) ||
3774
+ if ((size != 0ull && droppedDataSegments .count (curr->segment )) ||
3772
3775
end > seg.data .size ()) {
3773
3776
trap (" out of bounds segment access in array.new_data" );
3774
3777
}
@@ -3797,10 +3800,12 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
3797
3800
3798
3801
const auto & seg = *wasm.getElementSegment (curr->segment );
3799
3802
auto end = offset + size;
3800
- // TODO: Handle dropped element segments once we support those.
3801
3803
if (end > seg.data .size ()) {
3802
3804
trap (" out of bounds segment access in array.new_elem" );
3803
3805
}
3806
+ if (end > 0 && droppedElementSegments.count (curr->segment )) {
3807
+ trap (" out of bounds segment access in array.new_elem" );
3808
+ }
3804
3809
contents.reserve (size);
3805
3810
for (Index i = offset; i < end; ++i) {
3806
3811
auto val = self ()->visit (seg.data [i]).getSingleValue ();
@@ -3848,7 +3853,7 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
3848
3853
if (offsetVal + readSize > seg->data .size ()) {
3849
3854
trap (" out of bounds segment access in array.init_data" );
3850
3855
}
3851
- if (offsetVal + sizeVal > 0 && droppedSegments .count (curr->segment )) {
3856
+ if (offsetVal + sizeVal > 0 && droppedDataSegments .count (curr->segment )) {
3852
3857
trap (" out of bounds segment access in array.init_data" );
3853
3858
}
3854
3859
for (size_t i = 0 ; i < sizeVal; i++) {
@@ -3891,11 +3896,13 @@ class ModuleRunnerBase : public ExpressionRunner<SubType> {
3891
3896
Module& wasm = *self ()->getModule ();
3892
3897
3893
3898
auto * seg = wasm.getElementSegment (curr->segment );
3894
- if ((uint64_t )offsetVal + sizeVal > seg->data .size ()) {
3895
- trap (" out of bounds segment access in array.init" );
3899
+ auto max = (uint64_t )offsetVal + sizeVal;
3900
+ if (max > seg->data .size ()) {
3901
+ trap (" out of bounds segment access in array.init_elem" );
3902
+ }
3903
+ if (max > 0 && droppedElementSegments.count (curr->segment )) {
3904
+ trap (" out of bounds segment access in array.init_elem" );
3896
3905
}
3897
- // TODO: Check whether the segment has been dropped once we support
3898
- // dropping element segments.
3899
3906
for (size_t i = 0 ; i < sizeVal; i++) {
3900
3907
// TODO: This is not correct because it does not preserve the identity
3901
3908
// of references in the table! ArrayNew suffers the same problem.
0 commit comments