@Override public Void call() throws Exception { final GroupKey firstKey = new GroupKey(fileId, 0); final GroupKey lastKey = new GroupKey(fileId, Long.MAX_VALUE); NavigableMap<GroupKey, WriteGroup> subMap = writeGroups.subMap(firstKey, true, lastKey, true); Iterator<Map.Entry<GroupKey, WriteGroup>> entryIterator = subMap.entrySet().iterator(); groupsLoop: while (entryIterator.hasNext()) { Map.Entry<GroupKey, WriteGroup> entry = entryIterator.next(); final WriteGroup writeGroup = entry.getValue(); final GroupKey groupKey = entry.getKey(); lockManager.acquireLock(Thread.currentThread(), groupKey, OLockManager.LOCK.EXCLUSIVE); try { int flushedPages = 0; for (int i = 0; i < 16; i++) { OCachePointer pagePointer = writeGroup.pages[i]; if (pagePointer != null) { if (!pagePointer.tryAcquireExclusiveLock()) continue groupsLoop; try { flushPage( groupKey.fileId, (groupKey.groupIndex << 4) + i, pagePointer.getDataPointer()); flushedPages++; } finally { pagePointer.releaseExclusiveLock(); } } } for (OCachePointer pagePointer : writeGroup.pages) if (pagePointer != null) pagePointer.decrementReferrer(); cacheSize.addAndGet(-flushedPages); entryIterator.remove(); } finally { lockManager.releaseLock( Thread.currentThread(), entry.getKey(), OLockManager.LOCK.EXCLUSIVE); } } files.get(fileId).synch(); return null; }
private int iterateBySubRing( NavigableMap<GroupKey, WriteGroup> subMap, int writeGroupsToFlush, int flushedWriteGroups, boolean forceFlush) throws IOException { Iterator<Map.Entry<GroupKey, WriteGroup>> entriesIterator = subMap.entrySet().iterator(); long currentTime = System.currentTimeMillis(); groupsLoop: while (entriesIterator.hasNext() && flushedWriteGroups < writeGroupsToFlush) { Map.Entry<GroupKey, WriteGroup> entry = entriesIterator.next(); final WriteGroup group = entry.getValue(); final GroupKey groupKey = entry.getKey(); final boolean weakLockMode = group.creationTime - currentTime < groupTTL && !forceFlush; if (group.recencyBit && weakLockMode) { group.recencyBit = false; continue; } lockManager.acquireLock( Thread.currentThread(), entry.getKey(), OLockManager.LOCK.EXCLUSIVE); try { if (group.recencyBit && weakLockMode) group.recencyBit = false; else { group.recencyBit = false; int flushedPages = 0; for (int i = 0; i < 16; i++) { final OCachePointer pagePointer = group.pages[i]; if (pagePointer != null) { if (!pagePointer.tryAcquireExclusiveLock()) continue groupsLoop; try { flushPage( groupKey.fileId, (groupKey.groupIndex << 4) + i, pagePointer.getDataPointer()); flushedPages++; final OLogSequenceNumber flushedLSN = ODurablePage.getLogSequenceNumberFromPage(pagePointer.getDataPointer()); pagePointer.setLastFlushedLsn(flushedLSN); } finally { pagePointer.releaseExclusiveLock(); } } } for (OCachePointer pagePointer : group.pages) if (pagePointer != null) pagePointer.decrementReferrer(); entriesIterator.remove(); flushedWriteGroups++; cacheSize.addAndGet(-flushedPages); } } finally { lockManager.releaseLock( Thread.currentThread(), entry.getKey(), OLockManager.LOCK.EXCLUSIVE); } lastGroupKey = groupKey; } return flushedWriteGroups; }