Skip to content

feat(sdk): throw AesGcmExhaustedException when the per-key GCM invocation budget is spent (DSPX-4492) - #417

Merged
dmihalcik-virtru merged 1 commit into
feat/tdf3-iv-constructionfrom
DSPX-4492-exhausted
Oct 9, 2026
Merged

dmihalcik-virtru merged 1 commit into
feat/tdf3-iv-constructionfrom
DSPX-4492-exhausted

Conversation

@dmihalcik-virtru

@dmihalcik-virtru dmihalcik-virtru commented Oct 8, 2026 •

Copy link
Copy Markdown
Member

Summary

Stacked on #412 (TDF3 IV construction). Review and merge that first.

Adds SDK.AesGcmExhaustedException (extends SDKException, nested alongside TamperException, KasInfoMissing, etc.). TDF.IvCounter.next() now throws it instead of a generic SDKException once a payload key's AES-GCM invocation budget is spent.

Why

NIST SP 800-38D §8 caps the probability of an IV collision under one key at 2^-32. #412 builds IVs as a random 64-bit fixed field followed by a 32-bit invocation counter, so at most 2^32 invocations can share a key: IV 0 for key-access metadata and 2^32 − 1 for payload segments. The same budget keeps random 96-bit IVs under the §8 limit, since their birthday bound is P ≈ k²/2^97 ≤ 2^-32 for k ≤ ~2^32.5. See the DSPX-4492 ADR (AES GCM i.v. Collision Risk).

#412 already refuses before it would issue an IV past the counter limit. That check runs before each segment is encrypted, on the only payload write path (createTDF), which also handles streams of unknown length. This PR gives that refusal a dedicated, catchable type so callers can tell it apart from other SDK failures. The partially written TDF must be discarded.

Crypto-risk callout

No behavior or wire-format change relative to #412: same limit, same check point, same IVs. Only the exception type changes, and it still extends SDKException, so existing catch (SDKException) blocks behave the same. At the 16 KiB minimum segment size, hitting the limit takes 64 TiB of input.

Test plan

  • mvn -pl sdk -am test (JDK 21): 284 tests, 0 failures, 8 skipped
  • TDFTest's testIvCounterRejectsReuseAfterExhaustion now asserts SDK.AesGcmExhaustedException (and that it is an SDKException) once invocation 2^32 − 1 has been issued. No test encrypts 2^32 segments.

@coderabbitai

coderabbitai Bot commented Oct 8, 2026 •

Copy link
Copy Markdown
Contributor

Important

Review skipped

Auto reviews are disabled on base/target branches other than the default branch.

🗂️ Base branches to auto review (1)
  • main

Please check the settings in the CodeRabbit UI or the .coderabbit.yaml file in this repository. To trigger a single review, invoke the @coderabbitai review command.

⚙️ Run configuration
  • Configuration used: Organization UI
  • Review profile: CHILL
  • Plan: Advanced
  • Run ID: f06aaf7f-af77-48a4-bf06-6870eda74f72

You can disable this status message by setting the reviews.review_status to false in the CodeRabbit configuration file.

Use the checkbox below for a quick retry:

  • 🔍 Trigger review
  • Autopilot · Keep fixing CodeRabbit findings and required CI, and resolving merge conflicts

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@dmihalcik-virtru
dmihalcik-virtru marked this pull request as ready for review October 8, 2026 20:27
@dmihalcik-virtru
dmihalcik-virtru requested review from a team as code owners October 8, 2026 20:27
@dmihalcik-virtru
dmihalcik-virtru changed the base branch from main to feat/tdf3-iv-construction October 8, 2026 20:30
…tion budget is spent (DSPX-4492)

Add SDK.AesGcmExhaustedException (extends SDKException) and throw it from
TDF.IvCounter.next() in place of a generic SDKException. The 32-bit invocation
counter caps a payload key at 2^32 invocations (IV 0 for the metadata, 2^32 - 1
payload segments) and refuses before the segment that would cross it is
encrypted, on every write path including streams of unknown length. A
dedicated type lets callers distinguish this condition, matching the NIST
SP 800-38D section 8 limit of a 2^-32 IV collision probability per key.

Signed-off-by: Dave Mihalcik <dmihalcik@virtru.com>
@github-actions

github-actions Bot commented Oct 8, 2026

Copy link
Copy Markdown
Contributor

@sonarqubecloud

sonarqubecloud Bot commented Oct 8, 2026

Copy link
Copy Markdown

@github-actions

github-actions Bot commented Oct 8, 2026

Copy link
Copy Markdown
Contributor

@dmihalcik-virtru
dmihalcik-virtru merged commit 213ff99 into feat/tdf3-iv-construction Oct 9, 2026
5 checks passed
@dmihalcik-virtru
dmihalcik-virtru deleted the DSPX-4492-exhausted branch October 9, 2026 18:01
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.

2 participants