|
| 1 | +// Copyright 2009-2025 NTESS. Under the terms |
| 2 | +// of Contract DE-NA0003525 with NTESS, the U.S. |
| 3 | +// Government retains certain rights in this software. |
| 4 | +// |
| 5 | +// Copyright (c) 2009-2025, NTESS |
| 6 | +// All rights reserved. |
| 7 | +// |
| 8 | +// This file is part of the SST software package. For license |
| 9 | +// information, see the LICENSE file in the top level directory of the |
| 10 | +// distribution. |
| 11 | + |
| 12 | +#include "sst_config.h" |
| 13 | + |
| 14 | +#include "sst/core/impl/oneshotManager.h" |
| 15 | + |
| 16 | +#include "sst/core/simulation_impl.h" |
| 17 | +#include "sst/core/timeVortex.h" |
| 18 | + |
| 19 | +namespace SST::Core { |
| 20 | + |
| 21 | +void |
| 22 | +OneShot::execute() |
| 23 | +{ |
| 24 | + // Call all the handlers. Delete each one once after calling. |
| 25 | + // The handlers are guaranteed not to be shared. |
| 26 | + for ( auto* x : handlers ) { |
| 27 | + (*x)(); |
| 28 | + delete x; |
| 29 | + } |
| 30 | + |
| 31 | + manager->oneshotCallback(time, this); |
| 32 | +} |
| 33 | + |
| 34 | + |
| 35 | +OneShotManager::OneShotManager(Simulation_impl* sim) : |
| 36 | + sim_(sim) |
| 37 | +{} |
| 38 | + |
| 39 | +OneShotManager::~OneShotManager() |
| 40 | +{ |
| 41 | + // Need to delete all the Handlers |
| 42 | + for ( auto& list : handler_vector_map_ ) { |
| 43 | + for ( auto* item : list.second.first ) { |
| 44 | + delete item; |
| 45 | + } |
| 46 | + } |
| 47 | +} |
| 48 | + |
| 49 | +void |
| 50 | +OneShotManager::registerHandlerBase(SimTime_t trigger_time, int priority, bool relative, OneShot::HandlerBase* handler) |
| 51 | +{ |
| 52 | + |
| 53 | + // Check to make sure this isn't in the past |
| 54 | + TimeStamp_t curr_time = std::make_pair(sim_->getCurrentSimCycle(), sim_->getCurrentPriority()); |
| 55 | + TimeStamp_t trig_time = std::make_pair(trigger_time + (relative ? sim_->getCurrentSimCycle() : 0), priority); |
| 56 | + |
| 57 | + if ( trig_time <= curr_time ) { |
| 58 | + // Emit warning and ignore request |
| 59 | + sim_->getSimulationOutput().output( |
| 60 | + "WARNING: Trying to register a OneShot for a time in the past, ignoring request\n"); |
| 61 | + return; |
| 62 | + } |
| 63 | + |
| 64 | + // Get the handler list for the specified time stamp. If it's not |
| 65 | + // already there, it will be created. |
| 66 | + std::pair<OneShot::HandlerList_t, bool>& map_item = handler_vector_map_[trig_time]; |
| 67 | + |
| 68 | + // Push handler onto the list |
| 69 | + map_item.first.push_back(handler); |
| 70 | + |
| 71 | + // Check to see if anything needs to be scheduled |
| 72 | + scheduleNextOneShot(); |
| 73 | +} |
| 74 | + |
| 75 | +void |
| 76 | +OneShotManager::oneshotCallback(TimeStamp_t time, OneShot* oneshot) |
| 77 | +{ |
| 78 | + // Remove the data for this time, schedule the next time and |
| 79 | + // delete the OneShot. |
| 80 | + handler_vector_map_.erase(time); |
| 81 | + delete oneshot; |
| 82 | + |
| 83 | + scheduleNextOneShot(); |
| 84 | +} |
| 85 | + |
| 86 | +void |
| 87 | +OneShotManager::scheduleNextOneShot() |
| 88 | +{ |
| 89 | + // Get next event to schdule. Iterator maps as follows: |
| 90 | + // it.first : TimeStamp_t : trigger time |
| 91 | + // it.second.first = HandlerList_t : list of handlers to call |
| 92 | + // it.second.second = bool : scheduled |
| 93 | + auto it = handler_vector_map_.begin(); |
| 94 | + |
| 95 | + // If there are no events, return |
| 96 | + if ( it == handler_vector_map_.end() ) return; |
| 97 | + |
| 98 | + // If first event is already scheduled, nothing to do |
| 99 | + if ( it->second.second ) return; |
| 100 | + |
| 101 | + // Not yet scheduled, create a OneShot and insert into TimeVortex |
| 102 | + TimeStamp_t t = it->first; |
| 103 | + |
| 104 | + OneShot* oneshot = new OneShot(t, this, it->second.first); |
| 105 | + sim_->timeVortex->insert(oneshot); |
| 106 | + it->second.second = true; |
| 107 | +} |
| 108 | + |
| 109 | +} // namespace SST::Core |
0 commit comments