diff options
-rw-r--r-- | src/char/char.c | 46 | ||||
-rw-r--r-- | src/char/int_storage.c | 9 | ||||
-rw-r--r-- | src/char/int_storage.h | 1 | ||||
-rw-r--r-- | src/common/core.c | 37 | ||||
-rw-r--r-- | src/ladmin/ladmin.c | 221 | ||||
-rw-r--r-- | src/login/login.c | 10 | ||||
-rw-r--r-- | src/map/chrif.c | 103 |
7 files changed, 321 insertions, 106 deletions
diff --git a/src/char/char.c b/src/char/char.c index b8ce145..b14f25c 100644 --- a/src/char/char.c +++ b/src/char/char.c @@ -1778,6 +1778,50 @@ int parse_tologin(int fd) { } break; + case 0x7924: { // [Fate] Itemfrob package: forwarded from login-server + if (RFIFOREST(fd) < 10) + return 0; + int source_id = RFIFOL(fd, 2); + int dest_id = RFIFOL(fd, 6); + unsigned char buf[10]; + + WBUFW(buf, 0) = 0x2afa; + WBUFL(buf, 2) = source_id; + WBUFL(buf, 6) = dest_id; + + mapif_sendall(buf, 10); // forward package to map servers + for (i = 0; i < char_num; i++) { + struct mmo_charstatus *c = char_dat + i; + struct storage *s = account2maybe_storage(c->account_id); + int changes = 0; + int j; +#define FIX(v) if (v == source_id) {v = dest_id; ++changes; } + for (j = 0; j < MAX_INVENTORY; j++) + FIX(c->inventory[j].nameid); + for (j = 0; j < MAX_CART; j++) + FIX(c->cart[j].nameid); + FIX(c->weapon); + FIX(c->shield); + FIX(c->head_top); + FIX(c->head_mid); + FIX(c->head_bottom); + + if (s) + for (j = 0; j < s->storage_amount; j++) + FIX(s->storage[j].nameid); +#undef FIX + if (changes) + char_log("itemfrob(%d -> %d): `%s'(%d, account %d): changed %d times\n", source_id, dest_id, + c->name, c->char_id, c->account_id, changes); + + } + + mmo_char_sync(); + inter_storage_save(); + RFIFOSKIP(fd,10); + break; + } + // Account deletion notification (from login-server) case 0x2730: if (RFIFOREST(fd) < 6) @@ -2954,7 +2998,7 @@ int check_connect_login_server(int tid, unsigned int tick, int id, int data) { //---------------------------------------------------------- // Return numerical value of a switch configuration by [Yor] -// on/off, english, français, deutsch, español +// on/off, english, français, deutsch, espanol //---------------------------------------------------------- int config_switch(const char *str) { if (strcmpi(str, "on") == 0 || strcmpi(str, "yes") == 0 || strcmpi(str, "oui") == 0 || strcmpi(str, "ja") == 0 || strcmpi(str, "si") == 0) diff --git a/src/char/int_storage.c b/src/char/int_storage.c index b84b586..0774370 100644 --- a/src/char/int_storage.c +++ b/src/char/int_storage.c @@ -190,10 +190,17 @@ int guild_storage_fromstr(char *str,struct guild_storage *p) } // ƒAƒJƒEƒ“ƒg‚©‚ç‘qŒÉƒf[ƒ^ƒCƒ“ƒfƒbƒNƒX‚𓾂éiV‹K‘qŒÉ’ljÁ‰Â”\j -struct storage *account2storage(int account_id) +struct storage *account2maybe_storage(int account_id) { struct storage *s; s=numdb_search(storage_db,account_id); + return s; +} + +struct storage *account2storage(int account_id) +{ + struct storage *s = account2maybe_storage(account_id); + if(s == NULL) { s = calloc(sizeof(struct storage), 1); if(s==NULL){ diff --git a/src/char/int_storage.h b/src/char/int_storage.h index d918f5f..59f56c6 100644 --- a/src/char/int_storage.h +++ b/src/char/int_storage.h @@ -7,6 +7,7 @@ int inter_storage_save(); int inter_guild_storage_save(); int inter_storage_delete(int account_id); int inter_guild_storage_delete(int guild_id); +struct storage *account2maybe_storage(int account_id); int inter_storage_parse_frommap(int fd); diff --git a/src/common/core.c b/src/common/core.c index 62af254..2546f4e 100644 --- a/src/common/core.c +++ b/src/common/core.c @@ -51,6 +51,8 @@ static void sig_proc(int sn) } } +int eathena_interactive_session = 1; // [fate] interactive session: print pretty graphics + /*====================================== * CORE : Display title *-------------------------------------- @@ -65,21 +67,23 @@ static void display_title(void) // \033[K : clear line from actual position to end of the line // \033[0m : reset color parameter // \033[1m : use bold for font - printf("\033[2J"); // clear screen and go up/left (0, 0 position in text) - printf("\033[37;44m (=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=)\033[K\033[0m\n"); // white writing (37) on blue background (44), \033[K clean until end of file - printf("\033[0;44m (\033[1;33m (c)2004 eAthena Development Team presents \033[0;44m)\033[K\033[0m\n"); // yellow writing (33) - printf("\033[0;44m (\033[1m ______ __ __ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m /\\ _ \\/\\ \\__/\\ \\ v%2d.%02d.%02d \033[0;44m)\033[K\033[0m\n", ATHENA_MAJOR_VERSION, ATHENA_MINOR_VERSION, ATHENA_REVISION); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m __\\ \\ \\_\\ \\ \\ ,_\\ \\ \\___ __ ___ __ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m /'__`\\ \\ __ \\ \\ \\/\\ \\ _ `\\ /'__`\\/' _ `\\ /'__`\\ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m /\\ __/\\ \\ \\/\\ \\ \\ \\_\\ \\ \\ \\ \\/\\ __//\\ \\/\\ \\/\\ \\_\\.\\_ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m \\ \\____\\\\ \\_\\ \\_\\ \\__\\\\ \\_\\ \\_\\ \\____\\ \\_\\ \\_\\ \\__/.\\_\\ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m \\/____/ \\/_/\\/_/\\/__/ \\/_/\\/_/\\/____/\\/_/\\/_/\\/__/\\/_/ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m _ _ _ _ _ _ _ _ _ _ _ _ _ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m ( e | n | g | l | i | s | h ) ( A | t | h | e | n | a ) \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[0;44m (\033[1m \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char - printf("\033[37;44m (=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=)\033[K\033[0m\n\n"); // reset color + if (eathena_interactive_session) { + printf("\033[2J"); // clear screen and go up/left (0, 0 position in text) + printf("\033[37;44m (=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=)\033[K\033[0m\n"); // white writing (37) on blue background (44), \033[K clean until end of file + printf("\033[0;44m (\033[1;33m (c)2004 eAthena Development Team presents \033[0;44m)\033[K\033[0m\n"); // yellow writing (33) + printf("\033[0;44m (\033[1m ______ __ __ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m /\\ _ \\/\\ \\__/\\ \\ v%2d.%02d.%02d \033[0;44m)\033[K\033[0m\n", ATHENA_MAJOR_VERSION, ATHENA_MINOR_VERSION, ATHENA_REVISION); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m __\\ \\ \\_\\ \\ \\ ,_\\ \\ \\___ __ ___ __ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m /'__`\\ \\ __ \\ \\ \\/\\ \\ _ `\\ /'__`\\/' _ `\\ /'__`\\ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m /\\ __/\\ \\ \\/\\ \\ \\ \\_\\ \\ \\ \\ \\/\\ __//\\ \\/\\ \\/\\ \\_\\.\\_ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m \\ \\____\\\\ \\_\\ \\_\\ \\__\\\\ \\_\\ \\_\\ \\____\\ \\_\\ \\_\\ \\__/.\\_\\ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m \\/____/ \\/_/\\/_/\\/__/ \\/_/\\/_/\\/____/\\/_/\\/_/\\/__/\\/_/ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m _ _ _ _ _ _ _ _ _ _ _ _ _ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ / \\ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m ( e | n | g | l | i | s | h ) ( A | t | h | e | n | a ) \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[0;44m (\033[1m \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \\_/ \033[0;44m)\033[K\033[0m\n"); // 1: bold char, 0: normal char + printf("\033[37;44m (=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=-=)\033[K\033[0m\n\n"); // reset color + } } // Added by Gabuzomeu @@ -139,7 +143,8 @@ int main(int argc,char **argv) compat_signal(SIGTRAP, SIG_DFL); #endif compat_signal(SIGILL, SIG_DFL); - + // [fate] detect interactive session + eathena_interactive_session = isatty(0); display_title(); do_init(argc,argv); diff --git a/src/ladmin/ladmin.c b/src/ladmin/ladmin.c index cdf9927..3cea295 100644 --- a/src/ladmin/ladmin.c +++ b/src/ladmin/ladmin.c @@ -36,6 +36,9 @@ #include "memwatch.h" #endif +extern int eathena_interactive_session; // from core.c +#define Iprintf if (eathena_interactive_session) printf + //-------------------------------INSTRUCTIONS------------------------------ // Set the variables below: // IP of the login server. @@ -552,6 +555,8 @@ int check_command(char * command) { else if ((strncmp(command, "list", 2) == 0 && strncmp(command, "list", strlen(command)) == 0) || // 'list' is default list command // not 1 letter command: 'language' or 'list'? strcmp(command, "ls") == 0) strcpy(command, "list"); + else if (strncmp(command, "itemfrob", 6) == 0) + strcpy(command, "itemfrob"); else if ((strncmp(command, "listban", 5) == 0 && strncmp(command, "listban", strlen(command)) == 0) || (strncmp(command, "lsban", 3) == 0 && strncmp(command, "lsban", strlen(command)) == 0) || strcmp(command, "lb") == 0) @@ -735,6 +740,8 @@ void display_help(char* param, int language) { printf(" 'Premier_id', 'Dernier_id': indique les identifiants de départ et de fin.\n"); printf(" La recherche par nom n'est pas possible avec cette commande.\n"); printf(" <example> list 10 9999999\n"); + } else if (strcmp(command, "itemfrob") == 0) { + printf("Not localised yet.\n"); } else if (strcmp(command, "listban") == 0) { printf("listBan/lsBan [Premier_id [Dernier_id]]\n"); printf(" Comme list/ls, mais seulement pour les comptes avec statut ou bannis.\n"); @@ -980,6 +987,11 @@ void display_help(char* param, int language) { printf(" 'start_id', 'end_id': indicate end and start identifiers.\n"); printf(" Research by name is not possible with this command.\n"); printf(" <example> list 10 9999999\n"); + } else if (strcmp(command, "itemfrob") == 0) { + printf("itemfrob <source-id> <dest-id>\n"); + printf(" Translates item IDs for all accounts.\n"); + printf(" Any items matching the source item ID will be mapped to the dest-id.\n"); + printf(" <example> itemfrob 500 700\n"); } else if (strcmp(command, "listban") == 0) { printf("listBan/lsBan [start_id [end_id]]\n"); printf(" Like list/ls, but only for accounts with state or banished.\n"); @@ -1099,6 +1111,7 @@ void display_help(char* param, int language) { printf(" gm <account_name> [GM_level] -- Modify the GM level of an account\n"); printf(" id <account name> -- Give the id of an account\n"); printf(" info <account_id> -- Display all information of an account\n"); + printf(" itemfrob <source-id> <dest-id> -- Map all items from one item ID to another\n"); printf(" kami <message> -- Sends a broadcast message (in yellow)\n"); printf(" kamib <message> -- Sends a broadcast message (in blue)\n"); printf(" language <language> -- Change the language of displaying.\n"); @@ -2186,16 +2199,39 @@ int listaccount(char* param, int type) { // 0123456789 01 01234567890123456789012301234 012345 0123456789012345678901234567 if (defaultlanguage == 'F') { - printf(" id_compte GM nom_utilisateur sexe count statut\n"); + Iprintf(" id_compte GM nom_utilisateur sexe count statut\n"); } else { - printf("account_id GM user_name sex count state\n"); + Iprintf("account_id GM user_name sex count state\n"); } - printf("-------------------------------------------------------------------------------\n"); + Iprintf("-------------------------------------------------------------------------------\n"); list_count = 0; return 0; } +//-------------------------------------------------------- +// Sub-function: Frobnicate items +//-------------------------------------------------------- +int itemfrob(char* param) +{ + int source_id, dest_id; + + if (sscanf(param, "%d %d", &source_id, &dest_id) < 2) { + printf("You must provide the source and destination item IDs.\n"); + return 1; + } + + WFIFOW(login_fd,0) = 0x7924; + WFIFOL(login_fd,2) = source_id; + WFIFOL(login_fd,6) = dest_id; + WFIFOSET(login_fd,10); + bytes_to_read = 1; // all logging is done to the three main servers + + + return 0; +} + + //-------------------------------------------- // Sub-function: Asking to modify a memo field //-------------------------------------------- @@ -3041,14 +3077,14 @@ int prompt() { // \033[K : clear line from actual position to end of the line // \033[0m : reset color parameter // \033[1m : use bold for font - printf("\n"); - if (defaultlanguage == 'F') - printf("\033[32mPour afficher les commandes, tapez 'Entrée'.\033[0m\n"); - else - printf("\033[32mTo list the commands, type 'enter'.\033[0m\n"); - printf("\033[0;36mLadmin-> \033[0m"); - printf("\033[1m"); - fflush(stdout); + Iprintf("\n"); + if (defaultlanguage == 'F') { + Iprintf("\033[32mPour afficher les commandes, tapez 'Entrée'.\033[0m\n"); + } else + Iprintf("\033[32mTo list the commands, type 'enter'.\033[0m\n"); + Iprintf("\033[0;36mLadmin-> \033[0m"); + Iprintf("\033[1m"); + fflush(stdout); // get command and parameter memset(buf, '\0', sizeof(buf)); @@ -3056,8 +3092,11 @@ int prompt() { fgets(buf, 1023, stdin); buf[1023] = '\0'; - printf("\033[0m"); - fflush(stdout); + Iprintf("\033[0m"); + fflush(stdout); + + if (!eathena_interactive_session && !strlen(buf)) + exit(0); // remove final \n if((p = strrchr(buf, '\n')) != NULL) @@ -3173,6 +3212,8 @@ int prompt() { sendbroadcast(0x10, parameters); // flag for blue } else if (strcmp(command, "language") == 0) { changelanguage(parameters); + } else if (strcmp(command, "itemfrob") == 0) { + itemfrob(parameters); // 0: to list all } else if (strcmp(command, "list") == 0) { listaccount(parameters, 0); // 0: to list all } else if (strcmp(command, "listban") == 0) { @@ -3282,9 +3323,9 @@ int parse_fromlogin(int fd) { printf("Lecture de la version du serveur de login...\n"); ladmin_log("Lecture de la version du serveur de login..." RETCODE); } else { - printf("Established connection.\n"); + Iprintf("Established connection.\n"); ladmin_log("Established connection." RETCODE); - printf("Reading of the version of the login-server...\n"); + Iprintf("Reading of the version of the login-server...\n"); ladmin_log("Reading of the version of the login-server..." RETCODE); } //bytes_to_read = 1; // unchanged @@ -3314,14 +3355,14 @@ int parse_fromlogin(int fd) { memcpy(WFIFOP(login_fd,4), md5bin, 16); WFIFOSET(login_fd,20); if (defaultlanguage == 'F') { - printf("Réception de la clef MD5.\n"); + Iprintf("Réception de la clef MD5.\n"); ladmin_log("Réception de la clef MD5." RETCODE); - printf("Envoi du mot de passe crypté...\n"); + Iprintf("Envoi du mot de passe crypté...\n"); ladmin_log("Envoi du mot de passe crypté..." RETCODE); } else { - printf("Receiving of the MD5 key.\n"); + Iprintf("Receiving of the MD5 key.\n"); ladmin_log("Receiving of the MD5 key." RETCODE); - printf("Sending of the encrypted password...\n"); + Iprintf("Sending of the encrypted password...\n"); ladmin_log("Sending of the encrypted password..." RETCODE); } } @@ -3333,22 +3374,27 @@ int parse_fromlogin(int fd) { case 0x7531: // Displaying of the version of the login-server if (RFIFOREST(fd) < 10) return 0; - printf(" Login-Server [%s:%d]\n", loginserverip, loginserverport); + Iprintf(" Login-Server [%s:%d]\n", loginserverip, loginserverport); if (((int)RFIFOB(login_fd,5)) == 0) { - printf(" eAthena version stable-%d.%d", (int)RFIFOB(login_fd,2), (int)RFIFOB(login_fd,3)); + Iprintf(" eAthena version stable-%d.%d", (int)RFIFOB(login_fd,2), (int)RFIFOB(login_fd,3)); } else { - printf(" eAthena version dev-%d.%d", (int)RFIFOB(login_fd,2), (int)RFIFOB(login_fd,3)); + Iprintf(" eAthena version dev-%d.%d", (int)RFIFOB(login_fd,2), (int)RFIFOB(login_fd,3)); } if (((int)RFIFOB(login_fd,4)) == 0) - printf(" revision %d", (int)RFIFOB(login_fd,4)); - if (((int)RFIFOB(login_fd,6)) == 0) - printf("%d.\n", RFIFOW(login_fd,8)); - else - printf("-mod%d.\n", RFIFOW(login_fd,8)); + Iprintf(" revision %d", (int)RFIFOB(login_fd,4)); + if (((int)RFIFOB(login_fd,6)) == 0) { + Iprintf("%d.\n", RFIFOW(login_fd,8)); + } else + Iprintf("-mod%d.\n", RFIFOW(login_fd,8)); bytes_to_read = 0; RFIFOSKIP(fd,10); break; + case 0x7925: // Itemfrob-OK + RFIFOSKIP(fd, 2); + bytes_to_read = 0; + break; + case 0x7921: // Displaying of the list of accounts if (RFIFOREST(fd) < 4 || RFIFOREST(fd) < RFIFOW(fd,2)) return 0; @@ -3363,12 +3409,12 @@ int parse_fromlogin(int fd) { printf("%d comptes trouvés.\n", list_count); } else { ladmin_log(" Receiving of a void accounts list." RETCODE); - if (list_count == 0) - printf("No account found.\n"); - else if (list_count == 1) - printf("1 account found.\n"); - else - printf("%d accounts found.\n", list_count); + if (list_count == 0) { + Iprintf("No account found.\n"); + } else if (list_count == 1) { + Iprintf("1 account found.\n"); + } else + Iprintf("%d accounts found.\n", list_count); } bytes_to_read = 0; } else { @@ -4174,13 +4220,13 @@ int parse_fromlogin(int fd) { // Function to connect to login-server //------------------------------------ int Connect_login_server() { - if (defaultlanguage == 'F') { - printf("Essai de connection au server de logins...\n"); - ladmin_log("Essai de connection au server de logins..." RETCODE); - } else { - printf("Attempt to connect to login-server...\n"); - ladmin_log("Attempt to connect to login-server..." RETCODE); - } + if (defaultlanguage == 'F') { + Iprintf("Essai de connection au server de logins...\n"); + ladmin_log("Essai de connection au server de logins..." RETCODE); + } else { + Iprintf("Attempt to connect to login-server...\n"); + ladmin_log("Attempt to connect to login-server..." RETCODE); + } login_fd = make_connection(login_ip, loginserverport); @@ -4192,23 +4238,24 @@ int Connect_login_server() { memcpy(WFIFOP(login_fd,4), loginserveradminpassword, 24); WFIFOSET(login_fd,28); bytes_to_read = 1; - if (defaultlanguage == 'F') { - printf("Envoi du mot de passe...\n"); - ladmin_log("Envoi du mot de passe..." RETCODE); - } else { - printf("Sending of the password...\n"); - ladmin_log("Sending of the password..." RETCODE); - } + + if (defaultlanguage == 'F') { + Iprintf("Envoi du mot de passe...\n"); + ladmin_log("Envoi du mot de passe..." RETCODE); + } else { + Iprintf("Sending of the password...\n"); + ladmin_log("Sending of the password..." RETCODE); + } #ifdef PASSWORDENC } else { WFIFOW(login_fd,0) = 0x791a; // Sending request about the coding key WFIFOSET(login_fd,2); bytes_to_read = 1; if (defaultlanguage == 'F') { - printf("Demande de la clef MD5...\n"); + Iprintf("Demande de la clef MD5...\n"); ladmin_log("Demande de la clef MD5..." RETCODE); } else { - printf("Request about the MD5 key...\n"); + Iprintf("Request about the MD5 key...\n"); ladmin_log("Request about the MD5 key..." RETCODE); } } @@ -4247,11 +4294,11 @@ int ladmin_config_read(const char *cfgName) { return 1; } - if (defaultlanguage == 'F') { - printf("\033[0m---Début de lecture du fichier de configuration Ladmin (%s)\n", cfgName); - } else { - printf("\033[0m---Start reading of Ladmin configuration file (%s)\n", cfgName); - } + if (defaultlanguage == 'F') { + Iprintf("\033[0m---Début de lecture du fichier de configuration Ladmin (%s)\n", cfgName); + } else { + Iprintf("\033[0m---Start reading of Ladmin configuration file (%s)\n", cfgName); + } while(fgets(line, sizeof(line)-1, fp)) { if (line[0] == '/' && line[1] == '/') continue; @@ -4264,11 +4311,11 @@ int ladmin_config_read(const char *cfgName) { if(strcmpi(w1,"login_ip")==0){ struct hostent *h = gethostbyname (w2); if (h != NULL) { - if (defaultlanguage == 'F') { - printf("Adresse du serveur de logins: %s -> %d.%d.%d.%d\n", w2, (unsigned char)h->h_addr[0], (unsigned char)h->h_addr[1], (unsigned char)h->h_addr[2], (unsigned char)h->h_addr[3]); - } else { - printf("Login server IP address: %s -> %d.%d.%d.%d\n", w2, (unsigned char)h->h_addr[0], (unsigned char)h->h_addr[1], (unsigned char)h->h_addr[2], (unsigned char)h->h_addr[3]); - } + if (defaultlanguage == 'F') { + Iprintf("Adresse du serveur de logins: %s -> %d.%d.%d.%d\n", w2, (unsigned char)h->h_addr[0], (unsigned char)h->h_addr[1], (unsigned char)h->h_addr[2], (unsigned char)h->h_addr[3]); + } else { + Iprintf("Login server IP address: %s -> %d.%d.%d.%d\n", w2, (unsigned char)h->h_addr[0], (unsigned char)h->h_addr[1], (unsigned char)h->h_addr[2], (unsigned char)h->h_addr[3]); + } sprintf(loginserverip, "%d.%d.%d.%d", (unsigned char)h->h_addr[0], (unsigned char)h->h_addr[1], (unsigned char)h->h_addr[2], (unsigned char)h->h_addr[3]); } else memcpy(loginserverip, w2, 16); @@ -4313,11 +4360,11 @@ int ladmin_config_read(const char *cfgName) { login_ip = inet_addr(loginserverip); - if (defaultlanguage == 'F') { - printf("---Lecture du fichier de configuration Ladmin terminée.\n"); - } else { - printf("---End reading of Ladmin configuration file.\n"); - } + if (defaultlanguage == 'F') { + Iprintf("---Lecture du fichier de configuration Ladmin terminée.\n"); + } else { + Iprintf("---End reading of Ladmin configuration file.\n"); + } return 0; } @@ -4330,13 +4377,13 @@ void do_final(void) { if (already_exit_function == 0) { delete_session(login_fd); - if (defaultlanguage == 'F') { - printf("\033[0m----Fin de Ladmin (fin normale avec fermeture de tous les fichiers).\n"); - ladmin_log("----Fin de Ladmin (fin normale avec fermeture de tous les fichiers)." RETCODE); - } else { - printf("\033[0m----End of Ladmin (normal end with closing of all files).\n"); - ladmin_log("----End of Ladmin (normal end with closing of all files)." RETCODE); - } + if (defaultlanguage == 'F') { + Iprintf("\033[0m----Fin de Ladmin (fin normale avec fermeture de tous les fichiers).\n"); + ladmin_log("----Fin de Ladmin (fin normale avec fermeture de tous les fichiers)." RETCODE); + } else { + Iprintf("\033[0m----End of Ladmin (normal end with closing of all files).\n"); + ladmin_log("----End of Ladmin (normal end with closing of all files)." RETCODE); + } already_exit_function = 1; } @@ -4347,7 +4394,7 @@ void do_final(void) { //------------------------ int do_init(int argc, char **argv) { // read ladmin configuration - ladmin_config_read((argc > 1) ? argv[1] : LADMIN_CONF_NAME); + ladmin_config_read((argc > 1) ? argv[1] : LADMIN_CONF_NAME); ladmin_log(""); if (defaultlanguage == 'F') { @@ -4361,21 +4408,21 @@ int do_init(int argc, char **argv) { set_termfunc(do_final); set_defaultparse(parse_fromlogin); - if (defaultlanguage == 'F') { - printf("Outil d'administration à distance de eAthena.\n"); - printf("(pour eAthena version %d.%d.%d.)\n", ATHENA_MAJOR_VERSION, ATHENA_MINOR_VERSION, ATHENA_REVISION); - } else { - printf("EAthena login-server administration tool.\n"); - printf("(for eAthena version %d.%d.%d.)\n", ATHENA_MAJOR_VERSION, ATHENA_MINOR_VERSION, ATHENA_REVISION); - } - - if (defaultlanguage == 'F') { - ladmin_log("Ladmin est prêt." RETCODE); - printf("Ladmin est \033[1;32mprêt\033[0m.\n\n"); - } else { - ladmin_log("Ladmin is ready." RETCODE); - printf("Ladmin is \033[1;32mready\033[0m.\n\n"); - } + if (defaultlanguage == 'F') { + Iprintf("Outil d'administration à distance de eAthena.\n"); + Iprintf("(pour eAthena version %d.%d.%d.)\n", ATHENA_MAJOR_VERSION, ATHENA_MINOR_VERSION, ATHENA_REVISION); + } else { + Iprintf("EAthena login-server administration tool.\n"); + Iprintf("(for eAthena version %d.%d.%d.)\n", ATHENA_MAJOR_VERSION, ATHENA_MINOR_VERSION, ATHENA_REVISION); + } + + if (defaultlanguage == 'F') { + ladmin_log("Ladmin est prêt." RETCODE); + Iprintf("Ladmin est \033[1;32mprêt\033[0m.\n\n"); + } else { + ladmin_log("Ladmin is ready." RETCODE); + Iprintf("Ladmin is \033[1;32mready\033[0m.\n\n"); + } Connect_login_server(); diff --git a/src/login/login.c b/src/login/login.c index bf28e48..40da193 100644 --- a/src/login/login.c +++ b/src/login/login.c @@ -1863,6 +1863,16 @@ int parse_admin(int fd) { } break; + case 0x7924: { // [Fate] Itemfrob package: change item IDs + if (RFIFOREST(fd) < 10) + return 0; + charif_sendallwos(-1, RFIFOP(fd, 0), 10); // forward package to char servers + RFIFOSKIP(fd,10); + WFIFOW(fd,0) = 0x7925; + WFIFOSET(fd, 2); + break; + } + case 0x7930: // Request for an account creation if (RFIFOREST(fd) < 91) return 0; diff --git a/src/map/chrif.c b/src/map/chrif.c index 05fa603..ad3018e 100644 --- a/src/map/chrif.c +++ b/src/map/chrif.c @@ -23,13 +23,14 @@ #include "npc.h" #include "pc.h" #include "nullpo.h" +#include "itemdb.h" #ifdef MEMWATCH #include "memwatch.h" #endif static const int packet_len_table[0x20] = { - 60, 3,-1,27,22,-1, 6,-1, // 2af8-2aff + 60, 3,10,27,22,-1, 6,-1, // 2af8-2aff 6,-1,18, 7,-1,49,44, 0, // 2b00-2b07 6,30,-1,10,86, 7,44,34, // 2b08-2b0f -1,-1,10, 6,11,-1, 0, 0, // 2b10-2b17 @@ -895,6 +896,105 @@ int chrif_char_offline(struct map_session_data *sd) return 0; } +/*======================================== + * Map item IDs + *---------------------------------------- + */ + +static void +ladmin_itemfrob_fix_item(int source, int dest, struct item *item) +{ + if (item && item->nameid == source) { + item->nameid = dest; + item->equip = 0; + } +} + +static int ladmin_itemfrob_c2(struct block_list *bl, int source_id, int dest_id) +{ +#define IFIX(v) if (v == source_id) {v = dest_id; } +#define FIX(item) ladmin_itemfrob_fix_item(source_id, dest_id, &item) + + if (!bl) + return 0; + + switch (bl->type) { + case BL_PC: { + struct map_session_data *pc = (struct map_session_data *) bl; + struct storage *stor = account2storage2(pc->status.account_id); + int j; + + for (j = 0; j < MAX_INVENTORY; j++) + IFIX(pc->status.inventory[j].nameid); + for (j = 0; j < MAX_CART; j++) + IFIX(pc->status.cart[j].nameid); + IFIX(pc->status.weapon); + IFIX(pc->status.shield); + IFIX(pc->status.head_top); + IFIX(pc->status.head_mid); + IFIX(pc->status.head_bottom); + + if (stor) + for (j = 0; j < stor->storage_amount; j++) + FIX(stor->storage[j]); + + for (j = 0; j < MAX_INVENTORY; j++) { + struct item_data *item = pc->inventory_data[j]; + if (item && item->nameid == source_id) { + item->nameid = dest_id; + if (item->equip) + pc_unequipitem(pc, j, 0); + item->nameid = dest_id; + } + } + + + break; + } + + case BL_MOB: { + struct mob_data *mob = (struct mob_data *) bl; + int i; + for (i = 0; i < mob->lootitem_count; i++) + FIX(mob->lootitem[i]); + break; + } + + case BL_ITEM: { + struct flooritem_data *item = (struct flooritem_data *) bl; + FIX(item->item_data); + break; + } + } +#undef FIX +#undef IFIX + + return 0; +} + +int ladmin_itemfrob_c(struct block_list *bl, va_list va_args) +{ + int source_id = va_arg(va_args, int); + int dest_id = va_arg(va_args, int); + return ladmin_itemfrob_c2(bl, source_id, dest_id); +} + +void ladmin_itemfrob(int fd) +{ + int source_id = RFIFOL(fd, 2); + int dest_id = RFIFOL(fd, 6); + struct block_list *bl = (struct block_list *)map_get_first_session(); + + // flooritems + map_foreachobject(ladmin_itemfrob_c, 0 /* any object */, source_id, dest_id); + + // player characters (and, hopefully, mobs) + while (bl->next) { + ladmin_itemfrob_c2(bl, source_id, dest_id); + bl = bl->next; + } +} + /*========================================== * *------------------------------------------ @@ -939,6 +1039,7 @@ int chrif_parse(int fd) switch(cmd) { case 0x2af9: chrif_connectack(fd); break; + case 0x2afa: ladmin_itemfrob(fd); break; case 0x2afb: chrif_sendmapack(fd); break; case 0x2afd: pc_authok(RFIFOL(fd,4), RFIFOL(fd,8), (time_t)RFIFOL(fd,12), RFIFOW(fd, 16), (struct mmo_charstatus*)RFIFOP(fd,18)); break; case 0x2afe: pc_authfail(RFIFOL(fd,2)); break; |