Skip to content

Commit

Permalink
Follow up 95705d4
Browse files Browse the repository at this point in the history
* Changed bonus script list to link list
* Merged 'pc_bonus_script_clear_all' to 'pc_bonus_script_clear'
* Now bonus script will be saved on auto-save timer or other save request, prevent losing the bonus when "something" happen. But, saving when player is quiting, will removes the bonus that won't be saved on logout.

Signed-off-by: Cydh Ramdh <house.bad@gmail.com>
  • Loading branch information
cydh committed Feb 3, 2015
1 parent 95705d4 commit 148353e
Show file tree
Hide file tree
Showing 11 changed files with 261 additions and 220 deletions.
5 changes: 4 additions & 1 deletion src/char/char_mapif.c
Expand Up @@ -1328,6 +1328,9 @@ int chmapif_bonus_script_save(int fd) {
uint32 cid = RFIFOL(fd,4);
uint8 count = RFIFOB(fd,8);

if (SQL_ERROR == Sql_Query(sql_handle,"DELETE FROM `%s` WHERE `char_id` = '%d'", schema_config.bonus_script_db, cid))
Sql_ShowDebug(sql_handle);

if (count > 0) {
char esc_script[MAX_BONUS_SCRIPT_LENGTH*2];
struct bonus_script_data bsdata;
Expand All @@ -1346,9 +1349,9 @@ int chmapif_bonus_script_save(int fd) {
if (SQL_ERROR == Sql_QueryStr(sql_handle,StringBuf_Value(&buf)))
Sql_ShowDebug(sql_handle);

ShowInfo("Bonus Script saved for CID=%d. Total: %d.\n", cid, count);
StringBuf_Destroy(&buf);
}
ShowInfo("Bonus Script saved for CID=%d. Total: %d.\n", cid, count);
RFIFOSKIP(fd,RFIFOW(fd,2));
}
return 1;
Expand Down
25 changes: 18 additions & 7 deletions src/common/db.c
Expand Up @@ -2717,18 +2717,29 @@ void linkdb_insert( struct linkdb_node** head, void *key, void* data)
node->data = data;
}

