Skip to content

chore(antithesis): Bound contexts in runs - #2216

Open
blt wants to merge 1 commit into
blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regimefrom
blt/chore_antithesis_bound_contexts_in_runs
Open

chore(antithesis): Bound contexts in runs#2216
blt wants to merge 1 commit into
blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regimefrom
blt/chore_antithesis_bound_contexts_in_runs

Conversation

@blt

@blt blt commented Jul 27, 2026

Copy link
Copy Markdown
Contributor

Summary

This commit introduces a new protocol to the intake node to allow for
context bounding in runs. The purposes are twofold. First, while it's
interesting to explore timelines in which there are too many contexts
for either lane to handle these are less relevant to me now, so I've
capped total contexts at 1M. Second, in order for timeseries equality
to work I need to be certain that I have at least some timeseries
with more than one point emitted into them. Previously drivers were
emitting essentially random contexts and it was very unlikely for more
than one point to be emitted per context. Oops.

Drivers now request N contexts from the intake service for each sub-kind
of dogstatsd they emit, meaning all contexts are sourced from a single
spot in a topology and not from pure randomness.

Change Type

  • Bug fix
  • New feature
  • Non-functional (chore, refactoring, docs)
  • Performance

How did you test this PR?

References

@dd-octo-sts dd-octo-sts Bot added the area/test All things testing: unit/integration, correctness, SMP regression, etc. label Jul 27, 2026
@blt blt mentioned this pull request Jul 27, 2026
4 tasks

blt commented Jul 27, 2026

Copy link
Copy Markdown
Contributor Author

@pr-commenter

pr-commenter Bot commented Jul 27, 2026

Copy link
Copy Markdown

Binary Size Analysis (Agent Data Plane)

Baseline: 20f18cf · Comparison: 39f3b2a · diff
Analysis Configuration: stripped binaries · Pass/Fail Threshold: +5%
Sizes: 40.83 MiB (baseline) vs 40.83 MiB (comparison)
Size Change: +0 B (+0.00%)

✅ Binary size difference within threshold

Changes by Module
Module File Size Symbols
anon.44a0faa3240fa409baa379409d152aec.1.llvm.15298435345870820272 +130 B 1
anon.44a0faa3240fa409baa379409d152aec.1.llvm.13856889450204013776 -130 B 1
anon.44a0faa3240fa409baa379409d152aec.4.llvm.15298435345870820272 +114 B 1
anon.44a0faa3240fa409baa379409d152aec.4.llvm.13856889450204013776 -114 B 1
anon.44a0faa3240fa409baa379409d152aec.3.llvm.15298435345870820272 +109 B 1
anon.44a0faa3240fa409baa379409d152aec.3.llvm.13856889450204013776 -109 B 1
anon.44a0faa3240fa409baa379409d152aec.0.llvm.15298435345870820272 +97 B 1
anon.44a0faa3240fa409baa379409d152aec.0.llvm.13856889450204013776 -97 B 1
anon.44a0faa3240fa409baa379409d152aec.2.llvm.15298435345870820272 +95 B 1
anon.44a0faa3240fa409baa379409d152aec.2.llvm.13856889450204013776 -95 B 1
Detailed Symbol Changes
    FILE SIZE        VM SIZE    
 --------------  -------------- 
  [NEW]    +130  [NEW]     +40    anon.44a0faa3240fa409baa379409d152aec.1.llvm.15298435345870820272
  [NEW]    +114  [NEW]     +24    anon.44a0faa3240fa409baa379409d152aec.4.llvm.15298435345870820272
  [NEW]    +109  [NEW]     +19    anon.44a0faa3240fa409baa379409d152aec.3.llvm.15298435345870820272
  [NEW]     +97  [NEW]      +7    anon.44a0faa3240fa409baa379409d152aec.0.llvm.15298435345870820272
  [NEW]     +95  [NEW]      +5    anon.44a0faa3240fa409baa379409d152aec.2.llvm.15298435345870820272
  [DEL]     -95  [DEL]      -5    anon.44a0faa3240fa409baa379409d152aec.2.llvm.13856889450204013776
  [DEL]     -97  [DEL]      -7    anon.44a0faa3240fa409baa379409d152aec.0.llvm.13856889450204013776
  [DEL]    -109  [DEL]     -19    anon.44a0faa3240fa409baa379409d152aec.3.llvm.13856889450204013776
  [DEL]    -114  [DEL]     -24    anon.44a0faa3240fa409baa379409d152aec.4.llvm.13856889450204013776
  [DEL]    -130  [DEL]     -40    anon.44a0faa3240fa409baa379409d152aec.1.llvm.13856889450204013776
  [ = ]       0  [ = ]       0    TOTAL

