use of org.apache.ignite.internal.processors.cache.persistence.freelist.io.PagesListMetaIO in project ignite by apache.
the class PagesList method saveMetadata.
/**
* @throws IgniteCheckedException If failed.
*/
public void saveMetadata() throws IgniteCheckedException {
assert metaPageId != 0;
long curId = 0L;
long curPage = 0L;
long curAddr = 0L;
PagesListMetaIO curIo = null;
long nextPageId = metaPageId;
if (!changed)
return;
try {
for (int bucket = 0; bucket < buckets; bucket++) {
Stripe[] tails = getBucket(bucket);
if (tails != null) {
int tailIdx = 0;
while (tailIdx < tails.length) {
int written = curPage != 0L ? curIo.addTails(pageMem.pageSize(), curAddr, bucket, tails, tailIdx) : 0;
if (written == 0) {
if (nextPageId == 0L) {
nextPageId = allocatePageNoReuse();
if (curPage != 0L) {
curIo.setNextMetaPageId(curAddr, nextPageId);
releaseAndClose(curId, curPage, curAddr);
}
curId = nextPageId;
curPage = acquirePage(curId);
curAddr = writeLock(curId, curPage);
curIo = PagesListMetaIO.VERSIONS.latest();
curIo.initNewPage(curAddr, curId, pageSize());
} else {
releaseAndClose(curId, curPage, curAddr);
curId = nextPageId;
curPage = acquirePage(curId);
curAddr = writeLock(curId, curPage);
curIo = PagesListMetaIO.VERSIONS.forPage(curAddr);
curIo.resetCount(curAddr);
}
nextPageId = curIo.getNextMetaPageId(curAddr);
} else
tailIdx += written;
}
}
}
} finally {
releaseAndClose(curId, curPage, curAddr);
}
while (nextPageId != 0L) {
long pageId = nextPageId;
long page = acquirePage(pageId);
try {
long pageAddr = writeLock(pageId, page);
try {
PagesListMetaIO io = PagesListMetaIO.VERSIONS.forPage(pageAddr);
io.resetCount(pageAddr);
if (needWalDeltaRecord(pageId, page, null))
wal.log(new PageListMetaResetCountRecord(grpId, pageId));
nextPageId = io.getNextMetaPageId(pageAddr);
} finally {
writeUnlock(pageId, page, pageAddr, true);
}
} finally {
releasePage(pageId, page);
}
}
changed = false;
}
use of org.apache.ignite.internal.processors.cache.persistence.freelist.io.PagesListMetaIO in project ignite by apache.
the class PageListMetaResetCountRecord method applyDelta.
/**
* {@inheritDoc}
*/
@Override
public void applyDelta(PageMemory pageMem, long pageAddr) throws IgniteCheckedException {
PagesListMetaIO io = PagesListMetaIO.VERSIONS.forPage(pageAddr);
io.resetCount(pageAddr);
}
use of org.apache.ignite.internal.processors.cache.persistence.freelist.io.PagesListMetaIO in project ignite by apache.
the class PagesList method init.
/**
* @param metaPageId Metadata page ID.
* @param initNew {@code True} if new list if created, {@code false} if should be initialized from metadata.
* @throws IgniteCheckedException If failed.
*/
protected final void init(long metaPageId, boolean initNew) throws IgniteCheckedException {
if (metaPageId != 0L) {
if (initNew)
init(metaPageId, PagesListMetaIO.VERSIONS.latest());
else {
Map<Integer, GridLongList> bucketsData = new HashMap<>();
long nextId = metaPageId;
while (nextId != 0) {
final long pageId = nextId;
final long page = acquirePage(pageId, IoStatisticsHolderNoOp.INSTANCE);
try {
// No concurrent recycling on init.
long pageAddr = readLock(pageId, page);
assert pageAddr != 0L;
try {
PagesListMetaIO io = PagesListMetaIO.VERSIONS.forPage(pageAddr);
io.getBucketsData(pageAddr, bucketsData);
nextId = io.getNextMetaPageId(pageAddr);
assert nextId != pageId : "Loop detected [next=" + U.hexLong(nextId) + ", cur=" + U.hexLong(pageId) + ']';
} finally {
readUnlock(pageId, page, pageAddr);
}
} finally {
releasePage(pageId, page);
}
}
for (Map.Entry<Integer, GridLongList> e : bucketsData.entrySet()) {
int bucket = e.getKey();
long bucketSize = 0;
Stripe[] old = getBucket(bucket);
assert old == null;
long[] upd = e.getValue().array();
Stripe[] tails = new Stripe[upd.length];
for (int i = 0; i < upd.length; i++) {
long tailId = upd[i];
long prevId = tailId;
int cnt = 0;
while (prevId != 0L) {
final long pageId = prevId;
final long page = acquirePage(pageId, IoStatisticsHolderNoOp.INSTANCE);
try {
long pageAddr = readLock(pageId, page);
assert pageAddr != 0L;
try {
PagesListNodeIO io = PagesListNodeIO.VERSIONS.forPage(pageAddr);
cnt += io.getCount(pageAddr);
prevId = io.getPreviousId(pageAddr);
// In reuse bucket the page itself can be used as a free page.
if (isReuseBucket(bucket) && prevId != 0L)
cnt++;
} finally {
readUnlock(pageId, page, pageAddr);
}
} finally {
releasePage(pageId, page);
}
}
Stripe stripe = new Stripe(tailId, cnt == 0);
tails[i] = stripe;
bucketSize += cnt;
}
boolean ok = casBucket(bucket, null, tails);
assert ok;
bucketsSize.set(bucket, bucketSize);
}
}
}
}
use of org.apache.ignite.internal.processors.cache.persistence.freelist.io.PagesListMetaIO in project ignite by apache.
the class PagesList method writeFreeList.
/**
* Write free list data to page memory.
*
* @param nextPageId First free page id.
* @return Unused free list page id.
* @throws IgniteCheckedException If failed.
*/
private long writeFreeList(long nextPageId) throws IgniteCheckedException {
long curId = 0L;
long curPage = 0L;
long curAddr = 0L;
PagesListMetaIO curIo = null;
try {
for (int bucket = 0; bucket < buckets; bucket++) {
Stripe[] tails = getBucket(bucket);
if (tails != null) {
int tailIdx = 0;
while (tailIdx < tails.length) {
int written = curPage != 0L ? curIo.addTails(pageMem.realPageSize(grpId), curAddr, bucket, tails, tailIdx) : 0;
if (written == 0) {
if (nextPageId == 0L) {
nextPageId = allocatePageNoReuse();
if (curPage != 0L) {
curIo.setNextMetaPageId(curAddr, nextPageId);
releaseAndClose(curId, curPage, curAddr);
}
curId = nextPageId;
curPage = acquirePage(curId, IoStatisticsHolderNoOp.INSTANCE);
curAddr = writeLock(curId, curPage);
curIo = PagesListMetaIO.VERSIONS.latest();
curIo.initNewPage(curAddr, curId, pageSize(), metrics);
} else {
releaseAndClose(curId, curPage, curAddr);
curId = nextPageId;
curPage = acquirePage(curId, IoStatisticsHolderNoOp.INSTANCE);
curAddr = writeLock(curId, curPage);
curIo = PagesListMetaIO.VERSIONS.forPage(curAddr);
curIo.resetCount(curAddr);
}
nextPageId = curIo.getNextMetaPageId(curAddr);
} else
tailIdx += written;
}
}
}
} finally {
releaseAndClose(curId, curPage, curAddr);
}
return nextPageId;
}
use of org.apache.ignite.internal.processors.cache.persistence.freelist.io.PagesListMetaIO in project ignite by apache.
the class PagesList method markUnusedPagesDirty.
/**
* Mark unused pages as dirty.
*
* @param nextPageId First unused page.
* @throws IgniteCheckedException If failed.
*/
private void markUnusedPagesDirty(long nextPageId) throws IgniteCheckedException {
while (nextPageId != 0L) {
long pageId = nextPageId;
long page = acquirePage(pageId, IoStatisticsHolderNoOp.INSTANCE);
try {
long pageAddr = writeLock(pageId, page);
try {
PagesListMetaIO io = PagesListMetaIO.VERSIONS.forPage(pageAddr);
io.resetCount(pageAddr);
if (needWalDeltaRecord(pageId, page, null))
wal.log(new PageListMetaResetCountRecord(grpId, pageId));
nextPageId = io.getNextMetaPageId(pageAddr);
} finally {
writeUnlock(pageId, page, pageAddr, true);
}
} finally {
releasePage(pageId, page);
}
}
}
Aggregations