Skip to content

Commit

Permalink
Merge pull request #7104 from theresa-m/fix_5988
Browse files Browse the repository at this point in the history
Round maxRequiredSize to match romSize calculation
  • Loading branch information
pshipton authored Sep 19, 2019
2 parents 1b35e0a + e3156d2 commit 217b85d
Showing 1 changed file with 9 additions and 37 deletions.
46 changes: 9 additions & 37 deletions runtime/bcutil/ROMClassBuilder.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -478,9 +478,7 @@ ROMClassBuilder::prepareAndLaydown( BufferManager *bufferManager, ClassFileParse
if (isLambda) {
/* calculate the romSize to compare the ROM sizes in the compareROMClassForEquality method for lambda classes */
romSize = U_32(sizeInformation.rcWithOutUTF8sSize + sizeInformation.utf8sSize + sizeInformation.rawClassDataSize + sizeInformation.varHandleMethodTypeLookupTableSize);
/* round up to sizeof(U_64) */
romSize += (sizeof(U_64) - 1);
romSize &= ~(sizeof(U_64) - 1);
romSize = ROUND_UP_TO_POWEROF2(romSize, sizeof(U_64));
}

if ( context->shouldCompareROMClassForEquality() ) {
Expand Down Expand Up @@ -599,17 +597,13 @@ ROMClassBuilder::prepareAndLaydown( BufferManager *bufferManager, ClassFileParse
sizeRequirements.romClassMinimalSize =
U_32(sizeInformation.rcWithOutUTF8sSize
+ sizeInformation.utf8sSize + sizeInformation.rawClassDataSize + sizeInformation.varHandleMethodTypeLookupTableSize);
/* round up to sizeof(U_64) */
sizeRequirements.romClassMinimalSize += (sizeof(U_64) - 1);
sizeRequirements.romClassMinimalSize &= ~(sizeof(U_64) - 1);
sizeRequirements.romClassMinimalSize = ROUND_UP_TO_POWEROF2(sizeRequirements.romClassMinimalSize, sizeof(U_64));

sizeRequirements.romClassSizeFullSize =
U_32(sizeRequirements.romClassMinimalSize
+ sizeInformation.lineNumberSize
+ sizeInformation.variableInfoSize);
/* round up to sizeof(U_64) */
sizeRequirements.romClassSizeFullSize += (sizeof(U_64) - 1);
sizeRequirements.romClassSizeFullSize &= ~(sizeof(U_64)-1);
sizeRequirements.romClassSizeFullSize = ROUND_UP_TO_POWEROF2(sizeRequirements.romClassSizeFullSize, sizeof(U_64));


sizeRequirements.lineNumberTableSize = U_32(sizeInformation.lineNumberSize);
Expand Down Expand Up @@ -701,31 +695,11 @@ ROMClassBuilder::prepareAndLaydown( BufferManager *bufferManager, ClassFileParse
lineNumberBuffer = allocatedBuffers.lineNumberBuffer;
variableInfoBuffer = allocatedBuffers.variableInfoBuffer;
} else {
if (countDebugDataOutOfLine) {
/* Pad maxRequiredSize to the size to sizeof(U_64) in order to prevent memory corruption.
*
* In rare cases it is possible that maxRequiredSize is 2 bytes too small, due to
* counting the data 'out-of-line', and then writing the debug data 'in-line' with
* padding U_64 adjustments. The extra 2 bytes is a result of a switch from U_16
* alignment for debug data (when writing out of line), to U_32 alignment (when
* writing inline). It should also be noted that these extra 2 bytes are only
* visible when only one method with debug data exists. If there are more, then the removal
* of 'SRPs to debug data' from each method will hide the extra padding for in-line
* debug data.
*
* Without this padding any new segment returned by the below call to allocate could be
* too small to contain the rom class that is about to be written.
*
* Note: When the problem described above occurs maxRequiredSize will not be U_64 aligned
* until the below code runs.
*/
UDATA alignmentBits = (sizeof (U_64) - 1);
UDATA adjustedCount = (maxRequiredSize + alignmentBits) & ~alignmentBits;
UDATA bytesToPad = adjustedCount - maxRequiredSize;
if (0 != bytesToPad) {
maxRequiredSize += bytesToPad;
}
}
/* Pad maxRequiredSize to the size to sizeof(U_64) in order to prevent memory corruption.
* This mirrors ROM class padding in finishPrepareAndLaydown when the final ROM class size
* is calculated.
*/
maxRequiredSize = ROUND_UP_TO_POWEROF2(maxRequiredSize, sizeof(U_64));
romClassBuffer = context->allocationStrategy()->allocate(maxRequiredSize);
}
if ( romClassBuffer == NULL ) {
Expand Down Expand Up @@ -1041,9 +1015,7 @@ ROMClassBuilder::finishPrepareAndLaydown(
* Record the romSize as the final size of the ROMClass with interned strings space removed.
*/
U_32 romSize = U_32(sizeInformation->rcWithOutUTF8sSize + sizeInformation->utf8sSize + sizeInformation->rawClassDataSize + sizeInformation->varHandleMethodTypeLookupTableSize);
/* round up to sizeof(U_64) */
romSize += (sizeof(U_64) - 1);
romSize &= ~(sizeof(U_64) - 1);
romSize = ROUND_UP_TO_POWEROF2(romSize, sizeof(U_64));

/*
* update the SRP Offset Table with the base addresses for main ROMClass section (RC_TAG),
Expand Down

0 comments on commit 217b85d

Please sign in to comment.