[Freeciv-Dev] (PR#11126) unify map_get_known
[Top] [All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index] [Thread Index]
<URL: http://rt.freeciv.org/Ticket/Display.html?id=11126 >
Here is an updated patch.
jason
Index: client/climap.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/climap.c,v
retrieving revision 1.5
diff -u -r1.5 climap.c
--- client/climap.c 29 Sep 2004 02:24:19 -0000 1.5
+++ client/climap.c 6 Dec 2004 20:57:15 -0000
@@ -34,7 +34,7 @@
*************************************************************************/
enum known_type tile_get_known(const struct tile *ptile)
{
- return (enum known_type) ptile->known;
+ return map_get_known(ptile, game.player_ptr);
}
/**************************************************************************
Index: client/climisc.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/climisc.c,v
retrieving revision 1.143
diff -u -r1.143 climisc.c
--- client/climisc.c 20 Oct 2004 04:34:27 -0000 1.143
+++ client/climisc.c 6 Dec 2004 20:57:15 -0000
@@ -955,16 +955,6 @@
output_window_force_thaw();
}
-/*************************************************************************
-...
-*************************************************************************/
-enum known_type map_get_known(const struct tile *ptile,
- struct player *pplayer)
-{
- assert(pplayer == game.player_ptr);
- return tile_get_known(ptile);
-}
-
/**************************************************************************
Find city nearest to given unit and optionally return squared city
distance Parameter sq_dist may be NULL. Returns NULL only if no city is
Index: client/mapview_common.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/mapview_common.c,v
retrieving revision 1.163
diff -u -r1.163 mapview_common.c
--- client/mapview_common.c 6 Dec 2004 18:01:14 -0000 1.163
+++ client/mapview_common.c 6 Dec 2004 20:57:16 -0000
@@ -1463,7 +1463,7 @@
int count = fill_sprite_array(tile_sprs, ptile,
get_drawable_unit(ptile, citymode),
ptile->city, citymode);
- bool fog = ptile->known == TILE_KNOWN_FOGGED && draw_fog_of_war;
+ bool fog = tile_get_known(ptile) == TILE_KNOWN_FOGGED && draw_fog_of_war;
/*** Draw terrain and specials ***/
put_drawn_sprites(pcanvas, canvas_x, canvas_y, count, tile_sprs, fog);
Index: client/packhand.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/client/packhand.c,v
retrieving revision 1.438
diff -u -r1.438 packhand.c
--- client/packhand.c 6 Dec 2004 18:01:14 -0000 1.438
+++ client/packhand.c 6 Dec 2004 20:57:16 -0000
@@ -1930,7 +1930,7 @@
void handle_tile_info(struct packet_tile_info *packet)
{
struct tile *ptile = map_pos_to_tile(packet->x, packet->y);
- enum known_type old_known = ptile->known;
+ enum known_type old_known = tile_get_known(ptile);
bool tile_changed = FALSE;
bool known_changed = FALSE;
@@ -1955,10 +1955,25 @@
tile_changed = TRUE;
}
}
- if (ptile->known != packet->known) {
+ if (old_known != packet->known) {
known_changed = TRUE;
}
- ptile->known = packet->known;
+ BV_CLR(ptile->tile_known, game.player_idx);
+ BV_CLR(ptile->tile_seen, game.player_idx);
+ switch (packet->known) {
+ case TILE_KNOWN:
+ BV_SET(ptile->tile_known, game.player_idx);
+ BV_SET(ptile->tile_seen, game.player_idx);
+ break;
+ case TILE_KNOWN_FOGGED:
+ BV_SET(ptile->tile_known, game.player_idx);
+ break;
+ case TILE_UNKNOWN:
+ break;
+ default:
+ freelog(LOG_NORMAL, "Unknown tile value %d.", packet->known);
+ break;
+ }
if (packet->spec_sprite[0] != '\0') {
if (!ptile->spec_sprite
@@ -1979,7 +1994,8 @@
reset_move_costs(ptile);
- if (ptile->known <= TILE_KNOWN_FOGGED && old_known == TILE_KNOWN) {
+ if (tile_get_known(ptile) <= TILE_KNOWN_FOGGED
+ && old_known == TILE_KNOWN) {
/* This is an error. So first we log the error, then make an assertion.
* But for NDEBUG clients we fix the error. */
unit_list_iterate(ptile->units, punit) {
@@ -2012,9 +2028,9 @@
* A tile can only change if it was known before and is still
* known. In the other cases the tile is new or removed.
*/
- if (known_changed && ptile->known == TILE_KNOWN) {
+ if (known_changed && tile_get_known(ptile) == TILE_KNOWN) {
agents_tile_new(ptile);
- } else if (known_changed && ptile->known == TILE_KNOWN_FOGGED) {
+ } else if (known_changed && tile_get_known(ptile) == TILE_KNOWN_FOGGED) {
agents_tile_remove(ptile);
} else {
agents_tile_changed(ptile);
@@ -2024,7 +2040,7 @@
/* refresh tiles */
if (can_client_change_view()) {
/* the tile itself */
- if (tile_changed || old_known!=ptile->known)
+ if (tile_changed || old_known != tile_get_known(ptile))
refresh_tile_mapcanvas(ptile, FALSE);
/* if the terrain or the specials of the tile
Index: common/map.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/common/map.c,v
retrieving revision 1.208
diff -u -r1.208 map.c
--- common/map.c 30 Nov 2004 05:39:12 -0000 1.208
+++ common/map.c 6 Dec 2004 20:57:17 -0000
@@ -355,7 +355,8 @@
{
ptile->terrain = T_UNKNOWN;
ptile->special = S_NO_SPECIAL;
- ptile->known = 0;
+ BV_CLR_ALL(ptile->tile_known);
+ BV_CLR_ALL(ptile->tile_seen);
ptile->continent = 0;
ptile->city = NULL;
unit_list_init(&ptile->units);
@@ -1286,6 +1287,23 @@
ptile->terrain = ter;
}
+/*************************************************************************
+ Return a known_type enumeration value for the tile.
+
+ Note that the client only knows known data about game.player_ptr.
+*************************************************************************/
+enum known_type map_get_known(const struct tile *ptile,
+ const struct player *pplayer)
+{
+ if (!BV_ISSET(ptile->tile_known, pplayer->player_no)) {
+ return TILE_UNKNOWN;
+ } else if (!BV_ISSET(ptile->tile_seen, pplayer->player_no)) {
+ return TILE_KNOWN_FOGGED;
+ } else {
+ return TILE_KNOWN;
+ }
+}
+
/***************************************************************
...
***************************************************************/
Index: common/map.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/common/map.h,v
retrieving revision 1.229
diff -u -r1.229 map.h
--- common/map.h 30 Nov 2004 05:39:12 -0000 1.229
+++ common/map.h 6 Dec 2004 20:57:17 -0000
@@ -44,9 +44,7 @@
enum tile_special_type special;
struct city *city;
struct unit_list units;
- unsigned int known; /* A bitvector on the server side, an
- enum known_type on the client side.
- Player_no is index */
+ player_bv tile_known, tile_seen;
int assigned; /* these can save a lot of CPU usage -- Syela */
struct city *worked; /* city working tile, or NULL if none */
Continent_id continent;
@@ -348,9 +346,8 @@
bool is_real_map_pos(int x, int y);
bool is_normal_map_pos(int x, int y);
-/* implemented in server/maphand.c and client/climisc.c */
enum known_type map_get_known(const struct tile *ptile,
- struct player *pplayer);
+ const struct player *pplayer);
/* special testing */
bool map_has_special(const struct tile *ptile,
Index: common/player.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/common/player.h,v
retrieving revision 1.133
diff -u -r1.133 player.h
--- common/player.h 30 Nov 2004 00:36:08 -0000 1.133
+++ common/player.h 6 Dec 2004 20:57:17 -0000
@@ -57,6 +57,8 @@
H_DIPLOMACY = 2048 /* Not very good at diplomacy */
};
+BV_DEFINE(player_bv, MAX_NUM_PLAYERS + MAX_NUM_BARBARIANS);
+
struct player_economic {
int gold;
int tax;
Index: server/maphand.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/maphand.c,v
retrieving revision 1.151
diff -u -r1.151 maphand.c
--- server/maphand.c 22 Nov 2004 19:14:42 -0000 1.151
+++ server/maphand.c 6 Dec 2004 20:57:18 -0000
@@ -912,7 +912,7 @@
***************************************************************/
bool map_is_known(const struct tile *ptile, struct player *pplayer)
{
- return TEST_BIT(ptile->known, pplayer->player_no);
+ return BV_ISSET(ptile->tile_known, pplayer->player_no);
}
/***************************************************************
@@ -920,8 +920,10 @@
***************************************************************/
bool map_is_known_and_seen(const struct tile *ptile, struct player *pplayer)
{
- return TEST_BIT(ptile->known, pplayer->player_no)
- && ((pplayer->private_map + ptile->index)->seen != 0);
+ assert(BV_ISSET(ptile->tile_seen, pplayer->player_no)
+ == (map_get_player_tile(ptile, pplayer)->seen_count > 0));
+ return (BV_ISSET(ptile->tile_known, pplayer->player_no)
+ && BV_ISSET(ptile->tile_seen, pplayer->player_no));
}
/***************************************************************
@@ -929,7 +931,9 @@
***************************************************************/
static int map_get_seen(const struct tile *ptile, struct player *pplayer)
{
- return map_get_player_tile(ptile, pplayer)->seen;
+ assert(BV_ISSET(ptile->tile_seen, pplayer->player_no)
+ == (map_get_player_tile(ptile, pplayer)->seen_count > 0));
+ return map_get_player_tile(ptile, pplayer)->seen_count;
}
/***************************************************************
@@ -937,10 +941,16 @@
***************************************************************/
void map_change_seen(struct tile *ptile, struct player *pplayer, int change)
{
- map_get_player_tile(ptile, pplayer)->seen += change;
+ struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
+
+ plrtile->seen_count += change;
+ if (plrtile->seen_count != 0) {
+ BV_SET(ptile->tile_seen, pplayer->player_no);
+ } else {
+ BV_CLR(ptile->tile_seen, pplayer->player_no);
+ }
freelog(LOG_DEBUG, "%d,%d, p: %d, change %d, result %d\n", TILE_XY(ptile),
- pplayer->player_no, change, map_get_player_tile(ptile,
- pplayer)->seen);
+ pplayer->player_no, change, plrtile->seen_count);
}
/***************************************************************
@@ -969,7 +979,7 @@
***************************************************************/
void map_set_known(struct tile *ptile, struct player *pplayer)
{
- ptile->known |= (1u<<pplayer->player_no);
+ BV_SET(ptile->tile_known, pplayer->player_no);
}
/***************************************************************
@@ -977,7 +987,7 @@
***************************************************************/
void map_clear_known(struct tile *ptile, struct player *pplayer)
{
- ptile->known &= ~(1u<<pplayer->player_no);
+ BV_CLR(ptile->tile_known, pplayer->player_no);
}
/***************************************************************
@@ -1057,18 +1067,20 @@
plrtile->special = S_NO_SPECIAL;
plrtile->city = NULL;
- plrtile->seen = 0;
+ plrtile->seen_count = 0;
plrtile->pending_seen = 0;
+ BV_CLR(ptile->tile_seen, pplayer->player_no);
if (!game.fogofwar_old) {
if (map_is_known(ptile, pplayer)) {
- plrtile->seen = 1;
+ plrtile->seen_count = 1;
+ BV_SET(ptile->tile_seen, pplayer->player_no);
} else {
plrtile->pending_seen = 1;
}
}
plrtile->last_updated = GAME_START_YEAR;
- plrtile->own_seen = plrtile->seen;
+ plrtile->own_seen = plrtile->seen_count;
}
/***************************************************************
@@ -1358,23 +1370,6 @@
/*************************************************************************
...
*************************************************************************/
-enum known_type map_get_known(const struct tile *ptile,
- struct player *pplayer)
-{
- if (map_is_known(ptile, pplayer)) {
- if (map_get_seen(ptile, pplayer) > 0) {
- return TILE_KNOWN;
- } else {
- return TILE_KNOWN_FOGGED;
- }
- } else {
- return TILE_UNKNOWN;
- }
-}
-
-/*************************************************************************
-...
-*************************************************************************/
static void enable_fog_of_war_player(struct player *pplayer)
{
whole_map_iterate(ptile) {
Index: server/maphand.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/maphand.h,v
retrieving revision 1.50
diff -u -r1.50 maphand.h
--- server/maphand.h 11 Nov 2004 16:50:54 -0000 1.50
+++ server/maphand.h 6 Dec 2004 20:57:18 -0000
@@ -38,7 +38,7 @@
struct player_tile {
Terrain_type_id terrain;
enum tile_special_type special;
- unsigned short seen;
+ unsigned short seen_count;
unsigned short own_seen;
/* If you build a city with an unknown square within city radius
the square stays unknown. However, we still have to keep count
Index: server/sanitycheck.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/sanitycheck.c,v
retrieving revision 1.55
diff -u -r1.55 sanitycheck.c
--- server/sanitycheck.c 22 Nov 2004 07:12:39 -0000 1.55
+++ server/sanitycheck.c 6 Dec 2004 20:57:18 -0000
@@ -82,11 +82,17 @@
players_iterate(pplayer) {
struct player_tile *plr_tile = map_get_player_tile(ptile, pplayer);
/* underflow of unsigned int */
- SANITY_CHECK(plr_tile->seen < 60000);
+ SANITY_CHECK(plr_tile->seen_count < 60000);
SANITY_CHECK(plr_tile->own_seen < 60000);
SANITY_CHECK(plr_tile->pending_seen < 60000);
- SANITY_CHECK(plr_tile->own_seen <= plr_tile->seen);
+ if (plr_tile->seen_count > 0) {
+ SANITY_CHECK(BV_ISSET(ptile->tile_seen, pplayer->player_no));
+ } else {
+ SANITY_CHECK(!BV_ISSET(ptile->tile_seen, pplayer->player_no));
+ }
+
+ SANITY_CHECK(plr_tile->own_seen <= plr_tile->seen_count);
if (map_is_known(ptile, pplayer)) {
SANITY_CHECK(plr_tile->pending_seen == 0);
}
Index: server/savegame.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/savegame.c,v
retrieving revision 1.210
diff -u -r1.210 savegame.c
--- server/savegame.c 30 Nov 2004 08:37:03 -0000 1.210
+++ server/savegame.c 6 Dec 2004 20:57:19 -0000
@@ -618,36 +618,48 @@
ptile->special |= ascii_hex2bin(ch, 3));
if (secfile_lookup_bool_default(file, TRUE, "game.save_known")) {
+ int known[MAX_MAP_INDEX];
/* get 4-bit segments of the first half of the 32-bit "known" field */
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.a%03d", nat_y),
- ptile->known = ascii_hex2bin(ch, 0));
+ known[ptile->index] = ascii_hex2bin(ch, 0));
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.b%03d", nat_y),
- ptile->known |= ascii_hex2bin(ch, 1));
+ known[ptile->index] |= ascii_hex2bin(ch, 1));
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.c%03d", nat_y),
- ptile->known |= ascii_hex2bin(ch, 2));
+ known[ptile->index] |= ascii_hex2bin(ch, 2));
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.d%03d", nat_y),
- ptile->known |= ascii_hex2bin(ch, 3));
+ known[ptile->index] |= ascii_hex2bin(ch, 3));
if (has_capability("known32fix", savefile_options)) {
/* get 4-bit segments of the second half of the 32-bit "known" field */
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.e%03d", nat_y),
- ptile->known |= ascii_hex2bin(ch, 4));
+ known[ptile->index] |= ascii_hex2bin(ch, 4));
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.g%03d", nat_y),
- ptile->known |= ascii_hex2bin(ch, 5));
+ known[ptile->index] |= ascii_hex2bin(ch, 5));
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.h%03d", nat_y),
- ptile->known |= ascii_hex2bin(ch, 6));
+ known[ptile->index] |= ascii_hex2bin(ch, 6));
LOAD_MAP_DATA(ch, nat_y, ptile,
secfile_lookup_str(file, "map.i%03d", nat_y),
- ptile->known |= ascii_hex2bin(ch, 7));
+ known[ptile->index] |= ascii_hex2bin(ch, 7));
}
+
+ /* HACK: we read the known data from hex into a 32-bit integer, and
+ * now we convert it to player_bv. */
+ whole_map_iterate(ptile) {
+ BV_CLR_ALL(ptile->tile_known);
+ players_iterate(pplayer) {
+ if (known[ptile->index] & (1u << pplayer->player_no)) {
+ BV_SET(ptile->tile_known, pplayer->player_no);
+ }
+ } players_iterate_end;
+ } whole_map_iterate_end;
}
@@ -713,27 +725,40 @@
secfile_insert_bool(file, game.save_options.save_known, "game.save_known");
if (game.save_options.save_known) {
+ int known[MAX_MAP_INDEX];
+
/* put the top 4 bits (bits 12-15) of special flags */
SAVE_NORMAL_MAP_DATA(ptile, file, "map.f%03d",
bin2ascii_hex(ptile->special, 3));
+ /* HACK: we convert the data into a 32-bit integer, and then save it as
+ * hex. */
+ memset(known, 0, sizeof(known));
+ whole_map_iterate(ptile) {
+ players_iterate(pplayer) {
+ if (map_is_known(ptile, pplayer)) {
+ known[ptile->index] |= (1u << pplayer->player_no);
+ }
+ } players_iterate_end;
+ } whole_map_iterate_end;
+
/* put 4-bit segments of the 32-bit "known" field */
SAVE_NORMAL_MAP_DATA(ptile, file, "map.a%03d",
- bin2ascii_hex(ptile->known, 0));
+ bin2ascii_hex(known[ptile->index], 0));
SAVE_NORMAL_MAP_DATA(ptile, file, "map.b%03d",
- bin2ascii_hex(ptile->known, 1));
+ bin2ascii_hex(known[ptile->index], 1));
SAVE_NORMAL_MAP_DATA(ptile, file, "map.c%03d",
- bin2ascii_hex(ptile->known, 2));
+ bin2ascii_hex(known[ptile->index], 2));
SAVE_NORMAL_MAP_DATA(ptile, file, "map.d%03d",
- bin2ascii_hex(ptile->known, 3));
+ bin2ascii_hex(known[ptile->index], 3));
SAVE_NORMAL_MAP_DATA(ptile, file, "map.e%03d",
- bin2ascii_hex(ptile->known, 4));
+ bin2ascii_hex(known[ptile->index], 4));
SAVE_NORMAL_MAP_DATA(ptile, file, "map.g%03d",
- bin2ascii_hex(ptile->known, 5));
+ bin2ascii_hex(known[ptile->index], 5));
SAVE_NORMAL_MAP_DATA(ptile, file, "map.h%03d",
- bin2ascii_hex(ptile->known, 6));
+ bin2ascii_hex(known[ptile->index], 6));
SAVE_NORMAL_MAP_DATA(ptile, file, "map.i%03d",
- bin2ascii_hex(ptile->known, 7));
+ bin2ascii_hex(known[ptile->index], 7));
}
whole_map_iterate(ptile) {
Index: server/score.c
===================================================================
RCS file: /home/freeciv/CVS/freeciv/server/score.c,v
retrieving revision 1.12
diff -u -r1.12 score.c
--- server/score.c 30 Nov 2004 08:37:03 -0000 1.12
+++ server/score.c 6 Dec 2004 20:57:19 -0000
@@ -36,7 +36,7 @@
struct claim_cell {
int when;
int whom;
- int know;
+ player_bv know;
int cities;
};
@@ -197,7 +197,7 @@
nextedge++;
pcmap->player_landarea[owner]++;
pcmap->player_owndarea[owner]++;
- pclaim->know = ptile->known;
+ BV_COPY(pclaim->know, ptile->tile_known);
} else if (ptile->worked) {
owner = ptile->worked->owner;
pclaim->when = turn + 1;
@@ -206,7 +206,7 @@
nextedge++;
pcmap->player_landarea[owner]++;
pcmap->player_owndarea[owner]++;
- pclaim->know = ptile->known;
+ BV_COPY(pclaim->know, ptile->tile_known);
} else if (unit_list_size(&ptile->units) > 0) {
owner = (unit_list_get(&ptile->units, 0))->owner;
pclaim->when = turn + 1;
@@ -217,11 +217,11 @@
if (TEST_BIT(pclaim->cities, owner)) {
pcmap->player_owndarea[owner]++;
}
- pclaim->know = ptile->known;
+ BV_COPY(pclaim->know, ptile->tile_known);
} else {
/* pclaim->when = 0; */
pclaim->whom = no_owner;
- pclaim->know = ptile->known;
+ BV_COPY(pclaim->know, ptile->tile_known);
}
} whole_map_iterate_end;
@@ -258,7 +258,7 @@
int j = tile1->index;
struct claim_cell *pclaim = &pcmap->claims[j];
- if (TEST_BIT(pclaim->know, owner)) {
+ if (BV_ISSET(pclaim->know, owner)) {
if (pclaim->when == 0) {
pclaim->when = turn + 1;
pclaim->whom = owner;
Index: utility/shared.h
===================================================================
RCS file: /home/freeciv/CVS/freeciv/utility/shared.h,v
retrieving revision 1.138
diff -u -r1.138 shared.h
--- utility/shared.h 26 Nov 2004 22:28:43 -0000 1.138
+++ utility/shared.h 6 Dec 2004 20:57:19 -0000
@@ -185,6 +185,10 @@
#define BV_ARE_EQUAL(vec1, vec2) \
bv_are_equal((vec1).vec, (vec2).vec, sizeof((vec1).vec), sizeof((vec2).vec))
+#define BV_COPY(dst, src) \
+ (assert(sizeof((src).vec) == sizeof((dst).vec)), \
+ memcpy((dst).vec, (src).vec, sizeof((dst).vec)))
+
#define BV_DEFINE(name, bits) \
typedef struct { unsigned char vec[_BV_BYTES(bits)]; } name
[Prev in Thread] |
Current Thread |
[Next in Thread] |
- [Freeciv-Dev] (PR#11126) unify map_get_known,
Jason Short <=
|
|