Merge 'core/vdbe: Micro-optimize "zero_or_null" opcode' from Pekka Enberg

It's a hot instruction for TPC-H, for example, so worth optimizing.
Reduces op_zero_or_null() from 5.6% to 2.4% in CPU flamegraph for TCP-H
Q1.

Reviewed-by: Preston Thorpe <preston@turso.tech>

Closes #2842
This commit is contained in:
Preston Thorpe
2025-08-29 10:23:31 -04:00
committed by GitHub
2 changed files with 8 additions and 3 deletions

View File

@@ -6667,9 +6667,7 @@ pub fn op_zero_or_null(
mv_store: Option<&Arc<MvStore>>,
) -> Result<InsnFunctionStepResult> {
load_insn!(ZeroOrNull { rg1, rg2, dest }, insn);
if *state.registers[*rg1].get_value() == Value::Null
|| *state.registers[*rg2].get_value() == Value::Null
{
if state.registers[*rg1].is_null() || state.registers[*rg2].is_null() {
state.registers[*dest] = Register::Value(Value::Null)
} else {
state.registers[*dest] = Register::Value(Value::Integer(0));

View File

@@ -229,6 +229,13 @@ pub enum Register {
Record(ImmutableRecord),
}
impl Register {
#[inline]
pub fn is_null(&self) -> bool {
matches!(self, Register::Value(Value::Null))
}
}
/// A row is a the list of registers that hold the values for a filtered row. This row is a pointer, therefore
/// after stepping again, row will be invalidated to be sure it doesn't point to somewhere unexpected.
#[derive(Debug)]