From de68948bc5ba6b9eecaa2f64e65b2970e2c0824a Mon Sep 17 00:00:00 2001 From: orbiter Date: Sun, 12 Apr 2009 09:24:32 +0000 Subject: [PATCH] better handling of free memory computation and emrgency cache flush for index cell git-svn-id: https://svn.berlios.de/svnroot/repos/yacy/trunk@5798 6c8d7289-2bf4-0310-a012-ef5d649a1542 --- source/de/anomic/kelondro/text/IndexCell.java | 2 +- .../anomic/kelondro/util/MemoryControl.java | 38 ++++++++----------- 2 files changed, 17 insertions(+), 23 deletions(-) diff --git a/source/de/anomic/kelondro/text/IndexCell.java b/source/de/anomic/kelondro/text/IndexCell.java index 439095f8f..a30792daa 100644 --- a/source/de/anomic/kelondro/text/IndexCell.java +++ b/source/de/anomic/kelondro/text/IndexCell.java @@ -270,7 +270,7 @@ public final class IndexCell extends AbstractBufferedIndex implements BufferedIn private synchronized void cleanCache() { // dump the cache if necessary - if (this.ram.size() > this.maxRamEntries || (this.ram.size() > 2000 && MemoryControl.available() < 100L * 1024L * 1024L)) { + if (this.ram.size() > this.maxRamEntries || (this.ram.size() > 2000 && !MemoryControl.request(100L * 1024L * 1024L, false))) { try { cacheDump(); } catch (IOException e) { diff --git a/source/de/anomic/kelondro/util/MemoryControl.java b/source/de/anomic/kelondro/util/MemoryControl.java index f86a39da8..21dd77e49 100644 --- a/source/de/anomic/kelondro/util/MemoryControl.java +++ b/source/de/anomic/kelondro/util/MemoryControl.java @@ -45,7 +45,7 @@ public class MemoryControl { * @param last time which must be passed since lased gc * @param info additional info for log */ - public final synchronized static void gc(final int last, final String info) { // thq + public final synchronized static boolean gc(final int last, final String info) { // thq assert last >= 10000; // too many forced GCs will cause bad execution performance final long elapsed = System.currentTimeMillis() - lastGC; if (elapsed > last) { @@ -56,29 +56,18 @@ public class MemoryControl { //System.out.println("^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^^ if you see this many times please report to forum"); lastGC = System.currentTimeMillis(); final long after = free(); + gcs[gcs_pos++] = before - after; + if (gcs_pos >= gcs.length) gcs_pos = 0; + if (log.isFine()) log.logInfo("[gc] before: " + Formatter.bytesToString(before) + ", after: " + Formatter.bytesToString(after) + ", freed: " + Formatter.bytesToString(after - before) + ", rt: " + (lastGC - start) + " ms, call: " + info); - } else if (log.isFine()) { - if (log.isFinest()) log.logFinest("[gc] no execute, last run: " + (elapsed / 1000) + " seconds ago, call: " + info); + return true; } - } - - /** - * Tries to free count bytes - * @param count bytes - * @return the amount of freed bytes by a forced GC this method performes - */ - private static long runGC(final boolean count) { - final long memBefore = available(); - gc(10000, "serverMemory.runGC(...)"); - final long freed = available() - memBefore; - if (count) { - gcs[gcs_pos] = freed; - gcs_pos = (gcs_pos + 1) % gcs.length; - } - return freed; + + if (log.isFinest()) log.logFinest("[gc] no execute, last run: " + (elapsed / 1000) + " seconds ago, call: " + info); + return false; } /** @@ -160,14 +149,19 @@ public class MemoryControl { final long avg = getAverageGCFree(); if (force || avg == 0 || avg + avail >= size) { // this is only called if we expect that an allocation of bytes would cause the jvm to call the GC anyway - final long freed = runGC(false); + + final long memBefore = avail; + boolean performedGC = gc(10000, "serverMemory.runGC(...)"); avail = available(); - log.logInfo("performed " + ((force) ? "explicit" : "necessary") + " GC, freed " + (freed >> 10) + if (performedGC) { + final long freed = avail - memBefore; + log.logInfo("performed " + ((force) ? "explicit" : "necessary") + " GC, freed " + (freed >> 10) + " KB (requested/available/average: " + (size >> 10) + " / " + (avail >> 10) + " / " + (avg >> 10) + " KB)"); + } return avail >= size; } else { - log.logInfo("former GCs indicate to not be able to free enough memory (requested/available/average: " + if (log.isFine()) log.logFine("former GCs indicate to not be able to free enough memory (requested/available/average: " + (size >> 10) + " / " + (avail >> 10) + " / " + (avg >> 10) + " KB)"); return false; }