Skip to content

MutablePage.move mis-tracks modified range for backward shifts — WAL omits defrag bytes #4319

@ruispereira

Description

@ruispereira

Affected version: 26.4.2 (confirmed still present in 26.5.1)
Component: com.arcadedb.engine.MutablePage

Summary

move(int startPosition, int destPosition, int length) calls updateModifiedRange(startPosition, destPosition + length). The actual bytes
mutated by System.arraycopy are [destPosition, destPosition + length). For backward shifts (destPosition < startPosition — the canonical case is LocalBucket.defragPage shifting records leftward into freed holes), the window [destPosition, startPosition) is written to the page but not tracked. WAL only persists [modifiedRangeFrom, modifiedRangeTo], so the uncovered window does not get logged.

Code

engine/com/arcadedb/engine/MutablePage.java:216–225

public void move(int startPosition, int destPosition, final int length) {
  …
  startPosition += PAGE_HEADER_SIZE;
  destPosition += PAGE_HEADER_SIZE;
  updateModifiedRange(startPosition, destPosition + length);    // assumes dest >= start
  content.move(startPosition, destPosition, length);
}

Impact

A crash + recovery after defragPage runs will leave the missing window uncovered by the WAL delta; replay reverts those bytes to pre-defrag content, corrupting the bucket page (stale record bytes after defragmentation).

Suggested fix

- updateModifiedRange(startPosition, destPosition + length);
+ updateModifiedRange(
+     Math.min(startPosition, destPosition),
+     Math.max(startPosition, destPosition) + length);

Metadata

Metadata

Assignees

Labels

No labels
No labels

Type

No fields configured for Bug.

Projects

No projects

Milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions