From 53e1375cb6926b55a1487b61e5616b299e34e2be Mon Sep 17 00:00:00 2001 From: skotlex Date: Thu, 29 Mar 2007 20:34:17 +0000 Subject: - Added "do_abort" function to the core. It is invoked when the server has received a Segmentation Fault or Floating Point Exception signal. Currently the only one that uses it is the map-server, which then attempts to save all online characters before aborting. - Note that due to the current coding of the sig plugin, do_abort will not be invoked if you use it! This plugin needs to be updated... - Cleaned up a bit the change element code. val1 is the elemental level, val2 is the element now. - Hardcoded the element and elemental level of SC_CHANGEUNDEAD. git-svn-id: https://rathena.svn.sourceforge.net/svnroot/rathena/trunk@10089 54d463be-8e91-2dee-dedb-b68131a5f0ec --- src/char/char.c | 7 +++++++ src/char_sql/char.c | 8 ++++++++ src/common/core.c | 11 +++++++++-- src/common/core.h | 1 + src/ladmin/ladmin.c | 6 ++++++ src/login/login.c | 7 +++++++ src/login_sql/login.c | 7 +++++++ src/map/map.c | 28 ++++++++++++++++++++++++++++ src/map/skill.c | 2 +- src/map/status.c | 18 +++++++++++------- src/txt-converter/char-converter.c | 4 +++- src/txt-converter/login-converter.c | 3 ++- 12 files changed, 90 insertions(+), 12 deletions(-) (limited to 'src') diff --git a/src/char/char.c b/src/char/char.c index be691808a..68d67f56c 100644 --- a/src/char/char.c +++ b/src/char/char.c @@ -4297,6 +4297,13 @@ void do_final(void) { char_log("----End of char-server (normal end with closing of all files)." RETCODE); } +//------------------------------ +// Function called when the server +// has received a crash signal. +//------------------------------ +void do_abort(void) { +} + void set_server_type(void) { SERVER_TYPE = ATHENA_SERVER_CHAR; diff --git a/src/char_sql/char.c b/src/char_sql/char.c index 693ddee12..4e325700e 100644 --- a/src/char_sql/char.c +++ b/src/char_sql/char.c @@ -3909,6 +3909,14 @@ void do_final(void) { ShowInfo("ok! all done...\n"); } + +//------------------------------ +// Function called when the server +// has received a crash signal. +//------------------------------ +void do_abort(void) { +} + #endif //TXT_SQL_CONVERT void sql_config_read(const char *cfgName){ /* Kalaspuff, to get login_db */ char line[1024], w1[1024], w2[1024]; diff --git a/src/common/core.c b/src/common/core.c index 5924a0aa6..60d25546a 100644 --- a/src/common/core.c +++ b/src/common/core.c @@ -92,6 +92,13 @@ static void sig_proc(int sn) exit(0); runflag = 0; break; + case SIGSEGV: + case SIGFPE: + do_abort(); + // Pass the signal to the system's default handler + compat_signal(sn, SIG_DFL); + raise(sn); + break; #ifndef _WIN32 case SIGXFSZ: // ignore and allow it to set errno to EFBIG @@ -109,10 +116,10 @@ void signals_init (void) { compat_signal(SIGTERM, sig_proc); compat_signal(SIGINT, sig_proc); + compat_signal(SIGSEGV, sig_proc); + compat_signal(SIGFPE, sig_proc); // Signal to create coredumps by system when necessary (crash) - compat_signal(SIGSEGV, SIG_DFL); - compat_signal(SIGFPE, SIG_DFL); compat_signal(SIGILL, SIG_DFL); #ifndef _WIN32 compat_signal(SIGXFSZ, sig_proc); diff --git a/src/common/core.h b/src/common/core.h index 5e396cc7a..f59a87e3e 100644 --- a/src/common/core.h +++ b/src/common/core.h @@ -18,6 +18,7 @@ extern const char *get_svn_revision(void); extern int do_init(int,char**); extern void set_server_type(void); extern void set_termfunc(void (*termfunc)(void)); +extern void do_abort(void); extern void do_final(void); #endif /* _CORE_H_ */ diff --git a/src/ladmin/ladmin.c b/src/ladmin/ladmin.c index 947af1900..4f4099493 100644 --- a/src/ladmin/ladmin.c +++ b/src/ladmin/ladmin.c @@ -4361,6 +4361,12 @@ int ladmin_config_read(const char *cfgName) { return 0; } +//------------------------------ +// Function called when the server +// has received a crash signal. +//------------------------------ +void do_abort(void) {} + //-------------------------------------- // Function called at exit of the server //-------------------------------------- diff --git a/src/login/login.c b/src/login/login.c index 25f91c3d6..1b5e96596 100644 --- a/src/login/login.c +++ b/src/login/login.c @@ -4034,6 +4034,13 @@ void do_final(void) { ShowStatus("Finished.\n"); } +//------------------------------ +// Function called when the server +// has received a crash signal. +//------------------------------ +void do_abort(void) { +} + //------------------------------ // Main function of login-server //------------------------------ diff --git a/src/login_sql/login.c b/src/login_sql/login.c index 6173d0fe1..2d2e7af9f 100644 --- a/src/login_sql/login.c +++ b/src/login_sql/login.c @@ -2038,6 +2038,13 @@ void do_final(void) aFree(gm_account_db); } +//------------------------------ +// Function called when the server +// has received a crash signal. +//------------------------------ +void do_abort(void) { +} + void set_server_type(void) { SERVER_TYPE = ATHENA_SERVER_LOGIN; diff --git a/src/map/map.c b/src/map/map.c index fba8faa88..9cf047d56 100644 --- a/src/map/map.c +++ b/src/map/map.c @@ -3156,6 +3156,34 @@ void do_final(void) { ShowStatus("Successfully terminated.\n"); } +static int map_abort_sub(DBKey key,void * data,va_list ap) +{ + struct map_session_data *sd = (TBL_PC*)data; + + if (!sd->state.auth || sd->state.waitingdisconnect || sd->state.finalsave) + return 0; + + chrif_save(sd,1); + return 1; +} + + +//------------------------------ +// Function called when the server +// has received a crash signal. +//------------------------------ +void do_abort(void) { + //Save all characters and then flush the inter-connection. + if (!chrif_isconnect()) + { + ShowFatalError("Server has crashed without a connection to the char-server, character data can't be saved!\n"); + return; + } + ShowError("Server received crash signal! Attempting to save all online characters!\n"); + map_foreachpc(map_abort_sub); + chrif_flush_fifo(); +} + /*====================================================== * Map-Server Version Screen [MC Cameri] *------------------------------------------------------ diff --git a/src/map/skill.c b/src/map/skill.c index 5c77f186a..65cc19bcf 100644 --- a/src/map/skill.c +++ b/src/map/skill.c @@ -4831,7 +4831,7 @@ int skill_castend_nodamage_id (struct block_list *src, struct block_list *bl, in case NPC_CHANGETELEKINESIS: case NPC_CHANGEUNDEAD: clif_skill_nodamage(src,bl,skillid,skilllv, - sc_start4(bl, type, 100, skilllv, skillid, skill_get_pl(skillid,skilllv), 0, + sc_start2(bl, type, 100, skilllv, skill_get_pl(skillid,skilllv), skill_get_time(skillid, skilllv))); break; diff --git a/src/map/status.c b/src/map/status.c index b7c595d51..993be24ea 100644 --- a/src/map/status.c +++ b/src/map/status.c @@ -3874,9 +3874,9 @@ static unsigned char status_calc_element(struct block_list *bl, struct status_ch if( sc->data[SC_BENEDICTIO].timer!=-1 ) return ELE_HOLY; if( sc->data[SC_CHANGEUNDEAD].timer!=-1) - return sc->data[SC_CHANGEUNDEAD].val3; + return ELE_UNDEAD; if( sc->data[SC_ELEMENTALCHANGE].timer!=-1) - return sc->data[SC_ELEMENTALCHANGE].val3; + return sc->data[SC_ELEMENTALCHANGE].val2; return cap_value(element,0,UCHAR_MAX); } @@ -3893,7 +3893,7 @@ static unsigned char status_calc_element_lv(struct block_list *bl, struct status if( sc->data[SC_CHANGEUNDEAD].timer!=-1) return 1; if(sc->data[SC_ELEMENTALCHANGE].timer!=-1) - return sc->data[SC_ELEMENTALCHANGE].val4; + return sc->data[SC_ELEMENTALCHANGE].val1; return cap_value(lv,1,4); } @@ -5007,10 +5007,14 @@ int status_change_start(struct block_list *bl,int type,int rate,int val1,int val skill_enchant_elemental_end(bl,type); break; case SC_ELEMENTALCHANGE: - //Val1 is skill level, val2 is skill that invoked this. - if (!val3) //Val 3 holds the element, when not given, a random one is picked. - val3 = rand()%ELE_MAX; - val4 =1+rand()%4; //Elemental Lv is always a random value between 1 and 4. + //Val1 is elemental change level, val2 is eleemnt to use. + if (!val2) //Val 3 holds the element, when not given, a random one is picked. + val2 = rand()%ELE_MAX; + //Elemental Lv is always a random value between 1 and 4. + if (val1 == 1) + val1 =1+rand()%4; + else if (val1 > 4) + val1 = 4; break; case SC_PROVIDENCE: val2=val1*5; //Race/Ele resist diff --git a/src/txt-converter/char-converter.c b/src/txt-converter/char-converter.c index b5f604bf8..3d1f59391 100644 --- a/src/txt-converter/char-converter.c +++ b/src/txt-converter/char-converter.c @@ -278,4 +278,6 @@ int do_init(int argc, char **argv){ exit (0); } -void do_final () {} +void do_abort(void) {} + +void do_final (void) {} diff --git a/src/txt-converter/login-converter.c b/src/txt-converter/login-converter.c index 840d61e1c..1f5b4141c 100644 --- a/src/txt-converter/login-converter.c +++ b/src/txt-converter/login-converter.c @@ -228,5 +228,6 @@ int do_init(int argc,char **argv) exit (0); } +void do_abort(void) {} -void do_final() {} +void do_final(void) {} -- cgit v1.2.3-60-g2f50