@datadog-datadog-prod-us1-2

This comment has been minimized.

@blt
blt marked this pull request as ready for review July 27, 2026 23:19
@blt
blt requested review from a team as code owners July 27, 2026 23:19

@datadog-datadog-prod-us1-2 datadog-datadog-prod-us1-2 Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Datadog Autotest: FAIL

Sampling three independent per-kind maxima permits the intake to retain up to 3,000,000 contexts, rather than the stated 1,000,000 total bound, so long runs can still exceed the memory and cardinality budget this change is intended to enforce.

Open Bits AI session

🤖 Datadog Autotest · Commit 34de63f · What is Autotest? · @DataDog review to ask questions · Any feedback? Reach out in #autotest

#[must_use]
pub fn sample<R: Rng + ?Sized>(rng: &mut R) -> Self {
Self {
metric_contexts: sample_cap(rng),

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Enforce the context cap globally

Antithesis runs can still exceed the intended memory and cardinality budget by three times, undermining the context-bounding change.

Assertion details
  • Input: A sampled context source whose metric, event, and service-check caps each reach 1,000,000, followed by enough requests to fill all three pools.
  • Expected: The shared pool retains at most 1,000,000 contexts in total, matching the PR's stated bound.
  • Actual: Each of the three caps is sampled independently up to 1,000,000, and Pool stores a separate vector for each kind, permitting 3,000,000 retained contexts.

Was this helpful? React 👍 or 👎
🤖 Datadog Autotest · What is Autotest? · @DataDog review to ask questions · Any feedback? Reach out in #autotest

@pr-commenter

pr-commenter Bot commented Jul 27, 2026

Copy link
Copy Markdown

Regression Detector (Agent Data Plane)

Run ID: dd5aabd6-0a40-4628-996d-35a4072d0084
Baseline: 20f18cf6 · Comparison: 639f6b7f · diff

Optimization Goals: ✅ No significant changes detected

Fine details of change detection per experiment (5)

Experiments configured erratic: true are tagged (ignored) and skipped when determining which experiments regressed or improved. Experiments which are detected as erratic at runtime are tagged (erratic) to flag that the run's sample dispersion was high, but their regression / improvement signal still counts.

experiment goal Δ mean % links
quality_gates_rss_dsd_low memory ⚪ +0.30 metrics profiles logs
quality_gates_rss_dsd_heavy memory ⚪ +0.15 metrics profiles logs
quality_gates_rss_dsd_ultraheavy memory ⚪ +0.13 metrics profiles logs
quality_gates_rss_dsd_medium memory ⚪ -0.10 metrics profiles logs
quality_gates_rss_idle memory ⚪ -0.11 metrics profiles logs
Bounds Checks: ✅ Passed (5)
experiment check replicates observed links
quality_gates_rss_dsd_heavy memory_usage 10/10 ✅ 133 MiB ≤ 140 MiB metrics profiles logs
quality_gates_rss_dsd_low memory_usage 10/10 ✅ 45.7 MiB ≤ 50 MiB metrics profiles logs
quality_gates_rss_dsd_medium memory_usage 10/10 ✅ 68.8 MiB ≤ 75 MiB metrics profiles logs
quality_gates_rss_dsd_ultraheavy memory_usage 10/10 ✅ 194 MiB ≤ 200 MiB metrics profiles logs
quality_gates_rss_idle memory_usage 10/10 ✅ 31.7 MiB ≤ 40 MiB metrics profiles logs
Explanation

A change is flagged as a regression when |Δ mean %| > 5.00% in the regressing direction for its optimization goal AND SMP marks the experiment as a regression (is_regression: true). Improvements use the matching criteria for the improving direction. Experiments configured erratic: true (tagged (ignored)) are skipped outright; experiments detected as erratic at runtime (tagged (erratic)) still count, since that flag describes sample dispersion rather than directional certainty. The Δ mean % cell is colored accordingly: 🟢 = improvement, 🔴 = regression, ⚪ = neutral. Reduction in CPU or memory is an improvement; reduction in ingress throughput is a regression.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 34de63f221

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

/// forwards. Content carries delimiters, so a raw render may occasionally drop; the repair
/// loop is the sorter and must always yield a forwardable line.
#[test]
fn render_wellformed_always_forwards(seed: u64, kind in any_kind()) {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Prefix the new property tests with property_test_

The three new proptests in this module, plus empty_pool_yields_empty_payload in payload/dogstatsd.rs, lack the required literal property_test_ prefix. The Makefile filters on that name, so these tests run in the ordinary debug-mode test job and are omitted from the dedicated release-mode test-property job; rename all four new property-test functions so they receive the intended coverage.

AGENTS.md reference: AGENTS.md:L39-L41

Useful? React with 👍 / 👎.

return context;
}
}
Context::Metric(metric::MetricContext::fallback())

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Preserve the requested kind in the mint fallback

When all remint attempts are exhausted for an event or service check, this unconditional metric fallback is inserted into the event or service-check vector selected by Pool::serve. On those random branches, later requests for that kind therefore return metrics instead, and the actual number of metric identities can exceed metric_contexts while the advertised event/service-check working set is missing an entry; provide a valid fallback for each requested Kind rather than changing the variant.

Useful? React with 👍 / 👎.

@blt
blt force-pushed the blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regime branch from e4ff7fa to f89d2be Compare July 29, 2026 17:15
@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from 34de63f to a827899 Compare July 29, 2026 17:15

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: a82789926a

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

}
out.truncate(start);
}
out.extend_from_slice(FALLBACK_LINE);

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Keep repair fallbacks within the pooled identity

