Freeciv-3.1: /fast/freeciv/nightly/S3_1/server/maphand.c Source File

Freeciv-3.1

Loading...
Searching...
No Matches
maphand.c
Go to the documentation of this file.
1/***********************************************************************
2 Freeciv - Copyright (C) 1996 - A Kjeldberg, L Gregersen, P Unold
3 This program is free software; you can redistribute it and/or modify
4 it under the terms of the GNU General Public License as published by
5 the Free Software Foundation; either version 2, or (at your option)
6 any later version.
7
8 This program is distributed in the hope that it will be useful,
9 but WITHOUT ANY WARRANTY; without even the implied warranty of
10 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 GNU General Public License for more details.
12***********************************************************************/
13
14#ifdef HAVE_CONFIG_H
15#include <fc_config.h>
16#endif
17
18/* utility */
19#include "bitvector.h"
20#include "fcintl.h"
21#include "log.h"
22#include "mem.h"
23#include "rand.h"
24#include "support.h"
25
26/* common */
27#include "ai.h"
28#include "base.h"
29#include "borders.h"
30#include "events.h"
31#include "game.h"
32#include "map.h"
33#include "movement.h"
34#include "nation.h"
35#include "packets.h"
36#include "player.h"
37#include "road.h"
38#include "specialist.h"
39#include "unit.h"
40#include "unitlist.h"
41#include "vision.h"
42
43/* server */
44#include "citytools.h"
45#include "cityturn.h"
46#include "notify.h"
47#include "plrhand.h"
48#include "sanitycheck.h"
49#include "sernet.h"
50#include "srv_main.h"
51#include "unithand.h"
52#include "unittools.h"
53
54/* server/advisors */
55#include "advdata.h"
56
57/* server/generator */
58#include "mapgen_utils.h"
59
60#include "maphand.h"
61
62#define MAXIMUM_CLAIMED_OCEAN_SIZE (20)
63
64/* Suppress send_tile_info() during game_load() */
65 static bool send_tile_suppressed = FALSE;
66
67static void player_tile_init(struct tile *ptile, struct player *pplayer);
68static void player_tile_free(struct tile *ptile, struct player *pplayer);
69static bool give_tile_info_from_player_to_player(struct player *pfrom,
70 struct player *pdest,
71 struct tile *ptile);
72static void shared_vision_change_seen(struct player *pplayer,
73 struct tile *ptile,
74 const v_radius_t change,
75 bool can_reveal_tiles);
76static void map_change_seen(struct player *pplayer,
77 struct tile *ptile,
78 const v_radius_t change,
79 bool can_reveal_tiles);
80static void map_change_own_seen(struct player *pplayer,
81 struct tile *ptile,
82 const v_radius_t change);
83static inline int map_get_seen(const struct player *pplayer,
84 const struct tile *ptile,
85 enum vision_layer vlayer);
86
87static bool is_claimable_ocean(struct tile *ptile, struct tile *source,
88 struct player *pplayer);
89
90/**********************************************************************/
93 static bool is_terrain_ecologically_wet(struct tile *ptile)
94{
95 return (is_terrain_class_near_tile(&(wld.map), ptile, TC_OCEAN)
96 || tile_has_river(ptile)
97 || count_river_near_tile(&(wld.map), ptile, NULL) > 0);
98}
99
100/**********************************************************************/
103 void global_warming(int effect)
104{
105 climate_change(TRUE, effect);
106 notify_player(NULL, NULL, E_GLOBAL_ECO, ftc_server,
107 _("Global warming has occurred!"));
108 notify_player(NULL, NULL, E_GLOBAL_ECO, ftc_server,
109 _("Coastlines have been flooded and vast "
110 "ranges of grassland have become deserts."));
111}
112
113/**********************************************************************/
116 void nuclear_winter(int effect)
117{
118 climate_change(FALSE, effect);
119 notify_player(NULL, NULL, E_GLOBAL_ECO, ftc_server,
120 _("Nuclear winter has occurred!"));
121 notify_player(NULL, NULL, E_GLOBAL_ECO, ftc_server,
122 _("Wetlands have dried up and vast "
123 "ranges of grassland have become tundra."));
124}
125
126/**********************************************************************/
130 void climate_change(bool warming, int effect)
131{
132 int k = map_num_tiles();
133 bool used[k];
134 const struct civ_map *nmap = &(wld.map);
135
136 memset(used, 0, sizeof(used));
137
138 log_verbose("Climate change: %s (%d)",
139 warming ? "Global warming" : "Nuclear winter", effect);
140
141 while (effect > 0 && (k--) > 0) {
142 struct terrain *old, *candidates[2], *new;
143 struct tile *ptile;
144 int i;
145
146 do {
147 /* We want to transform a tile at most once due to a climate change. */
148 ptile = rand_map_pos(&(wld.map));
149 } while (used[tile_index(ptile)]);
150 used[tile_index(ptile)] = TRUE;
151
152 old = tile_terrain(ptile);
153 /* Prefer the transformation that's appropriate to the ambient moisture,
154 * but be prepared to fall back in exceptional circumstances */
155 {
156 struct terrain *wetter, *drier;
157
158 wetter = warming ? old->warmer_wetter_result : old->cooler_wetter_result;
159 drier = warming ? old->warmer_drier_result : old->cooler_drier_result;
160 if (is_terrain_ecologically_wet(ptile)) {
161 candidates[0] = wetter;
162 candidates[1] = drier;
163 } else {
164 candidates[0] = drier;
165 candidates[1] = wetter;
166 }
167 }
168
169 /* If the preferred transformation is ruled out for some exceptional reason
170 * specific to this tile, fall back to the other, rather than letting this
171 * tile be immune to change. */
172 for (i = 0; i < 2; i++) {
173 new = candidates[i];
174
175 /* If the preferred transformation simply hasn't been specified
176 * for this terrain at all, don't fall back to the other. */
177 if (new == T_NONE) {
178 break;
179 }
180
181 if (tile_city(ptile) != NULL && terrain_has_flag(new, TER_NO_CITIES)) {
182 /* do not change to a terrain with the flag TER_NO_CITIES if the tile
183 * has a city */
184 continue;
185 }
186
187 /* Only change between water and land at coastlines, and between
188 * frozen and unfrozen at ice margin */
189 if (!terrain_surroundings_allow_change(nmap, ptile, new)) {
190 continue;
191 }
192
193 /* OK! */
194 break;
195 }
196 if (i == 2) {
197 /* Neither transformation was permitted. Give up. */
198 continue;
199 }
200
201 if (new != T_NONE && old != new) {
202 effect--;
203
204 /* Check terrain changing activities.
205 These would not be caught by the check if unit can continue activity
206 after the terrain change has taken place, as the activity itself is still
207 legal, but would be towards different terrain, and terrain types are not
208 activity targets (target is NULL) */
209 unit_list_iterate(ptile->units, punit) {
210 if (punit->activity_target == NULL) {
211 /* Target is always NULL for terrain changing activities. */
212 if (punit->activity == ACTIVITY_CULTIVATE
213 || punit->activity == ACTIVITY_PLANT
214 || punit->activity == ACTIVITY_TRANSFORM) {
215 unit_activities_cancel(punit);
216 }
217 }
218 } unit_list_iterate_end;
219
220 /* Really change the terrain. */
221 tile_change_terrain(ptile, new);
222 check_terrain_change(ptile, old);
223 update_tile_knowledge(ptile);
224
225 tile_change_side_effects(ptile, FALSE);
226
227 } else if (old == new) {
228 /* This counts toward a climate change although nothing is changed. */
229 effect--;
230 }
231 }
232}
233
234/**********************************************************************/
238 bool upgrade_city_extras(struct city *pcity, struct extra_type **gained)
239{
240 struct tile *ptile = pcity->tile;
241 struct player *pplayer = city_owner(pcity);
242 bool upgradet = FALSE;
243
244 extra_type_iterate(pextra) {
245 if (!tile_has_extra(ptile, pextra)) {
246 if (extra_has_flag(pextra, EF_ALWAYS_ON_CITY_CENTER)
247 || (extra_has_flag(pextra, EF_AUTO_ON_CITY_CENTER)
248 && player_can_build_extra(pextra, pplayer, ptile)
249 && !tile_has_conflicting_extra(ptile, pextra))) {
250 tile_add_extra(pcity->tile, pextra);
251 if (gained != NULL) {
252 if (upgradet) {
253 *gained = NULL;
254 } else {
255 *gained = pextra;
256 }
257 }
258 upgradet = TRUE;
259 }
260 }
261 } extra_type_iterate_end;
262
263 return upgradet;
264}
265
266/**********************************************************************/
273 void upgrade_all_city_extras(struct player *pplayer, bool discovery)
274{
275 int cities_upgradet = 0;
276 struct extra_type *upgradet = NULL;
277 bool multiple_types = FALSE;
278 int cities_total = city_list_size(pplayer->cities);
279 int percent;
280
281 conn_list_do_buffer(pplayer->connections);
282
283 city_list_iterate(pplayer->cities, pcity) {
284 struct extra_type *new_upgrade;
285
286 if (upgrade_city_extras(pcity, &new_upgrade)) {
287 update_tile_knowledge(pcity->tile);
288 cities_upgradet++;
289 if (new_upgrade == NULL) {
290 /* This single city alone had multiple types */
291 multiple_types = TRUE;
292 } else if (upgradet == NULL) {
293 /* First gained */
294 upgradet = new_upgrade;
295 } else if (upgradet != new_upgrade) {
296 /* Different type from what another city got. */
297 multiple_types = TRUE;
298 }
299 }
300 } city_list_iterate_end;
301
302 if (cities_total > 0) {
303 percent = cities_upgradet * 100 / cities_total;
304 } else {
305 percent = 0;
306 }
307
308 if (cities_upgradet > 0) {
309 if (discovery) {
310 if (percent >= 75) {
311 notify_player(pplayer, NULL, E_TECH_GAIN, ftc_server,
312 _("New hope sweeps like fire through the country as "
313 "the discovery of new infrastructure building technology "
314 "is announced."));
315 }
316 } else {
317 if (percent >= 75) {
318 notify_player(pplayer, NULL, E_TECH_GAIN, ftc_server,
319 _("The people are pleased to hear that your "
320 "scientists finally know about new infrastructure building "
321 "technology."));
322 }
323 }
324
325 if (multiple_types) {
326 notify_player(pplayer, NULL, E_TECH_GAIN, ftc_server,
327 _("Workers spontaneously gather and upgrade all "
328 "possible cities with better infrastructure."));
329 } else {
330 notify_player(pplayer, NULL, E_TECH_GAIN, ftc_server,
331 _("Workers spontaneously gather and upgrade all "
332 "possible cities with %s."), extra_name_translation(upgradet));
333 }
334 }
335
336 conn_list_do_unbuffer(pplayer->connections);
337}
338
339/**********************************************************************/
342 bool really_gives_vision(struct player *me, struct player *them)
343{
344 return BV_ISSET(me->server.really_gives_vision, player_index(them));
345}
346
347/**********************************************************************/
350 static void buffer_shared_vision(struct player *pplayer)
351{
352 players_iterate(pplayer2) {
353 if (really_gives_vision(pplayer, pplayer2)) {
354 conn_list_compression_freeze(pplayer2->connections);
355 conn_list_do_buffer(pplayer2->connections);
356 }
357 } players_iterate_end;
358 conn_list_compression_freeze(pplayer->connections);
359 conn_list_do_buffer(pplayer->connections);
360}
361
362/**********************************************************************/
365 static void unbuffer_shared_vision(struct player *pplayer)
366{
367 players_iterate(pplayer2) {
368 if (really_gives_vision(pplayer, pplayer2)) {
369 conn_list_do_unbuffer(pplayer2->connections);
370 conn_list_compression_thaw(pplayer2->connections);
371 }
372 } players_iterate_end;
373 conn_list_do_unbuffer(pplayer->connections);
374 conn_list_compression_thaw(pplayer->connections);
375}
376
377/**********************************************************************/
381 void give_map_from_player_to_player(struct player *pfrom, struct player *pdest)
382{
383 buffer_shared_vision(pdest);
384
385 whole_map_iterate(&(wld.map), ptile) {
386 give_tile_info_from_player_to_player(pfrom, pdest, ptile);
387 } whole_map_iterate_end;
388
389 unbuffer_shared_vision(pdest);
390 city_thaw_workers_queue();
391 sync_cities();
392}
393
394/**********************************************************************/
397 void give_seamap_from_player_to_player(struct player *pfrom, struct player *pdest)
398{
399 buffer_shared_vision(pdest);
400
401 whole_map_iterate(&(wld.map), ptile) {
402 if (is_ocean_tile(ptile)) {
403 give_tile_info_from_player_to_player(pfrom, pdest, ptile);
404 }
405 } whole_map_iterate_end;
406
407 unbuffer_shared_vision(pdest);
408 city_thaw_workers_queue();
409 sync_cities();
410}
411
412/**********************************************************************/
415 void give_citymap_from_player_to_player(struct city *pcity,
416 struct player *pfrom, struct player *pdest)
417{
418 struct tile *pcenter = city_tile(pcity);
419 const struct civ_map *nmap = &(wld.map);
420
421 buffer_shared_vision(pdest);
422
423 city_tile_iterate(nmap, city_map_radius_sq_get(pcity), pcenter, ptile) {
424 give_tile_info_from_player_to_player(pfrom, pdest, ptile);
425 } city_tile_iterate_end;
426
427 unbuffer_shared_vision(pdest);
428 city_thaw_workers_queue();
429 sync_cities();
430}
431
432/**********************************************************************/
441 void send_all_known_tiles(struct conn_list *dest)
442{
443 int tiles_sent;
444
445 if (!dest) {
446 dest = game.est_connections;
447 }
448
449 /* send whole map piece by piece to each player to balance the load
450 of the send buffers better */
451 tiles_sent = 0;
452 conn_list_do_buffer(dest);
453
454 whole_map_iterate(&(wld.map), ptile) {
455 tiles_sent++;
456 if ((tiles_sent % wld.map.xsize) == 0) {
457 conn_list_do_unbuffer(dest);
458 flush_packets();
459 conn_list_do_buffer(dest);
460 }
461
462 send_tile_info(dest, ptile, FALSE);
463 } whole_map_iterate_end;
464
465 conn_list_do_unbuffer(dest);
466 flush_packets();
467}
468
469/**********************************************************************/
472 bool send_tile_suppression(bool now)
473{
474 bool formerly = send_tile_suppressed;
475
476 send_tile_suppressed = now;
477 return formerly;
478}
479
480/**********************************************************************/
488 void send_tile_info(struct conn_list *dest, struct tile *ptile,
489 bool send_unknown)
490{
491 struct packet_tile_info info;
492 const struct player *owner;
493 const struct player *eowner;
494
495 if (dest == NULL) {
496 CALL_FUNC_EACH_AI(tile_info, ptile);
497 }
498
499 if (send_tile_suppressed) {
500 return;
501 }
502
503 if (!dest) {
504 dest = game.est_connections;
505 }
506
507 info.tile = tile_index(ptile);
508
509 if (ptile->spec_sprite) {
510 sz_strlcpy(info.spec_sprite, ptile->spec_sprite);
511 } else {
512 info.spec_sprite[0] = '\0';
513 }
514
515 conn_list_iterate(dest, pconn) {
516 struct player *pplayer = pconn->playing;
517
518 if (NULL == pplayer && !pconn->observer) {
519 continue;
520 }
521
522 if (!pplayer || map_is_known_and_seen(ptile, pplayer, V_MAIN)) {
523 struct extra_type *resource;
524
525 info.known = TILE_KNOWN_SEEN;
526 info.continent = tile_continent(ptile);
527 owner = tile_owner(ptile);
528 eowner = extra_owner(ptile);
529 info.owner = (owner ? player_number(owner) : MAP_TILE_OWNER_NULL);
530 info.extras_owner = (eowner ? player_number(eowner) : MAP_TILE_OWNER_NULL);
531 info.worked32 = (NULL != tile_worked(ptile))
532 ? tile_worked(ptile)->id
533 : IDENTITY_NUMBER_ZERO;
534 info.worked16 = info.worked32;
535
536 info.terrain = (NULL != tile_terrain(ptile))
537 ? terrain_number(tile_terrain(ptile))
538 : terrain_count();
539
540 resource = tile_resource(ptile);
541 if (resource != NULL
542 && (pplayer == NULL
543 || player_knows_extra_exist(pplayer, resource, ptile))) {
544 info.resource = extra_number(resource);
545 } else {
546 info.resource = MAX_EXTRA_TYPES;
547 }
548
549 info.placing = (NULL != ptile->placing)
550 ? extra_number(ptile->placing)
551 : -1;
552 info.place_turn = (NULL != ptile->placing)
553 ? game.info.turn + ptile->infra_turns
554 : 0;
555
556 if (pplayer != NULL) {
557 info.extras = map_get_player_tile(ptile, pplayer)->extras;
558 } else {
559 info.extras = ptile->extras;
560 }
561
562 if (ptile->label != NULL) {
563 /* Always leave final '\0' in place */
564 strncpy(info.label, ptile->label, sizeof(info.label) - 1);
565 } else {
566 info.label[0] = '\0';
567 }
568
569 send_packet_tile_info(pconn, &info);
570 } else if (pplayer && map_is_known(ptile, pplayer)) {
571 struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
572 struct vision_site *psite = map_get_player_site(ptile, pplayer);
573
574 info.known = TILE_KNOWN_UNSEEN;
575 info.continent = tile_continent(ptile);
576 owner = (game.server.foggedborders
577 ? plrtile->owner
578 : tile_owner(ptile));
579 eowner = plrtile->extras_owner;
580 info.owner = (owner ? player_number(owner) : MAP_TILE_OWNER_NULL);
581 info.extras_owner = (eowner ? player_number(eowner) : MAP_TILE_OWNER_NULL);
582 info.worked32 = (NULL != psite)
583 ? psite->identity
584 : IDENTITY_NUMBER_ZERO;
585 info.worked16 = info.worked32;
586
587 info.terrain = (NULL != plrtile->terrain)
588 ? terrain_number(plrtile->terrain)
589 : terrain_count();
590 info.resource = (NULL != plrtile->resource)
591 ? extra_number(plrtile->resource)
592 : MAX_EXTRA_TYPES;
593 info.placing = -1;
594 info.place_turn = 0;
595
596 info.extras = plrtile->extras;
597
598 /* Labels never change, so they are not subject to fog of war */
599 if (ptile->label != NULL) {
600 sz_strlcpy(info.label, ptile->label);
601 } else {
602 info.label[0] = '\0';
603 }
604
605 send_packet_tile_info(pconn, &info);
606 } else if (send_unknown) {
607 info.known = TILE_UNKNOWN;
608 info.continent = 0;
609 info.owner = MAP_TILE_OWNER_NULL;
610 info.extras_owner = MAP_TILE_OWNER_NULL;
611 info.worked32 = IDENTITY_NUMBER_ZERO;
612 info.worked16 = IDENTITY_NUMBER_ZERO;
613
614 info.terrain = terrain_count();
615 info.resource = MAX_EXTRA_TYPES;
616 info.placing = -1;
617 info.place_turn = 0;
618
619 BV_CLR_ALL(info.extras);
620
621 info.label[0] = '\0';
622
623 send_packet_tile_info(pconn, &info);
624 }
625 }
626 conn_list_iterate_end;
627}
628
629/**********************************************************************/
635 static bool unit_is_on_layer(const struct unit *punit,
636 enum vision_layer vlayer)
637{
638 return unit_type_get(punit)->vlayer == vlayer;
639}
640
641/**********************************************************************/
644 void send_map_info(struct conn_list *dest)
645{
646 struct packet_map_info minfo;
647
648 minfo.xsize = wld.map.xsize;
649 minfo.ysize = wld.map.ysize;
650 minfo.topology_id = wld.map.topology_id;
651
652 lsend_packet_map_info(dest, &minfo);
653}
654
655/**********************************************************************/
659 static void shared_vision_change_seen(struct player *pplayer,
660 struct tile *ptile,
661 const v_radius_t change,
662 bool can_reveal_tiles)
663{
664 map_change_own_seen(pplayer, ptile, change);
665 map_change_seen(pplayer, ptile, change, can_reveal_tiles);
666
667 players_iterate(pplayer2) {
668 if (really_gives_vision(pplayer, pplayer2)) {
669 map_change_seen(pplayer2, ptile, change, can_reveal_tiles);
670 }
671 } players_iterate_end;
672}
673
674/**********************************************************************/
677 void map_vision_update(struct player *pplayer, struct tile *ptile,
678 const v_radius_t old_radius_sq,
679 const v_radius_t new_radius_sq,
680 bool can_reveal_tiles)
681{
682 v_radius_t change;
683 int max_radius;
684
685 if (old_radius_sq[V_MAIN] == new_radius_sq[V_MAIN]
686 && old_radius_sq[V_INVIS] == new_radius_sq[V_INVIS]
687 && old_radius_sq[V_SUBSURFACE] == new_radius_sq[V_SUBSURFACE]) {
688 return;
689 }
690
691 /* Determines 'max_radius' value. */
692 max_radius = 0;
693 vision_layer_iterate(v) {
694 if (max_radius < old_radius_sq[v]) {
695 max_radius = old_radius_sq[v];
696 }
697 if (max_radius < new_radius_sq[v]) {
698 max_radius = new_radius_sq[v];
699 }
700 } vision_layer_iterate_end;
701
702#ifdef FREECIV_DEBUG
703 log_debug("Updating vision at (%d, %d) in a radius of %d.",
704 TILE_XY(ptile), max_radius);
705 vision_layer_iterate(v) {
706 log_debug(" vision layer %d is changing from %d to %d.",
707 v, old_radius_sq[v], new_radius_sq[v]);
708 } vision_layer_iterate_end;
709#endif /* FREECIV_DEBUG */
710
711 buffer_shared_vision(pplayer);
712 circle_dxyr_iterate(&(wld.map), ptile, max_radius, tile1, dx, dy, dr) {
713 vision_layer_iterate(v) {
714 if (dr > old_radius_sq[v] && dr <= new_radius_sq[v]) {
715 change[v] = 1;
716 } else if (dr > new_radius_sq[v] && dr <= old_radius_sq[v]) {
717 change[v] = -1;
718 } else {
719 change[v] = 0;
720 }
721 } vision_layer_iterate_end;
722 shared_vision_change_seen(pplayer, tile1, change, can_reveal_tiles);
723 } circle_dxyr_iterate_end;
724 unbuffer_shared_vision(pplayer);
725}
726
727/**********************************************************************/
732 void map_set_border_vision(struct player *pplayer,
733 const bool is_enabled)
734{
735 const v_radius_t radius_sq = V_RADIUS(is_enabled ? 1 : -1, 0, 0);
736
737 if (pplayer->server.border_vision == is_enabled) {
738 /* No change. Changing the seen count beyond what already exists would
739 * be a bug. */
740 return;
741 }
742
743 /* Set the new border seer value. */
744 pplayer->server.border_vision = is_enabled;
745
746 whole_map_iterate(&(wld.map), ptile) {
747 if (pplayer == ptile->owner) {
748 /* The tile is within the player's borders. */
749 shared_vision_change_seen(pplayer, ptile, radius_sq, TRUE);
750 }
751 } whole_map_iterate_end;
752}
753
754/**********************************************************************/
760 void map_show_tile(struct player *src_player, struct tile *ptile)
761{
762 static int recurse = 0;
763
764 log_debug("Showing %i,%i to %s", TILE_XY(ptile), player_name(src_player));
765
766 fc_assert(recurse == 0);
767 recurse++;
768
769 players_iterate(pplayer) {
770 if (pplayer == src_player || really_gives_vision(src_player, pplayer)) {
771 struct city *pcity;
772
773 if (!map_is_known_and_seen(ptile, pplayer, V_MAIN)) {
774 map_set_known(ptile, pplayer);
775
776 /* As the tile may be fogged send_tile_info won't always do this for us */
777 update_player_tile_knowledge(pplayer, ptile);
778 update_player_tile_last_seen(pplayer, ptile);
779
780 send_tile_info(pplayer->connections, ptile, FALSE);
781
782 /* Remove old cities that exist no more */
783 reality_check_city(pplayer, ptile);
784
785 if ((pcity = tile_city(ptile))) {
786 /* As the tile may be fogged send_city_info won't do this for us */
787 update_dumb_city(pplayer, pcity);
788 send_city_info(pplayer, pcity);
789 }
790
791 vision_layer_iterate(v) {
792 if (0 < map_get_seen(pplayer, ptile, v)) {
793 unit_list_iterate(ptile->units, punit) {
794 if (unit_is_on_layer(punit, v)) {
795 send_unit_info(pplayer->connections, punit);
796 }
797 } unit_list_iterate_end;
798 }
799 } vision_layer_iterate_end;
800 }
801 }
802 } players_iterate_end;
803
804 recurse--;
805}
806
807/**********************************************************************/
812 void map_hide_tile(struct player *src_player, struct tile *ptile)
813{
814 static int recurse = 0;
815
816 log_debug("Hiding %d,%d to %s", TILE_XY(ptile), player_name(src_player));
817
818 fc_assert(recurse == 0);
819 recurse++;
820
821 players_iterate(pplayer) {
822 if (pplayer == src_player || really_gives_vision(src_player, pplayer)) {
823 if (map_is_known(ptile, pplayer)) {
824 if (0 < map_get_seen(pplayer, ptile, V_MAIN)) {
825 update_player_tile_last_seen(pplayer, ptile);
826 }
827
828 /* Remove city. */
829 remove_dumb_city(pplayer, ptile);
830
831 /* Remove units. */
832 vision_layer_iterate(v) {
833 if (0 < map_get_seen(pplayer, ptile, v)) {
834 unit_list_iterate(ptile->units, punit) {
835 if (unit_is_on_layer(punit, v)) {
836 unit_goes_out_of_sight(pplayer, punit);
837 }
838 } unit_list_iterate_end;
839 }
840 } vision_layer_iterate_end;
841 }
842
843 map_clear_known(ptile, pplayer);
844
845 send_tile_info(pplayer->connections, ptile, TRUE);
846 }
847 } players_iterate_end;
848
849 recurse--;
850}
851
852/**********************************************************************/
856 void map_show_circle(struct player *pplayer, struct tile *ptile, int radius_sq)
857{
858 buffer_shared_vision(pplayer);
859
860 circle_iterate(&(wld.map), ptile, radius_sq, tile1) {
861 map_show_tile(pplayer, tile1);
862 } circle_iterate_end;
863
864 unbuffer_shared_vision(pplayer);
865}
866
867/**********************************************************************/
871 void map_show_all(struct player *pplayer)
872{
873 buffer_shared_vision(pplayer);
874
875 whole_map_iterate(&(wld.map), ptile) {
876 map_show_tile(pplayer, ptile);
877 } whole_map_iterate_end;
878
879 unbuffer_shared_vision(pplayer);
880}
881
882/**********************************************************************/
886 bool map_is_known(const struct tile *ptile, const struct player *pplayer)
887{
888 if (pplayer->tile_known.vec == NULL) {
889 /* Player map not initialized yet */
890 return FALSE;
891 }
892
893 return dbv_isset(&pplayer->tile_known, tile_index(ptile));
894}
895
896/**********************************************************************/
900 bool map_is_known_and_seen(const struct tile *ptile,
901 const struct player *pplayer,
902 enum vision_layer vlayer)
903{
904 return (map_is_known(ptile, pplayer)
905 && 0 < map_get_seen(pplayer, ptile, vlayer));
906}
907
908/**********************************************************************/
915 static inline int map_get_seen(const struct player *pplayer,
916 const struct tile *ptile,
917 enum vision_layer vlayer)
918{
919 return map_get_player_tile(ptile, pplayer)->seen_count[vlayer];
920}
921
922/**********************************************************************/
928 void map_change_seen(struct player *pplayer,
929 struct tile *ptile,
930 const v_radius_t change,
931 bool can_reveal_tiles)
932{
933 struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
934 bool revealing_tile = FALSE;
935
936#ifdef FREECIV_DEBUG
937 log_debug("%s() for player %s (nb %d) at (%d, %d).",
938 __FUNCTION__, player_name(pplayer), player_number(pplayer),
939 TILE_XY(ptile));
940 vision_layer_iterate(v) {
941 log_debug(" vision layer %d is changing from %d to %d.",
942 v, plrtile->seen_count[v], plrtile->seen_count[v] + change[v]);
943 } vision_layer_iterate_end;
944#endif /* FREECIV_DEBUG */
945
946 /* Removes units out of vision. First, check invisible layers because
947 * we must remove all units before fog of war because clients expect
948 * the tile is empty when it is fogged. */
949 if (0 > change[V_INVIS]
950 && plrtile->seen_count[V_INVIS] == -change[V_INVIS]) {
951 log_debug("(%d, %d): hiding invisible units to player %s (nb %d).",
952 TILE_XY(ptile), player_name(pplayer), player_number(pplayer));
953
954 unit_list_iterate(ptile->units, punit) {
955 if (unit_is_on_layer(punit, V_INVIS)
956 && can_player_see_unit(pplayer, punit)
957 && (plrtile->seen_count[V_MAIN] + change[V_MAIN] <= 0
958 || !pplayers_allied(pplayer, unit_owner(punit)))) {
959 /* Allied units on seen tiles (V_MAIN) are always seen.
960 * That's how can_player_see_unit_at() works. */
961 unit_goes_out_of_sight(pplayer, punit);
962 }
963 } unit_list_iterate_end;
964 }
965 if (0 > change[V_SUBSURFACE]
966 && plrtile->seen_count[V_SUBSURFACE] == -change[V_SUBSURFACE]) {
967 log_debug("(%d, %d): hiding subsurface units to player %s (nb %d).",
968 TILE_XY(ptile), player_name(pplayer), player_number(pplayer));
969
970 unit_list_iterate(ptile->units, punit) {
971 if (unit_is_on_layer(punit, V_SUBSURFACE)
972 && can_player_see_unit(pplayer, punit)) {
973 unit_goes_out_of_sight(pplayer, punit);
974 }
975 } unit_list_iterate_end;
976 }
977
978 if (0 > change[V_MAIN]
979 && plrtile->seen_count[V_MAIN] == -change[V_MAIN]) {
980 log_debug("(%d, %d): hiding visible units to player %s (nb %d).",
981 TILE_XY(ptile), player_name(pplayer), player_number(pplayer));
982
983 unit_list_iterate(ptile->units, punit) {
984 if (unit_is_on_layer(punit, V_MAIN)
985 && can_player_see_unit(pplayer, punit)) {
986 unit_goes_out_of_sight(pplayer, punit);
987 }
988 } unit_list_iterate_end;
989 }
990
991 vision_layer_iterate(v) {
992 /* Avoid underflow. */
993 fc_assert(0 <= change[v] || -change[v] <= plrtile->seen_count[v]);
994 plrtile->seen_count[v] += change[v];
995 } vision_layer_iterate_end;
996
997 /* V_MAIN vision ranges must always be more than invisible ranges
998 * (see comment in common/vision.h), so we assume that the V_MAIN
999 * seen count cannot be inferior to V_INVIS or V_SUBSURFACE seen count.
1000 * Moreover, when the fog of war is disabled, V_MAIN has an extra
1001 * seen count point. */
1002 fc_assert(plrtile->seen_count[V_INVIS] + !game.info.fogofwar
1003 <= plrtile->seen_count[V_MAIN]);
1004 fc_assert(plrtile->seen_count[V_SUBSURFACE] + !game.info.fogofwar
1005 <= plrtile->seen_count[V_MAIN]);
1006
1007 if (!map_is_known(ptile, pplayer)) {
1008 if (0 < plrtile->seen_count[V_MAIN] && can_reveal_tiles) {
1009 log_debug("(%d, %d): revealing tile to player %s (nb %d).",
1010 TILE_XY(ptile), player_name(pplayer),
1011 player_number(pplayer));
1012
1013 map_set_known(ptile, pplayer);
1014 revealing_tile = TRUE;
1015 } else {
1016 return;
1017 }
1018 }
1019
1020 /* Fog the tile. */
1021 if (0 > change[V_MAIN] && 0 == plrtile->seen_count[V_MAIN]) {
1022 struct city *pcity;
1023
1024 log_debug("(%d, %d): fogging tile for player %s (nb %d).",
1025 TILE_XY(ptile), player_name(pplayer), player_number(pplayer));
1026
1027 pcity = ptile->worked;
1028
1029 if (pcity != NULL && city_owner(pcity) == pplayer) {
1030 city_map_update_empty(pcity, ptile);
1031 pcity->specialists[DEFAULT_SPECIALIST]++;
1032 }
1033
1034 update_player_tile_last_seen(pplayer, ptile);
1035 if (game.server.foggedborders) {
1036 plrtile->owner = tile_owner(ptile);
1037 }
1038 plrtile->extras_owner = extra_owner(ptile);
1039 send_tile_info(pplayer->connections, ptile, FALSE);
1040 }
1041
1042 if ((revealing_tile && 0 < plrtile->seen_count[V_MAIN])
1043 || (0 < change[V_MAIN]
1044 /* plrtile->seen_count[V_MAIN] Always set to 1
1045 * when the fog of war is disabled. */
1046 && (change[V_MAIN] + !game.info.fogofwar
1047 == (plrtile->seen_count[V_MAIN])))) {
1048 struct city *pcity;
1049
1050 log_debug("(%d, %d): unfogging tile for player %s (nb %d).",
1051 TILE_XY(ptile), player_name(pplayer), player_number(pplayer));
1052
1053 /* Send info about the tile itself.
1054 * It has to be sent first because the client needs correct
1055 * continent number before it can handle following packets
1056 */
1057 update_player_tile_knowledge(pplayer, ptile);
1058 send_tile_info(pplayer->connections, ptile, FALSE);
1059
1060 /* Discover units. */
1061 unit_list_iterate(ptile->units, punit) {
1062 /* Be sure not to revive dead unit on client when it's not yet
1063 * removed from the tile. This could happen when "unit_lost" lua script
1064 * somehow causes tile of the dead unit to unfog again. */
1065 if (unit_is_on_layer(punit, V_MAIN)
1066 && !punit->server.dying) {
1067 send_unit_info(pplayer->connections, punit);
1068 }
1069 } unit_list_iterate_end;
1070
1071 /* Discover cities. */
1072 reality_check_city(pplayer, ptile);
1073
1074 if (NULL != (pcity = tile_city(ptile))) {
1075 send_city_info(pplayer, pcity);
1076 }
1077 }
1078
1079 if ((revealing_tile && 0 < plrtile->seen_count[V_INVIS])
1080 || (0 < change[V_INVIS]
1081 && change[V_INVIS] == plrtile->seen_count[V_INVIS])) {
1082 log_debug("(%d, %d): revealing invisible units to player %s (nb %d).",
1083 TILE_XY(ptile), player_name(pplayer),
1084 player_number(pplayer));
1085 /* Discover units. */
1086 unit_list_iterate(ptile->units, punit) {
1087 if (unit_is_on_layer(punit, V_INVIS)) {
1088 send_unit_info(pplayer->connections, punit);
1089 }
1090 } unit_list_iterate_end;
1091 }
1092 if ((revealing_tile && 0 < plrtile->seen_count[V_SUBSURFACE])
1093 || (0 < change[V_SUBSURFACE]
1094 && change[V_SUBSURFACE] == plrtile->seen_count[V_SUBSURFACE])) {
1095 log_debug("(%d, %d): revealing subsurface units to player %s (nb %d).",
1096 TILE_XY(ptile), player_name(pplayer),
1097 player_number(pplayer));
1098 /* Discover units. */
1099 unit_list_iterate(ptile->units, punit) {
1100 if (unit_is_on_layer(punit, V_SUBSURFACE)) {
1101 send_unit_info(pplayer->connections, punit);
1102 }
1103 } unit_list_iterate_end;
1104 }
1105}
1106
1107/**********************************************************************/
1114 static inline int player_tile_own_seen(const struct player_tile *plrtile,
1115 enum vision_layer vlayer)
1116{
1117 return plrtile->own_seen[vlayer];
1118}
1119
1120/**********************************************************************/
1123 static void map_change_own_seen(struct player *pplayer,
1124 struct tile *ptile,
1125 const v_radius_t change)
1126{
1127 struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
1128
1129 vision_layer_iterate(v) {
1130 plrtile->own_seen[v] += change[v];
1131 } vision_layer_iterate_end;
1132}
1133
1134/**********************************************************************/
1137 void change_playertile_site(struct player_tile *ptile,
1138 struct vision_site *new_site)
1139{
1140 if (ptile->site == new_site) {
1141 /* Do nothing. */
1142 return;
1143 }
1144
1145 if (ptile->site != NULL) {
1146 /* Releasing old site from tile */
1147 vision_site_destroy(ptile->site);
1148 }
1149
1150 ptile->site = new_site;
1151}
1152
1153/**********************************************************************/
1156 void map_set_known(struct tile *ptile, struct player *pplayer)
1157{
1158 dbv_set(&pplayer->tile_known, tile_index(ptile));
1159}
1160
1161/**********************************************************************/
1164 void map_clear_known(struct tile *ptile, struct player *pplayer)
1165{
1166 dbv_clr(&pplayer->tile_known, tile_index(ptile));
1167}
1168
1169/**********************************************************************/
1174 void map_know_and_see_all(struct player *pplayer)
1175{
1176 const v_radius_t radius_sq = V_RADIUS(1, 1, 1);
1177
1178 buffer_shared_vision(pplayer);
1179 whole_map_iterate(&(wld.map), ptile) {
1180 map_change_seen(pplayer, ptile, radius_sq, TRUE);
1181 } whole_map_iterate_end;
1182 unbuffer_shared_vision(pplayer);
1183}
1184
1185/**********************************************************************/
1188 void show_map_to_all(void)
1189{
1190 players_iterate(pplayer) {
1191 map_know_and_see_all(pplayer);
1192 } players_iterate_end;
1193}
1194
1195/**********************************************************************/
1199 void player_map_init(struct player *pplayer)
1200{
1201 pplayer->server.private_map
1202 = fc_realloc(pplayer->server.private_map,
1203 MAP_INDEX_SIZE * sizeof(*pplayer->server.private_map));
1204
1205 whole_map_iterate(&(wld.map), ptile) {
1206 player_tile_init(ptile, pplayer);
1207 } whole_map_iterate_end;
1208
1209 dbv_init(&pplayer->tile_known, MAP_INDEX_SIZE);
1210}
1211
1212/**********************************************************************/
1215 void player_map_free(struct player *pplayer)
1216{
1217 if (!pplayer->server.private_map) {
1218 return;
1219 }
1220
1221 whole_map_iterate(&(wld.map), ptile) {
1222 player_tile_free(ptile, pplayer);
1223 } whole_map_iterate_end;
1224
1225 free(pplayer->server.private_map);
1226 pplayer->server.private_map = NULL;
1227
1228 dbv_free(&pplayer->tile_known);
1229}
1230
1231/**********************************************************************/
1236 void remove_player_from_maps(struct player *pplayer)
1237{
1238 /* only after removing borders! */
1239 conn_list_do_buffer(game.est_connections);
1240 whole_map_iterate(&(wld.map), ptile) {
1241 /* Clear all players' knowledge about the removed player, and free
1242 * data structures (including those in removed player's player map). */
1243 bool reality_changed = FALSE;
1244
1245 players_iterate(aplayer) {
1246 struct player_tile *aplrtile;
1247 bool changed = FALSE;
1248
1249 if (!aplayer->server.private_map) {
1250 continue;
1251 }
1252 aplrtile = map_get_player_tile(ptile, aplayer);
1253
1254 /* Free vision sites (cities) for removed and other players */
1255 if (aplrtile && aplrtile->site
1256 && vision_site_owner(aplrtile->site) == pplayer) {
1257 change_playertile_site(aplrtile, NULL);
1258 changed = TRUE;
1259 }
1260
1261 /* Remove references to player from others' maps */
1262 if (aplrtile->owner == pplayer) {
1263 aplrtile->owner = NULL;
1264 changed = TRUE;
1265 }
1266 if (aplrtile->extras_owner == pplayer) {
1267 aplrtile->extras_owner = NULL;
1268 changed = TRUE;
1269 }
1270
1271 /* Must ensure references to dying player are gone from clients
1272 * before player is destroyed */
1273 if (changed) {
1274 /* This will use player tile if fogged */
1275 send_tile_info(pplayer->connections, ptile, FALSE);
1276 }
1277 } players_iterate_end;
1278
1279 /* Clear removed player's knowledge */
1280 if (pplayer->tile_known.vec) {
1281 map_clear_known(ptile, pplayer);
1282 }
1283
1284 /* Free all claimed tiles. */
1285 if (tile_owner(ptile) == pplayer) {
1286 tile_set_owner(ptile, NULL, NULL);
1287 reality_changed = TRUE;
1288 }
1289 if (extra_owner(ptile) == pplayer) {
1290 ptile->extras_owner = NULL;
1291 reality_changed = TRUE;
1292 }
1293
1294 if (reality_changed) {
1295 /* Update anyone who can see the tile (e.g. global observers) */
1296 send_tile_info(NULL, ptile, FALSE);
1297 }
1298 } whole_map_iterate_end;
1299 conn_list_do_unbuffer(game.est_connections);
1300}
1301
1302/**********************************************************************/
1306 static void player_tile_init(struct tile *ptile, struct player *pplayer)
1307{
1308 struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
1309
1310 plrtile->terrain = T_UNKNOWN;
1311 plrtile->resource = NULL;
1312 plrtile->owner = NULL;
1313 plrtile->extras_owner = NULL;
1314 plrtile->site = NULL;
1315 BV_CLR_ALL(plrtile->extras);
1316 if (!game.server.last_updated_year) {
1317 plrtile->last_updated = game.info.turn;
1318 } else {
1319 plrtile->last_updated = game.info.year;
1320 }
1321
1322 plrtile->seen_count[V_MAIN] = !game.server.fogofwar_old;
1323 plrtile->seen_count[V_INVIS] = 0;
1324 plrtile->seen_count[V_SUBSURFACE] = 0;
1325 memcpy(plrtile->own_seen, plrtile->seen_count, sizeof(v_radius_t));
1326}
1327
1328/**********************************************************************/
1331 static void player_tile_free(struct tile *ptile, struct player *pplayer)
1332{
1333 struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
1334
1335 if (plrtile->site != NULL) {
1336 vision_site_destroy(plrtile->site);
1337 }
1338}
1339
1340/**********************************************************************/
1343 struct vision_site *map_get_player_city(const struct tile *ptile,
1344 const struct player *pplayer)
1345{
1346 struct vision_site *psite = map_get_player_site(ptile, pplayer);
1347
1348 fc_assert_ret_val(psite == NULL || psite->location == ptile, NULL);
1349
1350 return psite;
1351}
1352
1353/**********************************************************************/
1356 struct vision_site *map_get_player_site(const struct tile *ptile,
1357 const struct player *pplayer)
1358{
1359 return map_get_player_tile(ptile, pplayer)->site;
1360}
1361
1362/**********************************************************************/
1367 struct player_tile *map_get_player_tile(const struct tile *ptile,
1368 const struct player *pplayer)
1369{
1370 fc_assert_ret_val(pplayer->server.private_map, NULL);
1371
1372 return pplayer->server.private_map + tile_index(ptile);
1373}
1374
1375/**********************************************************************/
1383 bool update_player_tile_knowledge(struct player *pplayer, struct tile *ptile)
1384{
1385 struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
1386
1387 if (plrtile->terrain != ptile->terrain
1388 || !BV_ARE_EQUAL(plrtile->extras, ptile->extras)
1389 || plrtile->resource != ptile->resource
1390 || plrtile->owner != tile_owner(ptile)
1391 || plrtile->extras_owner != extra_owner(ptile)) {
1392 plrtile->terrain = ptile->terrain;
1393 extra_type_iterate(pextra) {
1394 if (player_knows_extra_exist(pplayer, pextra, ptile)) {
1395 BV_SET(plrtile->extras, extra_number(pextra));
1396 } else {
1397 BV_CLR(plrtile->extras, extra_number(pextra));
1398 }
1399 } extra_type_iterate_end;
1400 if (ptile->resource != NULL
1401 && player_knows_extra_exist(pplayer, ptile->resource, ptile)) {
1402 plrtile->resource = ptile->resource;
1403 } else {
1404 plrtile->resource = NULL;
1405 }
1406 plrtile->owner = tile_owner(ptile);
1407 plrtile->extras_owner = extra_owner(ptile);
1408
1409 return TRUE;
1410 }
1411
1412 return FALSE;
1413}
1414
1415/**********************************************************************/
1424 void update_tile_knowledge(struct tile *ptile)
1425{
1426 if (server_state() == S_S_INITIAL) {
1427 return;
1428 }
1429
1430 /* Players */
1431 players_iterate(pplayer) {
1432 if (map_is_known_and_seen(ptile, pplayer, V_MAIN)) {
1433 if (update_player_tile_knowledge(pplayer, ptile)) {
1434 send_tile_info(pplayer->connections, ptile, FALSE);
1435 }
1436 }
1437 } players_iterate_end;
1438
1439 /* Global observers */
1440 conn_list_iterate(game.est_connections, pconn) {
1441 struct player *pplayer = pconn->playing;
1442
1443 if (NULL == pplayer && pconn->observer) {
1444 send_tile_info(pconn->self, ptile, FALSE);
1445 }
1446 } conn_list_iterate_end;
1447}
1448
1449/**********************************************************************/
1452 void update_player_tile_last_seen(struct player *pplayer,
1453 struct tile *ptile)
1454{
1455 if (!game.server.last_updated_year) {
1456 map_get_player_tile(ptile, pplayer)->last_updated = game.info.turn;
1457 } else {
1458 map_get_player_tile(ptile, pplayer)->last_updated = game.info.year;
1459 }
1460}
1461
1462/**********************************************************************/
1470 static bool really_give_tile_info_from_player_to_player(struct player *pfrom,
1471 struct player *pdest,
1472 struct tile *ptile)
1473{
1474 struct player_tile *from_tile, *dest_tile;
1475
1476 if (!map_is_known_and_seen(ptile, pdest, V_MAIN)) {
1477 /* I can just hear people scream as they try to comprehend this if :).
1478 * Let me try in words:
1479 * 1) if the tile is seen by pfrom the info is sent to pdest
1480 * OR
1481 * 2) if the tile is known by pfrom AND (they have more recent info
1482 * OR it is not known by pdest)
1483 */
1484 if (map_is_known_and_seen(ptile, pfrom, V_MAIN)
1485 || (map_is_known(ptile, pfrom)
1486 && (((map_get_player_tile(ptile, pfrom)->last_updated
1487 > map_get_player_tile(ptile, pdest)->last_updated))
1488 || !map_is_known(ptile, pdest)))) {
1489 from_tile = map_get_player_tile(ptile, pfrom);
1490 dest_tile = map_get_player_tile(ptile, pdest);
1491 /* Update and send tile knowledge */
1492 map_set_known(ptile, pdest);
1493 dest_tile->terrain = from_tile->terrain;
1494 dest_tile->extras = from_tile->extras;
1495 dest_tile->resource = from_tile->resource;
1496 dest_tile->owner = from_tile->owner;
1497 dest_tile->extras_owner = from_tile->extras_owner;
1498 dest_tile->last_updated = from_tile->last_updated;
1499 send_tile_info(pdest->connections, ptile, FALSE);
1500
1501 /* Update and send city knowledge */
1502 /* Remove outdated cities */
1503 if (dest_tile->site) {
1504 if (!from_tile->site) {
1505 /* As the city was gone on the newer from_tile
1506 it will be removed by this function */
1507 reality_check_city(pdest, ptile);
1508 } else { /* We have a dest_city. update */
1509 if (from_tile->site->identity
1510 != dest_tile->site->identity) {
1511 /* As the city was gone on the newer from_tile
1512 it will be removed by this function */
1513 reality_check_city(pdest, ptile);
1514 }
1515 }
1516 }
1517
1518 /* Set and send new city info */
1519 if (from_tile->site) {
1520 if (!dest_tile->site) {
1521 /* We cannot assign new vision site with change_playertile_site(),
1522 * since location is not yet set up for new site */
1523 dest_tile->site = vision_site_copy(from_tile->site);
1524 }
1525 /* Note that we don't care if receiver knows vision source city
1526 * or not. */
1527 send_city_info_at_tile(pdest, pdest->connections, NULL, ptile);
1528 }
1529
1530 city_map_update_tile_frozen(ptile);
1531
1532 return TRUE;
1533 }
1534 }
1535
1536 return FALSE;
1537}
1538
1539/**********************************************************************/
1543 static void really_give_map_from_player_to_player(struct player *pfrom,
1544 struct player *pdest)
1545{
1546 whole_map_iterate(&(wld.map), ptile) {
1547 really_give_tile_info_from_player_to_player(pfrom, pdest, ptile);
1548 } whole_map_iterate_end;
1549
1550 city_thaw_workers_queue();
1551 sync_cities();
1552}
1553
1554/**********************************************************************/
1563 static bool give_tile_info_from_player_to_player(struct player *pfrom,
1564 struct player *pdest,
1565 struct tile *ptile)
1566{
1567 bool updt = really_give_tile_info_from_player_to_player(pfrom, pdest, ptile);
1568
1569 players_iterate(pplayer2) {
1570 if (really_gives_vision(pdest, pplayer2)) {
1571 updt |= really_give_tile_info_from_player_to_player(pfrom, pplayer2, ptile);
1572 }
1573 } players_iterate_end;
1574
1575 return updt;
1576}
1577
1578/**********************************************************************/
1583 static void create_vision_dependencies(void)
1584{
1585 int added;
1586
1587 players_iterate(pplayer) {
1588 pplayer->server.really_gives_vision = pplayer->gives_shared_vision;
1589 } players_iterate_end;
1590
1591 /* In words: This terminates when it has run a round without adding
1592 a dependency. One loop only propagates dependencies one level deep,
1593 which is why we keep doing it as long as changes occur. */
1594 do {
1595 added = 0;
1596 players_iterate(pplayer) {
1597 players_iterate(pplayer2) {
1598 if (really_gives_vision(pplayer, pplayer2)
1599 && pplayer != pplayer2) {
1600 players_iterate(pplayer3) {
1601 if (really_gives_vision(pplayer2, pplayer3)
1602 && !really_gives_vision(pplayer, pplayer3)
1603 && pplayer != pplayer3) {
1604 BV_SET(pplayer->server.really_gives_vision, player_index(pplayer3));
1605 added++;
1606 }
1607 } players_iterate_end;
1608 }
1609 } players_iterate_end;
1610 } players_iterate_end;
1611 } while (added > 0);
1612}
1613
1614/**********************************************************************/
1617 void give_shared_vision(struct player *pfrom, struct player *pto)
1618{
1619 bv_player save_vision[player_slot_count()];
1620
1621 if (pfrom == pto) {
1622 return;
1623 }
1624
1625 if (gives_shared_vision(pfrom, pto)) {
1626 log_error("Trying to give shared vision from %s to %s, "
1627 "but that vision is already given!",
1628 player_name(pfrom), player_name(pto));
1629 return;
1630 }
1631
1632 players_iterate(pplayer) {
1633 save_vision[player_index(pplayer)] = pplayer->server.really_gives_vision;
1634 } players_iterate_end;
1635
1636 BV_SET(pfrom->gives_shared_vision, player_index(pto));
1637 create_vision_dependencies();
1638 log_debug("giving shared vision from %s to %s",
1639 player_name(pfrom), player_name(pto));
1640
1641 players_iterate(pplayer) {
1642 buffer_shared_vision(pplayer);
1643 players_iterate(pplayer2) {
1644 if (really_gives_vision(pplayer, pplayer2)
1645 && !BV_ISSET(save_vision[player_index(pplayer)],
1646 player_index(pplayer2))) {
1647 log_debug("really giving shared vision from %s to %s",
1648 player_name(pplayer), player_name(pplayer2));
1649 whole_map_iterate(&(wld.map), ptile) {
1650 const struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
1651 const v_radius_t change =
1652 V_RADIUS(player_tile_own_seen(plrtile, V_MAIN),
1653 player_tile_own_seen(plrtile, V_INVIS),
1654 player_tile_own_seen(plrtile, V_SUBSURFACE));
1655
1656 if (0 < change[V_MAIN] || 0 < change[V_INVIS]) {
1657 map_change_seen(pplayer2, ptile, change,
1658 map_is_known(ptile, pplayer));
1659 }
1660 } whole_map_iterate_end;
1661
1662 /* Squares that are not seen, but which pfrom may have more recent
1663 knowledge of */
1664 really_give_map_from_player_to_player(pplayer, pplayer2);
1665 }
1666 } players_iterate_end;
1667 unbuffer_shared_vision(pplayer);
1668 } players_iterate_end;
1669
1670 if (S_S_RUNNING == server_state()) {
1671 send_player_info_c(pfrom, NULL);
1672 }
1673}
1674
1675/**********************************************************************/
1678 void remove_shared_vision(struct player *pfrom, struct player *pto)
1679{
1680 bv_player save_vision[player_slot_count()];
1681
1682 fc_assert_ret(pfrom != pto);
1683 if (!gives_shared_vision(pfrom, pto)) {
1684 log_error("Tried removing the shared vision from %s to %s, "
1685 "but it did not exist in the first place!",
1686 player_name(pfrom), player_name(pto));
1687 return;
1688 }
1689
1690 players_iterate(pplayer) {
1691 save_vision[player_index(pplayer)] = pplayer->server.really_gives_vision;
1692 } players_iterate_end;
1693
1694 log_debug("removing shared vision from %s to %s",
1695 player_name(pfrom), player_name(pto));
1696
1697 BV_CLR(pfrom->gives_shared_vision, player_index(pto));
1698 create_vision_dependencies();
1699
1700 players_iterate(pplayer) {
1701 buffer_shared_vision(pplayer);
1702 players_iterate(pplayer2) {
1703 if (!really_gives_vision(pplayer, pplayer2)
1704 && BV_ISSET(save_vision[player_index(pplayer)],
1705 player_index(pplayer2))) {
1706 log_debug("really removing shared vision from %s to %s",
1707 player_name(pplayer), player_name(pplayer2));
1708 whole_map_iterate(&(wld.map), ptile) {
1709 const struct player_tile *plrtile = map_get_player_tile(ptile, pplayer);
1710 const v_radius_t change =
1711 V_RADIUS(-player_tile_own_seen(plrtile, V_MAIN),
1712 -player_tile_own_seen(plrtile, V_INVIS),
1713 -player_tile_own_seen(plrtile, V_SUBSURFACE));
1714
1715 if (0 > change[V_MAIN] || 0 > change[V_INVIS]) {
1716 map_change_seen(pplayer2, ptile, change, FALSE);
1717 }
1718 } whole_map_iterate_end;
1719 }
1720 } players_iterate_end;
1721 unbuffer_shared_vision(pplayer);
1722 } players_iterate_end;
1723
1724 if (S_S_RUNNING == server_state()) {
1725 send_player_info_c(pfrom, NULL);
1726 }
1727}
1728
1729/**********************************************************************/
1732 void enable_fog_of_war_player(struct player *pplayer)
1733{
1734 const v_radius_t radius_sq = V_RADIUS(-1, 0, 0);
1735
1736 buffer_shared_vision(pplayer);
1737 whole_map_iterate(&(wld.map), ptile) {
1738 map_change_seen(pplayer, ptile, radius_sq, FALSE);
1739 } whole_map_iterate_end;
1740 unbuffer_shared_vision(pplayer);
1741}
1742
1743/**********************************************************************/
1746 void enable_fog_of_war(void)
1747{
1748 players_iterate(pplayer) {
1749 enable_fog_of_war_player(pplayer);
1750 } players_iterate_end;
1751}
1752
1753/**********************************************************************/
1756 void disable_fog_of_war_player(struct player *pplayer)
1757{
1758 const v_radius_t radius_sq = V_RADIUS(1, 0, 0);
1759
1760 buffer_shared_vision(pplayer);
1761 whole_map_iterate(&(wld.map), ptile) {
1762 map_change_seen(pplayer, ptile, radius_sq, FALSE);
1763 } whole_map_iterate_end;
1764 unbuffer_shared_vision(pplayer);
1765}
1766
1767/**********************************************************************/
1770 void disable_fog_of_war(void)
1771{
1772 players_iterate(pplayer) {
1773 disable_fog_of_war_player(pplayer);
1774 } players_iterate_end;
1775}
1776
1777/**********************************************************************/
1786 static void ocean_to_land_fix_rivers(struct tile *ptile)
1787{
1788 cardinal_adjc_iterate(&(wld.map), ptile, tile1) {
1789 bool ocean_near = FALSE;
1790
1791 cardinal_adjc_iterate(&(wld.map), tile1, tile2) {
1792 if (is_ocean_tile(tile2))
1793 ocean_near = TRUE;
1794 } cardinal_adjc_iterate_end;
1795
1796 if (!ocean_near) {
1797 /* If ruleset has several river types defined, this
1798 * may cause same tile to contain more than one river. */
1799 extra_type_by_cause_iterate(EC_ROAD, priver) {
1800 if (tile_has_extra(tile1, priver)
1801 && road_has_flag(extra_road_get(priver), RF_RIVER)) {
1802 tile_add_extra(ptile, priver);
1803 }
1804 } extra_type_by_cause_iterate_end;
1805 }
1806 } cardinal_adjc_iterate_end;
1807}
1808
1809/**********************************************************************/
1812 static void terrain_change_bounce_single_unit(struct unit *punit,
1813 struct tile *from)
1814{
1815 bool unit_alive = TRUE;
1816
1817 /* Look for a nearby safe tile */
1818 adjc_iterate(&(wld.map), from, ptile2) {
1819 if (can_unit_exist_at_tile(&(wld.map), punit, ptile2)
1820 && !is_non_allied_unit_tile(ptile2, unit_owner(punit))
1821 && !is_non_allied_city_tile(ptile2, unit_owner(punit))) {
1822 log_verbose("Moved %s %s due to changing terrain at (%d,%d).",
1823 nation_rule_name(nation_of_unit(punit)),
1824 unit_rule_name(punit), TILE_XY(unit_tile(punit)));
1825 notify_player(unit_owner(punit), unit_tile(punit),
1826 E_UNIT_RELOCATED, ftc_server,
1827 _("Moved your %s due to changing terrain."),
1828 unit_link(punit));
1829
1830 /* TODO: should a unit be able to bounce to a transport like is
1831 * done below? What if the unit can't legally enter the transport,
1832 * say because the transport is Unreachable and the unit doesn't
1833 * have it in its embarks field or because "Transport Embark"
1834 * isn't enabled? Kept like it was to preserve the old rules for
1835 * now. -- Sveinung */
1836 unit_alive = unit_move(punit, ptile2, 0,
1837 NULL, TRUE, FALSE, FALSE, FALSE, FALSE);
1838 if (unit_alive && punit->activity == ACTIVITY_SENTRY) {
1839 unit_activity_handling(punit, ACTIVITY_IDLE);
1840 }
1841 break;
1842 }
1843 } adjc_iterate_end;
1844
1845 if (unit_alive && unit_tile(punit) == from) {
1846 /* If we get here we could not move punit. */
1847
1848 /* Try to bounce transported units. */
1849 if (0 < get_transporter_occupancy(punit)) {
1850 struct unit_list *pcargo_units;
1851
1852 pcargo_units = unit_transport_cargo(punit);
1853 unit_list_iterate_safe(pcargo_units, pcargo) {
1854 terrain_change_bounce_single_unit(pcargo, from);
1855 } unit_list_iterate_safe_end;
1856 }
1857 }
1858}
1859
1860/**********************************************************************/
1864 static void check_units_single_tile(struct tile *ptile)
1865{
1866 unit_list_iterate_safe(ptile->units, punit) {
1867 int id = punit->id;
1868
1869 /* Top-level transports only. Each handle their own cargo */
1870 if (!unit_transported(punit)
1871 && !can_unit_exist_at_tile(&(wld.map), punit, ptile)) {
1872 terrain_change_bounce_single_unit(punit, ptile);
1873
1874 if (unit_is_alive(id) && unit_tile(punit) == ptile) {
1875 log_verbose("Disbanded %s %s due to changing land "
1876 " to sea at (%d, %d).",
1877 nation_rule_name(nation_of_unit(punit)),
1878 unit_rule_name(punit), TILE_XY(unit_tile(punit)));
1879 notify_player(unit_owner(punit), unit_tile(punit),
1880 E_UNIT_LOST_MISC, ftc_server,
1881 _("Disbanded your %s due to changing terrain."),
1882 unit_tile_link(punit));
1883 wipe_unit(punit, ULR_NONNATIVE_TERR, NULL);
1884 }
1885 }
1886 } unit_list_iterate_safe_end;
1887}
1888
1889/**********************************************************************/
1894 void bounce_units_on_terrain_change(struct tile *ptile)
1895{
1896 /* Check this tile for direct effect on its units */
1897 check_units_single_tile(ptile);
1898 /* We have to check adjacent tiles too, in case units in cities are now
1899 * illegal (e.g., boat in a city that has become landlocked). */
1900 adjc_iterate(&(wld.map), ptile, ptile2) {
1901 check_units_single_tile(ptile2);
1902 } adjc_iterate_end;
1903}
1904
1905/**********************************************************************/
1909 bool need_to_reassign_continents(const struct terrain *oldter,
1910 const struct terrain *newter)
1911{
1912 bool old_is_ocean, new_is_ocean;
1913
1914 if (!oldter || !newter) {
1915 return FALSE;
1916 }
1917
1918 old_is_ocean = is_ocean(oldter);
1919 new_is_ocean = is_ocean(newter);
1920
1921 return (old_is_ocean && !new_is_ocean)
1922 || (!old_is_ocean && new_is_ocean);
1923}
1924
1925/**********************************************************************/
1928 void terrain_changed(struct tile *ptile)
1929{
1930 struct city *pcity = tile_city(ptile);
1931
1932 if (pcity != NULL) {
1933 /* Tile is city center and new terrain may support better extras. */
1934 upgrade_city_extras(pcity, NULL);
1935 }
1936
1937 bounce_units_on_terrain_change(ptile);
1938}
1939
1940/**********************************************************************/
1947 void fix_tile_on_terrain_change(struct tile *ptile,
1948 struct terrain *oldter,
1949 bool extend_rivers)
1950{
1951 if (is_ocean(oldter) && !is_ocean_tile(ptile)) {
1952 if (extend_rivers) {
1953 ocean_to_land_fix_rivers(ptile);
1954 }
1955 city_landlocked_sell_coastal_improvements(ptile);
1956 }
1957
1958 terrain_changed(ptile);
1959}
1960
1961/**********************************************************************/
1967 void check_terrain_change(struct tile *ptile, struct terrain *oldter)
1968{
1969 struct terrain *newter = tile_terrain(ptile);
1970 struct tile *claimer;
1971 bool cont_reassigned = FALSE;
1972
1973 /* Check if new terrain is a freshwater terrain next to non-freshwater.
1974 * In that case, the new terrain is *changed*. */
1975 if (is_ocean(newter) && terrain_has_flag(newter, TER_FRESHWATER)) {
1976 bool nonfresh = FALSE;
1977
1978 adjc_iterate(&(wld.map), ptile, atile) {
1979 if (is_ocean(tile_terrain(atile))
1980 && !terrain_has_flag(tile_terrain(atile), TER_FRESHWATER)) {
1981 nonfresh = TRUE;
1982 break;
1983 }
1984 } adjc_iterate_end;
1985 if (nonfresh) {
1986 /* Need to pick a new, non-freshwater ocean type for this tile.
1987 * We don't want e.g. Deep Ocean to be propagated to this tile
1988 * and then to a whole lake by the flooding below, so we pick
1989 * the shallowest non-fresh oceanic type.
1990 * Prefer terrain that matches the frozenness of the target. */
1991 newter = most_shallow_ocean(terrain_has_flag(newter, TER_FROZEN));
1992 tile_change_terrain(ptile, newter);
1993 }
1994 }
1995
1996 if (need_to_reassign_continents(oldter, newter)) {
1997 assign_continent_numbers();
1998 cont_reassigned = TRUE;
1999
2000 phase_players_iterate(pplayer) {
2001 if (is_adv_data_phase_open(pplayer)) {
2002 /* Player is using continent numbers that they would assume to remain accurate.
2003 * Force refresh:
2004 * 1) Close the phase, so that it can be opened
2005 * 2) Open the phase, recalculating
2006 */
2007 adv_data_phase_done(pplayer);
2008 adv_data_phase_init(pplayer, FALSE);
2009 }
2010 } phase_players_iterate_end;
2011 }
2012
2013 fix_tile_on_terrain_change(ptile, oldter, TRUE);
2014
2015 /* Check for saltwater filling freshwater lake */
2016 if (game.scenario.lake_flooding
2017 && is_ocean(newter) && !terrain_has_flag(newter, TER_FRESHWATER)) {
2018 adjc_iterate(&(wld.map), ptile, atile) {
2019 if (terrain_has_flag(tile_terrain(atile), TER_FRESHWATER)) {
2020 struct terrain *aold = tile_terrain(atile);
2021
2022 tile_change_terrain(atile,
2023 most_shallow_ocean(terrain_has_flag(aold,
2024 TER_FROZEN)));
2025
2026 /* Recursive, but as lakes are of limited size, this
2027 * won't recurse so much as to cause stack problems. */
2028 check_terrain_change(atile, aold);
2029 update_tile_knowledge(atile);
2030 }
2031 } adjc_iterate_end;
2032 }
2033
2034 if (cont_reassigned) {
2035 send_all_known_tiles(NULL);
2036 }
2037
2038 claimer = tile_claimer(ptile);
2039 if (claimer != NULL && is_ocean_tile(ptile)) {
2040 if (!is_claimable_ocean(ptile, claimer, tile_owner(ptile))) {
2041 map_clear_border(ptile);
2042 }
2043 }
2044
2045 sanity_check_tile(ptile);
2046}
2047
2048/**********************************************************************/
2059 static bool is_claimable_ocean(struct tile *ptile, struct tile *source,
2060 struct player *pplayer)
2061{
2062 Continent_id cont = tile_continent(ptile);
2063 Continent_id cont1 = tile_continent(source);
2064 Continent_id cont2;
2065 int ocean_tiles;
2066 bool other_continent;
2067
2068 if (get_ocean_size(-cont) <= MAXIMUM_CLAIMED_OCEAN_SIZE
2069 && get_lake_surrounders(cont) == cont1) {
2070 return TRUE;
2071 }
2072
2073 if (ptile == source) {
2074 /* Source itself is always claimable. */
2075 return TRUE;
2076 }
2077
2078 if (num_known_tech_with_flag(pplayer, TF_CLAIM_OCEAN) > 0
2079 || (cont1 < 0 && num_known_tech_with_flag(pplayer, TF_CLAIM_OCEAN_LIMITED) > 0)) {
2080 return TRUE;
2081 }
2082
2083 ocean_tiles = 0;
2084 other_continent = FALSE;
2085 adjc_iterate(&(wld.map), ptile, tile2) {
2086 cont2 = tile_continent(tile2);
2087 if (tile2 == source) {
2088 /* Water next to border source is always claimable */
2089 return TRUE;
2090 }
2091 if (cont2 == cont) {
2092 ocean_tiles++;
2093 } else if (cont1 <= 0) {
2094 /* First adjacent land (only if border source is not on land) */
2095 cont1 = cont2;
2096 } else if (cont2 != cont1) {
2097 /* This water has two land continents adjacent, or land adjacent
2098 * that is of a different continent from the border source */
2099 other_continent = TRUE;
2100 }
2101 } adjc_iterate_end;
2102 if (!other_continent && ocean_tiles <= 2) {
2103 return TRUE;
2104 } else {
2105 return FALSE;
2106 }
2107}
2108
2109/**********************************************************************/
2112 static void map_unit_homecity_enqueue(struct tile *ptile)
2113{
2114 unit_list_iterate(ptile->units, punit) {
2115 struct city *phome = game_city_by_number(punit->homecity);
2116
2117 if (NULL == phome) {
2118 continue;
2119 }
2120
2121 city_refresh_queue_add(phome);
2122 } unit_list_iterate_end;
2123}
2124
2125/**********************************************************************/
2128 static void map_claim_border_ownership(struct tile *ptile,
2129 struct player *powner,
2130 struct tile *psource)
2131{
2132 struct player *ploser = tile_owner(ptile);
2133
2134 if ((ploser != powner && ploser != NULL)
2135 && (BORDERS_SEE_INSIDE == game.info.borders
2136 || BORDERS_EXPAND == game.info.borders
2137 || ploser->server.border_vision)) {
2138 const v_radius_t radius_sq = V_RADIUS(-1, 0, 0);
2139
2140 shared_vision_change_seen(ploser, ptile, radius_sq, FALSE);
2141 }
2142
2143 if (powner != NULL
2144 && (BORDERS_SEE_INSIDE == game.info.borders
2145 || BORDERS_EXPAND == game.info.borders
2146 || powner->server.border_vision)) {
2147 const v_radius_t radius_sq = V_RADIUS(1, 0, 0);
2148
2149 shared_vision_change_seen(powner, ptile, radius_sq, TRUE);
2150 }
2151
2152 tile_set_owner(ptile, powner, psource);
2153
2154 /* Needed only when foggedborders enabled, but we do it unconditionally
2155 * in case foggedborders ever gets enabled later. Better to have correct
2156 * information in player map just in case. */
2157 update_tile_knowledge(ptile);
2158
2159 if (ploser != powner) {
2160 if (S_S_RUNNING == server_state() && game.info.happyborders != HB_DISABLED) {
2161 map_unit_homecity_enqueue(ptile);
2162 }
2163
2164 if (!city_map_update_tile_frozen(ptile)) {
2165 send_tile_info(NULL, ptile, FALSE);
2166 }
2167 }
2168}
2169
2170/**********************************************************************/
2173 void map_claim_ownership(struct tile *ptile, struct player *powner,
2174 struct tile *psource, bool claim_bases)
2175{
2176 map_claim_border_ownership(ptile, powner, psource);
2177
2178 if (claim_bases) {
2179 tile_claim_bases(ptile, powner);
2180 }
2181}
2182
2183/**********************************************************************/
2186 void tile_claim_bases(struct tile *ptile, struct player *powner)
2187{
2188 struct player *base_loser = extra_owner(ptile);
2189
2190 /* This MUST be before potentially recursive call to map_claim_base(),
2191 * so that the recursive call will get new owner == base_loser and
2192 * abort recursion. */
2193 ptile->extras_owner = powner;
2194
2195 extra_type_by_cause_iterate(EC_BASE, pextra) {
2196 map_claim_base(ptile, pextra, powner, base_loser);
2197 } extra_type_by_cause_iterate_end;
2198}
2199
2200/**********************************************************************/
2203 void map_clear_border(struct tile *ptile)
2204{
2205 int radius_sq = tile_border_source_radius_sq(ptile);
2206
2207 circle_dxyr_iterate(&(wld.map), ptile, radius_sq, dtile, dx, dy, dr) {
2208 struct tile *claimer = tile_claimer(dtile);
2209
2210 if (claimer == ptile) {
2211 map_claim_ownership(dtile, NULL, NULL, FALSE);
2212 }
2213 } circle_dxyr_iterate_end;
2214}
2215
2216/**********************************************************************/
2220 void map_update_border(struct tile *ptile, struct player *owner,
2221 int old_radius_sq, int new_radius_sq)
2222{
2223 if (old_radius_sq == new_radius_sq) {
2224 /* No change */
2225 return;
2226 }
2227
2228 if (BORDERS_DISABLED == game.info.borders) {
2229 return;
2230 }
2231
2232 if (old_radius_sq < new_radius_sq) {
2233 map_claim_border(ptile, owner, new_radius_sq);
2234 } else {
2235 circle_dxyr_iterate(&(wld.map), ptile, old_radius_sq, dtile, dx, dy, dr) {
2236 if (dr > new_radius_sq) {
2237 struct tile *claimer = tile_claimer(dtile);
2238
2239 if (claimer == ptile) {
2240 map_claim_ownership(dtile, NULL, NULL, FALSE);
2241 }
2242 }
2243 } circle_dxyr_iterate_end;
2244 }
2245}
2246
2247/**********************************************************************/
2252 void map_claim_border(struct tile *ptile, struct player *owner,
2253 int radius_sq)
2254{
2255 if (BORDERS_DISABLED == game.info.borders) {
2256 return;
2257 }
2258
2259 if (owner == NULL) {
2260 /* Clear the border instead of claiming. Code below this block
2261 * cannot handle NULL owner. */
2262 map_clear_border(ptile);
2263
2264 return;
2265 }
2266
2267 if (radius_sq < 0) {
2268 radius_sq = tile_border_source_radius_sq(ptile);
2269 }
2270
2271 circle_dxyr_iterate(&(wld.map), ptile, radius_sq, dtile, dx, dy, dr) {
2272 struct tile *dclaimer = tile_claimer(dtile);
2273
2274 if (dclaimer == ptile) {
2275 /* Already claimed by the ptile */
2276 continue;
2277 }
2278
2279 if (dr != 0 && is_border_source(dtile)) {
2280 /* Do not claim border sources other than self */
2281 /* Note that this is extremely important at the moment for
2282 * base claiming to work correctly in case there's two
2283 * fortresses near each other. There could be infinite
2284 * recursion in them claiming each other. */
2285 continue;
2286 }
2287
2288 if (!map_is_known(dtile, owner) && game.info.borders < BORDERS_EXPAND) {
2289 continue;
2290 }
2291
2292 /* Always claim source itself (distance, dr, to it 0) */
2293 if (dr != 0 && NULL != dclaimer && dclaimer != ptile) {
2294 struct city *ccity = tile_city(dclaimer);
2295 int strength_old, strength_new;
2296
2297 if (ccity != NULL) {
2298 /* Previously claimed by city */
2299 int city_x, city_y;
2300
2301 map_distance_vector(&city_x, &city_y, ccity->tile, dtile);
2302
2303 if (map_vector_to_sq_distance(city_x, city_y)
2304 <= city_map_radius_sq_get(ccity)
2305 + game.info.border_city_permanent_radius_sq) {
2306 /* Tile is within region permanently claimed by city */
2307 continue;
2308 }
2309 }
2310
2311 strength_old = tile_border_strength(dtile, dclaimer);
2312 strength_new = tile_border_strength(dtile, ptile);
2313
2314 if (strength_new <= strength_old) {
2315 /* Stronger shall prevail,
2316 * in case of equal strength older shall prevail */
2317 continue;
2318 }
2319 }
2320
2321 if (is_ocean_tile(dtile)) {
2322 /* Only certain water tiles are claimable */
2323 if (is_claimable_ocean(dtile, ptile, owner)) {
2324 map_claim_ownership(dtile, owner, ptile, dr == 0);
2325 }
2326 } else {
2327 /* Only land tiles on the same island as the border source
2328 * are claimable */
2329 if (tile_continent(dtile) == tile_continent(ptile)) {
2330 map_claim_ownership(dtile, owner, ptile, dr == 0);
2331 }
2332 }
2333 } circle_dxyr_iterate_end;
2334}
2335
2336/**********************************************************************/
2339 void map_calculate_borders(void)
2340{
2341 if (BORDERS_DISABLED == game.info.borders) {
2342 return;
2343 }
2344
2345 if (wld.map.tiles == NULL) {
2346 /* Map not yet initialized */
2347 return;
2348 }
2349
2350 log_verbose("map_calculate_borders()");
2351
2352 whole_map_iterate(&(wld.map), ptile) {
2353 if (is_border_source(ptile)) {
2354 map_claim_border(ptile, ptile->owner, -1);
2355 }
2356 } whole_map_iterate_end;
2357
2358 log_verbose("map_calculate_borders() workers");
2359 city_thaw_workers_queue();
2360 city_refresh_queue_processing();
2361}
2362
2363/**********************************************************************/
2366 void map_claim_base(struct tile *ptile, struct extra_type *pextra,
2367 struct player *powner, struct player *ploser)
2368{
2369 struct base_type *pbase;
2370 bv_player *could_see_unit = NULL;
2371 int units_num = 0;
2372 int ul_size;
2373
2374 if (!tile_has_extra(ptile, pextra)) {
2375 return;
2376 }
2377
2378 if (pextra->eus != EUS_NORMAL) {
2379 ul_size = unit_list_size(ptile->units);
2380 } else {
2381 ul_size = 0;
2382 }
2383
2384 int stored_units[ul_size + 1];
2385
2386 if (ul_size > 0) {
2387 int i;
2388
2389 could_see_unit = fc_malloc(sizeof(*could_see_unit) * ul_size);
2390
2391 unit_list_iterate(ptile->units, aunit) {
2392 stored_units[units_num++] = aunit->id;
2393 } unit_list_iterate_end;
2394
2395 fc_assert(units_num == ul_size);
2396
2397 for (i = 0; i < units_num; i++) {
2398 struct unit *aunit = game_unit_by_number(stored_units[i]);
2399
2400 BV_CLR_ALL(could_see_unit[i]);
2401 players_iterate(aplayer) {
2402 if (can_player_see_unit(aplayer, aunit)) {
2403 BV_SET(could_see_unit[i], player_index(aplayer));
2404 }
2405 } players_iterate_end;
2406 }
2407 }
2408
2409 pbase = extra_base_get(pextra);
2410
2411 fc_assert_ret(pbase != NULL);
2412
2413 /* Transfer base provided vision to new owner */
2414 if (powner != NULL) {
2415 const v_radius_t old_radius_sq = V_RADIUS(-1, -1, -1);
2416 const v_radius_t new_radius_sq = V_RADIUS(pbase->vision_main_sq,
2417 pbase->vision_invis_sq,
2418 pbase->vision_subs_sq);
2419
2420 map_vision_update(powner, ptile, old_radius_sq, new_radius_sq,
2421 game.server.vision_reveal_tiles);
2422 }
2423
2424 if (ploser != NULL) {
2425 const v_radius_t old_radius_sq = V_RADIUS(pbase->vision_main_sq,
2426 pbase->vision_invis_sq,
2427 pbase->vision_subs_sq);
2428 const v_radius_t new_radius_sq = V_RADIUS(-1, -1, -1);
2429
2430 map_vision_update(ploser, ptile, old_radius_sq, new_radius_sq,
2431 game.server.vision_reveal_tiles);
2432 }
2433
2434 if (BORDERS_DISABLED != game.info.borders
2435 && territory_claiming_base(pbase) && powner != ploser) {
2436 /* Clear borders from old owner. New owner may not know all those
2437 * tiles and thus does not claim them when borders mode is less
2438 * than EXPAND. */
2439 if (ploser != NULL) {
2440 /* Set this particular tile owner by NULL so in recursion
2441 * both loser and owner will be NULL. */
2442 map_claim_border_ownership(ptile, NULL, ptile);
2443 map_clear_border(ptile);
2444 }
2445
2446 /* We here first claim this tile ownership -> now on extra_owner()
2447 * will return new owner. Then we claim border, which will recursively
2448 * lead to this tile and base being claimed. But at that point
2449 * ploser == powner and above check will abort the recursion. */
2450 if (powner != NULL) {
2451 map_claim_border_ownership(ptile, powner, ptile);
2452 map_claim_border(ptile, powner, -1);
2453 }
2454 city_thaw_workers_queue();
2455 city_refresh_queue_processing();
2456 }
2457
2458 if (units_num > 0) {
2459 int i;
2460
2461 for (i = 0; i < units_num; i++) {
2462 struct unit *aunit = game_unit_by_number(stored_units[i]);
2463
2464 players_iterate(aplayer) {
2465 if (can_player_see_unit(aplayer, aunit)) {
2466 if (!BV_ISSET(could_see_unit[i], player_index(aplayer))) {
2467 send_unit_info(aplayer->connections, aunit);
2468 }
2469 } else {
2470 if (BV_ISSET(could_see_unit[i], player_index(aplayer))) {
2471 unit_goes_out_of_sight(aplayer, aunit);
2472 }
2473 }
2474 } players_iterate_end;
2475 }
2476
2477 free(could_see_unit);
2478 }
2479}
2480
2481/**********************************************************************/
2487 void vision_change_sight(struct vision *vision, const v_radius_t radius_sq)
2488{
2489 map_vision_update(vision->player, vision->tile, vision->radius_sq,
2490 radius_sq, vision->can_reveal_tiles);
2491 memcpy(vision->radius_sq, radius_sq, sizeof(v_radius_t));
2492}
2493
2494/**********************************************************************/
2499 void vision_clear_sight(struct vision *vision)
2500{
2501 const v_radius_t vision_radius_sq = V_RADIUS(-1, -1, -1);
2502
2503 vision_change_sight(vision, vision_radius_sq);
2504}
2505
2506/**********************************************************************/
2509 void create_extra(struct tile *ptile, struct extra_type *pextra,
2510 struct player *pplayer)
2511{
2512 bool extras_removed = FALSE;
2513
2514 extra_type_iterate(old_extra) {
2515 if (tile_has_extra(ptile, old_extra)
2516 && !can_extras_coexist(old_extra, pextra)) {
2517 destroy_extra(ptile, old_extra);
2518 extras_removed = TRUE;
2519 }
2520 } extra_type_iterate_end;
2521
2522 if (pextra->eus != EUS_NORMAL) {
2523 unit_list_iterate(ptile->units, aunit) {
2524 if (is_native_extra_to_utype(pextra, unit_type_get(aunit))) {
2525 players_iterate(aplayer) {
2526 if (!pplayers_allied(pplayer, aplayer)
2527 && can_player_see_unit(aplayer, aunit)) {
2528 unit_goes_out_of_sight(aplayer, aunit);
2529 }
2530 } players_iterate_end;
2531 }
2532 } unit_list_iterate_end;
2533 }
2534
2535 tile_add_extra(ptile, pextra);
2536
2537 /* Watchtower might become effective. */
2538 unit_list_refresh_vision(ptile->units);
2539
2540 if (pextra->data.base != NULL) {
2541 /* Claim bases on tile */
2542 if (pplayer) {
2543 struct player *old_owner = extra_owner(ptile);
2544
2545 /* Created base from NULL -> pplayer */
2546 map_claim_base(ptile, pextra, pplayer, NULL);
2547
2548 if (old_owner != pplayer) {
2549 /* Existing bases from old_owner -> pplayer */
2550 extra_type_by_cause_iterate(EC_BASE, oldbase) {
2551 if (oldbase != pextra) {
2552 map_claim_base(ptile, oldbase, pplayer, old_owner);
2553 }
2554 } extra_type_by_cause_iterate_end;
2555
2556 ptile->extras_owner = pplayer;
2557 }
2558 } else {
2559 /* Player who already owns bases on tile claims new base */
2560 map_claim_base(ptile, pextra, extra_owner(ptile), NULL);
2561 }
2562 }
2563
2564 if (extras_removed) {
2565 /* Maybe conflicting extra that was removed was the only thing
2566 * making tile native to some unit. */
2567 bounce_units_on_terrain_change(ptile);
2568 }
2569}
2570
2571/**********************************************************************/
2574 void destroy_extra(struct tile *ptile, struct extra_type *pextra)
2575{
2576 bv_player base_seen;
2577 bool real = tile_map_check(&(wld.map), ptile);
2578
2579 /* Remember what players were able to see the base. */
2580 if (real) {
2581 BV_CLR_ALL(base_seen);
2582 players_iterate(pplayer) {
2583 if (map_is_known_and_seen(ptile, pplayer, V_MAIN)) {
2584 BV_SET(base_seen, player_index(pplayer));
2585 }
2586 } players_iterate_end;
2587 }
2588
2589 if (real && is_extra_caused_by(pextra, EC_BASE)) {
2590 struct base_type *pbase = extra_base_get(pextra);
2591 struct player *owner = extra_owner(ptile);
2592
2593 if (territory_claiming_base(pbase)) {
2594 map_clear_border(ptile);
2595 }
2596
2597 if (NULL != owner
2598 && (0 <= pbase->vision_main_sq || 0 <= pbase->vision_invis_sq)) {
2599 /* Base provides vision, but no borders. */
2600 const v_radius_t old_radius_sq =
2601 V_RADIUS(0 <= pbase->vision_main_sq ? pbase->vision_main_sq : -1,
2602 0 <= pbase->vision_invis_sq ? pbase->vision_invis_sq : -1,
2603 0 <= pbase->vision_subs_sq ? pbase->vision_subs_sq : -1);
2604 const v_radius_t new_radius_sq = V_RADIUS(-1, -1, -1);
2605
2606 map_vision_update(owner, ptile, old_radius_sq, new_radius_sq,
2607 game.server.vision_reveal_tiles);
2608 }
2609 }
2610
2611 tile_remove_extra(ptile, pextra);
2612
2613 if (real) {
2614 /* Remove base from vision of players which were able to see the base. */
2615 players_iterate(pplayer) {
2616 if (BV_ISSET(base_seen, player_index(pplayer))
2617 && update_player_tile_knowledge(pplayer, ptile)) {
2618 send_tile_info(pplayer->connections, ptile, FALSE);
2619 }
2620 } players_iterate_end;
2621
2622 if (pextra->eus != EUS_NORMAL) {
2623 struct player *eowner = extra_owner(ptile);
2624
2625 unit_list_iterate(ptile->units, aunit) {
2626 if (is_native_extra_to_utype(pextra, unit_type_get(aunit))) {
2627 players_iterate(aplayer) {
2628 if (can_player_see_unit(aplayer, aunit)
2629 && !pplayers_allied(aplayer, eowner)) {
2630 send_unit_info(aplayer->connections, aunit);
2631 }
2632 } players_iterate_end;
2633 }
2634 } unit_list_iterate_end;
2635 }
2636 }
2637}
2638
2639/**********************************************************************/
2649 bool give_distorted_map(struct player *pfrom, struct player *pto,
2650 int prob, bool reveal_cities)
2651{
2652 bool updt = FALSE;
2653
2654 buffer_shared_vision(pto);
2655
2656 whole_map_iterate(&(wld.map), ptile) {
2657 if (fc_rand(100) < prob) {
2658 updt |= give_tile_info_from_player_to_player(pfrom, pto, ptile);
2659 } else if (reveal_cities && NULL != tile_city(ptile)) {
2660 updt|= give_tile_info_from_player_to_player(pfrom, pto, ptile);
2661 }
2662 } whole_map_iterate_end;
2663
2664 unbuffer_shared_vision(pto);
2665
2666 return updt;
2667}
2668
2669/**********************************************************************/
2677 void tile_change_side_effects(struct tile *ptile, bool refresh_city)
2678{
2679 struct city *pcity = ptile->worked;
2680
2681 /* Check the unit activities. */
2682 unit_activities_cancel_all_illegal_area(ptile);
2683
2684 if (pcity != NULL && !is_free_worked(pcity, ptile)
2685 && get_city_tile_output_bonus(pcity, ptile, NULL, EFT_TILE_WORKABLE) <= 0) {
2686 city_map_update_empty(pcity, ptile);
2687 pcity->specialists[DEFAULT_SPECIALIST]++;
2688
2689 if (refresh_city) {
2690 auto_arrange_workers(pcity);
2691 send_city_info(NULL, pcity);
2692 }
2693 }
2694}
is_adv_data_phase_open
bool is_adv_data_phase_open(struct player *pplayer)
Definition advdata.c:242
adv_data_phase_init
bool adv_data_phase_init(struct player *pplayer, bool is_new_phase)
Definition advdata.c:262
adv_data_phase_done
void adv_data_phase_done(struct player *pplayer)
Definition advdata.c:553
advdata.h
ai.h
CALL_FUNC_EACH_AI
#define CALL_FUNC_EACH_AI(_func,...)
Definition ai.h:384
territory_claiming_base
bool territory_claiming_base(const struct base_type *pbase)
Definition base.c:158
base.h
dbv_init
void dbv_init(struct dbv *pdbv, int bits)
Definition bitvector.c:50
dbv_set
void dbv_set(struct dbv *pdbv, int bit)
Definition bitvector.c:144
dbv_isset
bool dbv_isset(const struct dbv *pdbv, int bit)
Definition bitvector.c:120
dbv_free
void dbv_free(struct dbv *pdbv)
Definition bitvector.c:95
dbv_clr
void dbv_clr(struct dbv *pdbv, int bit)
Definition bitvector.c:167
bitvector.h
BV_CLR_ALL
#define BV_CLR_ALL(bv)
Definition bitvector.h:95
BV_SET
#define BV_SET(bv, bit)
Definition bitvector.h:81
BV_ARE_EQUAL
#define BV_ARE_EQUAL(vec1, vec2)
Definition bitvector.h:113
BV_ISSET
#define BV_ISSET(bv, bit)
Definition bitvector.h:78
BV_CLR
#define BV_CLR(bv, bit)
Definition bitvector.h:86
tile_border_source_radius_sq
int tile_border_source_radius_sq(struct tile *ptile)
Definition borders.c:33
is_border_source
bool is_border_source(struct tile *ptile)
Definition borders.c:114
tile_border_strength
int tile_border_strength(struct tile *ptile, struct tile *source)
Definition borders.c:99
borders.h
is_free_worked
bool is_free_worked(const struct city *pcity, const struct tile *ptile)
Definition city.c:3488
city_map_radius_sq_get
int city_map_radius_sq_get(const struct city *pcity)
Definition city.c:131
is_non_allied_city_tile
static bool is_non_allied_city_tile(const struct tile *ptile, const struct player *pplayer)
Definition city.h:740
city_list_iterate
#define city_list_iterate(citylist, pcity)
Definition city.h:488
city_tile
#define city_tile(_pcity_)
Definition city.h:544
city_owner
#define city_owner(_pcity_)
Definition city.h:543
city_list_iterate_end
#define city_list_iterate_end
Definition city.h:490
city_tile_iterate
#define city_tile_iterate(_nmap, _radius_sq, _city_tile, _tile)
Definition city.h:222
city_tile_iterate_end
#define city_tile_iterate_end
Definition city.h:230
city_map_update_empty
void city_map_update_empty(struct city *pcity, struct tile *ptile)
Definition citytools.c:3150
send_city_info
void send_city_info(struct player *dest, struct city *pcity)
Definition citytools.c:2313
update_dumb_city
bool update_dumb_city(struct player *pplayer, struct city *pcity)
Definition citytools.c:2669
sync_cities
void sync_cities(void)
Definition citytools.c:3224
city_map_update_tile_frozen
bool city_map_update_tile_frozen(struct tile *ptile)
Definition citytools.c:3207
remove_dumb_city
void remove_dumb_city(struct player *pplayer, struct tile *ptile)
Definition citytools.c:2759
city_landlocked_sell_coastal_improvements
void city_landlocked_sell_coastal_improvements(struct tile *ptile)
Definition citytools.c:3277
send_city_info_at_tile
void send_city_info_at_tile(struct player *pviewer, struct conn_list *dest, struct city *pcity, struct tile *ptile)
Definition citytools.c:2362
city_thaw_workers_queue
void city_thaw_workers_queue(void)
Definition citytools.c:191
reality_check_city
void reality_check_city(struct player *pplayer, struct tile *ptile)
Definition citytools.c:2737
citytools.h
auto_arrange_workers
void auto_arrange_workers(struct city *pcity)
Definition cityturn.c:368
city_refresh_queue_add
void city_refresh_queue_add(struct city *pcity)
Definition cityturn.c:199
city_refresh_queue_processing
void city_refresh_queue_processing(void)
Definition cityturn.c:215
cityturn.h
conn_list_do_unbuffer
void conn_list_do_unbuffer(struct conn_list *dest)
Definition connection.c:365
conn_list_compression_thaw
void conn_list_compression_thaw(const struct conn_list *pconn_list)
Definition connection.c:729
conn_list_do_buffer
void conn_list_do_buffer(struct conn_list *dest)
Definition connection.c:355
conn_list_compression_freeze
void conn_list_compression_freeze(const struct conn_list *pconn_list)
Definition connection.c:717
conn_list_iterate
#define conn_list_iterate(connlist, pconn)
Definition connection.h:113
conn_list_iterate_end
#define conn_list_iterate_end
Definition connection.h:115
punit
struct unit struct city struct unit struct tile struct extra_type const struct act_prob *act_probs int actor_unit_id struct unit struct unit * punit
Definition dialogs_g.h:73
get_city_tile_output_bonus
int get_city_tile_output_bonus(const struct city *pcity, const struct tile *ptile, const struct output_type *poutput, enum effect_type effect_type)
Definition effects.c:838
events.h
extra_owner
struct player * extra_owner(const struct tile *ptile)
Definition extras.c:1068
extra_number
int extra_number(const struct extra_type *pextra)
Definition extras.c:153
extra_has_flag
bool extra_has_flag(const struct extra_type *pextra, enum extra_flag_id flag)
Definition extras.c:810
player_can_build_extra
bool player_can_build_extra(const struct extra_type *pextra, const struct player *pplayer, const struct tile *ptile)
Definition extras.c:442
is_native_extra_to_utype
bool is_native_extra_to_utype(const struct extra_type *pextra, const struct unit_type *punittype)
Definition extras.c:801
can_extras_coexist
bool can_extras_coexist(const struct extra_type *pextra1, const struct extra_type *pextra2)
Definition extras.c:952
player_knows_extra_exist
bool player_knows_extra_exist(const struct player *pplayer, const struct extra_type *pextra, const struct tile *ptile)
Definition extras.c:1103
extra_name_translation
const char * extra_name_translation(const struct extra_type *pextra)
Definition extras.c:186
extra_type_iterate
#define extra_type_iterate(_p)
Definition extras.h:291
extra_type_iterate_end
#define extra_type_iterate_end
Definition extras.h:297
is_extra_caused_by
#define is_extra_caused_by(e, c)
Definition extras.h:196
extra_base_get
#define extra_base_get(_e_)
Definition extras.h:184
extra_road_get
#define extra_road_get(_e_)
Definition extras.h:185
extra_type_by_cause_iterate_end
#define extra_type_by_cause_iterate_end
Definition extras.h:315
extra_type_by_cause_iterate
#define extra_type_by_cause_iterate(_cause, _extra)
Definition extras.h:309
HB_DISABLED
@ HB_DISABLED
Definition fc_types.h:1142
MAX_EXTRA_TYPES
#define MAX_EXTRA_TYPES
Definition fc_types.h:50
Continent_id
signed short Continent_id
Definition fc_types.h:342
BORDERS_DISABLED
@ BORDERS_DISABLED
Definition fc_types.h:891
BORDERS_SEE_INSIDE
@ BORDERS_SEE_INSIDE
Definition fc_types.h:893
BORDERS_EXPAND
@ BORDERS_EXPAND
Definition fc_types.h:894
IDENTITY_NUMBER_ZERO
#define IDENTITY_NUMBER_ZERO
Definition fc_types.h:82
fcintl.h
_
#define _(String)
Definition fcintl.h:67
ftc_server
const struct ft_color ftc_server
Definition featured_text.c:77
unit_link
const char * unit_link(const struct unit *punit)
Definition featured_text.c:1200
unit_tile_link
const char * unit_tile_link(const struct unit *punit)
Definition featured_text.c:1217
game
struct civ_game game
Definition game.c:57
wld
struct world wld
Definition game.c:58
game_unit_by_number
struct unit * game_unit_by_number(int id)
Definition game.c:111
game_city_by_number
struct city * game_city_by_number(int id)
Definition game.c:102
game.h
owner
struct city * owner
Definition citydlg.c:219
source
static GtkWidget * source
Definition gotodlg.c:58
log.h
fc_assert_ret
#define fc_assert_ret(condition)
Definition log.h:191
log_verbose
#define log_verbose(message,...)
Definition log.h:109
fc_assert
#define fc_assert(condition)
Definition log.h:176
fc_assert_ret_val
#define fc_assert_ret_val(condition, val)
Definition log.h:194
log_debug
#define log_debug(message,...)
Definition log.h:115
log_error
#define log_error(message,...)
Definition log.h:103
map_num_tiles
int map_num_tiles(void)
Definition map.c:1012
rand_map_pos
struct tile * rand_map_pos(const struct civ_map *nmap)
Definition map.c:1086
map_vector_to_sq_distance
int map_vector_to_sq_distance(int dx, int dy)
Definition map.c:612
terrain_surroundings_allow_change
bool terrain_surroundings_allow_change(const struct civ_map *nmap, const struct tile *ptile, const struct terrain *pterrain)
Definition map.c:740
map_distance_vector
void map_distance_vector(int *dx, int *dy, const struct tile *tile0, const struct tile *tile1)
Definition map.c:1071
map.h
adjc_iterate_end
#define adjc_iterate_end
Definition map.h:427
MAP_INDEX_SIZE
#define MAP_INDEX_SIZE
Definition map.h:131
circle_dxyr_iterate
#define circle_dxyr_iterate(nmap, center_tile, sq_radius, _tile, dx, dy, dr)
Definition map.h:403
cardinal_adjc_iterate_end
#define cardinal_adjc_iterate_end
Definition map.h:453
adjc_iterate
#define adjc_iterate(nmap, center_tile, itr_tile)
Definition map.h:422
circle_dxyr_iterate_end
#define circle_dxyr_iterate_end
Definition map.h:414
cardinal_adjc_iterate
#define cardinal_adjc_iterate(nmap, center_tile, itr_tile)
Definition map.h:449
circle_iterate
#define circle_iterate(nmap, center_tile, sq_radius, tile_itr)
Definition map.h:395
whole_map_iterate
#define whole_map_iterate(_map, _tile)
Definition map.h:539
MAP_TILE_OWNER_NULL
#define MAP_TILE_OWNER_NULL
Definition map.h:568
whole_map_iterate_end
#define whole_map_iterate_end
Definition map.h:548
circle_iterate_end
#define circle_iterate_end
Definition map.h:398
assign_continent_numbers
void assign_continent_numbers(void)
Definition mapgen_utils.c:449
get_ocean_size
int get_ocean_size(Continent_id id)
Definition mapgen_utils.c:435
most_shallow_ocean
struct terrain * most_shallow_ocean(bool frozen)
Definition mapgen_utils.c:497
get_lake_surrounders
int get_lake_surrounders(Continent_id cont)
Definition mapgen_utils.c:417
mapgen_utils.h
player_map_init
void player_map_init(struct player *pplayer)
Definition maphand.c:1199
terrain_change_bounce_single_unit
static void terrain_change_bounce_single_unit(struct unit *punit, struct tile *from)
Definition maphand.c:1812
update_player_tile_last_seen
void update_player_tile_last_seen(struct player *pplayer, struct tile *ptile)
Definition maphand.c:1452
shared_vision_change_seen
static void shared_vision_change_seen(struct player *pplayer, struct tile *ptile, const v_radius_t change, bool can_reveal_tiles)
Definition maphand.c:659
vision_clear_sight
void vision_clear_sight(struct vision *vision)
Definition maphand.c:2499
map_claim_base
void map_claim_base(struct tile *ptile, struct extra_type *pextra, struct player *powner, struct player *ploser)
Definition maphand.c:2366
map_set_border_vision
void map_set_border_vision(struct player *pplayer, const bool is_enabled)
Definition maphand.c:732
map_claim_ownership
void map_claim_ownership(struct tile *ptile, struct player *powner, struct tile *psource, bool claim_bases)
Definition maphand.c:2173
player_tile_own_seen
static int player_tile_own_seen(const struct player_tile *plrtile, enum vision_layer vlayer)
Definition maphand.c:1114
map_is_known
bool map_is_known(const struct tile *ptile, const struct player *pplayer)
Definition maphand.c:886
send_map_info
void send_map_info(struct conn_list *dest)
Definition maphand.c:644
really_give_tile_info_from_player_to_player
static bool really_give_tile_info_from_player_to_player(struct player *pfrom, struct player *pdest, struct tile *ptile)
Definition maphand.c:1470
send_tile_suppression
bool send_tile_suppression(bool now)
Definition maphand.c:472
destroy_extra
void destroy_extra(struct tile *ptile, struct extra_type *pextra)
Definition maphand.c:2574
check_units_single_tile
static void check_units_single_tile(struct tile *ptile)
Definition maphand.c:1864
really_give_map_from_player_to_player
static void really_give_map_from_player_to_player(struct player *pfrom, struct player *pdest)
Definition maphand.c:1543
disable_fog_of_war
void disable_fog_of_war(void)
Definition maphand.c:1770
really_gives_vision
bool really_gives_vision(struct player *me, struct player *them)
Definition maphand.c:342
unit_is_on_layer
static bool unit_is_on_layer(const struct unit *punit, enum vision_layer vlayer)
Definition maphand.c:635
map_know_and_see_all
void map_know_and_see_all(struct player *pplayer)
Definition maphand.c:1174
map_change_own_seen
static void map_change_own_seen(struct player *pplayer, struct tile *ptile, const v_radius_t change)
Definition maphand.c:1123
show_map_to_all
void show_map_to_all(void)
Definition maphand.c:1188
send_tile_info
void send_tile_info(struct conn_list *dest, struct tile *ptile, bool send_unknown)
Definition maphand.c:488
update_player_tile_knowledge
bool update_player_tile_knowledge(struct player *pplayer, struct tile *ptile)
Definition maphand.c:1383
map_get_seen
static int map_get_seen(const struct player *pplayer, const struct tile *ptile, enum vision_layer vlayer)
Definition maphand.c:915
ocean_to_land_fix_rivers
static void ocean_to_land_fix_rivers(struct tile *ptile)
Definition maphand.c:1786
give_map_from_player_to_player
void give_map_from_player_to_player(struct player *pfrom, struct player *pdest)
Definition maphand.c:381
send_all_known_tiles
void send_all_known_tiles(struct conn_list *dest)
Definition maphand.c:441
bounce_units_on_terrain_change
void bounce_units_on_terrain_change(struct tile *ptile)
Definition maphand.c:1894
give_seamap_from_player_to_player
void give_seamap_from_player_to_player(struct player *pfrom, struct player *pdest)
Definition maphand.c:397
remove_shared_vision
void remove_shared_vision(struct player *pfrom, struct player *pto)
Definition maphand.c:1678
need_to_reassign_continents
bool need_to_reassign_continents(const struct terrain *oldter, const struct terrain *newter)
Definition maphand.c:1909
is_claimable_ocean
static bool is_claimable_ocean(struct tile *ptile, struct tile *source, struct player *pplayer)
Definition maphand.c:2059
map_get_player_city
struct vision_site * map_get_player_city(const struct tile *ptile, const struct player *pplayer)
Definition maphand.c:1343
is_terrain_ecologically_wet
static bool is_terrain_ecologically_wet(struct tile *ptile)
Definition maphand.c:93
tile_claim_bases
void tile_claim_bases(struct tile *ptile, struct player *powner)
Definition maphand.c:2186
disable_fog_of_war_player
void disable_fog_of_war_player(struct player *pplayer)
Definition maphand.c:1756
climate_change
void climate_change(bool warming, int effect)
Definition maphand.c:130
enable_fog_of_war
void enable_fog_of_war(void)
Definition maphand.c:1746
send_tile_suppressed
static bool send_tile_suppressed
Definition maphand.c:65
create_vision_dependencies
static void create_vision_dependencies(void)
Definition maphand.c:1583
upgrade_all_city_extras
void upgrade_all_city_extras(struct player *pplayer, bool discovery)
Definition maphand.c:273
create_extra
void create_extra(struct tile *ptile, struct extra_type *pextra, struct player *pplayer)
Definition maphand.c:2509
map_update_border
void map_update_border(struct tile *ptile, struct player *owner, int old_radius_sq, int new_radius_sq)
Definition maphand.c:2220
map_set_known
void map_set_known(struct tile *ptile, struct player *pplayer)
Definition maphand.c:1156
map_show_all
void map_show_all(struct player *pplayer)
Definition maphand.c:871
map_unit_homecity_enqueue
static void map_unit_homecity_enqueue(struct tile *ptile)
Definition maphand.c:2112
map_change_seen
static void map_change_seen(struct player *pplayer, struct tile *ptile, const v_radius_t change, bool can_reveal_tiles)
Definition maphand.c:928
map_show_tile
void map_show_tile(struct player *src_player, struct tile *ptile)
Definition maphand.c:760
give_citymap_from_player_to_player
void give_citymap_from_player_to_player(struct city *pcity, struct player *pfrom, struct player *pdest)
Definition maphand.c:415
nuclear_winter
void nuclear_winter(int effect)
Definition maphand.c:116
tile_change_side_effects
void tile_change_side_effects(struct tile *ptile, bool refresh_city)
Definition maphand.c:2677
player_tile_init
static void player_tile_init(struct tile *ptile, struct player *pplayer)
Definition maphand.c:1306
terrain_changed
void terrain_changed(struct tile *ptile)
Definition maphand.c:1928
player_map_free
void player_map_free(struct player *pplayer)
Definition maphand.c:1215
unbuffer_shared_vision
static void unbuffer_shared_vision(struct player *pplayer)
Definition maphand.c:365
map_claim_border_ownership
static void map_claim_border_ownership(struct tile *ptile, struct player *powner, struct tile *psource)
Definition maphand.c:2128
map_is_known_and_seen
bool map_is_known_and_seen(const struct tile *ptile, const struct player *pplayer, enum vision_layer vlayer)
Definition maphand.c:900
change_playertile_site
void change_playertile_site(struct player_tile *ptile, struct vision_site *new_site)
Definition maphand.c:1137
map_calculate_borders
void map_calculate_borders(void)
Definition maphand.c:2339
fix_tile_on_terrain_change
void fix_tile_on_terrain_change(struct tile *ptile, struct terrain *oldter, bool extend_rivers)
Definition maphand.c:1947
enable_fog_of_war_player
void enable_fog_of_war_player(struct player *pplayer)
Definition maphand.c:1732
map_show_circle
void map_show_circle(struct player *pplayer, struct tile *ptile, int radius_sq)
Definition maphand.c:856
map_vision_update
void map_vision_update(struct player *pplayer, struct tile *ptile, const v_radius_t old_radius_sq, const v_radius_t new_radius_sq, bool can_reveal_tiles)
Definition maphand.c:677
map_claim_border
void map_claim_border(struct tile *ptile, struct player *owner, int radius_sq)
Definition maphand.c:2252
update_tile_knowledge
void update_tile_knowledge(struct tile *ptile)
Definition maphand.c:1424
remove_player_from_maps
void remove_player_from_maps(struct player *pplayer)
Definition maphand.c:1236
give_shared_vision
void give_shared_vision(struct player *pfrom, struct player *pto)
Definition maphand.c:1617
check_terrain_change
void check_terrain_change(struct tile *ptile, struct terrain *oldter)
Definition maphand.c:1967
give_distorted_map
bool give_distorted_map(struct player *pfrom, struct player *pto, int prob, bool reveal_cities)
Definition maphand.c:2649
map_hide_tile
void map_hide_tile(struct player *src_player, struct tile *ptile)
Definition maphand.c:812
map_get_player_site
struct vision_site * map_get_player_site(const struct tile *ptile, const struct player *pplayer)
Definition maphand.c:1356
buffer_shared_vision
static void buffer_shared_vision(struct player *pplayer)
Definition maphand.c:350
give_tile_info_from_player_to_player
static bool give_tile_info_from_player_to_player(struct player *pfrom, struct player *pdest, struct tile *ptile)
Definition maphand.c:1563
global_warming
void global_warming(int effect)
Definition maphand.c:103
upgrade_city_extras
bool upgrade_city_extras(struct city *pcity, struct extra_type **gained)
Definition maphand.c:238
map_clear_border
void map_clear_border(struct tile *ptile)
Definition maphand.c:2203
map_clear_known
void map_clear_known(struct tile *ptile, struct player *pplayer)
Definition maphand.c:1164
player_tile_free
static void player_tile_free(struct tile *ptile, struct player *pplayer)
Definition maphand.c:1331
MAXIMUM_CLAIMED_OCEAN_SIZE
#define MAXIMUM_CLAIMED_OCEAN_SIZE
Definition maphand.c:62
map_get_player_tile
struct player_tile * map_get_player_tile(const struct tile *ptile, const struct player *pplayer)
Definition maphand.c:1367
vision_change_sight
void vision_change_sight(struct vision *vision, const v_radius_t radius_sq)
Definition maphand.c:2487
maphand.h
mem.h
fc_realloc
#define fc_realloc(ptr, sz)
Definition mem.h:36
fc_malloc
#define fc_malloc(sz)
Definition mem.h:34
can_unit_exist_at_tile
bool can_unit_exist_at_tile(const struct civ_map *nmap, const struct unit *punit, const struct tile *ptile)
Definition movement.c:304
movement.h
nation_rule_name
const char * nation_rule_name(const struct nation_type *pnation)
Definition nation.c:137
nation_of_unit
struct nation_type * nation_of_unit(const struct unit *punit)
Definition nation.c:462
nation.h
notify_player
void notify_player(const struct player *pplayer, const struct tile *ptile, enum event_type event, const struct ft_color color, const char *format,...)
Definition notify.c:292
notify.h
packets.h
lsend_packet_map_info
void lsend_packet_map_info(struct conn_list *dest, const struct packet_map_info *packet)
Definition packets_gen.c:9892
send_packet_tile_info
int send_packet_tile_info(struct connection *pc, const struct packet_tile_info *packet)
Definition packets_gen.c:4427
num_known_tech_with_flag
int num_known_tech_with_flag(const struct player *pplayer, enum tech_flag_id flag)
Definition player.c:1249
player_slot_count
int player_slot_count(void)
Definition player.c:411
player_number
int player_number(const struct player *pplayer)
Definition player.c:828
player_name
const char * player_name(const struct player *pplayer)
Definition player.c:886
can_player_see_unit
bool can_player_see_unit(const struct player *pplayer, const struct unit *punit)
Definition player.c:1084
player_index
int player_index(const struct player *pplayer)
Definition player.c:820
pplayers_allied
bool pplayers_allied(const struct player *pplayer, const struct player *pplayer2)
Definition player.c:1381
gives_shared_vision
bool gives_shared_vision(const struct player *me, const struct player *them)
Definition player.c:1461
player.h
players_iterate_end
#define players_iterate_end
Definition player.h:535
players_iterate
#define players_iterate(_pplayer)
Definition player.h:530
send_player_info_c
void send_player_info_c(struct player *src, struct conn_list *dest)
Definition plrhand.c:1000
plrhand.h
phase_players_iterate
#define phase_players_iterate(pplayer)
Definition plrhand.h:111
phase_players_iterate_end
#define phase_players_iterate_end
Definition plrhand.h:116
rand.h
fc_rand
#define fc_rand(_size)
Definition rand.h:34
road_has_flag
bool road_has_flag(const struct road_type *proad, enum road_flag_id flag)
Definition road.c:410
count_river_near_tile
int count_river_near_tile(struct civ_map *nmap, const struct tile *ptile, const struct extra_type *priver)
Definition road.c:334
road.h
sanitycheck.h
sanity_check_tile
#define sanity_check_tile(x)
Definition sanitycheck.h:42
flush_packets
void flush_packets(void)
Definition sernet.c:379
sernet.h
specialist.h
DEFAULT_SPECIALIST
#define DEFAULT_SPECIALIST
Definition specialist.h:43
server_state
enum server_states server_state(void)
Definition srv_main.c:323
srv_main.h
base_type
Definition base.h:41
base_type::vision_main_sq
int vision_main_sq
Definition base.h:45
base_type::vision_invis_sq
int vision_invis_sq
Definition base.h:46
base_type::vision_subs_sq
int vision_subs_sq
Definition base.h:47
city
Definition city.h:309
city::specialists
citizens specialists[SP_MAX]
Definition city.h:324
city::tile
struct tile * tile
Definition city.h:311
civ_game::last_updated_year
bool last_updated_year
Definition game.h:234
civ_game::server
struct civ_game::@30::@34 server
civ_game::vision_reveal_tiles
bool vision_reveal_tiles
Definition game.h:199
civ_game::fogofwar_old
bool fogofwar_old
Definition game.h:232
civ_game::est_connections
struct conn_list * est_connections
Definition game.h:97
civ_game::info
struct packet_game_info info
Definition game.h:89
civ_game::scenario
struct packet_scenario_info scenario
Definition game.h:87
civ_game::foggedborders
bool foggedborders
Definition game.h:146
civ_map
Definition map_types.h:71
civ_map::tiles
struct tile * tiles
Definition map_types.h:80
civ_map::xsize
int xsize
Definition map_types.h:77
civ_map::ysize
int ysize
Definition map_types.h:77
civ_map::topology_id
int topology_id
Definition map_types.h:72
dbv::vec
unsigned char * vec
Definition bitvector.h:34
effect
Definition effects.h:340
extra_type
Definition extras.h:85
extra_type::resource
struct resource_type * resource
Definition extras.h:150
extra_type::data
struct extra_type::@24 data
extra_type::eus
enum extra_unit_seen_type eus
Definition extras.h:124
extra_type::base
struct base_type * base
Definition extras.h:148
packet_game_info::borders
enum borders_mode borders
Definition packets_gen.h:133
packet_game_info::happyborders
enum happyborders_type happyborders
Definition packets_gen.h:177
packet_game_info::turn
int turn
Definition packets_gen.h:241
packet_game_info::year
int year
Definition packets_gen.h:243
packet_game_info::border_city_permanent_radius_sq
int border_city_permanent_radius_sq
Definition packets_gen.h:132
packet_game_info::fogofwar
bool fogofwar
Definition packets_gen.h:152
packet_map_info
Definition packets_gen.h:266
packet_map_info::ysize
int ysize
Definition packets_gen.h:268
packet_map_info::topology_id
int topology_id
Definition packets_gen.h:269
packet_map_info::xsize
int xsize
Definition packets_gen.h:267
packet_scenario_info::lake_flooding
bool lake_flooding
Definition packets_gen.h:1612
packet_tile_info
Definition packets_gen.h:102
packet_tile_info::resource
Resource_type_id resource
Definition packets_gen.h:111
packet_tile_info::extras
bv_extras extras
Definition packets_gen.h:112
packet_tile_info::place_turn
int place_turn
Definition packets_gen.h:114
packet_tile_info::placing
int placing
Definition packets_gen.h:113
packet_tile_info::owner
int owner
Definition packets_gen.h:106
packet_tile_info::known
enum known_type known
Definition packets_gen.h:105
packet_tile_info::label
char label[MAX_LEN_MAP_LABEL]
Definition packets_gen.h:116
packet_tile_info::extras_owner
int extras_owner
Definition packets_gen.h:107
packet_tile_info::tile
int tile
Definition packets_gen.h:103
packet_tile_info::continent
Continent_id continent
Definition packets_gen.h:104
packet_tile_info::terrain
Terrain_type_id terrain
Definition packets_gen.h:110
packet_tile_info::worked32
int worked32
Definition packets_gen.h:109
packet_tile_info::spec_sprite
char spec_sprite[MAX_LEN_NAME]
Definition packets_gen.h:115
packet_tile_info::worked16
int worked16
Definition packets_gen.h:108
player_tile
Definition maphand.h:30
player_tile::extras
bv_extras extras
Definition maphand.h:36
player_tile::extras_owner
struct player * extras_owner
Definition maphand.h:35
player_tile::seen_count
v_radius_t seen_count
Definition maphand.h:43
player_tile::site
struct vision_site * site
Definition maphand.h:31
player_tile::own_seen
v_radius_t own_seen
Definition maphand.h:42
player_tile::terrain
struct terrain * terrain
Definition maphand.h:33
player_tile::last_updated
short last_updated
Definition maphand.h:44
player_tile::owner
struct player * owner
Definition maphand.h:34
player_tile::resource
struct extra_type * resource
Definition maphand.h:32
player
Definition player.h:249
player::cities
struct city_list * cities
Definition player.h:281
player::tile_known
struct dbv tile_known
Definition player.h:306
player::connections
struct conn_list * connections
Definition player.h:298
player::gives_shared_vision
bv_player gives_shared_vision
Definition player.h:299
player::private_map
struct player_tile * private_map
Definition player.h:324
player::really_gives_vision
bv_player really_gives_vision
Definition player.h:329
player::border_vision
bool border_vision
Definition player.h:327
player::server
struct player::@69::@71 server
terrain
Definition terrain.h:176
terrain::cooler_wetter_result
struct terrain * cooler_wetter_result
Definition terrain.h:227
terrain::cooler_drier_result
struct terrain * cooler_drier_result
Definition terrain.h:227
terrain::warmer_wetter_result
struct terrain * warmer_wetter_result
Definition terrain.h:226
terrain::warmer_drier_result
struct terrain * warmer_drier_result
Definition terrain.h:226
tile
Definition tile.h:49
tile::spec_sprite
char * spec_sprite
Definition tile.h:65
tile::label
char * label
Definition tile.h:64
tile::extras
bv_extras extras
Definition tile.h:54
tile::resource
struct extra_type * resource
Definition tile.h:55
tile::units
struct unit_list * units
Definition tile.h:57
tile::extras_owner
struct player * extras_owner
Definition tile.h:62
tile::terrain
struct terrain * terrain
Definition tile.h:56
tile::infra_turns
int infra_turns
Definition tile.h:61
tile::placing
struct extra_type * placing
Definition tile.h:60
tile::worked
struct city * worked
Definition tile.h:58
tile::claimer
struct tile * claimer
Definition tile.h:63
unit_type::vlayer
enum vision_layer vlayer
Definition unittype.h:550
unit
Definition unit.h:138
unit::activity
enum unit_activity activity
Definition unit.h:157
unit::id
int id
Definition unit.h:145
unit::activity_target
struct extra_type * activity_target
Definition unit.h:164
unit::server
struct unit::@80::@83 server
unit::homecity
int homecity
Definition unit.h:146
unit::dying
bool dying
Definition unit.h:248
vision_site
Definition vision.h:109
vision_site::location
struct tile * location
Definition vision.h:111
vision_site::identity
int identity
Definition vision.h:114
vision
Definition vision.h:85
vision::tile
struct tile * tile
Definition vision.h:88
vision::can_reveal_tiles
bool can_reveal_tiles
Definition vision.h:89
vision::radius_sq
v_radius_t radius_sq
Definition vision.h:92
vision::player
struct player * player
Definition vision.h:87
world::map
struct civ_map map
Definition world_object.h:38
support.h
sz_strlcpy
#define sz_strlcpy(dest, src)
Definition support.h:161
TRUE
#define TRUE
Definition support.h:46
FALSE
#define FALSE
Definition support.h:47
is_terrain_class_near_tile
bool is_terrain_class_near_tile(const struct civ_map *nmap, const struct tile *ptile, enum terrain_class tclass)
Definition terrain.c:600
terrain_count
Terrain_type_id terrain_count(void)
Definition terrain.c:106
terrain_number
Terrain_type_id terrain_number(const struct terrain *pterrain)
Definition terrain.c:135
T_UNKNOWN
#define T_UNKNOWN
Definition terrain.h:57
is_ocean
#define is_ocean(pterrain)
Definition terrain.h:287
is_ocean_tile
#define is_ocean_tile(ptile)
Definition terrain.h:289
T_NONE
#define T_NONE
Definition terrain.h:56
terrain_has_flag
#define terrain_has_flag(terr, flag)
Definition terrain.h:269
tile_add_extra
void tile_add_extra(struct tile *ptile, const struct extra_type *pextra)
Definition tile.c:940
tile_has_river
bool tile_has_river(const struct tile *ptile)
Definition tile.c:837
tile_map_check
bool tile_map_check(struct civ_map *nmap, struct tile *vtile)
Definition tile.c:1050
tile_remove_extra
void tile_remove_extra(struct tile *ptile, const struct extra_type *pextra)
Definition tile.c:950
tile_change_terrain
void tile_change_terrain(struct tile *ptile, struct terrain *pterrain)
Definition tile.c:473
tile_has_conflicting_extra
bool tile_has_conflicting_extra(const struct tile *ptile, const struct extra_type *pextra)
Definition tile.c:886
tile_set_owner
void tile_set_owner(struct tile *ptile, struct player *pplayer, struct tile *claimer)
Definition tile.c:69
tile_city
struct city * tile_city(const struct tile *ptile)
Definition tile.c:83
tile_claimer
#define tile_claimer(_tile)
Definition tile.h:99
tile_index
#define tile_index(_pt_)
Definition tile.h:87
tile_worked
#define tile_worked(_tile)
Definition tile.h:113
tile_resource
#define tile_resource(_tile)
Definition tile.h:101
TILE_KNOWN_UNSEEN
@ TILE_KNOWN_UNSEEN
Definition tile.h:36
TILE_UNKNOWN
@ TILE_UNKNOWN
Definition tile.h:35
TILE_KNOWN_SEEN
@ TILE_KNOWN_SEEN
Definition tile.h:37
tile_terrain
#define tile_terrain(_tile)
Definition tile.h:109
TILE_XY
#define TILE_XY(ptile)
Definition tile.h:42
tile_continent
#define tile_continent(_tile)
Definition tile.h:91
tile_has_extra
#define tile_has_extra(ptile, pextra)
Definition tile.h:146
tile_owner
#define tile_owner(_tile)
Definition tile.h:95
get_transporter_occupancy
int get_transporter_occupancy(const struct unit *ptrans)
Definition unit.c:1763
unit_is_alive
bool unit_is_alive(int id)
Definition unit.c:2233
unit_transported
bool unit_transported(const struct unit *pcargo)
Definition unit.c:2405
unit_transport_cargo
struct unit_list * unit_transport_cargo(const struct unit *ptrans)
Definition unit.c:2431
unit.h
unit_tile
#define unit_tile(_pu)
Definition unit.h:388
unit_owner
#define unit_owner(_pu)
Definition unit.h:387
is_non_allied_unit_tile
static bool is_non_allied_unit_tile(const struct tile *ptile, const struct player *pplayer)
Definition unit.h:423
unit_activity_handling
bool unit_activity_handling(struct unit *punit, enum unit_activity new_activity)
Definition unithand.c:6176
unithand.h
unitlist.h
unit_list_iterate
#define unit_list_iterate(unitlist, punit)
Definition unitlist.h:31
unit_list_iterate_safe
#define unit_list_iterate_safe(unitlist, _unit)
Definition unitlist.h:39
unit_list_iterate_end
#define unit_list_iterate_end
Definition unitlist.h:33
unit_list_iterate_safe_end
#define unit_list_iterate_safe_end
Definition unitlist.h:61
unit_goes_out_of_sight
void unit_goes_out_of_sight(struct player *pplayer, struct unit *punit)
Definition unittools.c:2784
send_unit_info
void send_unit_info(struct conn_list *dest, struct unit *punit)
Definition unittools.c:2797
unit_activities_cancel
void unit_activities_cancel(struct unit *punit)
Definition unittools.c:792
wipe_unit
void wipe_unit(struct unit *punit, enum unit_loss_reason reason, struct player *killer)
Definition unittools.c:2251
unit_activities_cancel_all_illegal_area
void unit_activities_cancel_all_illegal_area(const struct tile *ptile)
Definition unittools.c:837
unit_move
bool unit_move(struct unit *punit, struct tile *pdesttile, int move_cost, struct unit *embark_to, bool find_embark_target, bool conquer_city_allowed, bool conquer_extras_allowed, bool enter_hut, bool frighten_hut)
Definition unittools.c:3882
unit_list_refresh_vision
void unit_list_refresh_vision(struct unit_list *punitlist)
Definition unittools.c:4867
unittools.h
unit_type_get
const struct unit_type * unit_type_get(const struct unit *punit)
Definition unittype.c:123
unit_rule_name
const char * unit_rule_name(const struct unit *punit)
Definition unittype.c:1639
vision_site_copy
struct vision_site * vision_site_copy(const struct vision_site *psite)
Definition vision.c:135
vision_site_destroy
void vision_site_destroy(struct vision_site *psite)
Definition vision.c:74
vision.h
V_RADIUS
#define V_RADIUS(main_sq, invis_sq, subs_sq)
Definition vision.h:96
vision_layer_iterate
#define vision_layer_iterate(v)
Definition vision.h:77
vision_site_owner
#define vision_site_owner(v)
Definition vision.h:128
v_radius_t
short int v_radius_t[V_COUNT]
Definition vision.h:83
vision_layer_iterate_end
#define vision_layer_iterate_end
Definition vision.h:80