diff options
author | shennetsind <ind@henn.et> | 2013-04-07 01:55:40 -0300 |
---|---|---|
committer | shennetsind <ind@henn.et> | 2013-04-07 01:55:40 -0300 |
commit | 2f9f7ce4aa46514c9173a3c91f4033b25901520e (patch) | |
tree | ec5656a546bcaf6d7820c3de252b63070d32b887 /src/map/clif.c | |
parent | 10b53b9fbc011a9224d118414517870af3e9e20c (diff) | |
download | hercules-2f9f7ce4aa46514c9173a3c91f4033b25901520e.tar.gz hercules-2f9f7ce4aa46514c9173a3c91f4033b25901520e.tar.bz2 hercules-2f9f7ce4aa46514c9173a3c91f4033b25901520e.tar.xz hercules-2f9f7ce4aa46514c9173a3c91f4033b25901520e.zip |
PacketDB Overhaul
Feature Design by GreenBox
Special Thanks to mkbu95 for bringing this topic up! (packet db)
http://hercules.ws/board/topic/353-packetdb-overhaul/
Signed-off-by: shennetsind <ind@henn.et>
Diffstat (limited to 'src/map/clif.c')
-rw-r--r-- | src/map/clif.c | 1416 |
1 files changed, 348 insertions, 1068 deletions
diff --git a/src/map/clif.c b/src/map/clif.c index 0ee3de1f2..63e72b3bb 100644 --- a/src/map/clif.c +++ b/src/map/clif.c @@ -54,11 +54,6 @@ //#define DUMP_UNKNOWN_PACKET //#define DUMP_INVALID_PACKET -struct Clif_Config { - int packet_db_ver; //Preferred packet version. - int connect_cmd[MAX_PACKET_VER + 1]; //Store the connect command for all versions. [Skotlex] -} clif_config; - //Converts item type in case of pet eggs. static inline int itemtype(int type) { return ( type == IT_PETEGG ) ? IT_WEAPON : type; @@ -314,10 +309,8 @@ int clif_send_sub(struct block_list *bl, va_list ap) { return 0; } - if (packet_db[sd->packet_ver][RBUFW(buf,0)].len) { // packet must exist for the client version - memcpy(WFIFOP(fd,0), buf, len); - WFIFOSET(fd,len); - } + memcpy(WFIFOP(fd,0), buf, len); + WFIFOSET(fd,len); return 0; } @@ -342,245 +335,221 @@ int clif_send(const uint8* buf, int len, struct block_list* bl, enum send_target switch(type) { - case ALL_CLIENT: //All player clients. - iter = mapit_getallusers(); - while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) { - if( packet_db[tsd->packet_ver][RBUFW(buf,0)].len ) { // packet must exist for the client version + case ALL_CLIENT: //All player clients. + iter = mapit_getallusers(); + while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) { WFIFOHEAD(tsd->fd, len); memcpy(WFIFOP(tsd->fd,0), buf, len); WFIFOSET(tsd->fd,len); } - } - mapit_free(iter); - break; + mapit_free(iter); + break; - case ALL_SAMEMAP: //All players on the same map - iter = mapit_getallusers(); - while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) { - if( bl->m == tsd->bl.m && packet_db[tsd->packet_ver][RBUFW(buf,0)].len ) { // packet must exist for the client version - WFIFOHEAD(tsd->fd, len); - memcpy(WFIFOP(tsd->fd,0), buf, len); - WFIFOSET(tsd->fd,len); + case ALL_SAMEMAP: //All players on the same map + iter = mapit_getallusers(); + while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) { + if( bl->m == tsd->bl.m ) { + WFIFOHEAD(tsd->fd, len); + memcpy(WFIFOP(tsd->fd,0), buf, len); + WFIFOSET(tsd->fd,len); + } } - } - mapit_free(iter); - break; + mapit_free(iter); + break; - case AREA: - case AREA_WOSC: - if (sd && bl->prev == NULL) //Otherwise source misses the packet.[Skotlex] - clif->send (buf, len, bl, SELF); - case AREA_WOC: - case AREA_WOS: - map_foreachinarea(clif->send_sub, bl->m, bl->x-AREA_SIZE, bl->y-AREA_SIZE, bl->x+AREA_SIZE, bl->y+AREA_SIZE, - BL_PC, buf, len, bl, type); - break; - case AREA_CHAT_WOC: - map_foreachinarea(clif->send_sub, bl->m, bl->x-(AREA_SIZE-5), bl->y-(AREA_SIZE-5), - bl->x+(AREA_SIZE-5), bl->y+(AREA_SIZE-5), BL_PC, buf, len, bl, AREA_WOC); - break; + case AREA: + case AREA_WOSC: + if (sd && bl->prev == NULL) //Otherwise source misses the packet.[Skotlex] + clif->send (buf, len, bl, SELF); + case AREA_WOC: + case AREA_WOS: + map_foreachinarea(clif->send_sub, bl->m, bl->x-AREA_SIZE, bl->y-AREA_SIZE, bl->x+AREA_SIZE, bl->y+AREA_SIZE, + BL_PC, buf, len, bl, type); + break; + case AREA_CHAT_WOC: + map_foreachinarea(clif->send_sub, bl->m, bl->x-(AREA_SIZE-5), bl->y-(AREA_SIZE-5), + bl->x+(AREA_SIZE-5), bl->y+(AREA_SIZE-5), BL_PC, buf, len, bl, AREA_WOC); + break; - case CHAT: - case CHAT_WOS: - { - struct chat_data *cd; - if (sd) { - cd = (struct chat_data*)map_id2bl(sd->chatID); - } else if (bl->type == BL_CHAT) { - cd = (struct chat_data*)bl; - } else break; - if (cd == NULL) - break; - for(i = 0; i < cd->users; i++) { - if (type == CHAT_WOS && cd->usersd[i] == sd) - continue; - if (packet_db[cd->usersd[i]->packet_ver][RBUFW(buf,0)].len) { // packet must exist for the client version - if ((fd=cd->usersd[i]->fd) >0 && session[fd]) // Added check to see if session exists [PoW] - { + case CHAT: + case CHAT_WOS: + { + struct chat_data *cd; + if (sd) { + cd = (struct chat_data*)map_id2bl(sd->chatID); + } else if (bl->type == BL_CHAT) { + cd = (struct chat_data*)bl; + } else break; + if (cd == NULL) + break; + for(i = 0; i < cd->users; i++) { + if (type == CHAT_WOS && cd->usersd[i] == sd) + continue; + if ((fd=cd->usersd[i]->fd) >0 && session[fd]) { // Added check to see if session exists [PoW] WFIFOHEAD(fd,len); memcpy(WFIFOP(fd,0), buf, len); WFIFOSET(fd,len); } } } - } - break; + break; - case PARTY_AREA: - case PARTY_AREA_WOS: - x0 = bl->x - AREA_SIZE; - y0 = bl->y - AREA_SIZE; - x1 = bl->x + AREA_SIZE; - y1 = bl->y + AREA_SIZE; - case PARTY: - case PARTY_WOS: - case PARTY_SAMEMAP: - case PARTY_SAMEMAP_WOS: - if (sd && sd->status.party_id) - p = party_search(sd->status.party_id); - - if (p) { - for(i=0;i<MAX_PARTY;i++){ - if( (sd = p->data[i].sd) == NULL ) - continue; + case PARTY_AREA: + case PARTY_AREA_WOS: + x0 = bl->x - AREA_SIZE; + y0 = bl->y - AREA_SIZE; + x1 = bl->x + AREA_SIZE; + y1 = bl->y + AREA_SIZE; + case PARTY: + case PARTY_WOS: + case PARTY_SAMEMAP: + case PARTY_SAMEMAP_WOS: + if (sd && sd->status.party_id) + p = party_search(sd->status.party_id); + + if (p) { + for(i=0;i<MAX_PARTY;i++){ + if( (sd = p->data[i].sd) == NULL ) + continue; - if( !(fd=sd->fd) ) - continue; + if( !(fd=sd->fd) ) + continue; - if( sd->bl.id == bl->id && (type == PARTY_WOS || type == PARTY_SAMEMAP_WOS || type == PARTY_AREA_WOS) ) - continue; + if( sd->bl.id == bl->id && (type == PARTY_WOS || type == PARTY_SAMEMAP_WOS || type == PARTY_AREA_WOS) ) + continue; - if( type != PARTY && type != PARTY_WOS && bl->m != sd->bl.m ) - continue; + if( type != PARTY && type != PARTY_WOS && bl->m != sd->bl.m ) + continue; - if( (type == PARTY_AREA || type == PARTY_AREA_WOS) && (sd->bl.x < x0 || sd->bl.y < y0 || sd->bl.x > x1 || sd->bl.y > y1) ) - continue; + if( (type == PARTY_AREA || type == PARTY_AREA_WOS) && (sd->bl.x < x0 || sd->bl.y < y0 || sd->bl.x > x1 || sd->bl.y > y1) ) + continue; - if( packet_db[sd->packet_ver][RBUFW(buf,0)].len ) - { // packet must exist for the client version WFIFOHEAD(fd,len); memcpy(WFIFOP(fd,0), buf, len); WFIFOSET(fd,len); } + if (!enable_spy) //Skip unnecessary parsing. [Skotlex] + break; + + iter = mapit_getallusers(); + while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) { + if( tsd->partyspy == p->party.party_id ) { + WFIFOHEAD(tsd->fd, len); + memcpy(WFIFOP(tsd->fd,0), buf, len); + WFIFOSET(tsd->fd,len); + } + } + mapit_free(iter); } - if (!enable_spy) //Skip unnecessary parsing. [Skotlex] - break; + break; + + case DUEL: + case DUEL_WOS: + if (!sd || !sd->duel_group) break; //Invalid usage. iter = mapit_getallusers(); - while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) - { - if( tsd->partyspy == p->party.party_id && packet_db[tsd->packet_ver][RBUFW(buf,0)].len ) - { // packet must exist for the client version + while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) { + if( type == DUEL_WOS && bl->id == tsd->bl.id ) + continue; + if( sd->duel_group == tsd->duel_group ) { WFIFOHEAD(tsd->fd, len); memcpy(WFIFOP(tsd->fd,0), buf, len); WFIFOSET(tsd->fd,len); } } mapit_free(iter); - } - break; - - case DUEL: - case DUEL_WOS: - if (!sd || !sd->duel_group) break; //Invalid usage. + break; - iter = mapit_getallusers(); - while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) - { - if( type == DUEL_WOS && bl->id == tsd->bl.id ) - continue; - if( sd->duel_group == tsd->duel_group && packet_db[tsd->packet_ver][RBUFW(buf,0)].len ) - { // packet must exist for the client version - WFIFOHEAD(tsd->fd, len); - memcpy(WFIFOP(tsd->fd,0), buf, len); - WFIFOSET(tsd->fd,len); + case SELF: + if (sd && (fd=sd->fd) ) { + WFIFOHEAD(fd,len); + memcpy(WFIFOP(fd,0), buf, len); + WFIFOSET(fd,len); } - } - mapit_free(iter); - break; - - case SELF: - if (sd && (fd=sd->fd) && packet_db[sd->packet_ver][RBUFW(buf,0)].len) { // packet must exist for the client version - WFIFOHEAD(fd,len); - memcpy(WFIFOP(fd,0), buf, len); - WFIFOSET(fd,len); - } - break; - - // New definitions for guilds [Valaris] - Cleaned up and reorganized by [Skotlex] - case GUILD_AREA: - case GUILD_AREA_WOS: - x0 = bl->x - AREA_SIZE; - y0 = bl->y - AREA_SIZE; - x1 = bl->x + AREA_SIZE; - y1 = bl->y + AREA_SIZE; - case GUILD_SAMEMAP: - case GUILD_SAMEMAP_WOS: - case GUILD: - case GUILD_WOS: - case GUILD_NOBG: - if (sd && sd->status.guild_id) - g = sd->guild; - - if (g) { - for(i = 0; i < g->max_member; i++) { - if( (sd = g->member[i].sd) != NULL ) - { - if( !(fd=sd->fd) ) - continue; - - if( type == GUILD_NOBG && sd->bg_id ) - continue; - - if( sd->bl.id == bl->id && (type == GUILD_WOS || type == GUILD_SAMEMAP_WOS || type == GUILD_AREA_WOS) ) - continue; - - if( type != GUILD && type != GUILD_NOBG && type != GUILD_WOS && sd->bl.m != bl->m ) - continue; - - if( (type == GUILD_AREA || type == GUILD_AREA_WOS) && (sd->bl.x < x0 || sd->bl.y < y0 || sd->bl.x > x1 || sd->bl.y > y1) ) - continue; + break; - if( packet_db[sd->packet_ver][RBUFW(buf,0)].len ) - { // packet must exist for the client version + // New definitions for guilds [Valaris] - Cleaned up and reorganized by [Skotlex] + case GUILD_AREA: + case GUILD_AREA_WOS: + x0 = bl->x - AREA_SIZE; + y0 = bl->y - AREA_SIZE; + x1 = bl->x + AREA_SIZE; + y1 = bl->y + AREA_SIZE; + case GUILD_SAMEMAP: + case GUILD_SAMEMAP_WOS: + case GUILD: + case GUILD_WOS: + case GUILD_NOBG: + if (sd && sd->status.guild_id) + g = sd->guild; + + if (g) { + for(i = 0; i < g->max_member; i++) { + if( (sd = g->member[i].sd) != NULL ) { + if( !(fd=sd->fd) ) + continue; + + if( type == GUILD_NOBG && sd->bg_id ) + continue; + + if( sd->bl.id == bl->id && (type == GUILD_WOS || type == GUILD_SAMEMAP_WOS || type == GUILD_AREA_WOS) ) + continue; + + if( type != GUILD && type != GUILD_NOBG && type != GUILD_WOS && sd->bl.m != bl->m ) + continue; + + if( (type == GUILD_AREA || type == GUILD_AREA_WOS) && (sd->bl.x < x0 || sd->bl.y < y0 || sd->bl.x > x1 || sd->bl.y > y1) ) + continue; WFIFOHEAD(fd,len); memcpy(WFIFOP(fd,0), buf, len); WFIFOSET(fd,len); } } - } - if (!enable_spy) //Skip unnecessary parsing. [Skotlex] - break; + if (!enable_spy) //Skip unnecessary parsing. [Skotlex] + break; - iter = mapit_getallusers(); - while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) - { - if( tsd->guildspy == g->guild_id && packet_db[tsd->packet_ver][RBUFW(buf,0)].len ) - { // packet must exist for the client version - WFIFOHEAD(tsd->fd, len); - memcpy(WFIFOP(tsd->fd,0), buf, len); - WFIFOSET(tsd->fd,len); + iter = mapit_getallusers(); + while( (tsd = (TBL_PC*)mapit_next(iter)) != NULL ) { + if( tsd->guildspy == g->guild_id ) { + WFIFOHEAD(tsd->fd, len); + memcpy(WFIFOP(tsd->fd,0), buf, len); + WFIFOSET(tsd->fd,len); + } } + mapit_free(iter); } - mapit_free(iter); - } - break; + break; - case BG_AREA: - case BG_AREA_WOS: - x0 = bl->x - AREA_SIZE; - y0 = bl->y - AREA_SIZE; - x1 = bl->x + AREA_SIZE; - y1 = bl->y + AREA_SIZE; - case BG_SAMEMAP: - case BG_SAMEMAP_WOS: - case BG: - case BG_WOS: - if( sd && sd->bg_id && (bg = bg_team_search(sd->bg_id)) != NULL ) - { - for( i = 0; i < MAX_BG_MEMBERS; i++ ) - { - if( (sd = bg->members[i].sd) == NULL || !(fd = sd->fd) ) - continue; - if( sd->bl.id == bl->id && (type == BG_WOS || type == BG_SAMEMAP_WOS || type == BG_AREA_WOS) ) - continue; - if( type != BG && type != BG_WOS && sd->bl.m != bl->m ) - continue; - if( (type == BG_AREA || type == BG_AREA_WOS) && (sd->bl.x < x0 || sd->bl.y < y0 || sd->bl.x > x1 || sd->bl.y > y1) ) - continue; - if( packet_db[sd->packet_ver][RBUFW(buf,0)].len ) - { // packet must exist for the client version + case BG_AREA: + case BG_AREA_WOS: + x0 = bl->x - AREA_SIZE; + y0 = bl->y - AREA_SIZE; + x1 = bl->x + AREA_SIZE; + y1 = bl->y + AREA_SIZE; + case BG_SAMEMAP: + case BG_SAMEMAP_WOS: + case BG: + case BG_WOS: + if( sd && sd->bg_id && (bg = bg_team_search(sd->bg_id)) != NULL ) { + for( i = 0; i < MAX_BG_MEMBERS; i++ ) { + if( (sd = bg->members[i].sd) == NULL || !(fd = sd->fd) ) + continue; + if( sd->bl.id == bl->id && (type == BG_WOS || type == BG_SAMEMAP_WOS || type == BG_AREA_WOS) ) + continue; + if( type != BG && type != BG_WOS && sd->bl.m != bl->m ) + continue; + if( (type == BG_AREA || type == BG_AREA_WOS) && (sd->bl.x < x0 || sd->bl.y < y0 || sd->bl.x > x1 || sd->bl.y > y1) ) + continue; WFIFOHEAD(fd,len); memcpy(WFIFOP(fd,0), buf, len); WFIFOSET(fd,len); } } - } - break; + break; - default: - ShowError("clif->send: Unrecognized type %d\n",type); - return -1; + default: + ShowError("clif->send: Unrecognized type %d\n",type); + return -1; } return 0; @@ -8960,79 +8929,6 @@ bool clif_process_message(struct map_session_data* sd, int format, char** name_, return true; } -// --------------------- -// clif_guess_PacketVer -// --------------------- -// Parses a WantToConnection packet to try to identify which is the packet version used. [Skotlex] -// error codes: -// 0 - Success -// 1 - Unknown packet_ver -// 2 - Invalid account_id -// 3 - Invalid char_id -// 4 - Invalid login_id1 (reserved) -// 5 - Invalid client_tick (reserved) -// 6 - Invalid sex -// Only the first 'invalid' error that appears is used. -int clif_guess_PacketVer(int fd, int get_previous, int *error) { - static int err = 1; - static int packet_ver = -1; - int cmd, packet_len, value; //Value is used to temporarily store account/char_id/sex - - if (get_previous) - {//For quick reruns, since the normal code flow is to fetch this once to identify the packet version, then again in the wanttoconnect function. [Skotlex] - if( error ) - *error = err; - return packet_ver; - } - - //By default, start searching on the default one. - err = 1; - packet_ver = clif_config.packet_db_ver; - cmd = RFIFOW(fd,0); - packet_len = RFIFOREST(fd); - -#define SET_ERROR(n) \ - if( err == 1 )\ - err = n;\ -//define SET_ERROR - - // FIXME: If the packet is not received at once, this will FAIL. - // Figure out, when it happens, that only part of the packet is - // received, or fix the function to be able to deal with that - // case. -#define CHECK_PACKET_VER() \ - if( cmd != clif_config.connect_cmd[packet_ver] || packet_len != packet_db[packet_ver][cmd].len )\ - ;/* not wanttoconnection or wrong length */\ - else if( (value=(int)RFIFOL(fd, packet_db[packet_ver][cmd].pos[0])) < START_ACCOUNT_NUM || value > END_ACCOUNT_NUM )\ - { SET_ERROR(2); }/* invalid account_id */\ - else if( (value=(int)RFIFOL(fd, packet_db[packet_ver][cmd].pos[1])) <= 0 )\ - { SET_ERROR(3); }/* invalid char_id */\ - /* RFIFOL(fd, packet_db[packet_ver][cmd].pos[2]) - don't care about login_id1 */\ - /* RFIFOL(fd, packet_db[packet_ver][cmd].pos[3]) - don't care about client_tick */\ - else if( (value=(int)RFIFOB(fd, packet_db[packet_ver][cmd].pos[4])) != 0 && value != 1 )\ - { SET_ERROR(6); }/* invalid sex */\ - else\ - {\ - err = 0;\ - if( error )\ - *error = 0;\ - return packet_ver;\ - }\ -//define CHECK_PACKET_VER - - CHECK_PACKET_VER();//Default packet version found. - - for (packet_ver = MAX_PACKET_VER; packet_ver > 0; packet_ver--) { //Start guessing the version, giving priority to the newer ones. [Skotlex] - CHECK_PACKET_VER(); - } - if( error ) - *error = err; - packet_ver = -1; - return -1; -#undef SET_ERROR -#undef CHECK_PACKET_VER -} - void clif_hercules_chsys_msg(struct hChSysCh *channel, struct map_session_data *sd, char *msg) { DBIterator *iter = db_iterator(channel->users); struct map_session_data *user; @@ -9068,13 +8964,11 @@ void clif_hercules_chsys_msg(struct hChSysCh *channel, struct map_session_data * /// 0072 <account id>.L <char id>.L <auth code>.L <client time>.L <gender>.B (CZ_ENTER) /// 0436 <account id>.L <char id>.L <auth code>.L <client time>.L <gender>.B (CZ_ENTER2) /// There are various variants of this packet, some of them have padding between fields. -void clif_parse_WantToConnection(int fd, struct map_session_data* sd) -{ +void clif_parse_WantToConnection(int fd, struct map_session_data* sd) { struct block_list* bl; struct auth_node* node; int cmd, account_id, char_id, login_id1, sex; unsigned int client_tick; //The client tick is a tick, therefore it needs be unsigned. [Skotlex] - int packet_ver; // 5: old, 6: 7july04, 7: 13july04, 8: 26july04, 9: 9aug04/16aug04/17aug04, 10: 6sept04, 11: 21sept04, 12: 18oct04, 13: 25oct04 (by [Yor]) if (sd) { ShowError("clif_parse_WantToConnection : invalid request (character already logged in)\n"); @@ -9082,27 +8976,13 @@ void clif_parse_WantToConnection(int fd, struct map_session_data* sd) } // Only valid packet version get here - packet_ver = clif->guess_PacketVer(fd, 1, NULL); cmd = RFIFOW(fd,0); - account_id = RFIFOL(fd, packet_db[packet_ver][cmd].pos[0]); - char_id = RFIFOL(fd, packet_db[packet_ver][cmd].pos[1]); - login_id1 = RFIFOL(fd, packet_db[packet_ver][cmd].pos[2]); - client_tick = RFIFOL(fd, packet_db[packet_ver][cmd].pos[3]); - sex = RFIFOB(fd, packet_db[packet_ver][cmd].pos[4]); - - if( packet_ver < 5 || // reject really old client versions - (packet_ver <= 9 && (battle_config.packet_ver_flag & 1) == 0) || // older than 6sept04 - (packet_ver > 9 && (battle_config.packet_ver_flag & 1<<(packet_ver-9)) == 0)) // version not allowed - {// packet version rejected - ShowInfo("Rejected connection attempt, forbidden packet version (AID/CID: '"CL_WHITE"%d/%d"CL_RESET"', Packet Ver: '"CL_WHITE"%d"CL_RESET"', IP: '"CL_WHITE"%s"CL_RESET"').\n", account_id, char_id, packet_ver, ip2str(session[fd]->client_addr, NULL)); - WFIFOHEAD(fd,packet_len(0x6a)); - WFIFOW(fd,0) = 0x6a; - WFIFOB(fd,2) = 5; // Your Game's EXE file is not the latest version - WFIFOSET(fd,packet_len(0x6a)); - set_eof(fd); - return; - } + account_id = RFIFOL(fd, packet_db[cmd].pos[0]); + char_id = RFIFOL(fd, packet_db[cmd].pos[1]); + login_id1 = RFIFOL(fd, packet_db[cmd].pos[2]); + client_tick = RFIFOL(fd, packet_db[cmd].pos[3]); + sex = RFIFOB(fd, packet_db[cmd].pos[4]); if( runflag != MAPSERVER_ST_RUNNING ) { // not allowed clif->authfail_fd(fd,1);// server closed @@ -9131,7 +9011,6 @@ void clif_parse_WantToConnection(int fd, struct map_session_data* sd) CREATE(sd, TBL_PC, 1); sd->fd = fd; - sd->packet_ver = packet_ver; session[fd]->session_data = sd; pc_setnewpc(sd, account_id, char_id, login_id1, client_tick, sex, fd); @@ -9492,7 +9371,7 @@ void clif_notify_time(struct map_session_data* sd, unsigned long time) { /// There are various variants of this packet, some of them have padding between fields. void clif_parse_TickSend(int fd, struct map_session_data *sd) { - sd->client_tick = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + sd->client_tick = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); clif->notify_time(sd, gettick()); } @@ -9532,12 +9411,12 @@ void clif_parse_Hotkey(int fd, struct map_session_data *sd) { int cmd; cmd = RFIFOW(fd, 0); - idx = RFIFOW(fd, packet_db[sd->packet_ver][cmd].pos[0]); + idx = RFIFOW(fd, packet_db[cmd].pos[0]); if (idx >= MAX_HOTKEYS) return; - sd->status.hotkeys[idx].type = RFIFOB(fd, packet_db[sd->packet_ver][cmd].pos[1]); - sd->status.hotkeys[idx].id = RFIFOL(fd, packet_db[sd->packet_ver][cmd].pos[2]); - sd->status.hotkeys[idx].lv = RFIFOW(fd, packet_db[sd->packet_ver][cmd].pos[3]); + sd->status.hotkeys[idx].type = RFIFOB(fd, packet_db[cmd].pos[1]); + sd->status.hotkeys[idx].id = RFIFOL(fd, packet_db[cmd].pos[2]); + sd->status.hotkeys[idx].lv = RFIFOW(fd, packet_db[cmd].pos[3]); #endif } @@ -9607,7 +9486,7 @@ void clif_parse_WalkToXY(int fd, struct map_session_data *sd) pc_delinvincibletimer(sd); - RFIFOPOS(fd, packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0], &x, &y, NULL); + RFIFOPOS(fd, packet_db[RFIFOW(fd,0)].pos[0], &x, &y, NULL); //Set last idle time... [Skotlex] sd->idletime = last_tick; @@ -9657,7 +9536,7 @@ void clif_parse_QuitGame(int fd, struct map_session_data *sd) /// There are various variants of this packet, some of them have padding between fields. void clif_parse_GetCharNameRequest(int fd, struct map_session_data *sd) { - int id = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + int id = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); struct block_list* bl; //struct status_change *sc; @@ -9838,8 +9717,8 @@ void clif_parse_ChangeDir(int fd, struct map_session_data *sd) { unsigned char headdir, dir; - headdir = RFIFOB(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); - dir = RFIFOB(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]); + headdir = RFIFOB(fd,packet_db[RFIFOW(fd,0)].pos[0]); + dir = RFIFOB(fd,packet_db[RFIFOW(fd,0)].pos[1]); pc_setdir(sd, dir, headdir); clif->changed_dir(&sd->bl, AREA_WOS); @@ -9852,7 +9731,7 @@ void clif_parse_ChangeDir(int fd, struct map_session_data *sd) /// @see enum emotion_type void clif_parse_Emotion(int fd, struct map_session_data *sd) { - int emoticon = RFIFOB(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + int emoticon = RFIFOB(fd,packet_db[RFIFOW(fd,0)].pos[0]); if (battle_config.basic_skill_check == 0 || pc_checkskill(sd, NV_BASIC) >= 2) { if (emoticon == E_MUTE) {// prevent use of the mute emote [Valaris] @@ -10036,8 +9915,8 @@ void clif_hercules_chsys_left(struct hChSysCh *channel, struct map_session_data void clif_parse_ActionRequest(int fd, struct map_session_data *sd) { clif->pActionRequest_sub(sd, - RFIFOB(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]), - RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]), + RFIFOB(fd,packet_db[RFIFOW(fd,0)].pos[1]), + RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]), gettick() ); } @@ -10239,7 +10118,7 @@ void clif_parse_TakeItem(int fd, struct map_session_data *sd) struct flooritem_data *fitem; int map_object_id; - map_object_id = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + map_object_id = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); fitem = (struct flooritem_data*)map_id2bl(map_object_id); @@ -10281,8 +10160,8 @@ void clif_parse_TakeItem(int fd, struct map_session_data *sd) /// There are various variants of this packet, some of them have padding between fields. void clif_parse_DropItem(int fd, struct map_session_data *sd) { - int item_index = RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0])-2; - int item_amount = RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]); + int item_index = RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[0])-2; + int item_amount = RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[1]); for(;;) { if (pc_isdead(sd)) @@ -10327,7 +10206,7 @@ void clif_parse_UseItem(int fd, struct map_session_data *sd) //Whether the item is used or not is irrelevant, the char ain't idle. [Skotlex] sd->idletime = last_tick; - n = RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0])-2; + n = RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[0])-2; if(n <0 || n >= MAX_INVENTORY) return; @@ -10949,9 +10828,9 @@ void clif_parse_UseSkillToId(int fd, struct map_session_data *sd) int tmp, target_id; unsigned int tick = gettick(); - skill_lv = RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); - skill_id = RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]); - target_id = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[2]); + skill_lv = RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[0]); + skill_id = RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[1]); + target_id = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[2]); if( skill_lv < 1 ) skill_lv = 1; //No clue, I have seen the client do this with guild skills :/ [Skotlex] @@ -11129,10 +11008,10 @@ void clif_parse_UseSkillToPos(int fd, struct map_session_data *sd) return; clif->pUseSkillToPosSub(fd, sd, - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]), //skill lv - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]), //skill num - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[2]), //pos x - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[3]), //pos y + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[0]), //skill lv + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[1]), //skill num + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[2]), //pos x + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[3]), //pos y -1 //Skill more info. ); } @@ -11150,11 +11029,11 @@ void clif_parse_UseSkillToPosMoreInfo(int fd, struct map_session_data *sd) return; clif->pUseSkillToPosSub(fd, sd, - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]), //Skill lv - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]), //Skill num - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[2]), //pos x - RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[3]), //pos y - packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[4] //skill more info + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[0]), //Skill lv + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[1]), //Skill num + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[2]), //pos x + RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[3]), //pos y + packet_db[RFIFOW(fd,0)].pos[4] //skill more info ); } @@ -11273,7 +11152,7 @@ void clif_parse_WeaponRefine(int fd, struct map_session_data *sd) clif_menuskill_clear(sd); return; } - idx = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + idx = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); skill->weaponrefine(sd, idx-2); clif_menuskill_clear(sd); } @@ -11445,7 +11324,7 @@ void clif_parse_SolveCharName(int fd, struct map_session_data *sd) { int charid; - charid = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + charid = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); map_reqnickdb(sd, charid); } @@ -11496,8 +11375,8 @@ void clif_parse_MoveToKafra(int fd, struct map_session_data *sd) if (pc_istrading(sd)) return; - item_index = RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0])-2; - item_amount = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]); + item_index = RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[0])-2; + item_amount = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[1]); if (item_index < 0 || item_index >= MAX_INVENTORY || item_amount < 1) return; @@ -11517,8 +11396,8 @@ void clif_parse_MoveFromKafra(int fd,struct map_session_data *sd) { int item_index, item_amount; - item_index = RFIFOW(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0])-1; - item_amount = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1]); + item_index = RFIFOW(fd,packet_db[RFIFOW(fd,0)].pos[0])-1; + item_amount = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[1]); if (sd->state.storage_flag == 1) storage_storageget(sd, item_index, item_amount); @@ -12602,7 +12481,7 @@ void clif_parse_GMRemove2(int fd, struct map_session_data* sd) int account_id; struct map_session_data* pl_sd; - account_id = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + account_id = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); if( (pl_sd = map_id2sd(account_id)) != NULL ) { char command[NAME_LENGTH+8]; sprintf(command, "%cjumpto %s", atcommand_symbol, pl_sd->status.name); @@ -12639,7 +12518,7 @@ void clif_parse_GMRecall2(int fd, struct map_session_data* sd) int account_id; struct map_session_data* pl_sd; - account_id = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + account_id = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); if( (pl_sd = map_id2sd(account_id)) != NULL ) { char command[NAME_LENGTH+8]; sprintf(command, "%crecall %s", atcommand_symbol, pl_sd->status.name); @@ -13511,7 +13390,7 @@ void clif_parse_HomMoveTo(int fd, struct map_session_data *sd) struct block_list *bl = NULL; short x, y; - RFIFOPOS(fd, packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[1], &x, &y, NULL); + RFIFOPOS(fd, packet_db[RFIFOW(fd,0)].pos[1], &x, &y, NULL); if( sd->md && sd->md->bl.id == id ) bl = &sd->md->bl; // Moving Mercenary @@ -13563,7 +13442,7 @@ void clif_parse_HomMenu(int fd, struct map_session_data *sd) if(!merc_is_hom_active(sd->hd)) return; - merc_menu(sd,RFIFOB(fd,packet_db[sd->packet_ver][cmd].pos[1])); + merc_menu(sd,RFIFOB(fd,packet_db[cmd].pos[1])); } @@ -13638,10 +13517,9 @@ void clif_parse_Check(int fd, struct map_session_data *sd) if(!pc_has_permission(sd, PC_PERM_USE_CHECK)) return; - safestrncpy(charname, (const char*)RFIFOP(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]), sizeof(charname)); + safestrncpy(charname, (const char*)RFIFOP(fd,packet_db[RFIFOW(fd,0)].pos[0]), sizeof(charname)); - if( ( pl_sd = map_nick2sd(charname) ) == NULL || pc_get_group_level(sd) < pc_get_group_level(pl_sd) ) - { + if( ( pl_sd = map_nick2sd(charname) ) == NULL || pc_get_group_level(sd) < pc_get_group_level(pl_sd) ) { return; } @@ -15424,7 +15302,7 @@ void clif_showdigit(struct map_session_data* sd, unsigned char type, int value) /// Graffiti. void clif_parse_LessEffect(int fd, struct map_session_data* sd) { - int isLess = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + int isLess = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); sd->state.lesseffect = ( isLess != 0 ); } @@ -15546,7 +15424,7 @@ void clif_parse_ReqOpenBuyingStore(int fd, struct map_session_data* sd) { unsigned char result; int zenylimit; unsigned int count, packet_len; - struct s_packet_db* info = &packet_db[sd->packet_ver][RFIFOW(fd,0)]; + struct s_packet_db* info = &packet_db[RFIFOW(fd,0)]; packet_len = RFIFOW(fd,info->pos[0]); @@ -15679,7 +15557,7 @@ void clif_parse_ReqClickBuyingStore(int fd, struct map_session_data* sd) { int account_id; - account_id = RFIFOL(fd,packet_db[sd->packet_ver][RFIFOW(fd,0)].pos[0]); + account_id = RFIFOL(fd,packet_db[RFIFOW(fd,0)].pos[0]); buyingstore_open(sd, account_id); } @@ -15718,7 +15596,7 @@ void clif_parse_ReqTradeBuyingStore(int fd, struct map_session_data* sd) { uint8* itemlist; int account_id; unsigned int count, packet_len, buyer_id; - struct s_packet_db* info = &packet_db[sd->packet_ver][RFIFOW(fd,0)]; + struct s_packet_db* info = &packet_db[RFIFOW(fd,0)]; packet_len = RFIFOW(fd,info->pos[0]); @@ -15834,7 +15712,7 @@ void clif_parse_SearchStoreInfo(int fd, struct map_session_data* sd) { const uint8* cardlist; unsigned char type; unsigned int min_price, max_price, packet_len, count, item_count, card_count; - struct s_packet_db* info = &packet_db[sd->packet_ver][RFIFOW(fd,0)]; + struct s_packet_db* info = &packet_db[RFIFOW(fd,0)]; packet_len = RFIFOW(fd,info->pos[0]); @@ -15982,7 +15860,7 @@ void clif_parse_SearchStoreInfoListItemClick(int fd, struct map_session_data* sd { unsigned short nameid; int account_id, store_id; - struct s_packet_db* info = &packet_db[sd->packet_ver][RFIFOW(fd,0)]; + struct s_packet_db* info = &packet_db[RFIFOW(fd,0)]; account_id = RFIFOL(fd,info->pos[0]); store_id = RFIFOL(fd,info->pos[1]); @@ -16014,20 +15892,13 @@ void clif_parse_debug(int fd,struct map_session_data *sd) { cmd = RFIFOW(fd,0); if( sd ) { - packet_len = packet_db[sd->packet_ver][cmd].len; + packet_len = packet_db[cmd].len; - if( packet_len == 0 ) - {// unknown - packet_len = RFIFOREST(fd); - } - else if( packet_len == -1 ) - {// variable length + if( packet_len == -1 ) {// variable length packet_len = RFIFOW(fd,2); // clif_parse ensures, that this amount of data is already received } ShowDebug("Packet debug of 0x%04X (length %d), %s session #%d, %d/%d (AID/CID)\n", cmd, packet_len, sd->state.active ? "authed" : "unauthed", fd, sd->status.account_id, sd->status.char_id); - } - else - { + } else { packet_len = RFIFOREST(fd); ShowDebug("Packet debug of 0x%04X (length %d), session #%d\n", cmd, packet_len, fd); } @@ -16413,753 +16284,167 @@ void clif_monster_hp_bar( struct mob_data* md, int fd ) { * Main client packet processing function *------------------------------------------*/ int clif_parse(int fd) { - int cmd, packet_ver, packet_len, err; + int cmd, packet_len; TBL_PC* sd; int pnum; //TODO apply delays or disconnect based on packet throughput [FlavioJS] // Note: "click masters" can do 80+ clicks in 10 seconds - for( pnum = 0; pnum < 3; ++pnum )// Limit max packets per cycle to 3 (delay packet spammers) [FlavioJS] -- This actually aids packet spammers, but stuff like /str+ gets slow without it [Ai4rei] - { // begin main client packet processing loop - - sd = (TBL_PC *)session[fd]->session_data; - if (session[fd]->flag.eof) { - if (sd) { - if (sd->state.autotrade) { - //Disassociate character from the socket connection. - session[fd]->session_data = NULL; - sd->fd = 0; - ShowInfo("Character '"CL_WHITE"%s"CL_RESET"' logged off (using @autotrade).\n", sd->status.name); - } else - if (sd->state.active) { - // Player logout display [Valaris] - ShowInfo("Character '"CL_WHITE"%s"CL_RESET"' logged off.\n", sd->status.name); - clif->quitsave(fd, sd); + for( pnum = 0; pnum < 3; ++pnum ) { // Limit max packets per cycle to 3 (delay packet spammers) [FlavioJS] -- This actually aids packet spammers, but stuff like /str+ gets slow without it [Ai4rei] + // begin main client packet processing loop + + sd = (TBL_PC *)session[fd]->session_data; + if (session[fd]->flag.eof) { + if (sd) { + if (sd->state.autotrade) { + //Disassociate character from the socket connection. + session[fd]->session_data = NULL; + sd->fd = 0; + ShowInfo("Character '"CL_WHITE"%s"CL_RESET"' logged off (using @autotrade).\n", sd->status.name); + } else + if (sd->state.active) { + // Player logout display [Valaris] + ShowInfo("Character '"CL_WHITE"%s"CL_RESET"' logged off.\n", sd->status.name); + clif->quitsave(fd, sd); + } else { + //Unusual logout (during log on/off/map-changer procedure) + ShowInfo("Player AID:%d/CID:%d logged off.\n", sd->status.account_id, sd->status.char_id); + map_quit(sd); + } } else { - //Unusual logout (during log on/off/map-changer procedure) - ShowInfo("Player AID:%d/CID:%d logged off.\n", sd->status.account_id, sd->status.char_id); - map_quit(sd); + ShowInfo("Closed connection from '"CL_WHITE"%s"CL_RESET"'.\n", ip2str(session[fd]->client_addr, NULL)); } - } else { - ShowInfo("Closed connection from '"CL_WHITE"%s"CL_RESET"'.\n", ip2str(session[fd]->client_addr, NULL)); + do_close(fd); + return 0; } - do_close(fd); - return 0; - } - if (RFIFOREST(fd) < 2) - return 0; + if (RFIFOREST(fd) < 2) + return 0; - cmd = RFIFOW(fd,0); + cmd = RFIFOW(fd,0); - // identify client's packet version - if (sd) { - packet_ver = sd->packet_ver; - } else { - // check authentification packet to know packet version - packet_ver = clif->guess_PacketVer(fd, 0, &err); - if( err ) {// failed to identify packet version - ShowInfo("clif_parse: Disconnecting session #%d with unknown packet version%s (p:0x%04x,l:%d).\n", fd, ( - err == 1 ? "" : - err == 2 ? ", possibly for having an invalid account_id" : - err == 3 ? ", possibly for having an invalid char_id." : - /* Uncomment when checks are added in clif_guess_PacketVer. [FlavioJS] - err == 4 ? ", possibly for having an invalid login_id1." : - err == 5 ? ", possibly for having an invalid client_tick." : - */ - err == 6 ? ", possibly for having an invalid sex." : - ". ERROR invalid error code"), cmd, RFIFOREST(fd)); - WFIFOHEAD(fd,packet_len(0x6a)); - WFIFOW(fd,0) = 0x6a; - WFIFOB(fd,2) = 3; // Rejected from Server - WFIFOSET(fd,packet_len(0x6a)); - -#ifdef DUMP_INVALID_PACKET + // filter out invalid / unsupported packets + if (cmd > MAX_PACKET_DB || packet_db[cmd].len == 0) { + ShowWarning("clif_parse: Received unsupported packet (packet 0x%04x, %d bytes received), disconnecting session #%d.\n", cmd, RFIFOREST(fd), fd); + #ifdef DUMP_INVALID_PACKET ShowDump(RFIFOP(fd,0), RFIFOREST(fd)); -#endif - - RFIFOSKIP(fd, RFIFOREST(fd)); + #endif set_eof(fd); return 0; } - } - // filter out invalid / unsupported packets - if (cmd > MAX_PACKET_DB || packet_db[packet_ver][cmd].len == 0) { - ShowWarning("clif_parse: Received unsupported packet (packet 0x%04x, %d bytes received), disconnecting session #%d.\n", cmd, RFIFOREST(fd), fd); -#ifdef DUMP_INVALID_PACKET - ShowDump(RFIFOP(fd,0), RFIFOREST(fd)); -#endif - set_eof(fd); - return 0; - } - - // determine real packet length - packet_len = packet_db[packet_ver][cmd].len; - if (packet_len == -1) { // variable-length packet - if (RFIFOREST(fd) < 4) - return 0; + // determine real packet length + packet_len = packet_db[cmd].len; + if (packet_len == -1) { // variable-length packet + if (RFIFOREST(fd) < 4) + return 0; - packet_len = RFIFOW(fd,2); - if (packet_len < 4 || packet_len > 32768) { - ShowWarning("clif_parse: Received packet 0x%04x specifies invalid packet_len (%d), disconnecting session #%d.\n", cmd, packet_len, fd); -#ifdef DUMP_INVALID_PACKET - ShowDump(RFIFOP(fd,0), RFIFOREST(fd)); -#endif - set_eof(fd); - return 0; + packet_len = RFIFOW(fd,2); + if (packet_len < 4 || packet_len > 32768) { + ShowWarning("clif_parse: Received packet 0x%04x specifies invalid packet_len (%d), disconnecting session #%d.\n", cmd, packet_len, fd); + #ifdef DUMP_INVALID_PACKET + ShowDump(RFIFOP(fd,0), RFIFOREST(fd)); + #endif + set_eof(fd); + return 0; + } } - } - if ((int)RFIFOREST(fd) < packet_len) - return 0; // not enough data received to form the packet - - if( packet_db[packet_ver][cmd].func == clif->pDebug ) - packet_db[packet_ver][cmd].func(fd, sd); - else if( packet_db[packet_ver][cmd].func != NULL ) { - if( !sd && packet_db[packet_ver][cmd].func != clif->pWantToConnection ) - ; //Only valid packet when there is no session - else - if( sd && sd->bl.prev == NULL && packet_db[packet_ver][cmd].func != clif->pLoadEndAck ) - ; //Only valid packet when player is not on a map - else - packet_db[packet_ver][cmd].func(fd, sd); - } -#ifdef DUMP_UNKNOWN_PACKET - else { - const char* packet_txt = "save/packet.txt"; - FILE* fp; + if ((int)RFIFOREST(fd) < packet_len) + return 0; // not enough data received to form the packet + + if( packet_db[cmd].func == clif->pDebug ) + packet_db[cmd].func(fd, sd); + else if( packet_db[cmd].func != NULL ) { + if( !sd && packet_db[cmd].func != clif->pWantToConnection ) + ; //Only valid packet when there is no session + else + if( sd && sd->bl.prev == NULL && packet_db[cmd].func != clif->pLoadEndAck ) + ; //Only valid packet when player is not on a map + else + packet_db[cmd].func(fd, sd); + } + #ifdef DUMP_UNKNOWN_PACKET + else { + const char* packet_txt = "save/packet.txt"; + FILE* fp; + + if( ( fp = fopen( packet_txt , "a" ) ) != NULL ) { + if( sd ) { + fprintf(fp, "Unknown packet 0x%04X (length %d), %s session #%d, %d/%d (AID/CID)\n", cmd, packet_len, sd->state.active ? "authed" : "unauthed", fd, sd->status.account_id, sd->status.char_id); + } else { + fprintf(fp, "Unknown packet 0x%04X (length %d), session #%d\n", cmd, packet_len, fd); + } - if( ( fp = fopen( packet_txt , "a" ) ) != NULL ) { - if( sd ) { - fprintf(fp, "Unknown packet 0x%04X (length %d), %s session #%d, %d/%d (AID/CID)\n", cmd, packet_len, sd->state.active ? "authed" : "unauthed", fd, sd->status.account_id, sd->status.char_id); + WriteDump(fp, RFIFOP(fd,0), packet_len); + fprintf(fp, "\n"); + fclose(fp); } else { - fprintf(fp, "Unknown packet 0x%04X (length %d), session #%d\n", cmd, packet_len, fd); - } + ShowError("Failed to write '%s'.\n", packet_txt); - WriteDump(fp, RFIFOP(fd,0), packet_len); - fprintf(fp, "\n"); - fclose(fp); - } else { - ShowError("Failed to write '%s'.\n", packet_txt); + // Dump on console instead + if( sd ) { + ShowDebug("Unknown packet 0x%04X (length %d), %s session #%d, %d/%d (AID/CID)\n", cmd, packet_len, sd->state.active ? "authed" : "unauthed", fd, sd->status.account_id, sd->status.char_id); + } else { + ShowDebug("Unknown packet 0x%04X (length %d), session #%d\n", cmd, packet_len, fd); + } - // Dump on console instead - if( sd ) { - ShowDebug("Unknown packet 0x%04X (length %d), %s session #%d, %d/%d (AID/CID)\n", cmd, packet_len, sd->state.active ? "authed" : "unauthed", fd, sd->status.account_id, sd->status.char_id); - } else { - ShowDebug("Unknown packet 0x%04X (length %d), session #%d\n", cmd, packet_len, fd); + ShowDump(RFIFOP(fd,0), packet_len); } - - ShowDump(RFIFOP(fd,0), packet_len); } - } -#endif + #endif - RFIFOSKIP(fd, packet_len); + RFIFOSKIP(fd, packet_len); }; // main loop end return 0; } -/*========================================== - * Reads packet_db.txt and setups its array reference - *------------------------------------------*/ -static int packetdb_readdb(void) -{ - FILE *fp; - char line[1024]; - int ln=0; - int cmd,i,j,packet_ver; - int max_cmd=-1; - int skip_ver = 0; - int warned = 0; - char *str[64],*p,*str2[64],*p2,w1[64],w2[64]; - int packet_len_table[MAX_PACKET_DB] = { - 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0040 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -#if PACKETVER <= 20081217 - 0, 0, 0, 0, 55, 17, 3, 37, 46, -1, 23, -1, 3,110, 3, 2, -#else - 0, 0, 0, 0, 55, 17, 3, 37, 46, -1, 23, -1, 3,114, 3, 2, -#endif -#if PACKETVER < 2 - 3, 28, 19, 11, 3, -1, 9, 5, 52, 51, 56, 58, 41, 2, 6, 6, -#elif PACKETVER < 20071106 // 78-7b Lv99 effect for later Kameshima - 3, 28, 19, 11, 3, -1, 9, 5, 54, 53, 58, 60, 41, 2, 6, 6, -#elif PACKETVER <= 20081217 // change in 0x78 and 0x7c - 3, 28, 19, 11, 3, -1, 9, 5, 55, 53, 58, 60, 42, 2, 6, 6, -#else - 3, 28, 19, 11, 3, -1, 9, 5, 55, 53, 58, 60, 44, 2, 6, 6, -#endif - //#0x0080 - 7, 3, 2, 2, 2, 5, 16, 12, 10, 7, 29, 2, -1, -1, -1, 0, // 0x8b changed to 2 (was 23) - 7, 22, 28, 2, 6, 30, -1, -1, 3, -1, -1, 5, 9, 17, 17, 6, -#if PACKETVER <= 20100622 - 23, 6, 6, -1, -1, -1, -1, 8, 7, 6, 7, 4, 7, 0, -1, 6, -#else - 23, 6, 6, -1, -1, -1, -1, 8, 7, 6, 9, 4, 7, 0, -1, 6, // 0xaa changed to 9 (was 7) -#endif - 8, 8, 3, 3, -1, 6, 6, -1, 7, 6, 2, 5, 6, 44, 5, 3, - //#0x00C0 - 7, 2, 6, 8, 6, 7, -1, -1, -1, -1, 3, 3, 6, 3, 2, 27, // 0xcd change to 3 (was 6) - 3, 4, 4, 2, -1, -1, 3, -1, 6, 14, 3, -1, 28, 29, -1, -1, - 30, 30, 26, 2, 6, 26, 3, 3, 8, 19, 5, 2, 3, 2, 2, 2, - 3, 2, 6, 8, 21, 8, 8, 2, 2, 26, 3, -1, 6, 27, 30, 10, - //#0x0100 - 2, 6, 6, 30, 79, 31, 10, 10, -1, -1, 4, 6, 6, 2, 11, -1, - 10, 39, 4, 10, 31, 35, 10, 18, 2, 13, 15, 20, 68, 2, 3, 16, - 6, 14, -1, -1, 21, 8, 8, 8, 8, 8, 2, 2, 3, 4, 2, -1, - 6, 86, 6, -1, -1, 7, -1, 6, 3, 16, 4, 4, 4, 6, 24, 26, - //#0x0140 - 22, 14, 6, 10, 23, 19, 6, 39, 8, 9, 6, 27, -1, 2, 6, 6, - 110, 6, -1, -1, -1, -1, -1, 6, -1, 54, 66, 54, 90, 42, 6, 42, - -1, -1, -1, -1, -1, 30, -1, 3, 14, 3, 30, 10, 43, 14,186,182, - 14, 30, 10, 3, -1, 6,106, -1, 4, 5, 4, -1, 6, 7, -1, -1, - //#0x0180 - 6, 3,106, 10, 10, 34, 0, 6, 8, 4, 4, 4, 29, -1, 10, 6, -#if PACKETVER < 1 - 90, 86, 24, 6, 30,102, 8, 4, 8, 4, 14, 10, -1, 6, 2, 6, -#else // 196 comodo icon status display for later - 90, 86, 24, 6, 30,102, 9, 4, 8, 4, 14, 10, -1, 6, 2, 6, -#endif -#if PACKETVER < 20081126 - 3, 3, 35, 5, 11, 26, -1, 4, 4, 6, 10, 12, 6, -1, 4, 4, -#else // 0x1a2 changed (35->37) - 3, 3, 37, 5, 11, 26, -1, 4, 4, 6, 10, 12, 6, -1, 4, 4, -#endif - 11, 7, -1, 67, 12, 18,114, 6, 3, 6, 26, 26, 26, 26, 2, 3, - //#0x01C0, Set 0x1d5=-1 - 2, 14, 10, -1, 22, 22, 4, 2, 13, 97, 3, 9, 9, 30, 6, 28, - 8, 14, 10, 35, 6, -1, 4, 11, 54, 53, 60, 2, -1, 47, 33, 6, - 30, 8, 34, 14, 2, 6, 26, 2, 28, 81, 6, 10, 26, 2, -1, -1, - -1, -1, 20, 10, 32, 9, 34, 14, 2, 6, 48, 56, -1, 4, 5, 10, - //#0x0200 - 26, -1, 26, 10, 18, 26, 11, 34, 14, 36, 10, 0, 0, -1, 32, 10, // 0x20c change to 0 (was 19) - 22, 0, 26, 26, 42, 6, 6, 2, 2,282,282, 10, 10, -1, -1, 66, -#if PACKETVER < 20071106 - 10, -1, -1, 8, 10, 2,282, 18, 18, 15, 58, 57, 64, 5, 71, 5, -#else // 0x22c changed - 10, -1, -1, 8, 10, 2,282, 18, 18, 15, 58, 57, 65, 5, 71, 5, -#endif - 12, 26, 9, 11, -1, -1, 10, 2,282, 11, 4, 36, 6, -1, 4, 2, - //#0x0240 - -1, -1, -1, -1, -1, 3, 4, 8, -1, 3, 70, 4, 8, 12, 4, 10, - 3, 32, -1, 3, 3, 5, 5, 8, 2, 3, -1, 6, 4, 6, 4, 6, - 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0280 -#if PACKETVER < 20070711 - 0, 0, 0, 6, 14, 0, 0, -1, 6, 8, 18, 0, 0, 0, 0, 0, -#else - 0, 0, 0, 6, 14, 0, 0, -1, 10, 12, 18, 0, 0, 0, 0, 0, // 0x288, 0x289 increase by 4 (kafra points) -#endif - 0, 4, 0, 70, 10, 0, 0, 0, 8, 6, 27, 80, 0, -1, 0, 0, - 0, 0, 8, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 85, -1, -1,107, 6, -1, 7, 7, 22,191, 0, 8, 0, 0, 0, 0, - //#0x02C0 - 0, -1, 0, 0, 0, 30, 30, 0, 0, 3, 0, 65, 4, 71, 10, 0, - -1, -1, -1, 0, 29, 0, 6, -1, 10, 10, 3, 0, -1, 32, 6, 36, - 34, 33, 0, 0, 0, 0, 0, 0, -1, -1, -1, 13, 67, 59, 60, 8, - 10, 2, 2, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0300 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0340 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0380 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x03C0 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0400 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 8, 0, 25, - //#0x0440 - 10, 4, -1, 0, 0, 0, 14, 0, 0, 0, 6, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0480 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x04C0 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0500 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 25, - //#0x0540 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0580 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x05C0 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0600 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 25, - //#0x0640 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0680 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x06C0 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0700 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 25, - //#0x0740 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0780 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x07C0 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, -#if PACKETVER < 20090617 - 6, 2, -1, 4, 4, 4, 4, 8, 8,254, 6, 8, 6, 54, 30, 54, -#else // 0x7d9 changed - 6, 2, -1, 4, 4, 4, 4, 8, 8,268, 6, 8, 6, 54, 30, 54, -#endif - 0, 15, 8, 6, -1, 8, 8, 32, -1, 5, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 14, -1, -1, -1, 8, 25, 0, 0, 26, 0, - //#0x0800 -#if PACKETVER < 20091229 - -1, -1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 14, 20, -#else // for Party booking ( PACKETVER >= 20091229 ) - -1, -1, 18, 4, 8, 6, 2, 4, 14, 50, 18, 6, 2, 3, 14, 20, -#endif - 3, -1, 8, -1, 86, 2, 6, 6, -1, -1, 4, 10, 10, 0, 0, 0, - 0, 0, 0, 0, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, -1, -1, 3, 2, 66, 5, 2, 12, 6, 0, 0, - //#0x0840 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, -1, -1, -1, -1, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0880 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x08C0 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 10, - 0, 0, 10, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0900 - 0, 0, 0, 0, 0, 0, 0, 0, 5, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0940 - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 14, 0, 0, 0, 0, 0, 0, 0, 0, - //#0x0980 - 0, 0, 0, 29, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 14, 0, 0, 0, 0, 0, 0, 0, 0, - - }; - struct { - void (*func)(int, struct map_session_data *); - char *name; - } clif_parse_func[]={ - {clif->pWantToConnection,"wanttoconnection"}, - {clif->pLoadEndAck,"loadendack"}, - {clif->pTickSend,"ticksend"}, - {clif->pWalkToXY,"walktoxy"}, - {clif->pQuitGame,"quitgame"}, - {clif->pGetCharNameRequest,"getcharnamerequest"}, - {clif->pGlobalMessage,"globalmessage"}, - {clif->pMapMove,"mapmove"}, - {clif->pChangeDir,"changedir"}, - {clif->pEmotion,"emotion"}, - {clif->pHowManyConnections,"howmanyconnections"}, - {clif->pActionRequest,"actionrequest"}, - {clif->pRestart,"restart"}, - {clif->pWisMessage,"wis"}, - {clif->pBroadcast,"broadcast"}, - {clif->pTakeItem,"takeitem"}, - {clif->pDropItem,"dropitem"}, - {clif->pUseItem,"useitem"}, - {clif->pEquipItem,"equipitem"}, - {clif->pUnequipItem,"unequipitem"}, - {clif->pNpcClicked,"npcclicked"}, - {clif->pNpcBuySellSelected,"npcbuysellselected"}, - {clif->pNpcBuyListSend,"npcbuylistsend"}, - {clif->pNpcSellListSend,"npcselllistsend"}, - {clif->pCreateChatRoom,"createchatroom"}, - {clif->pChatAddMember,"chataddmember"}, - {clif->pChatRoomStatusChange,"chatroomstatuschange"}, - {clif->pChangeChatOwner,"changechatowner"}, - {clif->pKickFromChat,"kickfromchat"}, - {clif->pChatLeave,"chatleave"}, - {clif->pTradeRequest,"traderequest"}, - {clif->pTradeAck,"tradeack"}, - {clif->pTradeAddItem,"tradeadditem"}, - {clif->pTradeOk,"tradeok"}, - {clif->pTradeCancel,"tradecancel"}, - {clif->pTradeCommit,"tradecommit"}, - {clif->pStopAttack,"stopattack"}, - {clif->pPutItemToCart,"putitemtocart"}, - {clif->pGetItemFromCart,"getitemfromcart"}, - {clif->pRemoveOption,"removeoption"}, - {clif->pChangeCart,"changecart"}, - {clif->pStatusUp,"statusup"}, - {clif->pSkillUp,"skillup"}, - {clif->pUseSkillToId,"useskilltoid"}, - {clif->pUseSkillToPos,"useskilltopos"}, - {clif->pUseSkillToPosMoreInfo,"useskilltoposinfo"}, - {clif->pUseSkillMap,"useskillmap"}, - {clif->pRequestMemo,"requestmemo"}, - {clif->pProduceMix,"producemix"}, - {clif->pCooking,"cooking"}, - {clif->pNpcSelectMenu,"npcselectmenu"}, - {clif->pNpcNextClicked,"npcnextclicked"}, - {clif->pNpcAmountInput,"npcamountinput"}, - {clif->pNpcStringInput,"npcstringinput"}, - {clif->pNpcCloseClicked,"npccloseclicked"}, - {clif->pItemIdentify,"itemidentify"}, - {clif->pSelectArrow,"selectarrow"}, - {clif->pAutoSpell,"autospell"}, - {clif->pUseCard,"usecard"}, - {clif->pInsertCard,"insertcard"}, - {clif->pRepairItem,"repairitem"}, - {clif->pWeaponRefine,"weaponrefine"}, - {clif->pSolveCharName,"solvecharname"}, - {clif->pResetChar,"resetchar"}, - {clif->pLocalBroadcast,"localbroadcast"}, - {clif->pMoveToKafra,"movetokafra"}, - {clif->pMoveFromKafra,"movefromkafra"}, - {clif->pMoveToKafraFromCart,"movetokafrafromcart"}, - {clif->pMoveFromKafraToCart,"movefromkafratocart"}, - {clif->pCloseKafra,"closekafra"}, - {clif->pCreateParty,"createparty"}, - {clif->pCreateParty2,"createparty2"}, - {clif->pPartyInvite,"partyinvite"}, - {clif->pPartyInvite2,"partyinvite2"}, - {clif->pReplyPartyInvite,"replypartyinvite"}, - {clif->pReplyPartyInvite2,"replypartyinvite2"}, - {clif->pLeaveParty,"leaveparty"}, - {clif->pRemovePartyMember,"removepartymember"}, - {clif->pPartyChangeOption,"partychangeoption"}, - {clif->pPartyMessage,"partymessage"}, - {clif->pPartyChangeLeader,"partychangeleader"}, - {clif->pCloseVending,"closevending"}, - {clif->pVendingListReq,"vendinglistreq"}, - {clif->pPurchaseReq,"purchasereq"}, - {clif->pPurchaseReq2,"purchasereq2"}, - {clif->pOpenVending,"openvending"}, - {clif->pCreateGuild,"createguild"}, - {clif->pGuildCheckMaster,"guildcheckmaster"}, - {clif->pGuildRequestInfo,"guildrequestinfo"}, - {clif->pGuildChangePositionInfo,"guildchangepositioninfo"}, - {clif->pGuildChangeMemberPosition,"guildchangememberposition"}, - {clif->pGuildRequestEmblem,"guildrequestemblem"}, - {clif->pGuildChangeEmblem,"guildchangeemblem"}, - {clif->pGuildChangeNotice,"guildchangenotice"}, - {clif->pGuildInvite,"guildinvite"}, - {clif->pGuildReplyInvite,"guildreplyinvite"}, - {clif->pGuildLeave,"guildleave"}, - {clif->pGuildExpulsion,"guildexpulsion"}, - {clif->pGuildMessage,"guildmessage"}, - {clif->pGuildRequestAlliance,"guildrequestalliance"}, - {clif->pGuildReplyAlliance,"guildreplyalliance"}, - {clif->pGuildDelAlliance,"guilddelalliance"}, - {clif->pGuildOpposition,"guildopposition"}, - {clif->pGuildBreak,"guildbreak"}, - {clif->pPetMenu,"petmenu"}, - {clif->pCatchPet,"catchpet"}, - {clif->pSelectEgg,"selectegg"}, - {clif->pSendEmotion,"sendemotion"}, - {clif->pChangePetName,"changepetname"}, - {clif->pGMKick,"gmkick"}, - {clif->pGMHide,"gmhide"}, - {clif->pGMReqNoChat,"gmreqnochat"}, - {clif->pGMReqAccountName,"gmreqaccname"}, - {clif->pGMKickAll,"killall"}, - {clif->pGMRecall,"recall"}, - {clif->pGMRecall,"summon"}, - {clif->pGM_Monster_Item,"itemmonster"}, - {clif->pGMShift,"remove"}, - {clif->pGMShift,"shift"}, - {clif->pGMChangeMapType,"changemaptype"}, - {clif->pGMRc,"rc"}, - {clif->pGMRecall2,"recall2"}, - {clif->pGMRemove2,"remove2"}, - - {clif->pNoviceDoriDori,"sndoridori"}, - {clif->pNoviceExplosionSpirits,"snexplosionspirits"}, - {clif->pPMIgnore,"wisexin"}, - {clif->pPMIgnoreList,"wisexlist"}, - {clif->pPMIgnoreAll,"wisall"}, - {clif->pFriendsListAdd,"friendslistadd"}, - {clif->pFriendsListRemove,"friendslistremove"}, - {clif->pFriendsListReply,"friendslistreply"}, - {clif->pBlacksmith,"blacksmith"}, - {clif->pAlchemist,"alchemist"}, - {clif->pTaekwon,"taekwon"}, - {clif->pRankingPk,"rankingpk"}, - {clif->pFeelSaveOk,"feelsaveok"}, - {clif->pDebug,"debug"}, - {clif->pChangeHomunculusName,"changehomunculusname"}, - {clif->pHomMoveToMaster,"hommovetomaster"}, - {clif->pHomMoveTo,"hommoveto"}, - {clif->pHomAttack,"homattack"}, - {clif->pHomMenu,"hommenu"}, - {clif->pStoragePassword,"storagepassword"}, - {clif->pHotkey,"hotkey"}, - {clif->pAutoRevive,"autorevive"}, - {clif->pCheck,"check"}, - {clif->pAdopt_request,"adoptrequest"}, - {clif->pAdopt_reply,"adoptreply"}, - // MAIL SYSTEM - {clif->pMail_refreshinbox,"mailrefresh"}, - {clif->pMail_read,"mailread"}, - {clif->pMail_getattach,"mailgetattach"}, - {clif->pMail_delete,"maildelete"}, - {clif->pMail_return,"mailreturn"}, - {clif->pMail_setattach,"mailsetattach"}, - {clif->pMail_winopen,"mailwinopen"}, - {clif->pMail_send,"mailsend"}, - // AUCTION SYSTEM - {clif->pAuction_search,"auctionsearch"}, - {clif->pAuction_buysell,"auctionbuysell"}, - {clif->pAuction_setitem,"auctionsetitem"}, - {clif->pAuction_cancelreg,"auctioncancelreg"}, - {clif->pAuction_register,"auctionregister"}, - {clif->pAuction_cancel,"auctioncancel"}, - {clif->pAuction_close,"auctionclose"}, - {clif->pAuction_bid,"auctionbid"}, - // Quest Log System - {clif->pquestStateAck,"queststate"}, - {clif->pcashshop_buy,"cashshopbuy"}, - {clif->pViewPlayerEquip,"viewplayerequip"}, - {clif->pEquipTick,"equiptickbox"}, - {clif->pBattleChat,"battlechat"}, - {clif->pmercenary_action,"mermenu"}, - {clif->pProgressbar,"progressbar"}, - {clif->pSkillSelectMenu,"skillselectmenu"}, - {clif->pItemListWindowSelected,"itemlistwindowselected"}, -#if PACKETVER >= 20091229 - {clif->pPartyBookingRegisterReq,"bookingregreq"}, - {clif->pPartyBookingSearchReq,"bookingsearchreq"}, - {clif->pPartyBookingUpdateReq,"bookingupdatereq"}, - {clif->pPartyBookingDeleteReq,"bookingdelreq"}, -#endif - {clif->pPVPInfo,"pvpinfo"}, - {clif->pLessEffect,"lesseffect"}, - // Buying Store - {clif->pReqOpenBuyingStore,"reqopenbuyingstore"}, - {clif->pReqCloseBuyingStore,"reqclosebuyingstore"}, - {clif->pReqClickBuyingStore,"reqclickbuyingstore"}, - {clif->pReqTradeBuyingStore,"reqtradebuyingstore"}, - // Store Search - {clif->pSearchStoreInfo,"searchstoreinfo"}, - {clif->pSearchStoreInfoNextPage,"searchstoreinfonextpage"}, - {clif->pCloseSearchStoreInfo,"closesearchstoreinfo"}, - {clif->pSearchStoreInfoListItemClick,"searchstoreinfolistitemclick"}, - /* */ - { clif->pMoveItem , "moveitem" }, - {NULL,NULL} - }; - - // initialize packet_db[SERVER] from hardcoded packet_len_table[] values - memset(packet_db,0,sizeof(packet_db)); - for( i = 0; i < ARRAYLENGTH(packet_len_table); ++i ) - packet_len(i) = packet_len_table[i]; - - sprintf(line, "%s/packet_db.txt", db_path); - if( (fp=fopen(line,"r"))==NULL ){ - ShowFatalError("can't read %s\n", line); - exit(EXIT_FAILURE); - } - - clif_config.packet_db_ver = MAX_PACKET_VER; - packet_ver = MAX_PACKET_VER; // read into packet_db's version by default - while( fgets(line, sizeof(line), fp) ) - { - ln++; - if(line[0]=='/' && line[1]=='/') - continue; - if (sscanf(line,"%256[^:]: %256[^\r\n]",w1,w2) == 2) - { - if(strcmpi(w1,"packet_ver")==0) { - int prev_ver = packet_ver; - skip_ver = 0; - packet_ver = atoi(w2); - if ( packet_ver > MAX_PACKET_VER ) - { //Check to avoid overflowing. [Skotlex] - if( (warned&1) == 0 ) - ShowWarning("The packet_db table only has support up to version %d.\n", MAX_PACKET_VER); - warned &= 1; - skip_ver = 1; - } - else if( packet_ver < 0 ) - { - if( (warned&2) == 0 ) - ShowWarning("Negative packet versions are not supported.\n"); - warned &= 2; - skip_ver = 1; - } - else if( packet_ver == SERVER ) - { - if( (warned&4) == 0 ) - ShowWarning("Packet version %d is reserved for server use only.\n", SERVER); - warned &= 4; - skip_ver = 1; - } - - if( skip_ver ) - { - ShowWarning("Skipping packet version %d.\n", packet_ver); - packet_ver = prev_ver; - continue; - } - // copy from previous version into new version and continue - // - indicating all following packets should be read into the newer version - memcpy(&packet_db[packet_ver], &packet_db[prev_ver], sizeof(packet_db[0])); - continue; - } else if(strcmpi(w1,"packet_db_ver")==0) { - if(strcmpi(w2,"default")==0) //This is the preferred version. - clif_config.packet_db_ver = MAX_PACKET_VER; - else // to manually set the packet DB version - clif_config.packet_db_ver = cap_value(atoi(w2), 0, MAX_PACKET_VER); - - continue; - } - } - - if( skip_ver != 0 ) - continue; // Skipping current packet version - - memset(str,0,sizeof(str)); - for(j=0,p=line;j<4 && p; ++j) - { - str[j]=p; - p=strchr(p,','); - if(p) *p++=0; - } - if(str[0]==NULL) - continue; - cmd=strtol(str[0],(char **)NULL,0); - - if(max_cmd < cmd) - max_cmd = cmd; - if(cmd <= 0 || cmd > MAX_PACKET_DB) - continue; - if(str[1]==NULL){ - ShowError("packet_db: packet len error\n"); - continue; - } - - packet_db[packet_ver][cmd].len = (short)atoi(str[1]); - - if(str[2]==NULL){ - packet_db[packet_ver][cmd].func = NULL; - ln++; - continue; - } - - // look up processing function by name - ARR_FIND( 0, ARRAYLENGTH(clif_parse_func), j, clif_parse_func[j].name != NULL && strcmp(str[2],clif_parse_func[j].name)==0 ); - if( j < ARRAYLENGTH(clif_parse_func) ) - packet_db[packet_ver][cmd].func = clif_parse_func[j].func; - - // set the identifying cmd for the packet_db version - if (strcmp(str[2],"wanttoconnection")==0) - clif_config.connect_cmd[packet_ver] = cmd; - - if(str[3]==NULL){ - ShowError("packet_db: packet error\n"); - exit(EXIT_FAILURE); - } - for(j=0,p2=str[3];p2;j++){ - short k; - str2[j]=p2; - p2=strchr(p2,':'); - if(p2) *p2++=0; - k = atoi(str2[j]); - // if (packet_db[packet_ver][cmd].pos[j] != k && clif_config.prefer_packet_db) // not used for now - - if( j >= MAX_PACKET_POS ) - { - ShowError("Too many positions found for packet 0x%04x (max=%d).\n", cmd, MAX_PACKET_POS); - break; - } - - packet_db[packet_ver][cmd].pos[j] = k; - } - } - fclose(fp); - if(max_cmd > MAX_PACKET_DB) - { - ShowWarning("Found packets up to 0x%X, ignored 0x%X and above.\n", max_cmd, MAX_PACKET_DB); - ShowWarning("Please increase MAX_PACKET_DB and recompile.\n"); +static void __attribute__ ((unused)) packetdb_addpacket(short cmd, int len, ...) { + va_list va; + int i; + int pos; + pFunc func; + + if (cmd > MAX_PACKET_DB) { + ShowError("Packet Error: packet 0x%x is greater than the maximum allowed (0x%x), skipping...\n", cmd, MAX_PACKET_DB); + return; } - if (!clif_config.connect_cmd[clif_config.packet_db_ver]) - { //Locate the nearest version that we still support. [Skotlex] - for(j = clif_config.packet_db_ver; j >= 0 && !clif_config.connect_cmd[j]; j--); - - clif_config.packet_db_ver = j?j:MAX_PACKET_VER; + + packet_db[cmd].len = len; + + va_start(va,len); + + pos = va_arg(va, int); + + if( pos == 0xFFFF ) /* nothing more to do */ + return; + + va_end(va); + va_start(va,len); + + func = va_arg(va,pFunc); + + packet_db[cmd].func = func; + + for (i = 0; i < MAX_PACKET_POS; i++) { + pos = va_arg(va, int); + + if (pos == 0xFFFF) + break; + + packet_db[cmd].pos[i] = pos; } - ShowStatus("Done reading packet database from '"CL_WHITE"%s"CL_RESET"'.\n","packet_db.txt"); - ShowStatus("Using default packet version: "CL_WHITE"%d"CL_RESET".\n", clif_config.packet_db_ver); - return 0; } - +void packetdb_loaddb(void) { + + memset(packet_db,0,sizeof(packet_db)); + + #define packet(id, size, ...) packetdb_addpacket(id, size, ##__VA_ARGS__, 0xFFFF) + #include "packets.h" /* load structure data */ + #undef packet +} /*========================================== * *------------------------------------------*/ @@ -17174,11 +16459,7 @@ int do_init_clif(void) { color_table[i] = (color_table[i] & 0x0000FF) << 16 | (color_table[i] & 0x00FF00) | (color_table[i] & 0xFF0000) >> 16;//RGB to BGR } - clif_config.packet_db_ver = -1; // the main packet version of the DB - memset(clif_config.connect_cmd, 0, sizeof(clif_config.connect_cmd)); //The default connect command will be determined after reading the packet_db [Skotlex] - - //Using the packet_db file is the only way to set up packets now [Skotlex] - packetdb_readdb(); + packetdb_loaddb(); set_defaultparse(clif->parse); if( make_listen_bind(clif->bind_ip,clif->map_port) == -1 ) { @@ -17650,7 +16931,6 @@ void clif_defaults(void) { clif->adopt_reply = clif_Adopt_reply; clif->adopt_request = clif_Adopt_request; clif->readbook = clif_readbook; - clif->guess_PacketVer = clif_guess_PacketVer; clif->notify_time = clif_notify_time; clif->user_count = clif_user_count; clif->noask_sub = clif_noask_sub; |