void linkdb_foreach( struct linkdb_node** head, LinkDBFunc func, ... )
{
int linkdb_vforeach( struct linkdb_node** head, LinkDBFunc func, va_list ap) {
struct linkdb_node *node;
if( head == NULL ) return;
int retCount = 0;
if( head == NULL )
return 0;
node = *head;
while ( node ) {
va_list args;
va_start(args, func);
func( node->key, node->data, args );
va_end(args);
va_list argscopy;
va_copy(argscopy, ap);
retCount += func(node->key, node->data, argscopy);
va_end(argscopy);
node = node->next;
}
return retCount;
}

int linkdb_foreach( struct linkdb_node** head, LinkDBFunc func, ... ) {
va_list ap;
int retCount = 0;
va_start(ap, func);
retCount = linkdb_vforeach(head, func, ap);
va_end(ap);
return retCount;
}

void* linkdb_search( struct linkdb_node** head, void *key)
Expand Down
5 changes: 3 additions & 2 deletions src/common/db.h
Expand Up @@ -875,14 +875,15 @@ struct linkdb_node {
void *data;
};

typedef void (*LinkDBFunc)(void* key, void* data, va_list args);
typedef int (*LinkDBFunc)(void* key, void* data, va_list args);

void linkdb_insert ( struct linkdb_node** head, void *key, void* data); // 重複を考慮しない
void linkdb_replace( struct linkdb_node** head, void *key, void* data); // 重複を考慮する
void* linkdb_search ( struct linkdb_node** head, void *key);
void* linkdb_erase ( struct linkdb_node** head, void *key);
void linkdb_final ( struct linkdb_node** head );
void linkdb_foreach( struct linkdb_node** head, LinkDBFunc func, ... );
int linkdb_vforeach(struct linkdb_node** head, LinkDBFunc func, va_list ap);
int linkdb_foreach( struct linkdb_node** head, LinkDBFunc func, ... );



Expand Down
112 changes: 60 additions & 52 deletions src/map/chrif.c
Expand Up @@ -282,8 +282,6 @@ int chrif_save(struct map_session_data *sd, int flag) {
if (chrif_isconnected()) {
chrif_save_scdata(sd);
chrif_skillcooldown_save(sd);
if (flag != 3)
chrif_bsdata_save(sd);
chrif_req_login_operation(sd->status.account_id, sd->status.name, CHRIF_OP_LOGIN_BANK, 0, 2, sd->status.bank_vault); //save Bank data
}
if ( flag != 3 && !chrif_auth_logout(sd,flag == 1 ? ST_LOGOUT : ST_MAPCHANGE) )
Expand All @@ -292,6 +290,8 @@ int chrif_save(struct map_session_data *sd, int flag) {

chrif_check(-1); //Character is saved on reconnect.

chrif_bsdata_save(sd, (flag && (flag != 3)));

//For data sync
if (sd->state.storage_flag == 2)
gstorage_storagesave(sd->status.account_id, sd->status.guild_id, flag);
Expand Down Expand Up @@ -1619,63 +1619,63 @@ int chrif_bsdata_request(uint32 char_id) {
/**
* ZA 0x2b2e
* <cmd>.W <len>.W <char_id>.L <count>.B { <bonus_script>.?B }
* Stores bonus_script data(s) to the table when player log out
* Stores bonus_script data(s) to the table
* @param sd
* @author [Cydh]
**/
int chrif_bsdata_save(struct map_session_data *sd) {
uint16 i;
uint8 count = 0;
unsigned int tick;
int chrif_bsdata_save(struct map_session_data *sd, bool quit) {
uint8 i = 0;

chrif_check(-1);

if (!sd || !sd->bonus_script_num)
if (!sd)
return 0;

tick = gettick();
// Removing...
if (quit && sd->bonus_script.head) {
uint16 flag = BSF_REM_ON_LOGOUT; //Remove bonus when logout
if (battle_config.debuff_on_logout&1) //Remove negative buffs
flag |= BSF_REM_DEBUFF;
if (battle_config.debuff_on_logout&2) //Remove positive buffs
flag |= BSF_REM_BUFF;
pc_bonus_script_clear(sd, flag);
}

//ShowInfo("Saving %d bonus script for CID=%d\n", sd->bonus_script.count, sd->status.char_id);

WFIFOHEAD(char_fd, 9 + sd->bonus_script_num * sizeof(struct bonus_script_data));
WFIFOHEAD(char_fd, 9 + sd->bonus_script.count * sizeof(struct bonus_script_data));
WFIFOW(char_fd, 0) = 0x2b2e;
WFIFOL(char_fd, 4) = sd->status.char_id;

i = BSF_REM_ON_LOGOUT; //Remove bonus with this flag
if (battle_config.debuff_on_logout&1) //Remove negative buffs
i |= BSF_REM_DEBUFF;
if (battle_config.debuff_on_logout&2) //Remove positive buffs
i |= BSF_REM_BUFF;
if (sd->bonus_script.count) {
unsigned int tick = gettick();
struct linkdb_node *node = NULL;

//Clear data that won't be stored
pc_bonus_script_clear(sd, i);
for (node = sd->bonus_script.head; node && i < MAX_PC_BONUS_SCRIPT; node = node->next) {
const struct TimerData *timer = NULL;
struct bonus_script_data bs;
struct s_bonus_script_entry *entry = (struct s_bonus_script_entry *)node->data;

if (!sd->bonus_script_num)
return 0;

for (i = 0; i < sd->bonus_script_num; i++) {
const struct TimerData *timer = get_timer(sd->bonus_script[i]->tid);
struct bonus_script_data bs;

if (timer == NULL || DIFF_TICK(timer->tick,tick) < 0)
continue;
if (!entry || !(timer = get_timer(entry->tid)) || DIFF_TICK(timer->tick,tick) < 0)
continue;

memset(&bs, 0, sizeof(bs));
safestrncpy(bs.script_str, StringBuf_Value(sd->bonus_script[i]->script_buf), StringBuf_Length(sd->bonus_script[i]->script_buf)+1);
bs.tick = DIFF_TICK(timer->tick, tick);
bs.flag = sd->bonus_script[i]->flag;
bs.type = sd->bonus_script[i]->type;
bs.icon = sd->bonus_script[i]->icon;
memcpy(WFIFOP(char_fd, 9 + count * sizeof(struct bonus_script_data)), &bs, sizeof(struct bonus_script_data));
count++;
}
memset(&bs, 0, sizeof(bs));
safestrncpy(bs.script_str, StringBuf_Value(entry->script_buf), StringBuf_Length(entry->script_buf)+1);
bs.tick = DIFF_TICK(timer->tick, tick);
bs.flag = entry->flag;
bs.type = entry->type;
bs.icon = entry->icon;
memcpy(WFIFOP(char_fd, 9 + i * sizeof(struct bonus_script_data)), &bs, sizeof(struct bonus_script_data));
i++;
}

if (count > 0) {
WFIFOB(char_fd, 8) = count;
WFIFOW(char_fd, 2) = 9 + sd->bonus_script_num * sizeof(struct bonus_script_data);
WFIFOSET(char_fd, WFIFOW(char_fd, 2));
if (i != sd->bonus_script.count && sd->bonus_script.count > MAX_PC_BONUS_SCRIPT)
ShowWarning("Only allowed to save %d (mmo.h::MAX_PC_BONUS_SCRIPT) bonus script each player.\n", MAX_PC_BONUS_SCRIPT);
}

// Clear All
pc_bonus_script_clear_all(sd,3);
WFIFOB(char_fd, 8) = i;
WFIFOW(char_fd, 2) = 9 + sd->bonus_script.count * sizeof(struct bonus_script_data);
WFIFOSET(char_fd, WFIFOW(char_fd, 2));

return 0;
}
Expand All @@ -1690,8 +1690,7 @@ int chrif_bsdata_save(struct map_session_data *sd) {
int chrif_bsdata_received(int fd) {
struct map_session_data *sd;
uint32 cid = RFIFOL(fd,4);
uint8 i, count = 0;
bool calc = false;
uint8 count = 0;

sd = map_charid2sd(cid);

Expand All @@ -1700,19 +1699,28 @@ int chrif_bsdata_received(int fd) {
return -1;
}

count = RFIFOB(fd,8);
if ((count = RFIFOB(fd,8))) {
struct s_bonus_script *list = NULL;
uint8 i = 0;

for (i = 0; i < count; i++) {
struct bonus_script_data *bs = (struct bonus_script_data*)RFIFOP(fd,9 + i*sizeof(struct bonus_script_data));
//ShowInfo("Loaded %d bonus script for CID=%d\n", count, sd->status.char_id);

if (bs->script_str[0] == '\0' || !bs->tick)
continue;
for (i = 0; i < count; i++) {
struct bonus_script_data *bs = (struct bonus_script_data*)RFIFOP(fd,9 + i*sizeof(struct bonus_script_data));
struct s_bonus_script_entry *entry = NULL;

if (bs->script_str[0] == '\0' || !bs->tick)
continue;

if (!(entry = pc_bonus_script_add(sd, bs->script_str, bs->tick, (enum si_type)bs->icon, bs->flag, bs->type)))
continue;

linkdb_insert(&sd->bonus_script.head, (void *)((intptr_t)entry), entry);
}

if (pc_bonus_script_add(sd, bs->script_str, bs->tick, (enum si_type)bs->icon, bs->flag, bs->type))
calc = true;
if (sd->bonus_script.head)
status_calc_pc(sd,SCO_NONE);
}
if (calc)
status_calc_pc(sd,SCO_NONE);
return 0;
}

Expand Down
2 changes: 1 addition & 1 deletion src/map/chrif.h
Expand Up @@ -89,7 +89,7 @@ int chrif_req_charunban(int aid, const char* character_name);
int chrif_load_bankdata(int fd);

int chrif_bsdata_request(uint32 char_id);
int chrif_bsdata_save(struct map_session_data *sd);
int chrif_bsdata_save(struct map_session_data *sd, bool quit);

void do_final_chrif(void);
void do_init_chrif(void);
Expand Down
3 changes: 2 additions & 1 deletion src/map/guild.c
Expand Up @@ -1945,11 +1945,12 @@ int guild_castledatasave(int castle_id, int index, int value) {
return 0;
}

void guild_castle_reconnect_sub(void *key, void *data, va_list ap) {
int guild_castle_reconnect_sub(void *key, void *data, va_list ap) {
int castle_id = GetWord((int)__64BPRTSIZE(key), 0);
int index = GetWord((int)__64BPRTSIZE(key), 1);
intif_guild_castle_datasave(castle_id, index, *(int *)data);
aFree(data);
return 1;
}

/**
Expand Down

0 comments on commit 148353e

Please sign in to comment.