jerrinot - running out of ideas (#631)

* another shameless copycat from thomas: less safepoints

* I have no idea what I am doing
This commit is contained in:
Jaromir Hamala 2024-01-28 22:43:53 +01:00 committed by GitHub
parent 3a790c99b9
commit 9da1660ba5
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
2 changed files with 15 additions and 22 deletions

View File

@ -18,9 +18,7 @@
source "$HOME/.sdkman/bin/sdkman-init.sh" source "$HOME/.sdkman/bin/sdkman-init.sh"
sdk use java 21.0.2-graal 1>&2 sdk use java 21.0.2-graal 1>&2
# ./mvnw clean verify removes target/ and will re-trigger native image creation.
if [ ! -f target/CalculateAverage_jerrinot_image ]; then if [ ! -f target/CalculateAverage_jerrinot_image ]; then
NATIVE_IMAGE_OPTS="--gc=epsilon -O3 -march=native --enable-preview -H:InlineAllBonus=10 -H:-ParseRuntimeOptions --initialize-at-build-time=dev.morling.onebrc.CalculateAverage_jerrinot" NATIVE_IMAGE_OPTS="--gc=epsilon -O3 -march=native --enable-preview -H:-GenLoopSafepoints -H:InlineAllBonus=10 --initialize-at-build-time=dev.morling.onebrc.CalculateAverage_jerrinot"
# Use -H:MethodFilter=CalculateAverage_jerrinot.* -H:Dump=:2 -H:PrintGraph=Network for IdealGraphVisualizer graph dumping.
native-image $NATIVE_IMAGE_OPTS -cp target/average-1.0.0-SNAPSHOT.jar -o target/CalculateAverage_jerrinot_image dev.morling.onebrc.CalculateAverage_jerrinot native-image $NATIVE_IMAGE_OPTS -cp target/average-1.0.0-SNAPSHOT.jar -o target/CalculateAverage_jerrinot_image dev.morling.onebrc.CalculateAverage_jerrinot
fi fi

View File

@ -214,7 +214,7 @@ public class CalculateAverage_jerrinot {
private long slowMap; private long slowMap;
private long slowMapNamesPtr; private long slowMapNamesPtr;
private long slowMapNamesLo; private long slowMapNamesLo;
private long fastMap; // private long fastMap;
private long cursorA; private long cursorA;
private long endA; private long endA;
private long cursorB; private long cursorB;
@ -227,7 +227,6 @@ public class CalculateAverage_jerrinot {
// credit: merykitty // credit: merykitty
private long parseAndStoreTemperature(long startCursor, long baseEntryPtr, long word) { private long parseAndStoreTemperature(long startCursor, long baseEntryPtr, long word) {
// long word = UNSAFE.getLong(startCursor);
long countPtr = baseEntryPtr + MAP_COUNT_OFFSET; long countPtr = baseEntryPtr + MAP_COUNT_OFFSET;
int cnt = UNSAFE.getInt(countPtr); int cnt = UNSAFE.getInt(countPtr);
UNSAFE.putInt(countPtr, cnt + 1); UNSAFE.putInt(countPtr, cnt + 1);
@ -297,18 +296,18 @@ public class CalculateAverage_jerrinot {
this.endC = endC; this.endC = endC;
} }
private void doTail() { private void doTail(long fastMAp) {
doOne(cursorA, endA); doOne(cursorA, endA);
doOne(cursorB, endB); doOne(cursorB, endB);
doOne(cursorC, endC); doOne(cursorC, endC);
transferToHeap(); transferToHeap(fastMAp);
// UNSAFE.freeMemory(fastMap); // UNSAFE.freeMemory(fastMap);
// UNSAFE.freeMemory(slowMap); // UNSAFE.freeMemory(slowMap);
// UNSAFE.freeMemory(slowMapNamesLo); // UNSAFE.freeMemory(slowMapNamesLo);
} }
private void transferToHeap() { private void transferToHeap(long fastMap) {
for (long baseAddress = slowMap; baseAddress < slowMap + SLOW_MAP_SIZE_BYTES; baseAddress += SLOW_MAP_ENTRY_SIZE_BYTES) { for (long baseAddress = slowMap; baseAddress < slowMap + SLOW_MAP_SIZE_BYTES; baseAddress += SLOW_MAP_ENTRY_SIZE_BYTES) {
long len = UNSAFE.getInt(baseAddress + MAP_LEN_OFFSET); long len = UNSAFE.getInt(baseAddress + MAP_LEN_OFFSET);
if (len == 0) { if (len == 0) {
@ -398,7 +397,7 @@ public class CalculateAverage_jerrinot {
this.slowMap = UNSAFE.allocateMemory(SLOW_MAP_SIZE_BYTES); this.slowMap = UNSAFE.allocateMemory(SLOW_MAP_SIZE_BYTES);
this.slowMapNamesPtr = UNSAFE.allocateMemory(SLOW_MAP_MAP_NAMES_BYTES); this.slowMapNamesPtr = UNSAFE.allocateMemory(SLOW_MAP_MAP_NAMES_BYTES);
this.slowMapNamesLo = slowMapNamesPtr; this.slowMapNamesLo = slowMapNamesPtr;
this.fastMap = UNSAFE.allocateMemory(FAST_MAP_SIZE_BYTES); long fastMap = UNSAFE.allocateMemory(FAST_MAP_SIZE_BYTES);
UNSAFE.setMemory(slowMap, SLOW_MAP_SIZE_BYTES, (byte) 0); UNSAFE.setMemory(slowMap, SLOW_MAP_SIZE_BYTES, (byte) 0);
UNSAFE.setMemory(fastMap, FAST_MAP_SIZE_BYTES, (byte) 0); UNSAFE.setMemory(fastMap, FAST_MAP_SIZE_BYTES, (byte) 0);
UNSAFE.setMemory(slowMapNamesPtr, SLOW_MAP_MAP_NAMES_BYTES, (byte) 0); UNSAFE.setMemory(slowMapNamesPtr, SLOW_MAP_MAP_NAMES_BYTES, (byte) 0);
@ -528,38 +527,38 @@ public class CalculateAverage_jerrinot {
baseEntryPtrA = getOrCreateEntryBaseOffsetSlow(lenA, startA, hashA, maskedLastWordA); baseEntryPtrA = getOrCreateEntryBaseOffsetSlow(lenA, startA, hashA, maskedLastWordA);
} }
else { else {
baseEntryPtrA = getOrCreateEntryBaseOffsetFast(mapIndexA, lenA, maskedLastWordA, maskedFirstWordA); baseEntryPtrA = getOrCreateEntryBaseOffsetFast(mapIndexA, lenA, maskedLastWordA, maskedFirstWordA, fastMap);
} }
if (slowB) { if (slowB) {
baseEntryPtrB = getOrCreateEntryBaseOffsetSlow(lenB, startB, hashB, maskedLastWordB); baseEntryPtrB = getOrCreateEntryBaseOffsetSlow(lenB, startB, hashB, maskedLastWordB);
} }
else { else {
baseEntryPtrB = getOrCreateEntryBaseOffsetFast(mapIndexB, lenB, maskedLastWordB, maskedFirstWordB); baseEntryPtrB = getOrCreateEntryBaseOffsetFast(mapIndexB, lenB, maskedLastWordB, maskedFirstWordB, fastMap);
} }
if (slowC) { if (slowC) {
baseEntryPtrC = getOrCreateEntryBaseOffsetSlow(lenC, startC, hashC, maskedLastWordC); baseEntryPtrC = getOrCreateEntryBaseOffsetSlow(lenC, startC, hashC, maskedLastWordC);
} }
else { else {
baseEntryPtrC = getOrCreateEntryBaseOffsetFast(mapIndexC, lenC, maskedLastWordC, maskedFirstWordC); baseEntryPtrC = getOrCreateEntryBaseOffsetFast(mapIndexC, lenC, maskedLastWordC, maskedFirstWordC, fastMap);
} }
} }
else { else {
baseEntryPtrA = getOrCreateEntryBaseOffsetFast(mapIndexA, lenA, maskedLastWordA, maskedFirstWordA); baseEntryPtrA = getOrCreateEntryBaseOffsetFast(mapIndexA, lenA, maskedLastWordA, maskedFirstWordA, fastMap);
baseEntryPtrB = getOrCreateEntryBaseOffsetFast(mapIndexB, lenB, maskedLastWordB, maskedFirstWordB); baseEntryPtrB = getOrCreateEntryBaseOffsetFast(mapIndexB, lenB, maskedLastWordB, maskedFirstWordB, fastMap);
baseEntryPtrC = getOrCreateEntryBaseOffsetFast(mapIndexC, lenC, maskedLastWordC, maskedFirstWordC); baseEntryPtrC = getOrCreateEntryBaseOffsetFast(mapIndexC, lenC, maskedLastWordC, maskedFirstWordC, fastMap);
} }
cursorA = parseAndStoreTemperature(digitStartA, baseEntryPtrA, temperatureWordA); cursorA = parseAndStoreTemperature(digitStartA, baseEntryPtrA, temperatureWordA);
cursorB = parseAndStoreTemperature(digitStartB, baseEntryPtrB, temperatureWordB); cursorB = parseAndStoreTemperature(digitStartB, baseEntryPtrB, temperatureWordB);
cursorC = parseAndStoreTemperature(digitStartC, baseEntryPtrC, temperatureWordC); cursorC = parseAndStoreTemperature(digitStartC, baseEntryPtrC, temperatureWordC);
} }
doTail(); doTail(fastMap);
// System.out.println("Longest chain: " + longestChain); // System.out.println("Longest chain: " + longestChain);
} }
private long getOrCreateEntryBaseOffsetFast(int mapIndexA, int lenA, long maskedLastWord, long maskedFirstWord) { private static long getOrCreateEntryBaseOffsetFast(int mapIndexA, int lenA, long maskedLastWord, long maskedFirstWord, long fastMap) {
for (;;) { for (;;) {
long basePtr = mapIndexA * FAST_MAP_ENTRY_SIZE_BYTES + fastMap; long basePtr = mapIndexA * FAST_MAP_ENTRY_SIZE_BYTES + fastMap;
long namePart1 = UNSAFE.getLong(basePtr + FAST_MAP_NAME_PART1); long namePart1 = UNSAFE.getLong(basePtr + FAST_MAP_NAME_PART1);
@ -596,7 +595,7 @@ public class CalculateAverage_jerrinot {
int len = UNSAFE.getInt(lenPtr); int len = UNSAFE.getInt(lenPtr);
if (len == lenA) { if (len == lenA) {
namePtr = UNSAFE.getLong(basePtr + SLOW_MAP_NAME_OFFSET); namePtr = UNSAFE.getLong(basePtr + SLOW_MAP_NAME_OFFSET);
if (nameMatch(startPtr, maskedLastWord, namePtr, fullLen)) { if (nameMatchSlow(startPtr, namePtr, fullLen, maskedLastWord)) {
return basePtr; return basePtr;
} }
} }
@ -614,10 +613,6 @@ public class CalculateAverage_jerrinot {
} }
} }
private static boolean nameMatch(long start, long maskedLastWord, long namePtr, long fullLen) {
return nameMatchSlow(start, namePtr, fullLen, maskedLastWord);
}
private static boolean nameMatchSlow(long start, long namePtr, long fullLen, long maskedLastWord) { private static boolean nameMatchSlow(long start, long namePtr, long fullLen, long maskedLastWord) {
long offset; long offset;
for (offset = 0; offset < fullLen; offset += 8) { for (offset = 0; offset < fullLen; offset += 8) {