When all eight per-occurrence render attempts are malformed—for example, repeated delimiter-bearing values for a pooled set metric—this emits the fixed harness.fallback metric rather than the context fetched from /contexts. That introduces a metric identity outside the shared pool and can make the observed metric inventory exceed its configured cap; unlike the already-flagged mint-time fallback, this happens later while rendering an otherwise accepted pooled context. Use a well-formed rendering that preserves the selected context's identity instead.

Useful? React with 👍 / 👎.

Comment on lines +268 to +270
metric_contexts: sample_cap(rng),
event_contexts: sample_cap(rng),
service_check_contexts: sample_cap(rng),

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Enforce the one-million cap across all context kinds

When the independently sampled caps are large, this configuration permits up to one million metrics, one million events, and one million service checks, so the pool's total bound is three million contexts rather than the intended one-million run-wide ceiling. Because the pool retains every minted context and each can carry several kilobytes of nested byte vectors, long runs can consume several times the memory implied by the advertised cap; sample or enforce a shared total budget instead of applying the full ceiling independently to every kind.

Useful? React with 👍 / 👎.

@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from a827899 to e45d94e Compare July 29, 2026 20:37
@blt
blt force-pushed the blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regime branch from f89d2be to 07e1995 Compare July 29, 2026 20:37

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: e45d94e437

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

};
let mut probe = Vec::new();
context.render(rng, &mut probe);
if probe.len() <= MAX_CONTEXT_RENDER && is_malformed(&probe).is_ok() {

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Admit contexts using the sampled datagram limit

When dogstatsd_buffer_size is sampled below 6,000 bytes (it can be as low as 128), this accepts contexts whose stable name, tags, or options already exceed the driver's payload_byte_limit. write_payload then rejects the first rendered line before adding anything; with the commonly sampled one-context working set, every configured datagram is empty and the invocation silently generates no load. Pass the sampled payload limit into context admission or otherwise ensure every served context has a rendering that fits that timeline's limit.

Useful? React with 👍 / 👎.

Comment on lines +177 to +179
1 => (b"c:", common::optional_text(rng)),
2 => (b"e:", common::optional_text(rng)),
_ => (b"card:", common::optional_text(rng)),

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Keep occurrence data from overriding pooled tags

When one of these generated extension bodies contains |#..., which is possible because optional_text deliberately samples protocol delimiters, the parser treats the suffix as a second tag extension after self.tags and replaces the pooled tag set with it. The service-check message has the same problem because it is also delimiter-bearing and serialized after its fixed tags. A recurring pooled context can therefore produce different actual identities on each render, growing observed cardinality beyond the configured pool cap and defeating multi-point recurrence; prevent per-occurrence fields from injecting extension separators or pool the resulting parsed identity.

Useful? React with 👍 / 👎.

Comment on lines +311 to +312
/// Distinct metric contexts the pool holds.
pub metric_contexts: usize,

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P1 Badge Document the context-cap configuration contracts

This public YAML field and its two sibling caps only state what they count; they do not document the generated default/range, accepted boundary values, behavioral impact, or guidance for changing them. In particular, Deserialize accepts 0 even though serving that kind then evaluates random_range(0..0) and panics, so a consumer cannot determine the safe contract from the API. Document the 1..=1_000_000 generated behavior, unsupported or validated edges, and the memory-versus-recurrence trade-off.

AGENTS.md reference: AGENTS.md:L149-L154

Useful? React with 👍 / 👎.

@blt
blt force-pushed the blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regime branch from 07e1995 to b943695 Compare July 29, 2026 20:50
@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from e45d94e to cb1f9df Compare July 29, 2026 20:50

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: cb1f9df376

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +259 to +261
/// Distinct contexts a driver invocation fetches from the shared pool as its working set, each
/// boundary-biased log-uniform in `1..=MAX_WORKING_SET`.
pub context_count: usize,

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Document or validate context_count boundaries

When a restored or hand-authored driver.yaml sets context_count to 0 or above 65_536, DriverConfig::read accepts it, but the intake rejects every /contexts request; the shared fetch loop then waits for its 30-second budget and both Antithesis drivers return empty stats without generating DogStatsD load. Document the accepted boundaries, invalid-value behavior, and workload-size trade-off here, or validate the field during deserialization, rather than describing only the range produced by the sampler.

AGENTS.md reference: AGENTS.md:L149-L154

Useful? React with 👍 / 👎.

@blt
blt force-pushed the blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regime branch from b943695 to a6dd29d Compare July 29, 2026 21:18
@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from cb1f9df to 639f6b7 Compare July 29, 2026 21:18

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 639f6b7fee

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +137 to +140
let ext_count = EXT_COUNTS[rng.random_range(0..EXT_COUNTS.len())];
for _ in 0..ext_count {
out.push(b'|');
ext_chunk(rng, out);

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Bound every per-occurrence metric rendering

When EXT_COUNTS selects 127 or 255, the freshly generated extension bodies can make a later rendering exceed MAX_CONTEXT_RENDER even though the same identity passed minting with a shorter probe render. write_payload then stops at that first non-fitting line and, if it was the first line, sends an empty datagram; this silently discards configured load for sampled receive limits and can occur even at the 8,192-byte ceiling. Enforce the size bound on each render or retry/skip an oversized occurrence instead of ending the payload.

Useful? React with 👍 / 👎.

@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from 639f6b7 to 39f3b2a Compare July 29, 2026 22:42
@blt
blt force-pushed the blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regime branch 2 times, most recently from 212be47 to 57f3d76 Compare July 29, 2026 22:55
@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from 39f3b2a to a8467bf Compare July 29, 2026 22:55
@blt
blt force-pushed the blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regime branch from 57f3d76 to 170d7ed Compare July 29, 2026 23:00
@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from a8467bf to 75b7b70 Compare July 29, 2026 23:00
This commit introduces a new protocol to the intake node to allow for
context bounding in runs. The purposes are twofold. First, while it's
interesting to explore timelines in which there are too many contexts
for either lane to handle these are less relevant to me _now_, so I've
capped total contexts at 1M. Second, in order for timeseries equality
to _work_ I need to be certain that I have at least _some_ timeseries
with more than one point emitted into them. Previously drivers were
emitting essentially random contexts and it was very unlikely for more
than one point to be emitted per context. Oops.

Drivers now request N contexts from the intake service for each sub-kind
of dogstatsd they emit, meaning all contexts are sourced from a single
spot in a topology and not from pure randomness.
@blt
blt force-pushed the blt/chore_antithesis_alter_dogstatsd_generation_to_is_malformed_regime branch from 170d7ed to 56c2a83 Compare July 29, 2026 23:06
@blt
blt force-pushed the blt/chore_antithesis_bound_contexts_in_runs branch from 75b7b70 to 9adb823 Compare July 29, 2026 23:06
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

area/test All things testing: unit/integration, correctness, SMP regression, etc.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant