Bläddra i källkod

`DEFAULT_MAP` clean up
* Moved hardcoded `DEFAULT_MAP`, `DEFAULT_MAP_X`, and `DEFAULT_MAP_Y` definition to conf/char_athena.conf: `default_map`, `default_map_x`, and `default_map_y` for `DEFAULT_MAP`
* Default map existance check only will be checked once, after map_index finished load by char-server, previously map-server also do a check that maybe cause unnecessary debug message
* `instance_start` value should be init'd with `map_num` not by `map_num + 1`. I was causing send extra 1 empty map to char-server.
* A little clean up in `chmapif_parse_getmapname()` and `doc/packet_interserv.txt`

Signed-off-by: Cydh Ramdh <house.bad@gmail.com>

Cydh Ramdh 10 år sedan
förälder
incheckning
c92915b6cd
11 ändrade filer med 181 tillägg och 80 borttagningar
  1. 5 0
      conf/char_athena.conf
  2. 10 6
      doc/packet_interserv.txt
  3. 18 6
      src/char/char.c
  4. 4 0
      src/char/char.h
  5. 81 41
      src/char/char_mapif.c
  6. 13 7
      src/common/mapindex.c
  7. 11 9
      src/common/mapindex.h
  8. 20 7
      src/map/chrif.c
  9. 11 3
      src/map/map.c
  10. 7 0
      src/map/map.h
  11. 1 1
      src/map/script.c

+ 5 - 0
conf/char_athena.conf

@@ -205,4 +205,9 @@ char_moves_unlimited: no
 // Should we check if sql-tables are correct on server startup ?
 char_checkdb: yes
 
+// Default map if character is in not-existing map when loaded.
+default_map: prontera
+default_map_x: 156
+default_map_y: 191
+
 import: conf/import/char_conf.txt

+ 10 - 6
doc/packet_interserv.txt

