Files
wyj 789549ed2f Fix: Validate asymptotic entries with precise roots and fallback
Use scaled long-double quadratic arithmetic without explicit FMA. Validate entry candidates against backend geometry and localize uncertain entries along the original exterior trajectory.

Preserve conservative miss semantics and propagate concrete entry failures. Add production-sample and numerical regression coverage.
2026-10-09 00:14:54 -04:00

1073 lines
49 KiB
C

#include "asymptotic.h"
#include "observer.h"
#include "ray.h"
#include "spacetime.h"
#include <float.h>
#include <math.h>
#include <stdio.h>
static int failures = 0;
#define CHECK(condition, message) \
do { \
if (!(condition)) { \
fprintf(stderr, "FAIL %s:%d: %s\n", __FILE__, __LINE__, message); \
++failures; \
} \
} while (0)
static ObserverState flat_observer(double x, double y, double z) {
ObserverState o = {0};
o.coordinate_position[0] = x;
o.coordinate_position[1] = y;
o.coordinate_position[2] = z;
o.tetrad[0][0] = 1.0;
o.tetrad[1][1] = 1.0;
o.tetrad[2][2] = 1.0;
o.tetrad[3][3] = 1.0;
return o;
}
/* Synthetic flat exterior with a Minkowski end whose worldtube center follows
* x_c(t) = vx t + accel t^2 / 2. `constant` selects the closed quadratic path;
* otherwise the generic bracketed driver runs. */
typedef struct {
double vx;
double accel;
double radius;
double radius_rate;
double valid_t_min;
int constant;
double segment_t; /* Motion-segment boundary for the cross-segment test. */
int has_segment;
int end_descriptor_fails; /* Protocol-error injection. */
int unsupported_kind;
double invalid_center, invalid_halfwidth; /* Isolated invalid time window. */
int schwarzschild_kind; /* Declare a Schwarzschild monopole end. */
int sample_callback_fails; /* make escape_worldtube_sample return -1 */
int sample_invalid; /* valid = 0 */
int sample_nan_radius;
int sample_nonpositive_radius;
int fail_on_sample_call; /* 1-based callback invocation to fail. */
int sample_call_count;
double frame_origin[3];
} SyntheticContext;
static SpacetimePointStatus synthetic_eval(const SpacetimeSource *source,
double t, const double x[3],
MetricData *metric) {
(void)source;
(void)t;
(void)x;
*metric = (MetricData){.alpha = 1.0,
.gamma = {{1.0, 0.0, 0.0},
{0.0, 1.0, 0.0},
{0.0, 0.0, 1.0}}};
return SPACETIME_POINT_OK;
}
static SpacetimeRayStatus synthetic_classify(const SpacetimeSource *source,
double t, const double x[3]) {
(void)source;
(void)t;
(void)x;
return SPACETIME_RAY_ACTIVE;
}
static size_t synthetic_end_count(const SpacetimeSource *source) {
(void)source;
return 1;
}
static int synthetic_end(const SpacetimeSource *source, size_t index,
SpacetimeAsymptoticEnd *out) {
const SyntheticContext *context = source->context;
if (index != 0 || context->end_descriptor_fails)
return -1;
AsymptoticExteriorKind kind = ASYMPTOTIC_EXTERIOR_MINKOWSKI;
double mass = 0.0;
if (context->unsupported_kind) {
kind = (AsymptoticExteriorKind)999;
} else if (context->schwarzschild_kind) {
kind = ASYMPTOTIC_EXTERIOR_SCHWARZSCHILD_MONOPOLE;
mass = 1.0;
}
*out = (SpacetimeAsymptoticEnd){
.end_id = 0,
.exterior_kind = kind,
.mass = mass,
.frame_origin = {context->frame_origin[0], context->frame_origin[1],
context->frame_origin[2]},
.frame_axes = {{1.0, 0.0, 0.0}, {0.0, 1.0, 0.0}, {0.0, 0.0, 1.0}}};
return 0;
}
static int synthetic_worldtube(const SpacetimeSource *source,
SpacetimeEndId end_id, double t,
SpacetimeEscapeWorldtubeSample *out) {
SyntheticContext *mutable_context = source->context;
const SyntheticContext *context = mutable_context;
if (end_id != 0)
return -1;
++mutable_context->sample_call_count;
if (context->fail_on_sample_call > 0 &&
mutable_context->sample_call_count == context->fail_on_sample_call)
return -1;
if (context->sample_callback_fails)
return -1;
if (context->sample_invalid) {
*out = (SpacetimeEscapeWorldtubeSample){.valid = 0};
return 0;
}
if (context->sample_nan_radius) {
*out = (SpacetimeEscapeWorldtubeSample){.radius = NAN, .valid = 1};
return 0;
}
if (context->sample_nonpositive_radius) {
*out = (SpacetimeEscapeWorldtubeSample){.radius = 0.0, .valid = 1};
return 0;
}
if (!isfinite(t) || t < context->valid_t_min) {
*out = (SpacetimeEscapeWorldtubeSample){.valid = 0};
return 0;
}
if (context->invalid_halfwidth > 0.0 &&
fabs(t - context->invalid_center) <= context->invalid_halfwidth) {
*out = (SpacetimeEscapeWorldtubeSample){.valid = 0};
return 0;
}
/* The sample contract is the worldtube value at this coordinate time, so the
* reported radius must carry its own time dependence: R(t) = R0 + rr t, with
* dR/dt = radius_rate. A constant `radius` with a nonzero rate would make
* the closed-form segment model and the callback geometry disagree. */
const double radius_t = context->radius + context->radius_rate * t;
if (context->has_segment && t < context->segment_t) {
/* Second segment: center moves toward +x as t decreases. */
*out = (SpacetimeEscapeWorldtubeSample){
.center = {context->segment_t - t, 0.0, 0.0},
.velocity = {-1.0, 0.0, 0.0},
.radius = radius_t,
.radius_rate = context->radius_rate,
.velocity_constant = context->constant,
.valid = 1};
return 0;
}
*out = (SpacetimeEscapeWorldtubeSample){
.center = {context->vx * t + 0.5 * context->accel * t * t, 0.0, 0.0},
.velocity = {context->vx + context->accel * t, 0.0, 0.0},
.radius = radius_t,
.radius_rate = context->radius_rate,
.velocity_constant = context->constant,
.valid = 1};
return 0;
}
static double synthetic_next_segment(const SpacetimeSource *source,
SpacetimeEndId end_id, double t) {
const SyntheticContext *context = source->context;
(void)end_id;
if (context->has_segment && t > context->segment_t)
return context->segment_t;
return NAN;
}
static void synthetic_destroy(SpacetimeSource *source) {
/* The test context lives on the stack, so it is not freed; but match the
* real destroy postcondition. */
source->context = NULL;
source->ops = NULL;
}
static const SpacetimeOps synthetic_ops = {
.eval = synthetic_eval,
.classify = synthetic_classify,
.asymptotic_end_count = synthetic_end_count,
.asymptotic_end = synthetic_end,
.escape_worldtube_sample = synthetic_worldtube,
.escape_worldtube_next_segment = synthetic_next_segment,
.destroy = synthetic_destroy,
};
static void test_fixed_sphere(void) {
SpacetimeSource source = {0};
CHECK(spacetime_create_minkowski(&source, 10.0) == 0, "create minkowski");
AsymptoticRoute route;
const ObserverState inside = flat_observer(0.0, 0.0, 0.0);
CHECK(asymptotic_route_camera(&source, &inside, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_INSIDE,
"origin camera is inside");
const ObserverState outside = flat_observer(50.0, 0.0, 0.0);
CHECK(asymptotic_route_camera(&source, &outside, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"outside ray toward sphere enters");
CHECK(fabs(route.activate_t + 40.0) < 1e-9, "fixed-sphere entry time");
CHECK(fabs(route.x[0] - 10.0) < 1e-9 && fabs(route.x[1]) < 1e-9 &&
fabs(route.x[2]) < 1e-9,
"fixed-sphere entry position");
CHECK(asymptotic_route_camera(&source, &outside, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"outside ray away misses");
CHECK(fabs(route.n_infinity[0] - 1.0) < 1e-12 &&
fabs(route.n_infinity[1]) < 1e-12,
"miss direction");
CHECK(fabs(route.frequency_ratio - 1.0) < 1e-12, "flat frequency ratio");
const ObserverState tangent = flat_observer(50.0, 10.0, 0.0);
CHECK(asymptotic_route_camera(&source, &tangent, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"tangent ray is not a crossing");
const ObserverState near_miss = flat_observer(50.0, 10.0 + 1e-6, 0.0);
CHECK(asymptotic_route_camera(&source, &near_miss,
(double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"near-tangent outside ray misses");
const ObserverState near_hit = flat_observer(50.0, 10.0 - 1e-6, 0.0);
CHECK(asymptotic_route_camera(&source, &near_hit,
(double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"near-tangent inside ray enters");
RayEndpoint endpoint;
CHECK(asymptotic_finish_escape(&source, 0, 0.0, (double[]){10.0, 0.0, 0.0},
(double[]){-1.0, 0.0, 0.0}, 0.0,
&endpoint) == ASYMPTOTIC_OK &&
endpoint.outcome == RAY_OUTCOME_ESCAPED && endpoint.end_id == 0,
"finish outward crossing");
CHECK(fabs(endpoint.n_infinity[0] - 1.0) < 1e-12 &&
fabs(endpoint.frequency_ratio - 1.0) < 1e-12,
"finish direction and frequency");
spacetime_destroy(&source);
}
static void test_large_radius_quadratic(void) {
SpacetimeSource source = {0};
CHECK(spacetime_create_minkowski(&source, 1.0e12) == 0,
"create huge minkowski sphere");
AsymptoticRoute route;
const ObserverState hit = flat_observer(2.0e12, 5.0e11, 0.0);
CHECK(asymptotic_route_camera(&source, &hit, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"large-radius hit stays quadratic");
const ObserverState miss = flat_observer(2.0e12, 2.0e12, 0.0);
CHECK(asymptotic_route_camera(&source, &miss, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"large-radius miss stays quadratic");
spacetime_destroy(&source);
/* Small entry root a hair outside a large sphere: the cancellation-prone
* case for the naive formula. */
SpacetimeSource big = {0};
CHECK(spacetime_create_minkowski(&big, 1.0e9) == 0, "create 1e9 sphere");
const ObserverState just_outside = flat_observer(1.0e9 + 1e-3, 0.0, 0.0);
CHECK(asymptotic_route_camera(&big, &just_outside,
(double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"just-outside hit");
const double expected_delta =
just_outside.coordinate_position[0] - 1.0e9;
CHECK(fabs(-route.activate_t - expected_delta) <
1e-7 + 1e-11 * fabs(expected_delta),
"just-outside entry time within budget");
double residual;
CHECK(asymptotic_worldtube_value(&big, route.end_id, route.activate_t,
route.x, &residual) == 0 &&
fabs(residual) <= 1e-12 * 1.0e9 * 1.0e9,
"just-outside entry on worldtube");
spacetime_destroy(&big);
}
static void test_boundary_semantics_minkowski(void) {
SpacetimeSource source = {0};
CHECK(spacetime_create_minkowski(&source, 10.0) == 0,
"create minkowski");
AsymptoticRoute route;
const ObserverState on_boundary = flat_observer(10.0, 0.0, 0.0);
CHECK(asymptotic_route_camera(&source, &on_boundary,
(double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_INSIDE,
"on-boundary past-inward is inside");
CHECK(asymptotic_route_camera(&source, &on_boundary,
(double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"on-boundary past-outward escapes");
CHECK(asymptotic_route_camera(&source, &on_boundary,
(double[]){0.0, 1.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"on-boundary tangent escapes");
spacetime_destroy(&source);
}
static void test_nonconstant_route_unsupported(void) {
/* velocity_constant == 0 signals an arbitrary accelerated worldtube. The
* camera-inside containment test still runs first; once the ray starts
* outside, the non-constant route is refused explicitly instead of being
* searched with a coarse bracket. */
SyntheticContext context = {.radius = 10.0,
.valid_t_min = -100.0,
.constant = 0};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState on_boundary = flat_observer(10.0, 0.0, 0.0);
AsymptoticRoute route;
const AsymptoticStatus inward = asymptotic_route_camera(
&source, &on_boundary, (double[]){-1.0, 0.0, 0.0}, &route);
CHECK(inward == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_INSIDE,
"nonconstant on-boundary inward is still inside");
const AsymptoticStatus outward = asymptotic_route_camera(
&source, &on_boundary, (double[]){1.0, 0.0, 0.0}, &route);
CHECK(outward == ASYMPTOTIC_UNSUPPORTED,
"nonconstant on-boundary outward is unsupported");
const AsymptoticStatus tangent = asymptotic_route_camera(
&source, &on_boundary, (double[]){0.0, 1.0, 0.0}, &route);
CHECK(tangent == ASYMPTOTIC_UNSUPPORTED,
"nonconstant on-boundary tangent is unsupported");
}
static void test_negative_radius_root_guard(void) {
/* Deliberately bypasses a constructor: every sampled radius is finite and
* positive, but the algebraic root sits where R < 0. The cheap root-level
* guard must reject it instead of fabricating a negative-radius entry. */
SyntheticContext context = {.radius = 10.0,
.radius_rate = 2.0,
.valid_t_min = -1.0e30,
.constant = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState on_boundary = flat_observer(10.0, 0.0, 0.0);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &on_boundary,
(double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_INVALID,
"negative-radius algebraic root is rejected");
}
static void test_source_finalize(void) {
/* A real constructor already finalizes: finalize is idempotent. */
SpacetimeSource good = {0};
CHECK(spacetime_create_minkowski(&good, 10.0) == 0, "create minkowski");
CHECK(spacetime_source_finalize(&good) == 0, "valid source finalizes");
spacetime_destroy(&good);
/* A structurally valid synthetic source must pass, so the failure cases
* below are attributable to their specific defect rather than to the test
* ops themselves. */
SyntheticContext well_formed = {.radius = 10.0,
.valid_t_min = -1.0e30,
.constant = 1};
SpacetimeSource valid_source = {.ops = &synthetic_ops,
.context = &well_formed};
CHECK(spacetime_source_finalize(&valid_source) == 0,
"well-formed synthetic source finalizes");
/* Structural protocol errors must be rejected before any ray trace. */
SyntheticContext bad_kind = {.radius = 10.0,
.valid_t_min = -1.0e30,
.constant = 1,
.unsupported_kind = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &bad_kind};
CHECK(spacetime_source_finalize(&source) != 0,
"unsupported exterior kind fails finalize");
SyntheticContext bad_desc = {.radius = 10.0,
.valid_t_min = -1.0e30,
.constant = 1,
.end_descriptor_fails = 1};
source = (SpacetimeSource){.ops = &synthetic_ops, .context = &bad_desc};
CHECK(spacetime_source_finalize(&source) != 0,
"broken end descriptor fails finalize");
}
static void test_motion_segment_domain(void) {
/* Segment 1 (t >= -50) is a static R=10 sphere; its quadratic root lies at
* s = 90, past the segment boundary. Segment 2 (t < -50) moves the center
* with velocity -1, so the true entry is at s = 70. The result must come
* from segment 2. */
SyntheticContext context = {.radius = 10.0,
.valid_t_min = -1.0e30,
.constant = 1,
.segment_t = -50.0,
.has_segment = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState camera = flat_observer(100.0, 0.0, 0.0);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &camera,
(double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"entry found in the second motion segment");
CHECK(fabs(route.activate_t + 70.0) < 1e-6,
"second-segment entry, not the stale first-segment root");
}
static void test_schwarzschild_sample_failures(void) {
const ObserverState camera = flat_observer(0.0, 0.0, 0.0);
AsymptoticRoute route;
SyntheticContext base = {.radius = 256.0,
.valid_t_min = -1.0e30,
.constant = 1,
.schwarzschild_kind = 1};
SyntheticContext callback = base;
callback.sample_callback_fails = 1;
SpacetimeSource s1 = {.ops = &synthetic_ops, .context = &callback};
CHECK(asymptotic_route_camera(&s1, &camera, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_INVALID,
"schwarzschild callback failure is invalid");
SyntheticContext invalid = base;
invalid.sample_invalid = 1;
SpacetimeSource s2 = {.ops = &synthetic_ops, .context = &invalid};
CHECK(asymptotic_route_camera(&s2, &camera, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_TIME_RANGE_EXHAUSTED,
"schwarzschild valid=0 is exhausted");
SyntheticContext nan = base;
nan.sample_nan_radius = 1;
SpacetimeSource s3 = {.ops = &synthetic_ops, .context = &nan};
CHECK(asymptotic_route_camera(&s3, &camera, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_INVALID,
"schwarzschild NaN radius is invalid");
SyntheticContext zero = base;
zero.sample_nonpositive_radius = 1;
SpacetimeSource s4 = {.ops = &synthetic_ops, .context = &zero};
CHECK(asymptotic_route_camera(&s4, &camera, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_INVALID,
"schwarzschild non-positive radius is invalid");
/* Second call fails: the containment sample (#1) succeeds with the camera
* outside, and schwarzschild_route's own sample (#2) is the one that fails.
* This locks the dedicated Schwarzschild sample handling. */
SyntheticContext second = base;
second.fail_on_sample_call = 2;
SpacetimeSource s5 = {.ops = &synthetic_ops, .context = &second};
const ObserverState outside = flat_observer(500.0, 0.0, 0.0);
CHECK(asymptotic_route_camera(&s5, &outside, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_INVALID,
"schwarzschild_route second-sample failure is invalid");
}
static void test_end_protocol_error(void) {
const ObserverState inside = flat_observer(0.0, 0.0, 0.0);
AsymptoticRoute route;
SyntheticContext bad = {.radius = 20.0,
.valid_t_min = -1.0e30,
.constant = 1,
.end_descriptor_fails = 1};
SpacetimeSource bad_source = {.ops = &synthetic_ops, .context = &bad};
CHECK(asymptotic_route_camera(&bad_source, &inside,
(double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_INVALID,
"bad end descriptor is an explicit protocol error");
SyntheticContext unsupported = {.radius = 20.0,
.valid_t_min = -1.0e30,
.constant = 1,
.unsupported_kind = 1};
SpacetimeSource unsupported_source = {.ops = &synthetic_ops,
.context = &unsupported};
CHECK(asymptotic_route_camera(&unsupported_source, &inside,
(double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_UNSUPPORTED,
"unsupported exterior with camera inside is not silently accepted");
/* The lifecycle layer, not just the pre-route, must refuse legacy fallback
* whenever ends are declared but broken. */
MetricSlab *slab = NULL;
CHECK(spacetime_load_slab(&bad_source, 0.0, -10.0, &slab) == 0,
"bad-descriptor slab");
GeodesicRayState state = {.coordinate_time = 0.0,
.x = {1.0, 0.0, 0.0},
.Pi = {0.0, 0.0, 0.0},
.log_alpha_p0 = 0.0,
.steps = 0};
const GeodesicTraceConfig config = {.coordinate_time_step = 1.0,
.max_steps = 10};
RayEndpoint endpoint = {.frequency_ratio = 0.0,
.magnification = 1.0,
.end_id = SPACETIME_END_NONE,
.outcome = RAY_OUTCOME_INCOMPLETE};
CHECK(geodesic_advance_past_ray(slab, &state, -10.0, &config, &endpoint) ==
GEODESIC_ADVANCE_FAILED &&
endpoint.outcome == RAY_OUTCOME_INCOMPLETE &&
endpoint.reason == RAY_REASON_END_DESCRIPTOR_FAILED,
"advance rejects a declared-but-broken end without legacy");
spacetime_free_slab(slab);
}
/* A worldtube sample callback failure and an invalid worldtube geometry are
* distinguished from each other and from the lifecycle/descriptor failure
* above when the same advance entry point classifies its pre-step scan. */
static void test_advance_worldtube_failure_reasons(void) {
const GeodesicTraceConfig config = {.coordinate_time_step = 1.0,
.max_steps = 10};
GeodesicRayState state = {.coordinate_time = 0.0,
.x = {1.0, 0.0, 0.0},
.Pi = {0.0, 0.0, 0.0},
.log_alpha_p0 = 0.0,
.steps = 0};
SyntheticContext sample_fail = {.radius = 20.0,
.valid_t_min = -1.0e30,
.constant = 1,
.sample_callback_fails = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &sample_fail};
MetricSlab *slab = NULL;
CHECK(spacetime_load_slab(&source, 0.0, -10.0, &slab) == 0,
"sample-fail slab");
RayEndpoint endpoint = {.frequency_ratio = 0.0,
.magnification = 1.0,
.end_id = SPACETIME_END_NONE,
.outcome = RAY_OUTCOME_INCOMPLETE};
CHECK(geodesic_advance_past_ray(slab, &state, -10.0, &config, &endpoint) ==
GEODESIC_ADVANCE_FAILED &&
endpoint.outcome == RAY_OUTCOME_INCOMPLETE &&
endpoint.reason == RAY_REASON_WORLDTUBE_SAMPLE_FAILED,
"worldtube sample callback failure is its own reason");
spacetime_free_slab(slab);
SyntheticContext bad_geometry = {.radius = 20.0,
.valid_t_min = -1.0e30,
.constant = 1,
.sample_nan_radius = 1};
source = (SpacetimeSource){.ops = &synthetic_ops, .context = &bad_geometry};
CHECK(spacetime_load_slab(&source, 0.0, -10.0, &slab) == 0,
"geometry slab");
endpoint = (RayEndpoint){.frequency_ratio = 0.0,
.magnification = 1.0,
.end_id = SPACETIME_END_NONE,
.outcome = RAY_OUTCOME_INCOMPLETE};
CHECK(geodesic_advance_past_ray(slab, &state, -10.0, &config, &endpoint) ==
GEODESIC_ADVANCE_FAILED &&
endpoint.outcome == RAY_OUTCOME_INCOMPLETE &&
endpoint.reason == RAY_REASON_WORLDTUBE_GEOMETRY_INVALID,
"invalid worldtube geometry is its own reason");
spacetime_free_slab(slab);
}
static void test_interior_crossing_bisection_failure(void) {
/* radius 20.3 makes the exit land strictly between steps: the accepted
* step goes from F < 0 (t = -119.7) to F > 0 (t = -120.7). The invalid
* window sits on the first bisection midpoint (t = -120.2), while both
* accepted-step endpoints stay valid. */
SyntheticContext context = {.radius = 20.3,
.valid_t_min = -1.0e30,
.constant = 1,
.invalid_center = -120.2,
.invalid_halfwidth = 0.05};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState observer = flat_observer(100.0, 0.0, 0.0);
const GeodesicTraceConfig config = {.coordinate_time_step = 1.0,
.max_steps = 2048};
const RayEndpoint endpoint = geodesic_trace_past(
&source, &observer, (double[]){-1.0, 0.0, 0.0}, &config);
CHECK(endpoint.outcome == RAY_OUTCOME_INCOMPLETE &&
endpoint.reason == RAY_REASON_TIME_RANGE_EXHAUSTED &&
endpoint.end_id == 0,
"interior crossing bisection propagates history exhaustion");
}
static void test_nonconstant_preroute_unsupported(void) {
/* The accelerated fixture is refused explicitly at the route entry; its
* former coarse bracketed search (and the bisection-midpoint history-hole
* case it exercised) is replaced by the unsupported contract. The history
* reason itself stays covered by the constant and piecewise-constant
* worldtube tests below. */
SyntheticContext context = {.radius = 20.0,
.valid_t_min = -1.0e30,
.constant = 0,
.invalid_center = -85.0,
.invalid_halfwidth = 1.0};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState camera = flat_observer(100.0, 0.0, 0.0);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &camera, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_UNSUPPORTED,
"nonconstant worldtube route is unsupported");
}
static void test_piecewise_constant_history_hole(void) {
/* Piecewise-constant motion stays supported, including its history
* contract: when the segment walk steps past the valid history, the route
* reports TIME_RANGE_EXHAUSTED and never disguises it as a miss. */
SyntheticContext context = {.radius = 10.0,
.valid_t_min = -3.0,
.constant = 1,
.segment_t = -5.0,
.has_segment = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState camera = flat_observer(50.0, 0.0, 0.0);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &camera, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_TIME_RANGE_EXHAUSTED,
"piecewise-constant segment history hole is exhausted");
}
static void test_interior_history_exhaustion(void) {
SyntheticContext context = {.radius = 20.0,
.valid_t_min = -100.0,
.constant = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState observer = flat_observer(100.0, 0.0, 0.0);
const GeodesicTraceConfig config = {.coordinate_time_step = 1.0,
.max_steps = 2048};
const RayEndpoint endpoint = geodesic_trace_past(
&source, &observer, (double[]){-1.0, 0.0, 0.0}, &config);
CHECK(endpoint.outcome == RAY_OUTCOME_INCOMPLETE &&
endpoint.reason == RAY_REASON_TIME_RANGE_EXHAUSTED &&
endpoint.end_id == 0,
"interior worldtube history exhaustion on a single trace");
RayPool pool;
CHECK(ray_pool_init(&pool, 1) == 0, "pool init");
CHECK(ray_pool_append(&pool, &observer, (double[]){-1.0, 0.0, 0.0}, 0, 0) ==
0,
"append exhaustion ray");
ray_pool_preroute(&pool, &source);
CHECK(pool.status[0] == RAY_POOL_PENDING, "exhaustion ray pends entry");
MetricSlab *slab = NULL;
CHECK(spacetime_load_slab(&source, -80.0, -3000.0, &slab) == 0,
"exhaustion slab");
ray_pool_activate_in_time_range(&pool, slab);
CHECK(pool.status[0] == RAY_POOL_ACTIVE, "exhaustion ray activates");
ray_pool_advance_active(&pool, slab, &config);
CHECK(pool.endpoint[0].outcome == RAY_OUTCOME_INCOMPLETE &&
pool.endpoint[0].reason == RAY_REASON_TIME_RANGE_EXHAUSTED &&
pool.endpoint[0].end_id == 0 &&
pool.status[0] == RAY_POOL_TERMINATED,
"interior worldtube history exhaustion on a RayPool");
spacetime_free_slab(slab);
ray_pool_destroy(&pool);
}
static void test_round_trip(void) {
SpacetimeSource source = {0};
CHECK(spacetime_create_minkowski(&source, 10.0) == 0, "create minkowski");
MetricData metric = {.alpha = 1.0,
.gamma = {{1.0, 0.0, 0.0},
{0.0, 1.0, 0.0},
{0.0, 0.0, 1.0}}};
AsymptoticPhotonState canonical;
CHECK(asymptotic_canonical_from_backend(&source, 0, &metric, 0.0,
(double[]){3.0, 4.0, 0.0},
(double[]){-0.6, 0.8, 0.0}, 0.25,
&canonical) == 0,
"backend to canonical");
double x[3], Pi[3], log_alpha_p0;
CHECK(asymptotic_backend_from_canonical(&source, &metric, &canonical, x, Pi,
&log_alpha_p0) == 0,
"canonical to backend");
CHECK(fabs(x[0] - 3.0) < 1e-14 && fabs(x[1] - 4.0) < 1e-14 &&
fabs(Pi[0] + 0.6) < 1e-14 && fabs(Pi[1] - 0.8) < 1e-14 &&
fabs(log_alpha_p0 - 0.25) < 1e-14,
"round trip matches");
spacetime_destroy(&source);
}
static void test_moving_sphere(void) {
SyntheticContext context = {.vx = 0.5, .accel = 0.0, .radius = 25.0,
.valid_t_min = -1.0e30, .constant = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
AsymptoticRoute route;
const ObserverState head_on = flat_observer(100.0, 0.0, 0.0);
CHECK(asymptotic_route_camera(&source, &head_on, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"head-on moving-sphere entry");
CHECK(fabs(route.activate_t + 150.0) < 1e-9, "head-on entry time");
CHECK(fabs(route.x[0] + 50.0) < 1e-9, "head-on entry position");
double value;
CHECK(asymptotic_worldtube_value(&source, route.end_id, route.activate_t,
route.x, &value) == 0 &&
fabs(value) <= 1e-13 * 25.0 * 25.0,
"head-on entry lies on worldtube");
const ObserverState transverse = flat_observer(0.0, 40.0, 0.0);
CHECK(asymptotic_route_camera(&source, &transverse,
(double[]){0.0, -1.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"transverse moving-sphere entry");
CHECK(asymptotic_worldtube_value(&source, route.end_id, route.activate_t,
route.x, &value) == 0 &&
fabs(value) <= 1e-13 * 25.0 * 25.0,
"transverse entry lies on worldtube");
const ObserverState away = flat_observer(100.0, 0.0, 0.0);
CHECK(asymptotic_route_camera(&source, &away, (double[]){1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"co-moving ray misses");
}
/* Fixed-observer tetrad used by the production Alcubierre observer-track rows
* 63/64, with spatial axes (e1, e2, e3) = (y-hat, z-hat, x-hat). The literal
* values are embedded here so this regression does not depend on the
* untracked observer CSV. */
static ObserverState track_observer(double coordinate_time) {
ObserverState o = {0};
o.coordinate_time = coordinate_time;
o.coordinate_position[0] = 0.0;
o.coordinate_position[1] = -24.0;
o.coordinate_position[2] = 0.0;
o.tetrad[0][0] = 1.0;
o.tetrad[1][2] = 1.0;
o.tetrad[2][3] = 1.0;
o.tetrad[3][1] = 1.0;
return o;
}
/* Two exact production RayPool pre-route samples (frame 63 sample 12315 and
* frame 64 sample 3994). They are grazing (disc/b^2 ~ 1e-4), so the plain
* double root solve left the reconstructed entry state at F ~ 1.0-1.2 x
* geom_tol, which the event layer rejected as OUTSIDE_WORLDTUBE. The moving
* sphere fixture reproduces the Alcubierre worldtube (center = 2 t, radius 5);
* the observer time/position/tetrad and the camera direction are the exact raw
* production values. The route must land inside the geometric tolerance with
* the entry direction (Pi) unchanged. */
static void test_grazing_production_entries(void) {
SyntheticContext context = {.vx = 2.0,
.accel = 0.0,
.radius = 5.0,
.radius_rate = 0.0,
.valid_t_min = -1.0e30,
.constant = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
struct {
double time;
double direction[3];
double pi[3];
} cases[2] = {
{0x1.fa8f5c28f5c29p+3,
{0x1.c7378f8e872d1p-1, 0x1.15bad4e30e8ddp-8, -0x1.d4afba4704cap-2},
{0x1.d4afba4704cap-2, -0x1.c7378f8e872d1p-1, -0x1.15bad4e30e8ddp-8}},
{0x1.fb17e4b17e4b1p+3,
{0x1.bd3bb364ac492p-1, 0x1.102d2a1c6ac74p-7, -0x1.f98ae1a782104p-2},
{0x1.f98ae1a782104p-2, -0x1.bd3bb364ac492p-1, -0x1.102d2a1c6ac74p-7}},
};
for (int c = 0; c < 2; ++c) {
ObserverState observer = track_observer(cases[c].time);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &observer, cases[c].direction,
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"grazing production entry found");
CHECK(route.entry_fallback_evaluations == 0,
"grazing production entry stays on the fast path");
for (int i = 0; i < 3; ++i)
CHECK(route.Pi[i] == cases[c].pi[i],
"grazing entry direction is unchanged");
SpacetimeEscapeWorldtubeSample sample;
CHECK(spacetime_escape_worldtube_sample(&source, route.end_id,
route.activate_t, &sample) == 0 &&
sample.valid && sample.radius > 0.0,
"grazing entry sample valid");
double d2 = 0.0;
for (int k = 0; k < 3; ++k) {
const double dk = route.x[k] - sample.center[k];
d2 += dk * dk;
}
const double r2 = sample.radius * sample.radius;
double value;
CHECK(asymptotic_worldtube_value(&source, route.end_id, route.activate_t,
route.x, &value) == 0,
"grazing entry worldtube value");
const double geom_tol = 128.0 * DBL_EPSILON * fmax(r2, d2);
/* The event layer rejects the entry (OUTSIDE_WORLDTUBE) exactly when
* F > geom_tol; require the residual to sit inside the tolerance band
* rather than accepting an arbitrary sign. */
CHECK(value <= geom_tol && value >= -geom_tol,
"grazing entry F within geometric tolerance");
}
}
/* Linear (a == 0) entry: a growing sphere whose radius rate cancels the
* relative closing speed, so qq == rr^2 and the quadratic degenerates. The
* stable solver must still take the smallest positive root. The fixture's
* sample() reports the consistent radius R(t) = 10 - t, i.e. R(s) = 10 + s
* along the past parameter s = -t, so the contact point is on the true
* ruled-surface boundary. */
static void test_linear_a_zero_entry(void) {
SyntheticContext context = {.vx = 0.0,
.accel = 0.0,
.radius = 10.0,
.radius_rate = -1.0, /* R(t) = 10 - t */
.valid_t_min = -1.0e30,
.constant = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState camera = flat_observer(100.0, 0.0, 0.0);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &camera, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"linear a~0 entry");
CHECK(fabs(route.activate_t + 45.0) < 1e-12, "linear entry time");
CHECK(fabs(route.x[0] - 55.0) < 1e-12 && fabs(route.x[1]) < 1e-12 &&
fabs(route.x[2]) < 1e-12,
"linear entry position");
}
/* Large-coordinate-time cancellation: the long-double closed-form root is
* accurate in the frame, but the entry state reconstructed in double at a huge
* t0 loses the sub-ULP part of the event and lands far outside the geometric
* ULP band (F ~ 0.3 >> tol). The common fallback must repropagate from the
* original camera, localize the first entry numerically, and return a
* strict-inside endpoint (F < 0) while preserving the camera direction Pi and
* reference L exactly. The fixture is a legitimate constant-velocity
* worldtube, not a nonlinearity injection. */
static void test_fallback_reconstruction_cancellation(void) {
SyntheticContext context = {.vx = 0x1.999999999999ap-4, /* 0.1 */
.accel = 0.0,
.radius = 10.0,
.radius_rate = 0.0,
.valid_t_min = -1.0e30,
.constant = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const double t0 = 1.0e15;
/* Exactly 0.1 * 1e15 + 100.123456789, pinned as a hex literal. The offset
* is not aligned to the t0 ULP, so activate_t = t0 - s rounds and the
* reconstructed boundary residual exceeds the tolerance band. */
const double camera_x = 0x1.6bcc41e901908p+46;
ObserverState observer = flat_observer(camera_x, 0.0, 0.0);
observer.coordinate_time = t0;
const double direction[3] = {-1.0, 0.0, 0.0};
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &observer, direction, &route) ==
ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"cancellation fallback still produces an entry");
CHECK(route.entry_fallback_evaluations > 0,
"cancellation entry used the common fallback");
CHECK(route.failure_reason == RAY_REASON_NONE,
"successful fallback has no failure reason");
double value;
CHECK(asymptotic_worldtube_value(&source, route.end_id, route.activate_t,
route.x, &value) == 0 &&
value <= 0.0,
"fallback entry state is inside the worldtube");
MetricData metric;
GeodesicRayState camera_state;
CHECK(spacetime_eval(&source, t0, observer.coordinate_position, &metric) ==
0 &&
geodesic_initialize_past_ray_metric(&metric, &observer, direction,
&camera_state) == 0,
"cancellation camera state");
for (int i = 0; i < 3; ++i)
CHECK(route.Pi[i] == camera_state.Pi[i],
"fallback preserves the entry direction exactly");
CHECK(route.log_alpha_p0_camera == camera_state.log_alpha_p0,
"fallback preserves the camera reference L exactly");
}
static void test_accelerated_worldtube_unsupported(void) {
/* A genuinely accelerating (non-constant velocity) worldtube has no strict
* relative-motion interval bound, so the route is explicitly unsupported.
* Its former finite-history branch is covered by the constant and
* piecewise-constant history tests instead. */
SyntheticContext context = {.vx = 0.0, .accel = 0.02, .radius = 20.0,
.valid_t_min = -1.0e30, .constant = 0};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState camera = flat_observer(100.0, 0.0, 0.0);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &camera, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_UNSUPPORTED,
"accelerated worldtube route is unsupported");
}
static void test_piecewise_segment_entry(void) {
/* The two-segment motion is piecewise constant, so velocity_constant == 1
* per segment and the closed quadratic path must still find the entry in
* the second segment (the analytic segmented first-entry case). */
SyntheticContext context = {.vx = 0.0,
.accel = 0.0,
.radius = 20.0,
.valid_t_min = -1.0e30,
.constant = 1,
.segment_t = -50.0,
.has_segment = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &context};
const ObserverState camera = flat_observer(100.0, 0.0, 0.0);
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &camera, (double[]){-1.0, 0.0, 0.0},
&route) == ASYMPTOTIC_OK &&
route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"piecewise cross-segment entry");
CHECK(route.activate_t < context.segment_t,
"entry lies past the motion-segment boundary");
CHECK(fabs(route.activate_t + 65.0) < 1e-6, "cross-segment entry time");
double value;
CHECK(asymptotic_worldtube_value(&source, route.end_id, route.activate_t,
route.x, &value) == 0 &&
fabs(value) <= 1e-13 * 20.0 * 20.0,
"cross-segment entry on worldtube");
}
static void test_ray_pool_lifecycle(void) {
SpacetimeSource source = {0};
CHECK(spacetime_create_minkowski(&source, 10.0) == 0, "create minkowski");
const ObserverState observer = flat_observer(50.0, 0.0, 0.0);
RayPool pool;
CHECK(ray_pool_init(&pool, 2) == 0, "pool init");
CHECK(ray_pool_append(&pool, &observer, (double[]){-1.0, 0.0, 0.0}, 0, 0) == 0,
"append hit");
CHECK(ray_pool_append(&pool, &observer, (double[]){1.0, 0.0, 0.0}, 0, 1) == 0,
"append miss");
ray_pool_preroute(&pool, &source);
CHECK(pool.status[0] == RAY_POOL_PENDING &&
pool.activate_t[0] < observer.coordinate_time - 1.0,
"entry ray stays pending until entry time");
CHECK(pool.status[1] == RAY_POOL_TERMINATED &&
pool.endpoint[1].outcome == RAY_OUTCOME_ESCAPED,
"miss ray escapes during pre-route");
MetricSlab *early = NULL;
CHECK(spacetime_load_slab(&source, -20.0, -30.0, &early) == 0, "early slab");
ray_pool_activate_in_time_range(&pool, early);
CHECK(pool.status[0] == RAY_POOL_PENDING, "entry ray not active early");
spacetime_free_slab(early);
MetricSlab *covering = NULL;
CHECK(spacetime_load_slab(&source, 0.0, -100.0, &covering) == 0,
"covering slab");
ray_pool_activate_in_time_range(&pool, covering);
CHECK(pool.status[0] == RAY_POOL_ACTIVE &&
fabs(pool.t[0] - pool.activate_t[0]) < 1e-30,
"entry ray activates at entry time");
spacetime_free_slab(covering);
ray_pool_destroy(&pool);
spacetime_destroy(&source);
}
static void test_zero_discriminant_is_not_miss(void) {
SpacetimeSource source;
CHECK(spacetime_create_minkowski(&source, 1.0) == 0,
"zero-discriminant source");
const ObserverState observer = flat_observer(1e10, 0.5, 0.0);
AsymptoticRoute route;
/* Forming c = 1e20 + 0.25 - 1 loses the transverse contribution even in
* 80-bit arithmetic; b*b - 4*a*c then rounds to zero despite a real entry. */
CHECK(asymptotic_route_camera(&source, &observer,
(double[]){-1.0, 0.0, 0.0}, &route) ==
ASYMPTOTIC_OK && route.kind == ASYMPTOTIC_ROUTE_ENTRY &&
route.entry_fallback_evaluations > 0,
"rounded zero discriminant uses entry fallback, not escape");
double value = 0.0;
CHECK(asymptotic_worldtube_value(&source, 0, route.activate_t, route.x,
&value) == ASYMPTOTIC_OK && value < 0.0,
"zero-discriminant fallback produces actual inside state");
const ObserverState tangent = flat_observer(1e10, 1.0, 0.0);
CHECK(asymptotic_route_camera(&source, &tangent,
(double[]){-1.0, 0.0, 0.0}, &route) ==
ASYMPTOTIC_OK && route.kind == ASYMPTOTIC_ROUTE_ESCAPED,
"fixed transverse coordinate independently certifies exact tangency");
spacetime_destroy(&source);
}
static void test_positive_reconstructed_minimum_is_not_miss(void) {
SyntheticContext ctx = {.vx = 0.1, .radius = 10.0, .constant = 1};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &ctx};
ObserverState observer = flat_observer(0x1.6bcc41e901904p+46,
0x1.3ffffde7210bfp+3, 0.0);
observer.coordinate_time = 1e15;
const double parameter = 0x1.bca8814065f1ep+6;
const double witness[3] = {observer.coordinate_position[0] - parameter,
observer.coordinate_position[1], 0.0};
double value = 0.0;
CHECK(asymptotic_worldtube_value(&source, 0,
observer.coordinate_time - parameter,
witness, &value) == ASYMPTOTIC_OK && value < 0,
"strict-inside witness exists despite positive reconstructed minimum");
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &observer,
(double[]){-1.0, 0.0, 0.0}, &route) ==
ASYMPTOTIC_INVALID &&
route.failure_reason == RAY_REASON_ENTRY_UNCONFIRMED,
"positive probe without a miss certificate fails explicitly");
RayPool pool;
CHECK(ray_pool_init(&pool, 1) == 0, "ambiguous entry pool");
CHECK(ray_pool_append(&pool, &observer, (double[]){-1.0, 0.0, 0.0},
0, 0) == 0, "ambiguous entry ray");
ray_pool_preroute(&pool, &source);
CHECK(pool.status[0] == RAY_POOL_FAILED &&
pool.endpoint[0].outcome == RAY_OUTCOME_INCOMPLETE &&
pool.endpoint[0].reason == RAY_REASON_ENTRY_UNCONFIRMED,
"pool propagates unconfirmed entry instead of fabricating escape");
ray_pool_destroy(&pool);
}
static void test_translated_frame_cannot_certify_miss(void) {
SyntheticContext ctx = {.radius = 1.0, .constant = 1,
.valid_t_min = -1e100,
.frame_origin = {0.0, 1e10, 0.0}};
SpacetimeSource source = {.ops = &synthetic_ops, .context = &ctx};
const ObserverState observer = flat_observer(1e10, 1.0 - 0x1p-22, 0.0);
double value = 0.0;
const double witness[3] = {0.0, observer.coordinate_position[1], 0.0};
CHECK(asymptotic_worldtube_value(&source, 0, -1e10, witness, &value) ==
ASYMPTOTIC_OK && value < 0.0,
"original untranslated trajectory has an inside witness");
AsymptoticRoute route;
CHECK(asymptotic_route_camera(&source, &observer,
(double[]){-1.0, 0.0, 0.0}, &route) ==
ASYMPTOTIC_INVALID &&
route.failure_reason == RAY_REASON_ENTRY_UNCONFIRMED,
"lossy translated frame must not certify a miss");
ctx.frame_origin[1] = 0.0;
CHECK(asymptotic_route_camera(&source, &observer,
(double[]){-1.0, 0.0, 0.0}, &route) ==
ASYMPTOTIC_OK && route.kind == ASYMPTOTIC_ROUTE_ENTRY,
"same unshifted trajectory confirms an entry");
}
int main(void) {
test_fixed_sphere();
test_large_radius_quadratic();
test_round_trip();
test_moving_sphere();
test_grazing_production_entries();
test_linear_a_zero_entry();
test_fallback_reconstruction_cancellation();
test_zero_discriminant_is_not_miss();
test_positive_reconstructed_minimum_is_not_miss();
test_translated_frame_cannot_certify_miss();
test_accelerated_worldtube_unsupported();
test_piecewise_segment_entry();
test_boundary_semantics_minkowski();
test_nonconstant_route_unsupported();
test_negative_radius_root_guard();
test_source_finalize();
test_motion_segment_domain();
test_schwarzschild_sample_failures();
test_end_protocol_error();
test_advance_worldtube_failure_reasons();
test_nonconstant_preroute_unsupported();
test_piecewise_constant_history_hole();
test_interior_history_exhaustion();
test_interior_crossing_bisection_failure();
test_ray_pool_lifecycle();
if (failures == 0)
puts("asymptotic regression passed");
else
fprintf(stderr, "%d asymptotic regression failures\n", failures);
return failures == 0 ? 0 : 1;
}