From ef07558bddc861bf275fde8a9b7359b4a76533e0 Mon Sep 17 00:00:00 2001 From: Goober5000 Date: Tue, 27 Dec 2022 00:30:39 -0500 Subject: [PATCH] add checks for Locked_sexp_* These are various sanity checks that the Locked_sexp values are properly initialized when we expect them to be. --- code/mission/missionparse.cpp | 15 +++++++++++++++ code/parse/sexp.cpp | 20 +++++++++++++++++++- code/ship/ship.cpp | 2 ++ fred2/FictionViewerDlg.cpp | 2 ++ fred2/briefingeditordlg.cpp | 2 ++ fred2/campaigntreeview.cpp | 6 ++++++ fred2/campaigntreewnd.cpp | 2 ++ fred2/freddoc.cpp | 2 ++ fred2/fredview.cpp | 2 ++ fred2/initialstatus.cpp | 6 ++++++ fred2/management.cpp | 2 ++ fred2/missionsave.cpp | 2 ++ fred2/reinforcementeditordlg.cpp | 2 ++ fred2/wing.cpp | 2 ++ fred2/wing_editor.cpp | 4 ++++ 15 files changed, 70 insertions(+), 1 deletion(-) diff --git a/code/mission/missionparse.cpp b/code/mission/missionparse.cpp index ddc935c9c60..123cef08d95 100644 --- a/code/mission/missionparse.cpp +++ b/code/mission/missionparse.cpp @@ -1065,6 +1065,8 @@ void parse_player_info2(mission *pm) void parse_cutscenes(mission *pm) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + if (optional_string("#Cutscenes")) { mission_cutscene scene; @@ -1367,6 +1369,8 @@ void parse_music(mission *pm, int flags) */ void parse_fiction(mission * /*pm*/) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + if (optional_string("#Fiction Viewer")) { bool fiction_viewer_loaded = false; @@ -1468,6 +1472,8 @@ void parse_cmd_briefs(mission *pm) */ void parse_briefing(mission * /*pm*/, int flags) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int nt, i, j, stage_num = 0, icon_num = 0; brief_stage *bs; brief_icon *bi; @@ -3012,6 +3018,8 @@ extern int parse_warp_params(const WarpParams *inherit_from, WarpDirection direc */ int parse_object(mission *pm, int /*flag*/, p_object *p_objp) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int i; char name[NAME_LENGTH]; ship_info *sip; @@ -7075,13 +7083,18 @@ bool sexp_is_locked_false(int node) { // dunno why these are different, but they are if (Fred_running) + { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); return (node == Locked_sexp_false); + } else return (Sexp_nodes[node].value == SEXP_KNOWN_FALSE); } void set_cue_to_false(int *cue) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + free_sexp2(*cue); *cue = Locked_sexp_false; } @@ -8563,6 +8576,8 @@ int get_warp_in_pos(vec3d *pos, object *objp, float x, float y, float z) */ void mission_bring_in_support_ship( object *requester_objp ) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + vec3d center, warp_in_pos; p_object *pobj; ship *requester_shipp; diff --git a/code/parse/sexp.cpp b/code/parse/sexp.cpp index 9e04e5251f0..d5867ff996a 100644 --- a/code/parse/sexp.cpp +++ b/code/parse/sexp.cpp @@ -1424,10 +1424,15 @@ int alloc_sexp(const char *text, int type, int subtype, int first, int rest) int sexp_const = get_operator_const(text); if ((sexp_const == OP_TRUE) && (type == SEXP_ATOM) && (subtype == SEXP_ATOM_OPERATOR)) + { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); return Locked_sexp_true; - + } else if ((sexp_const == OP_FALSE) && (type == SEXP_ATOM) && (subtype == SEXP_ATOM_OPERATOR)) + { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); return Locked_sexp_false; + } node = find_free_sexp(); @@ -1526,6 +1531,8 @@ void sexp_mark_persistent(int n) return; } + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + // total hack because of the true/false locked sexps -- we should make those persistent as well if ( (n == Locked_sexp_true) || (n == Locked_sexp_false) ){ return; @@ -1548,6 +1555,8 @@ void sexp_unmark_persistent(int n) return; } + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + // see sexp_mark_persistent if ( (n == Locked_sexp_true) || (n == Locked_sexp_false) ){ return; @@ -1570,6 +1579,8 @@ int free_one_sexp(int num) Assert(Sexp_nodes[num].type != SEXP_NOT_USED); // make sure it is actually used Assert(!(Sexp_nodes[num].type & SEXP_FLAG_PERSISTENT)); + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + // never free these nodes if ((num == Locked_sexp_true) || (num == Locked_sexp_false)) return 0; @@ -1594,6 +1605,8 @@ int free_sexp(int num, int calling_node) Assert(Sexp_nodes[num].type != SEXP_NOT_USED); // make sure it is actually used Assert(!(Sexp_nodes[num].type & SEXP_FLAG_PERSISTENT)); + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + // never free these nodes if ((num == -1) || (num == Locked_sexp_true) || (num == Locked_sexp_false)) return 0; @@ -4725,6 +4738,7 @@ int get_sexp() } else { const char *message = nullptr; Assert(last != -1); + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); // Locked_sexp_true and Locked_sexp_false are only meant to represent operator // nodes with no arguments, i.e. (true) and (false). If they appear as "bare" @@ -10953,6 +10967,8 @@ int eval_perform_actions(int n, int op_num) bool retval_first; Assert( n >= 0 ); + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + if (op_num == OP_PERFORM_ACTIONS_BOOL_FIRST) { return_cond = CAR(n); @@ -12198,6 +12214,8 @@ int sexp_num_valid_arguments( int n ) if (arg_handler < 0) return 0; + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + // the for-* sexps require special handling: they don't list their arguments explicitly but rather generate them on-the-fly auto op_const = get_operator_const(arg_handler); switch (op_const) diff --git a/code/ship/ship.cpp b/code/ship/ship.cpp index 6d2a8f74f33..0211a9e35f7 100644 --- a/code/ship/ship.cpp +++ b/code/ship/ship.cpp @@ -7355,6 +7355,8 @@ static void ship_set(int ship_index, int objnum, int ship_type) ship_weapon *swp = &shipp->weapons; polymodel *pm = model_get(sip->model_num); + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + Assert(strlen(shipp->ship_name) <= NAME_LENGTH - 1); shipp->ship_info_index = ship_type; shipp->objnum = objnum; diff --git a/fred2/FictionViewerDlg.cpp b/fred2/FictionViewerDlg.cpp index f4ec1df173d..21aecb1778b 100644 --- a/fred2/FictionViewerDlg.cpp +++ b/fred2/FictionViewerDlg.cpp @@ -82,6 +82,8 @@ BOOL FictionViewerDlg::OnInitDialog() void FictionViewerDlg::OnOK() { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + UpdateData(TRUE); // remove whitespace diff --git a/fred2/briefingeditordlg.cpp b/fred2/briefingeditordlg.cpp index f793fad4e9c..db6d3048ccc 100644 --- a/fred2/briefingeditordlg.cpp +++ b/fred2/briefingeditordlg.cpp @@ -927,6 +927,8 @@ void briefing_editor_dlg::OnInsertStage() void briefing_editor_dlg::copy_stage(int from, int to) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + if ((from < 0) || (from >= Briefing->num_stages)) { Briefing->stages[to].text = ""; strcpy_s(Briefing->stages[to].voice, "none.wav"); diff --git a/fred2/campaigntreeview.cpp b/fred2/campaigntreeview.cpp index 2f7dbe0c6d6..483545b2cc2 100644 --- a/fred2/campaigntreeview.cpp +++ b/fred2/campaigntreeview.cpp @@ -749,6 +749,8 @@ void campaign_tree_view::OnLButtonUp(UINT nFlags, CPoint point) int campaign_tree_view::add_link(int from, int to) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + if (Total_links >= MAX_CAMPAIGN_TREE_LINKS) return -1; @@ -892,6 +894,8 @@ DROPEFFECT campaign_tree_view::OnDragOver(COleDataObject* pDataObject, DWORD dwK BOOL campaign_tree_view::OnDrop(COleDataObject* pDataObject, DROPEFFECT dropEffect, CPoint point) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int i, level, pos; cmission *cm; HGLOBAL hGlobal; @@ -999,6 +1003,8 @@ BOOL campaign_tree_view::OnDrop(COleDataObject* pDataObject, DROPEFFECT dropEffe void campaign_tree_view::drop_mission(int m, CPoint point) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + char name[MAX_FILENAME_LEN + 1]; int i, item, level, pos; cmission *cm; diff --git a/fred2/campaigntreewnd.cpp b/fred2/campaigntreewnd.cpp index 7c093bbae5d..96722a3e3cb 100644 --- a/fred2/campaigntreewnd.cpp +++ b/fred2/campaigntreewnd.cpp @@ -305,6 +305,8 @@ void campaign_tree_wnd::OnErrorChecker() int campaign_tree_wnd::error_checker() { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int i, j, z; int mcount[MAX_CAMPAIGN_MISSIONS], true_at[MAX_CAMPAIGN_MISSIONS]; diff --git a/fred2/freddoc.cpp b/fred2/freddoc.cpp index 4e61c451cf4..ab0c507827d 100644 --- a/fred2/freddoc.cpp +++ b/fred2/freddoc.cpp @@ -213,6 +213,8 @@ void CFREDDoc::editor_init_mission() { } bool CFREDDoc::load_mission(const char *pathname, int flags) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + // make sure we're in the correct working directory!!!!!! chdir(Fred_base_dir); diff --git a/fred2/fredview.cpp b/fred2/fredview.cpp index e5ce41f34ef..82cc5d9d487 100644 --- a/fred2/fredview.cpp +++ b/fred2/fredview.cpp @@ -3083,6 +3083,8 @@ int CFREDView::global_error_check_mixed_player_wing(int w) int CFREDView::global_error_check_player_wings(int multi) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int i, z, err; int starting_wing_count[MAX_STARTING_WINGS]; int tvt_wing_count[MAX_TVT_WINGS]; diff --git a/fred2/initialstatus.cpp b/fred2/initialstatus.cpp index e745958fd16..469badaaa71 100644 --- a/fred2/initialstatus.cpp +++ b/fred2/initialstatus.cpp @@ -956,6 +956,8 @@ void initial_status::dock(object *objp, int dockpoint, object *other_objp, int o void initial_status::undock(object *objp1, object *objp2) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + vec3d v; int ship_num, other_ship_num; @@ -1004,6 +1006,8 @@ void initial_status::undock(object *objp1, object *objp2) bool set_cue_to_false(int *cue) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + // if the cue is not false, make it false. Be sure to set all ship editor dialog functions // to update data before and after we modify the cue. if (*cue != Locked_sexp_false) @@ -1057,6 +1061,8 @@ void reset_arrival_to_false(int shipnum, bool reset_wing) // group with a non-false arrival cue void initial_status_mark_dock_leader_helper(object *objp, dock_function_info *infop) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + ship *shipp = &Ships[objp->instance]; int cue_to_check; diff --git a/fred2/management.cpp b/fred2/management.cpp index 49024a82da7..6275c5def5f 100644 --- a/fred2/management.cpp +++ b/fred2/management.cpp @@ -725,6 +725,8 @@ int create_object(vec3d *pos, int waypoint_instance) int create_player(vec3d *pos, matrix *orient, int type) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int obj; if (type == -1){ diff --git a/fred2/missionsave.cpp b/fred2/missionsave.cpp index a04c1b7da6c..8ce1778ae53 100644 --- a/fred2/missionsave.cpp +++ b/fred2/missionsave.cpp @@ -2357,6 +2357,8 @@ int CFred_mission_save::save_events() int CFred_mission_save::save_fiction() { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + if (mission_has_fiction()) { if (Mission_save_format != FSO_FORMAT_RETAIL) { if (optional_string_fred("#Fiction Viewer")) diff --git a/fred2/reinforcementeditordlg.cpp b/fred2/reinforcementeditordlg.cpp index af06e0fa30e..d84443f922b 100644 --- a/fred2/reinforcementeditordlg.cpp +++ b/fred2/reinforcementeditordlg.cpp @@ -180,6 +180,8 @@ int reinforcement_editor_dlg::query_modified() void reinforcement_editor_dlg::OnOK() { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int i, j; save_data(); diff --git a/fred2/wing.cpp b/fred2/wing.cpp index 9c0d0a74606..2cd33f6f215 100644 --- a/fred2/wing.cpp +++ b/fred2/wing.cpp @@ -83,6 +83,8 @@ int check_wing_dependencies(int wing_num) { } int create_wing() { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + char msg[1024]; int i, ship, wing = -1, waypoints = 0, count = 0, illegal_ships = 0; int leader, leader_team; diff --git a/fred2/wing_editor.cpp b/fred2/wing_editor.cpp index 058f23f68c3..4829f568b4d 100644 --- a/fred2/wing_editor.cpp +++ b/fred2/wing_editor.cpp @@ -273,6 +273,8 @@ void wing_editor::OnClose() // initialize everything that update_data_safe() saves. void wing_editor::initialize_data_safe(int full_update) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + int i, enable = TRUE, player_wing = 0, player_enabled = 1; CComboBox *arrival_box, *departure_box; @@ -574,6 +576,8 @@ void wing_editor::initialize_data(int full_update) // Once the error no longer occurs, bypass mode is cleared and data is updated. int wing_editor::update_data(int redraw) { + Assertion(Locked_sexp_true >= 0 && Locked_sexp_false >= 0, "SEXPs are not yet initialized!"); + char *str, old_name[255], buf[512]; int i, z; object *ptr;