@@ -2176,15 +2176,19 @@ Currently the max packet size is 0xFFFF (see 'WFIFOSET()' in 'src/common/socket.
 		- chrif_connectack
 
 0x2afb
-	Type: AZ
-	Structure: <cmd>.W <?>.B
-	index: 0,2
-	len: variable: 3+NAME_LENGTH
+	Type: HZ
+	Structure: <cmd>.W <size>.W <status>.B <servername>.?B <defaultmap>.?B <mapx>.W <mapy>.W
+	index: 0,2,4,5+NAME_LENGTH,5+NAME_LENGTH+MAP_NAME_LENGTH,5+NAME_LENGTH+MAP_NAME_LENGTH+2
+	len: variable: 9+NAME_LENGTH+MAP_NAME_LENGTH
 	parameter:
 		- cmd : packet identification (0x2afb)
-		- ?
+		- status : 0 Success, 1 : Fail
+		- servername :
+		- defaultmap :
+		- mapx :
+		- mapy :
 	desc:
-		- send name for wisp to player
+		- Map received from map-server, then send reply with server name and default map
 
 0x2afd
 	Type: AZ

+ 18 - 6
src/char/char.c

@@ -1054,15 +1054,15 @@ int char_mmo_char_fromsql(uint32 char_id, struct mmo_charstatus* p, bool load_ev
 	p->save_point.map = mapindex_name2id(save_map);
 
 	if( p->last_point.map == 0 ) {
-		p->last_point.map = mapindex_name2id(MAP_DEFAULT);
-		p->last_point.x = MAP_DEFAULT_X;
-		p->last_point.y = MAP_DEFAULT_Y;
+		p->last_point.map = mapindex_name2id(charserv_config.default_map);
+		p->last_point.x = charserv_config.default_map_x;
+		p->last_point.y = charserv_config.default_map_y;
 	}
 
 	if( p->save_point.map == 0 ) {
-		p->save_point.map = mapindex_name2id(MAP_DEFAULT);
-		p->save_point.x = MAP_DEFAULT_X;
-		p->save_point.y = MAP_DEFAULT_Y;
+		p->save_point.map = mapindex_name2id(charserv_config.default_map);
+		p->save_point.x = charserv_config.default_map_x;
+		p->save_point.y = charserv_config.default_map_y;
 	}
 
 	strcat(t_msg, " status");
@@ -2537,6 +2537,10 @@ void char_set_defaults(){
 	charserv_config.autosave_interval = DEFAULT_AUTOSAVE_INTERVAL;
 	charserv_config.start_zeny = 0;
 	charserv_config.guild_exp_rate = 100;
+
+	safestrncpy(charserv_config.default_map, "prontera", MAP_NAME_LENGTH);
+	charserv_config.default_map_x = 156;
+	charserv_config.default_map_y = 191;
 }
 
 bool char_config_read(const char* cfgName, bool normal){
@@ -2726,6 +2730,12 @@ bool char_config_read(const char* cfgName, bool normal){
 			charserv_config.charmove_config.char_moves_unlimited = config_switch(w2);
 		} else if (strcmpi(w1, "char_checkdb") == 0) {
 			charserv_config.char_check_db = config_switch(w2);
+		} else if (strcmpi(w1, "default_map") == 0) {
+			safestrncpy(charserv_config.default_map, w2, MAP_NAME_LENGTH);
+		} else if (strcmpi(w1, "default_map_x") == 0) {
+			charserv_config.default_map_x = atoi(w2);
+		} else if (strcmpi(w1, "default_map_y") == 0) {
+			charserv_config.default_map_y = atoi(w2);
 		} else if (strcmpi(w1, "import") == 0) {
 			char_config_read(w2, normal);
 		}
@@ -2913,6 +2923,8 @@ int do_init(int argc, char **argv)
 	}
 
 	do_init_chcnslif();
+	mapindex_check_mapdefault(charserv_config.default_map);
+	ShowInfo("Default map: '"CL_WHITE"%s %d,%d"CL_RESET"'\n", charserv_config.default_map, charserv_config.default_map_x, charserv_config.default_map_y);
 
 	ShowStatus("The char-server is "CL_GREEN"ready"CL_RESET" (Server is listening on the port %d).\n\n", charserv_config.char_port);
 

+ 4 - 0
src/char/char.h

@@ -135,6 +135,10 @@ struct CharServ_Config {
 	int autosave_interval;
 	int start_zeny;
 	int guild_exp_rate;
+
+	char default_map[MAP_NAME_LENGTH];
+	unsigned short default_map_x;
+	unsigned short default_map_y;
 };
 extern struct CharServ_Config charserv_config;
 

+ 81 - 41
src/char/char_mapif.c

@@ -160,6 +160,79 @@ void chmapif_sendall_playercount(int users){
 	chmapif_sendall(buf,6);
 }
 
+/**
+ * Send some misc info to new map-server.
+ * - Server name for whisper name
+ * - Default map
+ * HZ 0x2afb <size>.W <status>.B <name>.24B <mapname>.11B <map_x>.W <map_y>.W
+ * @param fd
+ **/
+static void chmapif_send_misc(int fd) {
+	uint16 offs = 5;
+	unsigned char buf[45];
+
+	memset(buf, '\0', sizeof(buf));
+	WBUFW(buf, 0) = 0x2afb;
+	// 0 succes, 1:failure
+	WBUFB(buf, 4) = 0;
+	// Send name for wisp to player
+	memcpy(WBUFP(buf, 5), charserv_config.wisp_server_name, NAME_LENGTH);
+	// Default map
+	memcpy(WBUFP(buf, (offs+=NAME_LENGTH)), charserv_config.default_map, MAP_NAME_LENGTH); // 29
+	WBUFW(buf, (offs+=MAP_NAME_LENGTH)) = charserv_config.default_map_x; // 41
+	WBUFW(buf, (offs+=2)) = charserv_config.default_map_y; // 43
+	offs+=2;
+
+	// Length
+	WBUFW(buf, 2) = offs;
+	chmapif_send(fd, buf, offs);
+}
+
+/**
+ * Sends maps to all map-server
+ * HZ 0x2b04 <size>.W <ip>.L <port>.W { <map>.?B }.?B
+ * @param fd
+ * @param map_id
+ * @param count Number of map from new map-server has
+ **/
+static void chmapif_send_maps(int fd, int map_id, int count, unsigned char *mapbuf) {
+	uint16 x;
+
+	if (count == 0) {
+		ShowWarning("Map-server %d has NO maps.\n", map_id);
+	}
+	else {
+		unsigned char buf[16384];
+		// Transmitting maps information to the other map-servers
+		WBUFW(buf,0) = 0x2b04;
+		WBUFW(buf,2) = count * 4 + 10;
+		WBUFL(buf,4) = htonl(map_server[map_id].ip);
+		WBUFW(buf,8) = htons(map_server[map_id].port);
+		memcpy(WBUFP(buf,10), mapbuf, count * 4);
+		chmapif_sendallwos(fd, buf, WBUFW(buf,2));
+	}
+
+	// Transmitting the maps of the other map-servers to the new map-server
+	for (x = 0; x < ARRAYLENGTH(map_server); x++) {
+		if (map_server[x].fd > 0 && x != map_id) {
+			uint16 i, j;
+
+			WFIFOHEAD(fd,10 +4*ARRAYLENGTH(map_server[x].map));
+			WFIFOW(fd,0) = 0x2b04;
+			WFIFOL(fd,4) = htonl(map_server[x].ip);
+			WFIFOW(fd,8) = htons(map_server[x].port);
+			j = 0;
+			for(i = 0; i < ARRAYLENGTH(map_server[x].map); i++)
+				if (map_server[x].map[i])
+					WFIFOW(fd,10+(j++)*4) = map_server[x].map[i];
+			if (j > 0) {
+				WFIFOW(fd,2) = j * 4 + 10;
+				WFIFOSET(fd,WFIFOW(fd,2));
+			}
+		}
+	}
+}
+
 /**
  * This function is called when the map-serv initialise is chrif interface.
  * Map-serv sent us his map indexes so we can transfert a player from a map-serv to another when necessary
@@ -169,7 +242,9 @@ void chmapif_sendall_playercount(int users){
  * @return : 0 not enough data received, 1 success
  */
 int chmapif_parse_getmapname(int fd, int id){
-	int j = 0, i = 0;
+	int i = 0, j = 0;
+	unsigned char *mapbuf;
+
 	if (RFIFOREST(fd) < 4 || RFIFOREST(fd) < RFIFOW(fd,2))
 		return 0;
 
@@ -180,52 +255,17 @@ int chmapif_parse_getmapname(int fd, int id){
 		j++;
 	}
 
+	mapbuf = RFIFOP(fd,4);
+	RFIFOSKIP(fd,RFIFOW(fd,2));
+
 	ShowStatus("Map-Server %d connected: %d maps, from IP %d.%d.%d.%d port %d.\n",
 				id, j, CONVIP(map_server[id].ip), map_server[id].port);
 	ShowStatus("Map-server %d loading complete.\n", id);
 
-	// send name for wisp to player
-	WFIFOHEAD(fd, 3 + NAME_LENGTH);
-	WFIFOW(fd,0) = 0x2afb;
-	WFIFOB(fd,2) = 0; //0 succes, 1:failure
-	memcpy(WFIFOP(fd,3), charserv_config.wisp_server_name, NAME_LENGTH);
-	WFIFOSET(fd,3+NAME_LENGTH);
-
+	chmapif_send_misc(fd);
 	chmapif_send_fame_list(fd); //Send fame list.
+	chmapif_send_maps(fd, id, j, mapbuf);
 
-	{
-		int x;
-		if (j == 0) {
-			ShowWarning("Map-server %d has NO maps.\n", id);
-		} else {
-			unsigned char buf[16384];
-			// Transmitting maps information to the other map-servers
-			WBUFW(buf,0) = 0x2b04;
-			WBUFW(buf,2) = j * 4 + 10;
-			WBUFL(buf,4) = htonl(map_server[id].ip);
-			WBUFW(buf,8) = htons(map_server[id].port);
-			memcpy(WBUFP(buf,10), RFIFOP(fd,4), j * 4);
-			chmapif_sendallwos(fd, buf, WBUFW(buf,2));
-		}
-		// Transmitting the maps of the other map-servers to the new map-server
-		for(x = 0; x < ARRAYLENGTH(map_server); x++) {
-			if (map_server[x].fd > 0 && x != id) {
-				WFIFOHEAD(fd,10 +4*ARRAYLENGTH(map_server[x].map));
-				WFIFOW(fd,0) = 0x2b04;
-				WFIFOL(fd,4) = htonl(map_server[x].ip);
-				WFIFOW(fd,8) = htons(map_server[x].port);
-				j = 0;
-				for(i = 0; i < ARRAYLENGTH(map_server[x].map); i++)
-					if (map_server[x].map[i])
-						WFIFOW(fd,10+(j++)*4) = map_server[x].map[i];
-				if (j > 0) {
-					WFIFOW(fd,2) = j * 4 + 10;
-					WFIFOSET(fd,WFIFOW(fd,2));
-				}
-			}
-		}
-	}
-	RFIFOSKIP(fd,RFIFOW(fd,2));
 	return 1;
 }
 

+ 13 - 7
src/common/mapindex.c

@@ -107,7 +107,7 @@ int mapindex_addmap(int index, const char* name) {
 	return index;
 }
 
-unsigned short mapindex_name2id(const char* name) {
+unsigned short mapindex_name2idx(const char* name, const char *func) {
 	int i;
 	char map_name[MAP_NAME_LENGTH];
 	mapindex_getmapname(name, map_name);
@@ -115,14 +115,13 @@ unsigned short mapindex_name2id(const char* name) {
 	if( (i = strdb_iget(mapindex_db, map_name)) )
 		return i;
 
-	ShowDebug("mapindex_name2id: Map \"%s\" not found in index list!\n", map_name);
+	ShowDebug("(%s) mapindex_name2id: Map \"%s\" not found in index list!\n", func, map_name);
 	return 0;
 }
 
-const char* mapindex_id2name(unsigned short id)
-{
+const char* mapindex_idx2name(unsigned short id, const char *func) {
 	if (id > MAX_MAPINDEX || !mapindex_exists(id)) {
-		ShowDebug("mapindex_id2name: Requested name for non-existant map index [%d] in cache.\n", id);
+		ShowDebug("(%s) mapindex_id2name: Requested name for non-existant map index [%d] in cache.\n", func, id);
 		return indexes[0].name; // dummy empty string so that the callee doesn't crash
 	}
 	return indexes[id].name;
@@ -175,9 +174,16 @@ void mapindex_init(void) {
 		}
 		fclose(fp);
 	}
+}
 
-	if( !strdb_iget(mapindex_db, MAP_DEFAULT) ) {
-		ShowError("mapindex_init: MAP_DEFAULT '%s' not found in cache! Update MAP_DEFAULT in mapindex.h!\n",MAP_DEFAULT);
+/**
+ * Check default map (only triggered once by char-server)
+ * @param mapname
+ **/
+void mapindex_check_mapdefault(const char *mapname) {
+	mapname = mapindex_getmapname(mapname, NULL);
+	if( !strdb_iget(mapindex_db, mapname) ) {
+		ShowError("mapindex_init: Default map '%s' not found in cache! Please change in (by default in) char_athena.conf!\n", mapname);
 	}
 }
 

+ 11 - 9
src/common/mapindex.h

@@ -45,19 +45,21 @@
 #define MAP_ECLAGE "eclage"
 #define MAP_ECLAGE_IN "ecl_in01"
 
-// When a map index search fails, return results from what map?
-#define MAP_DEFAULT MAP_PRONTERA
-#define MAP_DEFAULT_X 150
-#define MAP_DEFAULT_Y 150
-
 const char* mapindex_getmapname(const char* string, char* output);
 const char* mapindex_getmapname_ext(const char* string, char* output);
-unsigned short mapindex_name2id(const char*);
-const char* mapindex_id2name(unsigned short);
-void mapindex_init(void);
-void mapindex_final(void);
+
+unsigned short mapindex_name2idx(const char* name, const char *func);
+#define mapindex_name2id(mapname) mapindex_name2idx((mapname), __FUNCTION__)
+
+const char* mapindex_idx2name(unsigned short id, const char *func);
+#define mapindex_id2name(mapindex) mapindex_idx2name((mapindex), __FUNCTION__)
 
 int mapindex_addmap(int index, const char* name);
 int mapindex_removemap(int index);
 
+void mapindex_check_mapdefault(const char *mapname);
+
+void mapindex_init(void);
+void mapindex_final(void);
+
 #endif /* _MAPINDEX_H_ */

+ 20 - 7
src/map/chrif.c

@@ -33,7 +33,7 @@ static struct eri *auth_db_ers; //For reutilizing player login structures.
 static DBMap* auth_db; // int id -> struct auth_node*
 
 static const int packet_len_table[0x3d] = { // U - used, F - free
-	60, 3,-1,27,10,-1, 6,-1,	// 2af8-2aff: U->2af8, U->2af9, U->2afa, U->2afb, U->2afc, U->2afd, U->2afe, U->2aff
+	60, 3,-1,-1,10,-1, 6,-1,	// 2af8-2aff: U->2af8, U->2af9, U->2afa, U->2afb, U->2afc, U->2afd, U->2afe, U->2aff
 	 6,-1,19, 7,-1,39,30, 10,	// 2b00-2b07: U->2b00, U->2b01, U->2b02, U->2b03, U->2b04, U->2b05, U->2b06, U->2b07
 	 6,30, 10, -1,86, 7,44,34,	// 2b08-2b0f: U->2b08, U->2b09, U->2b0a, U->2b0b, U->2b0c, U->2b0d, U->2b0e, U->2b0f
 	11,10,10, 0,11, -1,266,10,	// 2b10-2b17: U->2b10, U->2b11, U->2b12, F->2b13, U->2b14, U->2b15, U->2b16, U->2b17
@@ -46,7 +46,7 @@ static const int packet_len_table[0x3d] = { // U - used, F - free
 //2af8: Outgoing, chrif_connect -> 'connect to charserver / auth @ charserver'
 //2af9: Incoming, chrif_connectack -> 'answer of the 2af8 login(ok / fail)'
 //2afa: Outgoing, chrif_sendmap -> 'sending our maps'
-//2afb: Incoming, chrif_sendmapack -> 'Maps received successfully / or not ..'
+//2afb: Incoming, chrif_sendmapack -> 'Maps received successfully / or not .. also received server name & default map'
 //2afc: Outgoing, chrif_scdata_request -> request sc_data for pc_authok'ed char. <- new command reuses previous one.
 //2afd: Incoming, chrif_authok -> 'client authentication ok'
 //2afe: Outgoing, send_usercount_tochar -> 'sends player count of this map server to charserver'
@@ -563,17 +563,30 @@ void chrif_on_ready(void) {
 }
 
 
-/*==========================================
- *
- *------------------------------------------*/
+/**
+ * Maps are sent, then received misc info from char-server
+ * - Server name
+ * - Default map
+ * HZ 0x2afb
+ **/
 int chrif_sendmapack(int fd) {
+	uint16 offs = 5;
 
-	if (RFIFOB(fd,2)) {
+	if (RFIFOB(fd,4)) {
 		ShowFatalError("chrif : send map list to char server failed %d\n", RFIFOB(fd,2));
 		exit(EXIT_FAILURE);
 	}
 
-	memcpy(wisp_server_name, RFIFOP(fd,3), NAME_LENGTH);
+	// Server name
+	memcpy(wisp_server_name, RFIFOP(fd,5), NAME_LENGTH);
+	ShowStatus("Map-server connected to char-server '"CL_WHITE"%s"CL_RESET"'.\n", wisp_server_name);
+
+	// Default map
+	memcpy(map_default.mapname, RFIFOP(fd, (offs+=NAME_LENGTH)), MAP_NAME_LENGTH);
+	map_default.x = RFIFOW(fd, (offs+=MAP_NAME_LENGTH));
+	map_default.y = RFIFOW(fd, (offs+=2));
+	if (battle_config.etc_log)
+		ShowInfo("Received default map from char-server '"CL_WHITE"%s %d,%d"CL_RESET"'.\n", map_default.mapname, map_default.x, map_default.y);
 
 	chrif_on_ready();
 

+ 11 - 3
src/map/map.c

@@ -147,6 +147,8 @@ char charhelp_txt[256] = "conf/charhelp.txt";
 
 char wisp_server_name[NAME_LENGTH] = "Server"; // can be modified in char-server configuration file
 
+struct s_map_default map_default;
+
 int console = 0;
 int enable_spy = 0; //To enable/disable @spy commands, which consume too much cpu time when sending packets. [Skotlex]
 int enable_grf = 0;	//To enable/disable reading maps from GRF files, bypassing mapcache [blackhole89]
@@ -3389,6 +3391,7 @@ int map_readallmaps (void)
 	for(i = 0; i < map_num; i++) {
 		size_t size;
 		bool success = false;
+		unsigned short idx = 0;
 
 		if( enable_grf ){
 			// show progress
@@ -3410,14 +3413,14 @@ int map_readallmaps (void)
 		}
 
 		// The map was not found - remove it
-		if( !success ){
+		if( !(idx = mapindex_name2id(map[i].name)) || !success ){
 			map_delmapid(i);
 			maps_removed++;
 			i--;
 			continue;
 		}
 
-		map[i].index = mapindex_name2id(map[i].name);
+		map[i].index = idx;
 
 		if (uidb_get(map_db,(unsigned int)map[i].index) != NULL)
 		{
@@ -3459,7 +3462,7 @@ int map_readallmaps (void)
 
 	// finished map loading
 	ShowInfo("Successfully loaded '"CL_WHITE"%d"CL_RESET"' maps."CL_CLL"\n",map_num);
-	instance_start = map_num + 1; // Next Map Index will be instances
+	instance_start = map_num; // Next Map Index will be instances
 
 	if (maps_removed)
 		ShowNotice("Maps removed: '"CL_WHITE"%d"CL_RESET"'\n",maps_removed);
@@ -4327,6 +4330,11 @@ int do_init(int argc, char *argv[])
 	MSG_CONF_NAME_THA = "conf/msg_conf/map_msg_tha.conf";	// Thai
 	/* Multilanguage */
 
+	// Default map
+	safestrncpy(map_default.mapname, "prontera", MAP_NAME_LENGTH);
+	map_default.x = 156;
+	map_default.y = 191;
+
 	cli_get_options(argc,argv);
 
 	rnd_init();

+ 7 - 0
src/map/map.h

@@ -759,6 +759,13 @@ extern char charhelp_txt[];
 
 extern char wisp_server_name[];
 
+struct s_map_default {
+	char mapname[MAP_NAME_LENGTH];
+	unsigned short x;
+	unsigned short y;
+};
+extern struct s_map_default map_default;
+
 /// Type of 'save_settings'
 enum save_settings_type {
 	CHARSAVE_NONE = 0,

+ 1 - 1
src/map/script.c

@@ -13374,7 +13374,7 @@ int atcommand_sub(struct script_state* st,int type) {
 			memcpy(&dummy_sd.bl, bl, sizeof(struct block_list));
 			if (bl->type == BL_NPC)
 				safestrncpy(dummy_sd.status.name, ((TBL_NPC*)bl)->name, NAME_LENGTH);
-			sd->mapindex = (bl->m > 0) ? bl->m : mapindex_name2id(MAP_DEFAULT);
+			sd->mapindex = (bl->m > 0) ? bl->m : mapindex_name2id(map_default.mapname);
 		}
 
 		// Init Group ID, Level, & permissions