From 277fffcb0cac5eeb1ce86ad35a1fc7acd8038ce8 Mon Sep 17 00:00:00 2001 From: gfgtdf Date: Wed, 4 Feb 2015 15:43:26 +0100 Subject: [PATCH] use replay::process_error instead of ERR_REPLAY for OOS since replay::process_error might throw we cannot do this in set_sconext_synced destructor anymore and have to call do_final_checkup() ealier. --- src/actions/move.cpp | 1 + src/actions/undo.cpp | 6 ++++-- src/ai/actions.cpp | 1 + src/play_controller.cpp | 5 ++++- src/playsingle_controller.cpp | 2 +- src/replay.cpp | 1 + src/replay_controller.cpp | 3 ++- src/synced_context.cpp | 24 ++++++++++++++++++------ src/synced_context.hpp | 3 ++- 9 files changed, 34 insertions(+), 12 deletions(-) diff --git a/src/actions/move.cpp b/src/actions/move.cpp index 0ec4230db132..494da5ba491f 100644 --- a/src/actions/move.cpp +++ b/src/actions/move.cpp @@ -1270,6 +1270,7 @@ size_t move_unit_and_record(const std::vector &steps, set_scontext_synced sync; size_t r = move_unit_internal(undo_stack, show_move, interrupted, mover); resources::controller->check_victory(); + sync.do_final_checkup(); return r; } else diff --git a/src/actions/undo.cpp b/src/actions/undo.cpp index 3d8c9cd32e9a..b90f9d1f4ca4 100644 --- a/src/actions/undo.cpp +++ b/src/actions/undo.cpp @@ -929,7 +929,7 @@ bool undo_list::recall_action::redo(int side) if ( msg.empty() ) { recorder.redo(replay_data); replay_data.clear(); - set_scontext_synced sco; + set_scontext_synced sync; recall_unit(id, current_team, loc, from, true, false); // Quick error check. (Abuse of [allow_undo]?) @@ -940,6 +940,7 @@ bool undo_list::recall_action::redo(int side) // undoing this works. route.front() = loc; } + sync.do_final_checkup(); } else { gui::dialog(gui, "", msg, gui::OK_ONLY).show(); return false; @@ -976,7 +977,7 @@ bool undo_list::recruit_action::redo(int side) current_team.set_action_bonus_count(1 + current_team.action_bonus_count()); recorder.redo(replay_data); replay_data.clear(); - set_scontext_synced sco; + set_scontext_synced sync; recruit_unit(u_type, side, loc, from, true, false); // Quick error check. (Abuse of [allow_undo]?) @@ -987,6 +988,7 @@ bool undo_list::recruit_action::redo(int side) // undoing this works. route.front() = loc; } + sync.do_final_checkup(); } else { gui::dialog(gui, "", msg, gui::OK_ONLY).show(); return false; diff --git a/src/ai/actions.cpp b/src/ai/actions.cpp index 460d8630fc7b..4b687c191628 100644 --- a/src/ai/actions.cpp +++ b/src/ai/actions.cpp @@ -292,6 +292,7 @@ void attack_result::do_execute() set_scontext_synced sync; attack_unit_and_advance(attacker_loc_, defender_loc_, attacker_weapon, defender_weapon, true, advancements_); resources::controller->check_victory(); + sync.do_final_checkup(); } else { diff --git a/src/play_controller.cpp b/src/play_controller.cpp index 1219990561bd..7a822513e1cd 100644 --- a/src/play_controller.cpp +++ b/src/play_controller.cpp @@ -382,10 +382,11 @@ void play_controller::maybe_do_init_side(bool is_replay, bool only_visual) { return; } - if(!only_visual){ + if(!only_visual) { recorder.init_side(); set_scontext_synced sync; do_init_side(is_replay); + sync.do_final_checkup(); } else { @@ -529,6 +530,7 @@ void play_controller::finish_side_turn(){ pump().fire("side "+ side_num + " turn end"); pump().fire("side turn " + turn_num + " end"); pump().fire("side " + side_num + " turn " + turn_num + " end"); + sync.do_final_checkup(); } // This is where we refog, after all of a side's events are done. actions::recalculate_fog(player_number_); @@ -551,6 +553,7 @@ void play_controller::finish_turn() const std::string turn_num = str_cast(turn()); pump().fire("turn end"); pump().fire("turn " + turn_num + " end"); + sync.do_final_checkup(); } bool play_controller::enemies_visible() const diff --git a/src/playsingle_controller.cpp b/src/playsingle_controller.cpp index 7f312129a6bd..22a19338299c 100644 --- a/src/playsingle_controller.cpp +++ b/src/playsingle_controller.cpp @@ -251,7 +251,7 @@ boost::optional playsingle_controller::play_scenario_init(end_leve assert(false && "caugh end_turn exception in a bad place... terminating."); std::terminate(); } - + sync.do_final_checkup(); gui_->recalculate_minimap(); } else diff --git a/src/replay.cpp b/src/replay.cpp index 1df775e54970..8c0671b8d75b 100644 --- a/src/replay.cpp +++ b/src/replay.cpp @@ -828,6 +828,7 @@ REPLAY_RETURN do_replay_handle(bool one_move) { set_scontext_synced sync; resources::controller->do_init_side(true); + sync.do_final_checkup(); } } diff --git a/src/replay_controller.cpp b/src/replay_controller.cpp index 963cb0768164..c0eb3911df67 100644 --- a/src/replay_controller.cpp +++ b/src/replay_controller.cpp @@ -372,7 +372,7 @@ void replay_controller::reset_replay() // Scenario initialization. (c.f. playsingle_controller::play_scenario()) fire_preload(); - if(true){ //block for set_scontext_synced + { //block for set_scontext_synced if(recorder.add_start_if_not_there_yet()) { ERR_REPLAY << "inserted missing [start]" << std::endl; @@ -388,6 +388,7 @@ void replay_controller::reset_replay() fire_prestart(); init_gui(); fire_start(true); + sync.do_final_checkup(); } // Since we did not fire the start event, it_is_a_new_turn_ has the wrong value. it_is_a_new_turn_ = true; diff --git a/src/synced_context.cpp b/src/synced_context.cpp index 80dc6ea308ab..6613e38ff0d5 100644 --- a/src/synced_context.cpp +++ b/src/synced_context.cpp @@ -75,7 +75,7 @@ bool synced_context::run_in_synced_context(const std::string& commandname, const use this after recorder.add_synced_command because set_scontext_synced sets the checkup to the last added command */ - set_scontext_synced sco; + set_scontext_synced sync; synced_command::map::iterator it = synced_command::registry().find(commandname); if(it == synced_command::registry().end()) { @@ -95,6 +95,7 @@ bool synced_context::run_in_synced_context(const std::string& commandname, const // this might also be a good point to call resources::controller->check_victory(); // because before for example if someone kills all units during a moveto event they don't loose. resources::controller->check_victory(); + sync.do_final_checkup(); DBG_REPLAY << "run_in_synced_context end\n"; return true; } @@ -389,14 +390,16 @@ void set_scontext_synced::init() synced_context::reset_is_simultaneously(); synced_context::set_last_unit_id(n_unit::id_manager::instance().get_save_id()); + did_final_checkup_ = false; old_checkup_ = checkup_instance; checkup_instance = &*new_checkup_; old_rng_ = random_new::generator; random_new::generator = new_rng_.get(); } -void set_scontext_synced::do_final_checkup() +void set_scontext_synced::do_final_checkup(bool dont_throw) { + assert(!did_final_checkup_); std::stringstream msg; config co; config cn = config_of @@ -422,8 +425,16 @@ void set_scontext_synced::do_final_checkup() if(!msg.str().empty()) { msg << co.debug() << std::endl; - ERR_REPLAY << msg.str() << std::flush; + if(dont_throw) + { + ERR_REPLAY << msg.str() << std::flush; + } + else + { + replay::process_error(msg.str()); + } } + did_final_checkup_ = true; } set_scontext_synced::~set_scontext_synced() @@ -431,9 +442,10 @@ set_scontext_synced::~set_scontext_synced() LOG_REPLAY << "set_scontext_synced:: destructor\n"; assert(synced_context::get_synced_state() == synced_context::SYNCED); assert(checkup_instance == &*new_checkup_); - - do_final_checkup(); - + if(!did_final_checkup_) + { + do_final_checkup(true); + } random_new::generator = old_rng_; synced_context::set_synced_state(synced_context::UNSYNCED); diff --git a/src/synced_context.hpp b/src/synced_context.hpp index becb351145f4..1fd00ac67aea 100644 --- a/src/synced_context.hpp +++ b/src/synced_context.hpp @@ -149,7 +149,7 @@ class set_scontext_synced set_scontext_synced(int num); ~set_scontext_synced(); int get_random_calls(); - void do_final_checkup(); + void do_final_checkup(bool dont_throw = false); private: //only called by contructors. void init(); @@ -159,6 +159,7 @@ class set_scontext_synced checkup* old_checkup_; boost::scoped_ptr new_checkup_; events::command_disabler disabler_; + bool did_final_checkup_; }; /*