diff --git a/runtime/gc_base/IndexableObjectAllocationModel.cpp b/runtime/gc_base/IndexableObjectAllocationModel.cpp index c424f1773a4..b08965b84ef 100644 --- a/runtime/gc_base/IndexableObjectAllocationModel.cpp +++ b/runtime/gc_base/IndexableObjectAllocationModel.cpp @@ -145,7 +145,13 @@ MM_IndexableObjectAllocationModel::initializeIndexableObject(MM_EnvironmentBase /* Lay out arraylet and arrayoid pointers */ switch (_layout) { case GC_ArrayletObjectModel::InlineContiguous: - Assert_MM_true(1 == _numberOfArraylets); + /** + * _numberOfArraylets is set to 0 for 0-stride flattened array, and we + * can recognize this case by checking if _dataSize is 0. + * Note there are two cases that _dataSize is 0: 0-stride flattened array or 0-length array + * But the latter is treated as discontiguous and not following this path + */ + Assert_MM_true((0 == _dataSize) || (1 == _numberOfArraylets)); break; case GC_ArrayletObjectModel::Discontiguous: diff --git a/runtime/gc_glue_java/ArrayletObjectModel.cpp b/runtime/gc_glue_java/ArrayletObjectModel.cpp index 538691c2a83..37ac858cff1 100644 --- a/runtime/gc_glue_java/ArrayletObjectModel.cpp +++ b/runtime/gc_glue_java/ArrayletObjectModel.cpp @@ -94,7 +94,7 @@ GC_ArrayletObjectModel::getArrayletLayout(J9Class* clazz, UDATA dataSizeInBytes, /* CMVC 135307 : when checking for InlineContiguous layout, perform subtraction as adding to dataSizeInBytes could trigger overflow. */ if ((largestDesirableSpine == UDATA_MAX) || (dataSizeInBytes <= (largestDesirableSpine - minimumSpineSizeAfterGrowing - contiguousIndexableHeaderSize()))) { layout = InlineContiguous; - if(0 == dataSizeInBytes) { + if ((0 == dataSizeInBytes) && (0 < J9ARRAYCLASS_GET_STRIDE(clazz))) { /* Zero sized NUA uses the discontiguous shape */ layout = Discontiguous; } diff --git a/runtime/gc_glue_java/ArrayletObjectModel.hpp b/runtime/gc_glue_java/ArrayletObjectModel.hpp index 27a16bf0920..21c922ac9e0 100644 --- a/runtime/gc_glue_java/ArrayletObjectModel.hpp +++ b/runtime/gc_glue_java/ArrayletObjectModel.hpp @@ -366,7 +366,7 @@ class GC_ArrayletObjectModel : public GC_ArrayletObjectModelBase uintptr_t stride = J9ARRAYCLASS_GET_STRIDE(clazzPtr); uintptr_t size = numberOfElements * stride; uintptr_t alignedSize = UDATA_MAX; - if ((size / stride) == numberOfElements) { + if ((0 == stride) || ((size / stride) == numberOfElements)) { alignedSize = MM_Math::roundToSizeofUDATA(size); if (alignedSize < size) { alignedSize = UDATA_MAX; @@ -478,6 +478,9 @@ class GC_ArrayletObjectModel : public GC_ArrayletObjectModelBase void* srcData = getDataPointerForContiguous(srcObject); switch(elementSize) { + case 0: + break; + case 1: // byte/boolean { @@ -637,6 +640,9 @@ class GC_ArrayletObjectModel : public GC_ArrayletObjectModelBase void* destData = getDataPointerForContiguous(destObject); switch(elementSize) { + case 0: + break; + case 1: // byte/boolean { diff --git a/runtime/gc_include/ObjectAllocationAPI.hpp b/runtime/gc_include/ObjectAllocationAPI.hpp index fe5a9062abd..e46e601421d 100644 --- a/runtime/gc_include/ObjectAllocationAPI.hpp +++ b/runtime/gc_include/ObjectAllocationAPI.hpp @@ -447,10 +447,11 @@ class MM_ObjectAllocationAPI VMINLINE j9object_t inlineAllocateIndexableValueTypeObject(J9VMThread *currentThread, J9Class *arrayClass, uint32_t size, bool initializeSlots = true, bool memoryBarrier = true, bool sizeCheck = true) { - uintptr_t dataSize = ((uintptr_t)size) * J9ARRAYCLASS_GET_STRIDE(arrayClass); + uintptr_t stride = J9ARRAYCLASS_GET_STRIDE(arrayClass); + uintptr_t dataSize = ((uintptr_t)size) * stride; bool validSize = true; #if !defined(J9VM_ENV_DATA64) - validSize = !sizeCheck || (size < ((uint32_t)J9_MAXIMUM_INDEXABLE_DATA_SIZE / J9ARRAYCLASS_GET_STRIDE(arrayClass))); + validSize = (!sizeCheck) || (0 == stride) || (size < ((uint32_t)J9_MAXIMUM_INDEXABLE_DATA_SIZE / stride)); #endif /* J9VM_ENV_DATA64 */ return inlineAllocateIndexableObjectImpl(currentThread, arrayClass, size, dataSize, validSize, initializeSlots, memoryBarrier); } diff --git a/runtime/gc_structs/FlattenedContiguousArrayIterator.hpp b/runtime/gc_structs/FlattenedContiguousArrayIterator.hpp index 61c71115772..eaba1bcbd55 100644 --- a/runtime/gc_structs/FlattenedContiguousArrayIterator.hpp +++ b/runtime/gc_structs/FlattenedContiguousArrayIterator.hpp @@ -91,6 +91,9 @@ class GC_FlattenedContiguousArrayIterator */ MMINLINE UDATA getIndex() { + if (0 == _elementStride) { + return 0; + } return ((uintptr_t)_scanPtr - (uintptr_t)_basePtr) / _elementStride; }