Skip to content

[core] Fix integer overflow in FieldSumAgg causing silent data corruption#7338

Open
dubin555 wants to merge 1 commit intoapache:masterfrom
dubin555:oss-scout/verify-fix-fieldsum
Open

[core] Fix integer overflow in FieldSumAgg causing silent data corruption#7338
dubin555 wants to merge 1 commit intoapache:masterfrom
dubin555:oss-scout/verify-fix-fieldsum

Conversation

@dubin555
Copy link

@dubin555 dubin555 commented Mar 3, 2026

Purpose

FieldSumAgg performs unchecked arithmetic for TINYINT, SMALLINT, INTEGER, and BIGINT types. When the accumulator overflows, the result silently wraps around (e.g., Byte.MAX_VALUE + 1 becomes -128), producing incorrect aggregation results without any error or warning. This is silent data corruption in the merge-tree SUM aggregation path.

The root cause differs by type:

  • TINYINT/SMALLINT: Java promotes operands to int for arithmetic, then the (byte) or (short) cast silently truncates the overflow bits.
  • INTEGER/BIGINT: Standard + and - wrap around at MAX_VALUE / MIN_VALUE per Java spec.

This fix adds overflow detection to all three affected methods (agg, retract, negative):

  • For INTEGER and BIGINT: uses Math.addExact / Math.subtractExact / Math.negateExact, which throw ArithmeticException on overflow.
  • For TINYINT and SMALLINT: uses range-checked helper methods that perform arithmetic in int width and verify the result fits in byte / short range before casting.

This is consistent with the overflow-protection pattern already used in DecimalUtils.add() and DecimalUtils.subtract() in the same codebase.

Tests

  • testFieldSumByteOverflow — TINYINT: verifies normal addition works, positive overflow throws ArithmeticException, negative overflow throws, and retract overflow throws.
  • testFieldSumShortOverflow — SMALLINT: same coverage.
  • testFieldSumIntOverflow — INTEGER: same coverage.
  • testFieldSumLongOverflow — BIGINT: same coverage.

API and Format

No API or storage format changes.

Documentation

No new feature introduced.

Generative AI tooling

Generated-by: Claude Code 1.0.0

…tion

FieldSumAgg.agg() silently wraps on overflow for TINYINT, SMALLINT,
INTEGER, and BIGINT types. For example, SUM(Byte.MAX_VALUE, 1) returns
-128 instead of detecting the overflow. This causes silent data
corruption in merge-tree aggregation when accumulator values exceed
type bounds.

Use Math.addExact/subtractExact/negateExact for INTEGER and BIGINT,
and range-checked helpers for TINYINT and SMALLINT, to throw
ArithmeticException on overflow instead of silently producing wrong
results. Also fix the same issue in retract() and negative() methods.
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant