mirror of
https://github.com/aljazceru/turso.git
synced 2026-02-08 09:44:21 +01:00
handle case when target seek page has no matching entries
This commit is contained in:
@@ -1764,6 +1764,17 @@ impl BTreeCursor {
|
||||
return Ok(CursorResult::Ok(if eq_only {
|
||||
SeekResult::NotFound
|
||||
} else {
|
||||
let contents = page.get().contents.as_ref().unwrap();
|
||||
turso_assert!(
|
||||
contents.is_leaf(),
|
||||
"tablebtree_seek() called on non-leaf page"
|
||||
);
|
||||
let cell_count = contents.cell_count();
|
||||
// set cursor to the position where which would hold the op-boundary if it were present
|
||||
self.stack.set_cell_index(match &seek_op {
|
||||
SeekOp::GT | SeekOp::GE { .. } => cell_count as i32,
|
||||
SeekOp::LT | SeekOp::LE { .. } => 0,
|
||||
});
|
||||
SeekResult::TryAdvance
|
||||
}));
|
||||
};
|
||||
|
||||
@@ -2395,6 +2395,7 @@ pub fn op_deferred_seek(
|
||||
pub enum OpSeekState {
|
||||
Start,
|
||||
Seek { rowid: i64, op: SeekOp },
|
||||
Advance { op: SeekOp },
|
||||
MoveLast,
|
||||
}
|
||||
|
||||
@@ -2572,7 +2573,32 @@ pub fn op_seek_internal(
|
||||
let cursor = cursor.as_btree_mut();
|
||||
return_if_io!(cursor.seek(SeekKey::TableRowId(*rowid), *op))
|
||||
};
|
||||
if !matches!(seek_result, SeekResult::Found) {
|
||||
let found = match seek_result {
|
||||
SeekResult::Found => true,
|
||||
SeekResult::NotFound => false,
|
||||
SeekResult::TryAdvance => {
|
||||
state.op_seek_state = OpSeekState::Advance { op: *op };
|
||||
continue;
|
||||
}
|
||||
};
|
||||
if !found {
|
||||
state.pc = target_pc.as_offset_int()
|
||||
} else {
|
||||
state.pc += 1
|
||||
}
|
||||
return Ok(InsnFunctionStepResult::Step);
|
||||
}
|
||||
OpSeekState::Advance { op } => {
|
||||
let found = {
|
||||
let mut cursor = state.get_cursor(*cursor_id);
|
||||
let cursor = cursor.as_btree_mut();
|
||||
match op {
|
||||
SeekOp::GT | SeekOp::GE { eq_only: false } => return_if_io!(cursor.next()),
|
||||
SeekOp::LT | SeekOp::LE { eq_only: false } => return_if_io!(cursor.prev()),
|
||||
_ => unreachable!("eq_only: true state must be unreachable"),
|
||||
}
|
||||
};
|
||||
if !found {
|
||||
state.pc = target_pc.as_offset_int()
|
||||
} else {
|
||||
state.pc += 1
|
||||
@@ -4833,7 +4859,7 @@ pub fn op_idx_delete(
|
||||
cursor.root_page(),
|
||||
record
|
||||
);
|
||||
found
|
||||
matches!(seek_result, SeekResult::Found)
|
||||
};
|
||||
|
||||
if !found {
|
||||
|
||||
Reference in New Issue
Block a user