diff --git a/engine/sim/event.cpp b/engine/sim/event.cpp index 84fc92fc426..824cfcba540 100644 --- a/engine/sim/event.cpp +++ b/engine/sim/event.cpp @@ -14,8 +14,8 @@ event_t::event_t( sim_t& s, actor_t* a ) : _sim( s ), next( nullptr ), - time( timespan_t::zero() ), - reschedule_time( timespan_t::zero() ), + time( 0_ms ), + reschedule_time( no_reschedule ), id( 0 ), canceled( false ), recycled( false ), @@ -48,11 +48,12 @@ void* event_t::operator new( std::size_t size, sim_t& sim ) void event_t::reschedule( timespan_t delta_time ) { + id = ++_sim.event_mgr.global_event_id; delta_time += _sim.event_mgr.current_time; if ( _sim.debug ) { - if ( reschedule_time == timespan_t::zero() ) + if ( reschedule_time == no_reschedule ) { _sim.print_debug("Rescheduling event {} from {} to {}", *this, time, delta_time ); diff --git a/engine/sim/event.hpp b/engine/sim/event.hpp index 79ef68504a6..fe4048b0a94 100644 --- a/engine/sim/event.hpp +++ b/engine/sim/event.hpp @@ -44,6 +44,8 @@ constexpr unsigned next_power_of_two( unsigned v ) // (4) create events through make_event method struct event_t : private noncopyable { + static constexpr timespan_t no_reschedule = -1_ms; + sim_t& _sim; event_t* next; timespan_t time; @@ -70,7 +72,7 @@ struct event_t : private noncopyable schedule( delta_time ); } - timespan_t occurs() const { return ( reschedule_time != timespan_t::zero() ) ? reschedule_time : time; } + timespan_t occurs() const { return ( reschedule_time != no_reschedule ) ? reschedule_time : time; } timespan_t remains() const; void schedule( timespan_t delta_time ); diff --git a/engine/sim/event_manager.cpp b/engine/sim/event_manager.cpp index 3dfd9915c7f..bb110e745d0 100644 --- a/engine/sim/event_manager.cpp +++ b/engine/sim/event_manager.cpp @@ -17,8 +17,8 @@ event_manager_t::event_manager_t( sim_t* s ) total_events_processed( 0 ), max_events_remaining( 0 ), timing_slice( 0 ), - global_event_id( 1 ), // start at 1, so we can identify event -> id == 0 - // meaning a unscheduled event. + global_event_id( 0 ), // event->id == 0 represents an unscheduled event, + // make sure to use preincrement when assigning event ids timing_wheel(), recycled_event_list( nullptr ), wheel_seconds( 0 ), @@ -26,7 +26,7 @@ event_manager_t::event_manager_t( sim_t* s ) wheel_mask( 0 ), wheel_shift( 5 ), wheel_granularity( 0.0 ), - wheel_time( timespan_t::zero() ), + wheel_time( 0_ms ), event_stopwatch(), #ifndef NDEBUG max_events( 0U ), @@ -114,20 +114,21 @@ void event_manager_t::recycle_event( event_t* e ) void event_manager_t::add_event( event_t* e, timespan_t delta_time ) { assert( e -> next == nullptr ); - e->id = ++global_event_id; + if ( e->id == 0 ) + e->id = ++global_event_id; - if ( delta_time < timespan_t::zero() ) - delta_time = timespan_t::zero(); + if ( delta_time < 0_ms ) + delta_time = 0_ms; if ( delta_time > wheel_time ) { - e->time = current_time + wheel_time - timespan_t::from_seconds( 1 ); + e->time = current_time + wheel_time - 1_s; e->reschedule_time = current_time + delta_time; } else { e->time = current_time + delta_time; - e->reschedule_time = timespan_t::zero(); + e->reschedule_time = event_t::no_reschedule; } // Determine the timing wheel position to which the event will belong @@ -141,8 +142,10 @@ void event_manager_t::add_event( event_t* e, timespan_t delta_time ) unsigned traversed = 0; #endif + // Find the first event p (= *prev) for which (p->time, p->id) > (e->time, e->id) while ( ( *prev ) && - ( *prev )->time <= e->time ) // Find position in the list + ( ( *prev )->time < e->time || + ( ( *prev )->time == e->time && ( *prev )->id <= e->id ) ) ) { prev = &( ( *prev )->next ); #ifdef EVENT_QUEUE_DEBUG @@ -256,7 +259,7 @@ bool event_manager_t::execute() { sim->print_debug( "Canceled event: {}", *e ); } - else if ( e->reschedule_time > e->time ) + else if ( e->reschedule_time != event_t::no_reschedule ) { reschedule_event( e ); continue; @@ -394,7 +397,7 @@ void event_manager_t::reset() timing_slice = 0; global_event_id = 0; canceled = false; - current_time = timespan_t::zero(); + current_time = 0_ms; } // event_manager_t::merge ===================================================