teleport_gate gate;
u32 node_id;
- u32 passed_version; /* Incremented on every teleport */
+
+ struct route_timing
+ {
+ u32 version; /* Incremented on every teleport */
+ double time;
+ }
+ timing;
}
*gates;
struct route_collector
{
- double time_passed; /* When did we last pass this? */
+ struct route_timing timing;
}
*collectors;
}
}
+/*
+ * Get a list of node ids in stack, and return how many there is
+ */
static u32 world_routes_get_path( u32 starter, u32 stack[64] )
{
struct subworld_routes *r = subworld_routes();
return 0;
}
-static void world_routes_verify_run( u32 route, double new_pass_time )
+/*
+ * Will scan the whole run for two things;
+ * 1: we set a new record for the total, complete loop around the course
+ * 2: the time of each segment will be recorded into the data buffer
+ * (not implemented: TODO)
+ */
+static void world_routes_verify_run( u32 route )
{
struct subworld_routes *r = subworld_routes();
/*
* we only care about gates that ref gates, so shuffle down the array
*/
- u32 gates[64];
- u32 sj = 0;
+ struct route_timing *timings[64];
+ u32 sj = 0, maxv = 0, begin = 0;
for( u32 i=0; i<si; i++ )
- if( r->nodes[stack[i]].special_type == k_route_special_type_gate )
- gates[sj ++] = r->nodes[stack[i]].special_id;
-
- /*
- * run versions & times must always ASCEND apart from exactly once, where
- * the tail connects to the head
- */
-
- vg_info("Verifying run (%u)\n", route);
-
- u32 offset = 0xffffffff;
-
- vg_info( " ver: %u\n", r->current_run_version );
-
+ {
+ if( r->nodes[stack[i]].special_type == k_route_special_type_collector )
+ timings[sj ++] = &r->collectors[r->nodes[stack[i]].special_id].timing;
+ else if( r->nodes[stack[i]].special_type == k_route_special_type_gate )
+ timings[sj ++] = &r->gates[r->nodes[stack[i]].special_id].timing;
+ }
+
for( u32 i=0; i<sj; i++ )
{
- struct route_gate *pa = &r->gates[gates[i]];
- u32 na = r->nodes[r->nodes[pa->node_id].next[0]].special_id;
- struct route_collector *pca = &r->collectors[ na ];
-
- if( pa->passed_version != r->current_run_version )
- {
- vg_info( " [%u]: %u (%f)\n", gates[i], pa->passed_version,
- pca->time_passed );
- }
- else
+ if( timings[i]->version > maxv )
{
- vg_info( " [%u]: %u (%f & %f)\n", gates[i], pa->passed_version,
- pca->time_passed,
- new_pass_time );
- offset = i;
+ maxv = timings[i]->version;
+ begin = i;
}
}
- if( offset == 0xffffffff )
- {
- /* If we don't find the emitter we passed through, we've only just
- * started this route, so no blocks need to be emmited */
- return;
- }
-
+ vg_info( "== begin verification (%u) ==\n", route );
+ vg_info( " current version: %u\n", r->current_run_version );
+
+ int verified = 0;
+ if( timings[begin]->version == r->current_run_version )
+ verified = 1;
+
double lap_time = 0.0;
- int verify_count = 0;
for( u32 i=0; i<sj; i++ )
{
- u32 j = i+offset;
- struct route_gate *pa = &r->gates[gates[j%sj]],
- *pb = &r->gates[gates[(j+1) % sj]];
-
- u32 na = r->nodes[r->nodes[pa->node_id].next[0]].special_id,
- nb = r->nodes[r->nodes[pb->node_id].next[0]].special_id;
-
- struct route_collector *pca = &r->collectors[ na ],
- *pcb = &r->collectors[ nb ];
+ u32 j = (sj+begin-i-1) % sj,
+ j1 = (j+1) % sj;
double diff = 0.0;
-
- /* Verifying the path: either of this conditions must be true */
- int verified = 0;
- if( pa->passed_version == r->current_run_version )
- {
- /* The version should drop back down to pa+1-sj */
- }
- else
+
+ if( i<sj-1 )
{
- /* The version should be pa+1 */
+ /* j1v should equal jv+1 */
+ if( timings[j1]->version == timings[j]->version+1 )
+ {
+ diff = timings[j1]->time - timings[j]->time;
+ lap_time += diff;
+ }
+ else
+ verified = 0;
}
- verify_count += verified;
-
- if( pb->passed_version == r->current_run_version )
- {
- /* we need to use new val */
- diff = new_pass_time - pca->time_passed;
- vg_info( " LOOP %f\n", diff );
- }
+ if( verified )
+ vg_success( " [ %u %f ] %f\n", timings[j1]->time,
+ timings[j1]->version, diff );
else
- {
- diff = pcb->time_passed - pca->time_passed;
- vg_info( " %f\n", diff );
- }
-
- lap_time += diff;
+ vg_warn( " [ %u %f ]\n", timings[j1]->time, timings[j1]->version );
}
- /* Verify count is how many blocks we want to emit */
+ if( verified )
+ vg_success( " NEW LAP TIME: %f\n", lap_time );
+ else
+ vg_info( " ctime: %f\n", lap_time );
}
+/*
+ * When going through a gate this is called for bookkeeping purposes
+ */
static void world_routes_activate_gate( u32 id )
{
struct subworld_routes *r = subworld_routes();
struct route_collector *rc = &r->collectors[ pdest->special_id ];
r->active_gate = id;
- rg->passed_version = r->current_run_version;
-
- vg_info( "collector updated: %u\n", pdest->special_id );
-
+ rg->timing.version = r->current_run_version;
+ rg->timing.time = vg_time;
for( u32 i=0; i<r->route_count; i++ )
{
struct route *route = &r->routes[i];
{
if( pdest->route_ids[j] == i )
{
- world_routes_verify_run( i, vg_time );
+ world_routes_verify_run( i );
route->active = 1;
break;
}
}
}
- rc->time_passed = vg_time;
+ r->current_run_version ++;
+
+ rc->timing.version = r->current_run_version;
+ rc->timing.time = vg_time;
r->current_run_version ++;
}
*uid = 0xffffffff;
}
+/*
+ * Create the strips of colour that run through the world along course paths
+ */
static void world_routes_gen_meshes(void)
{
struct subworld_routes *r = subworld_routes();
static void world_routes_register(void)
{
+ struct subworld_routes *r = subworld_routes();
+ r->current_run_version = 2;
+
shader_route_register();
}
struct route_gate *rg = &r->gates[r->gate_count];
rg->node_id = r->node_count;
- rg->passed_version = 0xffffffff;
+ rg->timing.time = 0.0;
+ rg->timing.version = 0;
v3_copy( pnode->co, rg->gate.co[0] );
v3_copy( pother->co, rg->gate.co[1] );
1, sizeof( struct route_collector ));
struct route_collector *rc = &r->collectors[r->collector_count];
- rc->time_passed = 0.0;
+ rc->timing.time = 0.0;
+ rc->timing.version = 0;
rn->special_type = k_route_special_type_collector;
rn->special_id = r->collector_count;