From bb0dd7b8dc05f7791b1a23d60dc0585db579da82 Mon Sep 17 00:00:00 2001 From: Lemongrass3110 Date: Wed, 24 Jan 2018 19:30:05 +0100 Subject: [PATCH] Fixed mapserver crash on script command warp (#2766) Fixes #2765 Thanks to @LunarSHINING --- src/map/npc.cpp | 4 ++-- src/map/npc.hpp | 2 +- src/map/pc.cpp | 16 ++++++++++++++-- 3 files changed, 17 insertions(+), 5 deletions(-) diff --git a/src/map/npc.cpp b/src/map/npc.cpp index b78e7cfe77..ca9c2d7104 100644 --- a/src/map/npc.cpp +++ b/src/map/npc.cpp @@ -304,7 +304,7 @@ int npc_rr_secure_timeout_timer(int tid, unsigned int tick, int id, intptr_t dat /*========================================== * Dequeue event and add timer for execution (100ms) *------------------------------------------*/ -int npc_event_dequeue(struct map_session_data* sd) +int npc_event_dequeue(struct map_session_data* sd,bool free_script_stack) { nullpo_ret(sd); @@ -314,7 +314,7 @@ int npc_event_dequeue(struct map_session_data* sd) clif_clearunit_single(sd->npc_id, CLR_OUTSIGHT, sd->fd); sd->state.using_fake_npc = 0; } - if (sd->st) { + if (free_script_stack&&sd->st) { script_free_state(sd->st); sd->st = NULL; } diff --git a/src/map/npc.hpp b/src/map/npc.hpp index d64376d543..9e92d5fa2a 100644 --- a/src/map/npc.hpp +++ b/src/map/npc.hpp @@ -1123,7 +1123,7 @@ enum npce_event : uint8 { }; struct view_data* npc_get_viewdata(int class_); int npc_chat_sub(struct block_list* bl, va_list ap); -int npc_event_dequeue(struct map_session_data* sd); +int npc_event_dequeue(struct map_session_data* sd,bool free_script_stack=true); int npc_event(struct map_session_data* sd, const char* eventname, int ontouch); int npc_touch_areanpc(struct map_session_data* sd, int16 m, int16 x, int16 y); int npc_touch_areanpc2(struct mob_data *md); // [Skotlex] diff --git a/src/map/pc.cpp b/src/map/pc.cpp index e07802e1dd..6e6001f2e0 100755 --- a/src/map/pc.cpp +++ b/src/map/pc.cpp @@ -5524,12 +5524,19 @@ enum e_setpos pc_setpos(struct map_session_data* sd, unsigned short mapindex, in { uint32 ip; uint16 port; + struct script_state *st; + //if can't find any map-servers, just abort setting position. if(!sd->mapindex || map_mapname2ipport(mapindex,&ip,&port)) return SETPOS_NO_MAPSERVER; - if (sd->npc_id) - npc_event_dequeue(sd); + if (sd->npc_id){ + npc_event_dequeue(sd,false); + st = sd->st; + }else{ + st = nullptr; + } + npc_script_event(sd, NPCE_LOGOUT); //remove from map, THEN change x/y coordinates unit_remove_map_pc(sd,clrtype); @@ -5543,6 +5550,11 @@ enum e_setpos pc_setpos(struct map_session_data* sd, unsigned short mapindex, in //Free session data from this map server [Kevin] unit_free_pc(sd); + if( st ){ + // Has to be done here, because otherwise unit_free_pc will free the stack already + st->state = END; + } + return SETPOS_OK; }