Clarify character encoding arrangements, and stop claiming in various
[freeciv.git] / server / settings.c
blob2b05ec267455c73f0782f5615984fa2bc00b07a9
1 /**********************************************************************
2 Freeciv - Copyright (C) 1996-2004 - The Freeciv Project
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.
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 ***********************************************************************/
14 #ifdef HAVE_CONFIG_H
15 #include <fc_config.h>
16 #endif
18 /* utility */
19 #include "astring.h"
20 #include "fcintl.h"
21 #include "game.h"
22 #include "ioz.h"
23 #include "log.h"
24 #include "registry.h"
25 #include "shared.h"
26 #include "string_vector.h"
28 /* common */
29 #include "map.h"
31 /* server */
32 #include "gamehand.h"
33 #include "ggzserver.h"
34 #include "maphand.h"
35 #include "notify.h"
36 #include "plrhand.h"
37 #include "report.h"
38 #include "settings.h"
39 #include "srv_main.h"
40 #include "stdinhand.h"
42 /* The following classes determine what can be changed when.
43 * Actually, some of them have the same "changeability", but
44 * different types are separated here in case they have
45 * other uses.
46 * Also, SSET_GAME_INIT/SSET_RULES separate the two sections
47 * of server settings sent to the client.
48 * See the settings[] array and setting_is_changeable() for what
49 * these correspond to and explanations.
51 enum sset_class {
52 SSET_MAP_SIZE,
53 SSET_MAP_GEN,
54 SSET_MAP_ADD,
55 SSET_PLAYERS,
56 SSET_GAME_INIT,
57 SSET_RULES,
58 SSET_RULES_FLEXIBLE,
59 SSET_META
62 typedef bool (*bool_validate_func_t) (bool value, struct connection *pconn,
63 char *reject_msg,
64 size_t reject_msg_len);
65 typedef bool (*int_validate_func_t) (int value, struct connection *pconn,
66 char *reject_msg,
67 size_t reject_msg_len);
68 typedef bool (*string_validate_func_t) (const char * value,
69 struct connection *pconn,
70 char *reject_msg,
71 size_t reject_msg_len);
72 typedef bool (*enum_validate_func_t) (int value, struct connection *pconn,
73 char *reject_msg,
74 size_t reject_msg_len);
75 typedef bool (*bitwise_validate_func_t) (unsigned value,
76 struct connection *pconn,
77 char *reject_msg,
78 size_t reject_msg_len);
80 typedef void (*action_callback_func_t) (const struct setting *pset);
81 typedef const struct sset_val_name * (*val_name_func_t) (int value);
83 struct setting {
84 const char *name;
85 enum sset_class sclass;
86 bool to_client;
89 * Sould be less than 42 chars (?), or shorter if the values may
90 * have more than about 4 digits. Don't put "." on the end.
92 const char *short_help;
95 * May be empty string, if short_help is sufficient. Need not
96 * include embedded newlines (but may, for formatting); lines will
97 * be wrapped (and indented) automatically. Should have punctuation
98 * etc, and should end with a "."
100 const char *extra_help;
101 enum sset_type stype;
102 enum sset_category scategory;
103 enum sset_level slevel;
106 * About the *_validate functions: If the function is non-NULL, it
107 * is called with the new value, and returns whether the change is
108 * legal. The char * is an error message in the case of reject.
111 union {
112 /*** bool part ***/
113 struct {
114 bool *const pvalue;
115 const bool default_value;
116 const bool_validate_func_t validate;
117 const val_name_func_t name;
118 bool game_value;
119 } boolean;
120 /*** int part ***/
121 struct {
122 int *const pvalue;
123 const int default_value;
124 const int min_value;
125 const int max_value;
126 const int_validate_func_t validate;
127 int game_value;
128 } integer;
129 /*** string part ***/
130 struct {
131 char *const value;
132 const char *const default_value;
133 const size_t value_size;
134 const string_validate_func_t validate;
135 char *game_value;
136 } string;
137 /*** enumerator part ***/
138 struct {
139 void *const pvalue;
140 const int store_size;
141 const int default_value;
142 const enum_validate_func_t validate;
143 const val_name_func_t name;
144 int game_value;
145 } enumerator;
146 /*** bitwise part ***/
147 struct {
148 unsigned *const pvalue;
149 const unsigned default_value;
150 const bitwise_validate_func_t validate;
151 const val_name_func_t name;
152 unsigned game_value;
153 } bitwise;
156 /* action function */
157 const action_callback_func_t action;
159 /* ruleset lock for game settings */
160 bool locked;
163 static struct {
164 bool init;
165 struct setting_list *level[OLEVELS_NUM];
166 } setting_sorted = { .init = FALSE };
168 static void setting_set_to_default(struct setting *pset);
169 static bool setting_ruleset_one(struct section_file *file,
170 const char *name, const char *path);
171 static void setting_game_set(struct setting *pset, bool init);
172 static void setting_game_free(struct setting *pset);
173 static void setting_game_restore(struct setting *pset);
175 static void settings_list_init(void);
176 static void settings_list_free(void);
177 int settings_list_cmp(const struct setting *const *pset1,
178 const struct setting *const *pset2);
180 #define settings_snprintf(_buf, _buf_len, format, ...) \
181 if (_buf != NULL) { \
182 fc_snprintf(_buf, _buf_len, format, ## __VA_ARGS__); \
185 static bool set_enum_value(struct setting *pset, int val);
186 static int read_enum_value(const struct setting *pset);
188 /****************************************************************************
189 Enumerator name accessors.
191 Important note about compatibility:
192 1) you cannot modify the support name of an existant value. However, in a
193 developpement, you can modify it if it wasn't included in any stable
194 branch before.
195 2) Take care of modifiying the pretty name of an existant value: make sure
196 to modify the help texts which are using it.
197 ****************************************************************************/
199 #define NAME_CASE(_val, _support, _pretty) \
200 case _val: \
202 static const struct sset_val_name name = { _support, _pretty }; \
203 return &name; \
206 /****************************************************************************
207 Map size definition setting names accessor. This setting has an
208 hard-coded depedence in "server/meta.c".
209 ****************************************************************************/
210 static const struct sset_val_name *mapsize_name(int mapsize)
212 switch (mapsize) {
213 NAME_CASE(MAPSIZE_FULLSIZE, "FULLSIZE", N_("Number of tiles"));
214 NAME_CASE(MAPSIZE_PLAYER, "PLAYER", N_("Tiles per player"));
215 NAME_CASE(MAPSIZE_XYSIZE, "XYSIZE", N_("Width and height"));
217 return NULL;
220 /****************************************************************************
221 Topology setting names accessor.
222 ****************************************************************************/
223 static const struct sset_val_name *topology_name(int topology_bit)
225 switch (1 << topology_bit) {
226 NAME_CASE(TF_WRAPX, "WRAPX", N_("Wrap East-West"));
227 NAME_CASE(TF_WRAPY, "WRAPY", N_("Wrap North-South"));
228 NAME_CASE(TF_ISO, "ISO", N_("Isometric"));
229 NAME_CASE(TF_HEX, "HEX", N_("Hexagonal"));
231 return NULL;
234 /****************************************************************************
235 Generator setting names accessor.
236 ****************************************************************************/
237 static const struct sset_val_name *generator_name(int generator)
239 switch (generator) {
240 NAME_CASE(MAPGEN_SCENARIO, "SCENARIO", N_("Scenario map"));
241 NAME_CASE(MAPGEN_RANDOM, "RANDOM", N_("Fully random height"));
242 NAME_CASE(MAPGEN_FRACTAL, "FRACTAL", N_("Pseudo-fractal height"));
243 NAME_CASE(MAPGEN_ISLAND, "ISLAND", N_("Island-based"));
244 NAME_CASE(MAPGEN_FAIR, "FAIR", N_("Fair islands"));
246 return NULL;
249 /****************************************************************************
250 Start position setting names accessor.
251 ****************************************************************************/
252 static const struct sset_val_name *startpos_name(int startpos)
254 switch (startpos) {
255 NAME_CASE(MAPSTARTPOS_DEFAULT, "DEFAULT",
256 N_("Generator's choice"));
257 NAME_CASE(MAPSTARTPOS_SINGLE, "SINGLE",
258 N_("One player per continent"));
259 NAME_CASE(MAPSTARTPOS_2or3, "2or3",
260 N_("Two or three players per continent"));
261 NAME_CASE(MAPSTARTPOS_ALL, "ALL",
262 N_("All players on a single continent"));
263 NAME_CASE(MAPSTARTPOS_VARIABLE, "VARIABLE",
264 N_("Depending on size of continents"));
266 return NULL;
269 /****************************************************************************
270 Team placement setting names accessor.
271 ****************************************************************************/
272 static const struct sset_val_name *teamplacement_name(int team_placement)
274 switch (team_placement) {
275 NAME_CASE(TEAM_PLACEMENT_DISABLED, "DISABLED",
276 N_("Disabled"));
277 NAME_CASE(TEAM_PLACEMENT_CLOSEST, "CLOSEST",
278 N_("As close as possible"));
279 NAME_CASE(TEAM_PLACEMENT_CONTINENT, "CONTINENT",
280 N_("On the same continent"));
281 NAME_CASE(TEAM_PLACEMENT_HORIZONTAL, "HORIZONTAL",
282 N_("Horizontal placement"));
283 NAME_CASE(TEAM_PLACEMENT_VERTICAL, "VERTICAL",
284 N_("Vertical placement"));
286 return NULL;
289 /****************************************************************************
290 Autosaves setting names accessor.
291 ****************************************************************************/
292 static const struct sset_val_name *autosaves_name(int autosaves_bit)
294 switch (autosaves_bit) {
295 NAME_CASE(AS_TURN, "TURN", N_("New turn"));
296 NAME_CASE(AS_GAME_OVER, "GAMEOVER", N_("Game over"));
297 NAME_CASE(AS_QUITIDLE, "QUITIDLE", N_("No player connections"));
298 NAME_CASE(AS_INTERRUPT, "INTERRUPT", N_("Server interrupted"));
301 return NULL;
304 /****************************************************************************
305 Borders setting names accessor.
306 ****************************************************************************/
307 static const struct sset_val_name *borders_name(int borders)
309 switch (borders) {
310 NAME_CASE(BORDERS_DISABLED, "DISABLED", N_("Disabled"));
311 NAME_CASE(BORDERS_ENABLED, "ENABLED", N_("Enabled"));
312 NAME_CASE(BORDERS_SEE_INSIDE, "SEE_INSIDE",
313 N_("See everything inside borders"));
314 NAME_CASE(BORDERS_EXPAND, "EXPAND",
315 N_("Borders expand to unknown, revealing tiles"));
317 return NULL;
320 /****************************************************************************
321 Player colors configuration setting names accessor.
322 ****************************************************************************/
323 static const struct sset_val_name *plrcol_name(int plrcol)
325 switch (plrcol) {
326 NAME_CASE(PLRCOL_PLR_ORDER, "PLR_ORDER", N_("Per-player, in order"));
327 NAME_CASE(PLRCOL_PLR_RANDOM, "PLR_RANDOM", N_("Per-player, random"));
328 NAME_CASE(PLRCOL_PLR_SET, "PLR_SET", N_("Set manually"));
329 NAME_CASE(PLRCOL_TEAM_ORDER, "TEAM_ORDER", N_("Per-team, in order"));
330 NAME_CASE(PLRCOL_NATION_ORDER, "NATION_ORDER", N_("Per-nation, in order"));
332 return NULL;
335 /****************************************************************************
336 Diplomacy setting names accessor.
337 ****************************************************************************/
338 static const struct sset_val_name *diplomacy_name(int diplomacy)
340 switch (diplomacy) {
341 NAME_CASE(DIPLO_FOR_ALL, "ALL", N_("Enabled for everyone"));
342 NAME_CASE(DIPLO_FOR_HUMANS, "HUMAN",
343 N_("Only allowed between human players"));
344 NAME_CASE(DIPLO_FOR_AIS, "AI", N_("Only allowed between AI players"));
345 NAME_CASE(DIPLO_NO_AIS, "NOAI", N_("Only allowed when human involved"));
346 NAME_CASE(DIPLO_NO_MIXED, "NOMIXED", N_("Only allowed between two humans, or two AI players"));
347 NAME_CASE(DIPLO_FOR_TEAMS, "TEAM", N_("Restricted to teams"));
348 NAME_CASE(DIPLO_DISABLED, "DISABLED", N_("Disabled for everyone"));
350 return NULL;
353 /****************************************************************************
354 City names setting names accessor.
355 ****************************************************************************/
356 static const struct sset_val_name *citynames_name(int citynames)
358 switch (citynames) {
359 NAME_CASE(CNM_NO_RESTRICTIONS, "NO_RESTRICTIONS", N_("No restrictions"));
360 NAME_CASE(CNM_PLAYER_UNIQUE, "PLAYER_UNIQUE", N_("Unique to a player"));
361 NAME_CASE(CNM_GLOBAL_UNIQUE, "GLOBAL_UNIQUE", N_("Globally unique"));
362 NAME_CASE(CNM_NO_STEALING, "NO_STEALING", N_("No city name stealing"));
364 return NULL;
367 /****************************************************************************
368 Barbarian setting names accessor.
369 ****************************************************************************/
370 static const struct sset_val_name *barbarians_name(int barbarians)
372 switch (barbarians) {
373 NAME_CASE(BARBS_DISABLED, "DISABLED", N_("No barbarians"));
374 NAME_CASE(BARBS_HUTS_ONLY, "HUTS_ONLY", N_("Only in huts"));
375 NAME_CASE(BARBS_NORMAL, "NORMAL", N_("Normal rate of appearance"));
376 NAME_CASE(BARBS_FREQUENT, "FREQUENT", N_("Frequent barbarian uprising"));
377 NAME_CASE(BARBS_HORDES, "HORDES", N_("Raging hordes"));
379 return NULL;
382 /****************************************************************************
383 Revealmap setting names accessor.
384 ****************************************************************************/
385 static const struct sset_val_name *revealmap_name(int bit)
387 switch (1 << bit) {
388 NAME_CASE(REVEAL_MAP_START, "START", N_("Reveal map at game start"));
389 NAME_CASE(REVEAL_MAP_DEAD, "DEAD", N_("Unfog map for dead players"));
391 return NULL;
394 /****************************************************************************
395 Airlifting style setting names accessor.
396 ****************************************************************************/
397 static const struct sset_val_name *airliftingstyle_name(int bit)
399 switch (1 << bit) {
400 NAME_CASE(AIRLIFTING_ALLIED_SRC, "FROM_ALLIES",
401 N_("Allows units to be airlifted from allied cities"));
402 NAME_CASE(AIRLIFTING_ALLIED_DEST, "TO_ALLIES",
403 N_("Allows units to be airlifted to allied cities"));
404 NAME_CASE(AIRLIFTING_UNLIMITED_SRC, "SRC_UNLIMITED",
405 N_("Unlimited units from source city"));
406 NAME_CASE(AIRLIFTING_UNLIMITED_DEST, "DEST_UNLIMITED",
407 N_("Unlimited units to destination city"));
409 return NULL;
412 /****************************************************************************
413 Phase mode names accessor.
414 ****************************************************************************/
415 static const struct sset_val_name *phasemode_name(int phasemode)
417 switch (phasemode) {
418 NAME_CASE(PMT_CONCURRENT, "ALL", N_("All players move concurrently"));
419 NAME_CASE(PMT_PLAYERS_ALTERNATE,
420 "PLAYER", N_("All players alternate movement"));
421 NAME_CASE(PMT_TEAMS_ALTERNATE, "TEAM", N_("Team alternate movement"));
423 return NULL;
426 /****************************************************************************
427 Savegame compress type names accessor.
428 ****************************************************************************/
429 static const struct sset_val_name *
430 compresstype_name(enum fz_method compresstype)
432 switch (compresstype) {
433 NAME_CASE(FZ_PLAIN, "PLAIN", N_("No compression"));
434 #ifdef HAVE_LIBZ
435 NAME_CASE(FZ_ZLIB, "LIBZ", N_("Using zlib (gzip format)"));
436 #endif
437 #ifdef HAVE_LIBBZ2
438 NAME_CASE(FZ_BZIP2, "BZIP2", N_("Using bzip2"));
439 #endif
440 #ifdef HAVE_LIBLZMA
441 NAME_CASE(FZ_XZ, "XZ", N_("Using xz"));
442 #endif
444 return NULL;
447 /****************************************************************************
448 Names accessor for boolean settings (disable/enable).
449 ****************************************************************************/
450 static const struct sset_val_name *bool_name(int enable)
452 switch (enable) {
453 NAME_CASE(FALSE, "DISABLED", N_("disabled"));
454 NAME_CASE(TRUE, "ENABLED", N_("enabled"));
456 return NULL;
459 #undef NAME_CASE
462 /*************************************************************************
463 Action callback functions.
464 *************************************************************************/
466 /*************************************************************************
467 (De)initialze the score log.
468 *************************************************************************/
469 static void scorelog_action(const struct setting *pset)
471 if (*pset->boolean.pvalue) {
472 log_civ_score_init();
473 } else {
474 log_civ_score_free();
478 /*************************************************************************
479 Create the selected number of AI's.
480 *************************************************************************/
481 static void aifill_action(const struct setting *pset)
483 aifill(*pset->integer.pvalue);
486 /*************************************************************************
487 Restrict to the selected nation set.
488 *************************************************************************/
489 static void nationset_action(const struct setting *pset)
491 /* If any player's existing selection is invalid, abort it */
492 players_iterate(pplayer) {
493 if (pplayer->nation != NULL) {
494 if (!nation_is_in_current_set(pplayer->nation)) {
495 (void) player_set_nation(pplayer, NO_NATION_SELECTED);
496 send_player_info_c(pplayer, game.est_connections);
499 } players_iterate_end;
500 count_playable_nations();
501 aifill(game.info.aifill);
503 /* There might now be too many players for the available nations.
504 * Rather than getting rid of some players arbitrarily, we let the
505 * situation persist for all already-connected players; the server
506 * will simply refuse to start until someone reduces the number of
507 * players. This policy also avoids annoyance if nationset is
508 * accidentally and transiently set to an unintended value.
509 * (However, new connections will start out detached.) */
510 if (normal_player_count() > server.playable_nations) {
511 notify_conn(NULL, NULL, E_SETTING, ftc_server, "%s",
512 _("Warning: not enough nations for all current players."));
515 send_nation_availability(game.est_connections, TRUE);
518 /*************************************************************************
519 Clear any user-set player colors in modes other than PLRCOL_PLR_SET.
520 *************************************************************************/
521 static void plrcol_action(const struct setting *pset)
523 if (!game_was_started()) {
524 if (read_enum_value(pset) != PLRCOL_PLR_SET) {
525 players_iterate(pplayer) {
526 server_player_set_color(pplayer, NULL);
527 } players_iterate_end;
529 /* Update clients with new color scheme. */
530 send_player_info_c(NULL, NULL);
534 /*************************************************************************
535 Toggle player AI status.
536 *************************************************************************/
537 static void autotoggle_action(const struct setting *pset)
539 if (*pset->boolean.pvalue) {
540 players_iterate(pplayer) {
541 if (!pplayer->ai_controlled && !pplayer->is_connected) {
542 toggle_ai_player_direct(NULL, pplayer);
543 send_player_info_c(pplayer, game.est_connections);
545 } players_iterate_end;
549 /*************************************************************************
550 Enact a change in the 'timeout' server setting immediately, if the game
551 is afoot.
552 *************************************************************************/
553 static void timeout_action(const struct setting *pset)
555 if (S_S_RUNNING == server_state()) {
556 int timeout = *pset->integer.pvalue;
557 /* This may cause the current turn to end immediately. */
558 game.info.seconds_to_phasedone = timeout;
559 send_game_info(NULL);
563 /*************************************************************************
564 Validation callback functions.
565 *************************************************************************/
567 /****************************************************************************
568 Verify the selected savename definition.
569 ****************************************************************************/
570 static bool savename_validate(const char *value, struct connection *caller,
571 char *reject_msg, size_t reject_msg_len)
573 char buf[MAX_LEN_PATH];
575 generate_save_name(value, buf, sizeof(buf), NULL);
577 if (!is_safe_filename(buf)) {
578 settings_snprintf(reject_msg, reject_msg_len,
579 _("Invalid save name definition: '%s' "
580 "(resolves to '%s')."), value, buf);
581 return FALSE;
584 return TRUE;
587 /****************************************************************************
588 Verify the value of the generator option (notably the MAPGEN_SCENARIO
589 case).
590 ****************************************************************************/
591 static bool generator_validate(int value, struct connection *caller,
592 char *reject_msg, size_t reject_msg_len)
594 if (map_is_empty()) {
595 if (MAPGEN_SCENARIO == value
596 && (NULL != caller || !game.scenario.is_scenario)) {
597 settings_snprintf(reject_msg, reject_msg_len,
598 _("You cannot disable the map generator."));
599 return FALSE;
601 return TRUE;
602 } else {
603 if (MAPGEN_SCENARIO != value) {
604 settings_snprintf(reject_msg, reject_msg_len,
605 _("You cannot require a map generator "
606 "when a map is loaded."));
607 return FALSE;
610 return TRUE;
613 /****************************************************************************
614 Verify the name for the score log file.
615 ****************************************************************************/
616 static bool scorefile_validate(const char *value, struct connection *caller,
617 char *reject_msg, size_t reject_msg_len)
619 if (!is_safe_filename(value)) {
620 settings_snprintf(reject_msg, reject_msg_len,
621 _("Invalid score name definition: '%s'."), value);
622 return FALSE;
625 return TRUE;
628 /*************************************************************************
629 Verify that a given demography string is valid. See
630 game.demography.
631 *************************************************************************/
632 static bool demography_callback(const char *value,
633 struct connection *caller,
634 char *reject_msg,
635 size_t reject_msg_len)
637 int error;
639 if (is_valid_demography(value, &error)) {
640 return TRUE;
641 } else {
642 settings_snprintf(reject_msg, reject_msg_len,
643 _("Demography string validation failed at character: "
644 "'%c'. Try \"help demography\"."), value[error]);
645 return FALSE;
649 /*************************************************************************
650 Verify that a given allowtake string is valid. See
651 game.allow_take.
652 *************************************************************************/
653 static bool allowtake_callback(const char *value,
654 struct connection *caller,
655 char *reject_msg,
656 size_t reject_msg_len)
658 int len = strlen(value), i;
659 bool havecharacter_state = FALSE;
661 /* We check each character individually to see if it's valid. This
662 * does not check for duplicate entries.
664 * We also track the state of the machine. havecharacter_state is
665 * true if the preceeding character was a primary label, e.g.
666 * NHhAadb. It is false if the preceeding character was a modifier
667 * or if this is the first character. */
669 for (i = 0; i < len; i++) {
670 /* Check to see if the character is a primary label. */
671 if (strchr("HhAadbOo", value[i])) {
672 havecharacter_state = TRUE;
673 continue;
676 /* If we've already passed a primary label, check to see if the
677 * character is a modifier. */
678 if (havecharacter_state && strchr("1234", value[i])) {
679 havecharacter_state = FALSE;
680 continue;
683 /* Looks like the character was invalid. */
684 settings_snprintf(reject_msg, reject_msg_len,
685 _("Allowed take string validation failed at "
686 "character: '%c'. Try \"help allowtake\"."),
687 value[i]);
688 return FALSE;
691 /* All characters were valid. */
692 return TRUE;
695 /*************************************************************************
696 Verify that a given startunits string is valid. See
697 game.server.start_units.
698 *************************************************************************/
699 static bool startunits_callback(const char *value,
700 struct connection *caller,
701 char *reject_msg,
702 size_t reject_msg_len)
704 int len = strlen(value), i;
706 /* We check each character individually to see if it's valid, and
707 * also make sure there is at least one city founder. */
709 for (i = 0; i < len; i++) {
710 /* TODO: add 'f' back in here when we can support ferry units */
711 if (strchr("cwxksdDaA", value[i])) {
712 continue;
715 /* Looks like the character was invalid. */
716 settings_snprintf(reject_msg, reject_msg_len,
717 _("Starting units string validation failed at "
718 "character '%c'. Try \"help startunits\"."),
719 value[i]);
720 return FALSE;
723 /* All characters were valid. */
724 return TRUE;
727 /*************************************************************************
728 Verify that a given endturn is valid.
729 *************************************************************************/
730 static bool endturn_callback(int value, struct connection *caller,
731 char *reject_msg, size_t reject_msg_len)
733 if (value < game.info.turn) {
734 /* Tried to set endturn earlier than current turn */
735 settings_snprintf(reject_msg, reject_msg_len,
736 _("Cannot set endturn earlier than current turn."));
737 return FALSE;
739 return TRUE;
742 /*************************************************************************
743 Verify that a given maxplayers string is valid.
744 *************************************************************************/
745 static bool maxplayers_callback(int value, struct connection *caller,
746 char *reject_msg, size_t reject_msg_len)
748 #ifdef GGZ_SERVER
749 if (with_ggz) {
750 /* In GGZ mode the maxplayers is the number of actual players - set
751 * when the game is lauched and not changed thereafter. This may be
752 * changed in future. */
753 settings_snprintf(reject_msg, reject_msg_len,
754 _("Cannot change maxplayers in GGZ mode."));
755 return FALSE;
757 #endif /* GGZ_SERVER */
758 if (value < player_count()) {
759 settings_snprintf(reject_msg, reject_msg_len,
760 _("Number of players (%d) is higher than requested "
761 "value (%d). Keeping old value."), player_count(),
762 value);
763 return FALSE;
765 /* If any start positions are defined by a scenario, we can only
766 * accommodate as many players as we have start positions. */
767 if (0 < map_startpos_count() && value > map_startpos_count()) {
768 settings_snprintf(reject_msg, reject_msg_len,
769 _("Requested value (%d) is greater than number of "
770 "available start positions (%d). Keeping old value."),
771 value, map_startpos_count());
772 return FALSE;
775 return TRUE;
778 /*************************************************************************
779 Validate the 'nationset' server setting.
780 *************************************************************************/
781 static bool nationset_callback(const char *value,
782 struct connection *caller,
783 char *reject_msg,
784 size_t reject_msg_len)
786 if (strlen(value) == 0) {
787 return TRUE;
788 } else if (nation_set_by_rule_name(value)) {
789 return TRUE;
790 } else {
791 settings_snprintf(reject_msg, reject_msg_len,
792 /* TRANS: do not translate 'list nationsets' */
793 _("Unknown nation set \"%s\". See '%slist nationsets' "
794 "for possible values."), value, caller ? "/" : "");
795 return FALSE;
799 /*************************************************************************
800 Validate the 'timeout' server setting.
801 *************************************************************************/
802 static bool timeout_callback(int value, struct connection *caller,
803 char *reject_msg, size_t reject_msg_len)
805 /* Disallow low timeout values for non-hack connections. */
806 if (caller && caller->access_level < ALLOW_HACK && value < 30) {
807 settings_snprintf(reject_msg, reject_msg_len,
808 _("You are not allowed to set timeout values less "
809 "than 30 seconds."));
810 return FALSE;
813 if (value == -1 && game.server.unitwaittime != 0) {
814 /* autogame only with 'unitwaittime' = 0 */
815 settings_snprintf(reject_msg, reject_msg_len,
816 /* TRANS: Do not translate setting names in ''. */
817 _("For autogames ('timeout' = -1) 'unitwaittime' "
818 "should be deactivated (= 0)."));
819 return FALSE;
822 if (value > 0 && value < game.server.unitwaittime * 3 / 2) {
823 /* for normal games 'timeout' should be at least 3/2 times the value
824 * of 'unitwaittime' */
825 settings_snprintf(reject_msg, reject_msg_len,
826 /* TRANS: Do not translate setting names in ''. */
827 _("'timeout' can not be lower than 3/2 of the "
828 "'unitwaittime' setting (= %d). Please change "
829 "'unitwaittime' first."), game.server.unitwaittime);
830 return FALSE;
833 return TRUE;
836 /*************************************************************************
837 Check 'timeout' setting if 'unitwaittime' is changed.
838 *************************************************************************/
839 static bool unitwaittime_callback(int value, struct connection *caller,
840 char *reject_msg, size_t reject_msg_len)
842 if (game.info.timeout == -1 && value != 0) {
843 settings_snprintf(reject_msg, reject_msg_len,
844 /* TRANS: Do not translate setting names in ''. */
845 _("For autogames ('timeout' = -1) 'unitwaittime' "
846 "should be deactivated (= 0)."));
847 return FALSE;
850 if (game.info.timeout > 0 && value > game.info.timeout * 2 / 3) {
851 settings_snprintf(reject_msg, reject_msg_len,
852 /* TRANS: Do not translate setting names in ''. */
853 _("'unitwaittime' has to be lower than 2/3 of the "
854 "'timeout' setting (= %d). Please change 'timeout' "
855 "first."), game.info.timeout);
856 return FALSE;
859 return TRUE;
862 /*************************************************************************
863 Topology setting validation callback.
864 *************************************************************************/
865 static bool mapsize_callback(int value, struct connection *caller,
866 char *reject_msg, size_t reject_msg_len)
868 if (value == MAPSIZE_XYSIZE && MAP_IS_ISOMETRIC &&
869 map.ysize % 2 != 0) {
870 /* An isometric map needs a even ysize. Is is calculated automatically
871 * for all settings but mapsize=XYSIZE. */
872 settings_snprintf(reject_msg, reject_msg_len,
873 _("For an isometric or hexagonal map the ysize must be "
874 "even."));
875 return FALSE;
878 return TRUE;
881 /*************************************************************************
882 xsize setting validation callback.
883 *************************************************************************/
884 static bool xsize_callback(int value, struct connection *caller,
885 char *reject_msg, size_t reject_msg_len)
887 int size = value * map.ysize;
889 if (size < MAP_MIN_SIZE * 1000) {
890 settings_snprintf(reject_msg, reject_msg_len,
891 _("The map size (%d * %d = %d) must be larger than "
892 "%d tiles."), value, map.ysize, size,
893 MAP_MIN_SIZE * 1000);
894 return FALSE;
895 } else if (size > MAP_MAX_SIZE * 1000) {
896 settings_snprintf(reject_msg, reject_msg_len,
897 _("The map size (%d * %d = %d) must be lower than "
898 "%d tiles."), value, map.ysize, size,
899 MAP_MAX_SIZE * 1000);
900 return FALSE;
903 return TRUE;
906 /*************************************************************************
907 ysize setting validation callback.
908 *************************************************************************/
909 static bool ysize_callback(int value, struct connection *caller,
910 char *reject_msg, size_t reject_msg_len)
912 int size = map.xsize * value;
914 if (size < MAP_MIN_SIZE * 1000) {
915 settings_snprintf(reject_msg, reject_msg_len,
916 _("The map size (%d * %d = %d) must be larger than "
917 "%d tiles."), map.xsize, value, size,
918 MAP_MIN_SIZE * 1000);
919 return FALSE;
920 } else if (size > MAP_MAX_SIZE * 1000) {
921 settings_snprintf(reject_msg, reject_msg_len,
922 _("The map size (%d * %d = %d) must be lower than "
923 "%d tiles."), map.xsize, value, size,
924 MAP_MAX_SIZE * 1000);
925 return FALSE;
926 } else if (map.server.mapsize == MAPSIZE_XYSIZE && MAP_IS_ISOMETRIC &&
927 value % 2 != 0) {
928 /* An isometric map needs a even ysize. Is is calculated automatically
929 * for all settings but mapsize=XYSIZE. */
930 settings_snprintf(reject_msg, reject_msg_len,
931 _("For an isometric or hexagonal map the ysize must be "
932 "even."));
933 return FALSE;
936 return TRUE;
939 /*************************************************************************
940 Topology setting validation callback.
941 *************************************************************************/
942 static bool topology_callback(unsigned value, struct connection *caller,
943 char *reject_msg, size_t reject_msg_len)
945 if (map.server.mapsize == MAPSIZE_XYSIZE &&
946 ((value & (TF_ISO)) != 0 || (value & (TF_HEX)) != 0) &&
947 map.ysize % 2 != 0) {
948 /* An isometric map needs a even ysize. Is is calculated automatically
949 * for all settings but mapsize=XYSIZE. */
950 settings_snprintf(reject_msg, reject_msg_len,
951 _("For an isometric or hexagonal map the ysize must be "
952 "even."));
953 return FALSE;
956 return TRUE;
959 /*************************************************************************
960 Validate that the player color mode can be used.
961 *************************************************************************/
962 static bool plrcol_validate(int value, struct connection *caller,
963 char *reject_msg, size_t reject_msg_len)
965 enum plrcolor_mode mode = value;
966 if (mode == PLRCOL_NATION_ORDER) {
967 nations_iterate(pnation) {
968 if (nation_color(pnation)) {
969 /* At least one nation has a color. Allow this mode. */
970 return TRUE;
972 } nations_iterate_end;
973 settings_snprintf(reject_msg, reject_msg_len,
974 _("No nations in the currently loaded ruleset have "
975 "associated colors."));
976 return FALSE;
978 return TRUE;
981 #define GEN_BOOL(name, value, sclass, scateg, slevel, to_client, \
982 short_help, extra_help, func_validate, func_action, \
983 _default) \
984 {name, sclass, to_client, short_help, extra_help, SSET_BOOL, \
985 scateg, slevel, \
986 {.boolean = {&value, _default, func_validate, bool_name, \
987 FALSE}}, func_action, FALSE},
989 #define GEN_INT(name, value, sclass, scateg, slevel, to_client, \
990 short_help, extra_help, func_validate, func_action, \
991 _min, _max, _default) \
992 {name, sclass, to_client, short_help, extra_help, SSET_INT, \
993 scateg, slevel, \
994 {.integer = {(int *) &value, _default, _min, _max, func_validate, \
995 0}}, \
996 func_action, FALSE},
998 #define GEN_STRING(name, value, sclass, scateg, slevel, to_client, \
999 short_help, extra_help, func_validate, func_action, \
1000 _default) \
1001 {name, sclass, to_client, short_help, extra_help, SSET_STRING, \
1002 scateg, slevel, \
1003 {.string = {value, _default, sizeof(value), func_validate, ""}}, \
1004 func_action, FALSE},
1006 #define GEN_ENUM(name, value, sclass, scateg, slevel, to_client, \
1007 short_help, extra_help, func_validate, func_action, \
1008 func_name, _default) \
1009 { name, sclass, to_client, short_help, extra_help, SSET_ENUM, \
1010 scateg, slevel, \
1011 { .enumerator = { &value, sizeof(value), _default, \
1012 func_validate, \
1013 (val_name_func_t) func_name, 0 }}, func_action, FALSE},
1015 #define GEN_BITWISE(name, value, sclass, scateg, slevel, to_client, \
1016 short_help, extra_help, func_validate, func_action, \
1017 func_name, _default) \
1018 { name, sclass, to_client, short_help, extra_help, SSET_BITWISE, \
1019 scateg, slevel, \
1020 { .bitwise = { (unsigned *) (void *) &value, _default, func_validate, \
1021 func_name, 0 }}, func_action, FALSE},
1023 /* game settings */
1024 static struct setting settings[] = {
1026 /* These should be grouped by sclass */
1028 /* Map size parameters: adjustable if we don't yet have a map */
1029 GEN_ENUM("mapsize", map.server.mapsize, SSET_MAP_SIZE,
1030 SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1031 N_("Map size definition"),
1032 /* TRANS: The strings between double quotes are also translated
1033 * separately (they must match!). The strings between single
1034 * quotes are setting names and shouldn't be translated. The
1035 * strings between parentheses and in uppercase must stay as
1036 * untranslated. */
1037 N_("Chooses the method used to define the map size. Other options "
1038 "specify the parameters for each method.\n"
1039 "- \"Number of tiles\" (FULLSIZE): Map area (option 'size').\n"
1040 "- \"Tiles per player\" (PLAYER): Number of (land) tiles per "
1041 "player (option 'tilesperplayer').\n"
1042 "- \"Width and height\" (XYSIZE): Map width and height in "
1043 "tiles (options 'xsize' and 'ysize')."),
1044 mapsize_callback, NULL, mapsize_name, MAP_DEFAULT_MAPSIZE)
1046 GEN_INT("size", map.server.size, SSET_MAP_SIZE,
1047 SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1048 N_("Map area (in thousands of tiles)"),
1049 /* TRANS: The strings between double quotes are also translated
1050 * separately (they must match!). The strings between single
1051 * quotes are setting names and shouldn't be translated. The
1052 * strings between parentheses and in uppercase must stay as
1053 * untranslated. */
1054 N_("This value is used to determine the map area.\n"
1055 " size = 4 is a normal map of 4,000 tiles (default)\n"
1056 " size = 20 is a huge map of 20,000 tiles\n"
1057 "For this option to take effect, the \"Map size definition\" "
1058 "option ('mapsize') must be set to \"Number of tiles\" "
1059 "(FULLSIZE)."), NULL, NULL,
1060 MAP_MIN_SIZE, MAP_MAX_SIZE, MAP_DEFAULT_SIZE)
1062 GEN_INT("tilesperplayer", map.server.tilesperplayer, SSET_MAP_SIZE,
1063 SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1064 N_("Number of (land) tiles per player"),
1065 /* TRANS: The strings between double quotes are also translated
1066 * separately (they must match!). The strings between single
1067 * quotes are setting names and shouldn't be translated. The
1068 * strings between parentheses and in uppercase must stay as
1069 * untranslated. */
1070 N_("This value is used to determine the map dimensions. It "
1071 "calculates the map size at game start based on the number "
1072 "of players and the value of the setting 'landmass'.\n"
1073 "For this option to take effect, the \"Map size definition\" "
1074 "option ('mapsize') must be set to \"Tiles per player\" "
1075 "(PLAYER)."),
1076 NULL, NULL, MAP_MIN_TILESPERPLAYER,
1077 MAP_MAX_TILESPERPLAYER, MAP_DEFAULT_TILESPERPLAYER)
1079 GEN_INT("xsize", map.xsize, SSET_MAP_SIZE,
1080 SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1081 N_("Map width in tiles"),
1082 /* TRANS: The strings between double quotes are also translated
1083 * separately (they must match!). The strings between single
1084 * quotes are setting names and shouldn't be translated. The
1085 * strings between parentheses and in uppercase must stay as
1086 * untranslated. */
1087 N_("Defines the map width.\n"
1088 "For this option to take effect, the \"Map size definition\" "
1089 "option ('mapsize') must be set to \"Width and height\" "
1090 "(XYSIZE)."),
1091 xsize_callback, NULL,
1092 MAP_MIN_LINEAR_SIZE, MAP_MAX_LINEAR_SIZE, MAP_DEFAULT_LINEAR_SIZE)
1093 GEN_INT("ysize", map.ysize, SSET_MAP_SIZE,
1094 SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1095 N_("Map height in tiles"),
1096 /* TRANS: The strings between double quotes are also translated
1097 * separately (they must match!). The strings between single
1098 * quotes are setting names and shouldn't be translated. The
1099 * strings between parentheses and in uppercase must stay as
1100 * untranslated. */
1101 N_("Defines the map height.\n"
1102 "For this option to take effect, the \"Map size definition\" "
1103 "option ('mapsize') must be set to \"Width and height\" "
1104 "(XYSIZE)."),
1105 ysize_callback, NULL,
1106 MAP_MIN_LINEAR_SIZE, MAP_MAX_LINEAR_SIZE, MAP_DEFAULT_LINEAR_SIZE)
1108 GEN_BITWISE("topology", map.topology_id, SSET_MAP_SIZE,
1109 SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1110 N_("Map topology index"),
1111 /* TRANS: do not edit the ugly ASCII art */
1112 N_("Freeciv maps are always two-dimensional. They may wrap at "
1113 "the north-south and east-west directions to form a flat "
1114 "map, a cylinder, or a torus (donut). Individual tiles may "
1115 "be rectangular or hexagonal, with either a classic or "
1116 "isometric alignment - this should be set based on the "
1117 "tileset being used.\n"
1118 "Classic rectangular: Isometric rectangular:\n"
1119 " _________ /\\/\\/\\/\\/\\\n"
1120 " |_|_|_|_|_| /\\/\\/\\/\\/\\/\n"
1121 " |_|_|_|_|_| \\/\\/\\/\\/\\/\\\n"
1122 " |_|_|_|_|_| /\\/\\/\\/\\/\\/\n"
1123 " \\/\\/\\/\\/\\/\n"
1124 "Hex tiles: Iso-hex:\n"
1125 " /\\/\\/\\/\\/\\/\\ _ _ _ _ _\n"
1126 " | | | | | | | / \\_/ \\_/ \\_/ \\_/ \\\n"
1127 " \\/\\/\\/\\/\\/\\/\\"
1128 " \\_/ \\_/ \\_/ \\_/ \\_/\n"
1129 " | | | | | | | / \\_/ \\_/ \\_/ \\_/ \\\n"
1130 " \\/\\/\\/\\/\\/\\/"
1131 " \\_/ \\_/ \\_/ \\_/ \\_/\n"),
1132 topology_callback, NULL, topology_name, MAP_DEFAULT_TOPO)
1134 GEN_ENUM("generator", map.server.generator,
1135 SSET_MAP_GEN, SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1136 N_("Method used to generate map"),
1137 /* TRANS: The strings between double quotes are also translated
1138 * separately (they must match!). The strings between single
1139 * quotes (except 'fair') are setting names and shouldn't be
1140 * translated. The strings between parentheses and in uppercase
1141 * must stay as untranslated. */
1142 N_("Specifies the algorithm used to generate the map. If the "
1143 "default value of the 'startpos' option is used, then the "
1144 "chosen generator chooses an appropriate 'startpos' setting; "
1145 "otherwise, the generated map tries to accommodate the "
1146 "chosen 'startpos' setting.\n"
1147 "- \"Scenario map\" (SCENARIO): indicates a pre-generated map. "
1148 "By default, if the scenario does not specify start positions, "
1149 "they will be allocated depending on the size of continents.\n"
1150 "- \"Fully random height\" (RANDOM): generates maps with a "
1151 "number of equally spaced, relatively small islands. By default, "
1152 "start positions are allocated depending on continent size.\n"
1153 "- \"Pseudo-fractal height\" (FRACTAL): generates Earthlike "
1154 "worlds with one or more large continents and a scattering of "
1155 "smaller islands. By default, players are all placed on a "
1156 "single continent.\n"
1157 "- \"Island-based\" (ISLAND): generates 'fair' maps with a "
1158 "number of similarly-sized and -shaped islands, each with "
1159 "approximately the same ratios of terrain types. By default, "
1160 "each player gets their own island.\n"
1161 "- \"Fair islands\" (FAIR): generates the exact copy of the "
1162 "same island for every player or every team.\n"
1163 "If the requested generator is incompatible with other server "
1164 "settings, the server may fall back to another generator."),
1165 generator_validate, NULL, generator_name, MAP_DEFAULT_GENERATOR)
1167 GEN_ENUM("startpos", map.server.startpos,
1168 SSET_MAP_GEN, SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1169 N_("Method used to choose start positions"),
1170 /* TRANS: The strings between double quotes are also translated
1171 * separately (they must match!). The strings between single
1172 * quotes (except 'best') are setting names and shouldn't be
1173 * translated. The strings between parentheses and in uppercase
1174 * must stay as untranslated. */
1175 N_("The method used to choose where each player's initial units "
1176 "start on the map. (For scenarios which include pre-set "
1177 "start positions, this setting is ignored.)\n"
1178 "- \"Generator's choice\" (DEFAULT): the start position "
1179 "placement will depend on the map generator chosen. See the "
1180 "'generator' setting.\n"
1181 "- \"One player per continent\" (SINGLE): one player is "
1182 "placed on each of a set of continents of approximately "
1183 "equivalent value (if possible).\n"
1184 "- \"Two or three players per continent\" (2or3): similar "
1185 "to SINGLE except that two players will be placed on each "
1186 "continent, with three on the 'best' continent if there is an "
1187 "odd number of players.\n"
1188 "- \"All players on a single continent\" (ALL): all players "
1189 "will start on the 'best' available continent.\n"
1190 "- \"Depending on size of continents\" (VARIABLE): players "
1191 "will be placed on the 'best' available continents such that, "
1192 "as far as possible, the number of players on each continent "
1193 "is proportional to its value.\n"
1194 "If the server cannot satisfy the requested setting due to "
1195 "there being too many players for continents, it may fall "
1196 "back to one of the others. (However, map generators try to "
1197 "create the right number of continents for the choice of this "
1198 "'startpos' setting and the number of players, so this is "
1199 "unlikely to occur.)"),
1200 NULL, NULL, startpos_name, MAP_DEFAULT_STARTPOS)
1202 GEN_ENUM("teamplacement", map.server.team_placement,
1203 SSET_MAP_GEN, SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1204 N_("Method used for placement of team mates"),
1205 /* TRANS: The strings between double quotes are also translated
1206 * separately (they must match!). The strings between single
1207 * quotes are setting names and shouldn't be translated. The
1208 * strings between parentheses and in uppercase must stay as
1209 * untranslated. */
1210 N_("After start positions have been generated thanks to the "
1211 "'startpos' setting, this setting controls how the start "
1212 "positions will be assigned to the different players of the "
1213 "same team.\n"
1214 "- \"Disabled\" (DISABLED): the start positions will be "
1215 "randomly assigned to players, regardless of teams.\n"
1216 "- \"As close as possible\" (CLOSEST): players will be "
1217 "placed as close as possible, regardless of continents.\n"
1218 "- \"On the same continent\" (CONTINENT): if possible, place "
1219 "all players of the same team onto the same "
1220 "island/continent.\n"
1221 "- \"Horizontal placement\" (HORIZONTAL): players of the same "
1222 "team will be placed horizontally.\n"
1223 "- \"Vertical placement\" (VERTICAL): players of the same "
1224 "team will be placed vertically."),
1225 NULL, NULL, teamplacement_name, MAP_DEFAULT_TEAM_PLACEMENT)
1227 GEN_BOOL("tinyisles", map.server.tinyisles,
1228 SSET_MAP_GEN, SSET_GEOLOGY, SSET_RARE, SSET_TO_CLIENT,
1229 N_("Presence of 1x1 islands"),
1230 N_("This setting controls whether the map generator is allowed "
1231 "to make islands of one only tile size."), NULL, NULL,
1232 MAP_DEFAULT_TINYISLES)
1234 GEN_BOOL("separatepoles", map.server.separatepoles,
1235 SSET_MAP_GEN, SSET_GEOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1236 N_("Whether the poles are separate continents"),
1237 N_("If this setting is disabled, the continents may attach to "
1238 "poles."), NULL, NULL, MAP_DEFAULT_SEPARATE_POLES)
1240 GEN_BOOL("alltemperate", map.server.alltemperate,
1241 SSET_MAP_GEN, SSET_GEOLOGY, SSET_RARE, SSET_TO_CLIENT,
1242 N_("All the map is temperate"),
1243 N_("If this setting is enabled, the temperature will be "
1244 "equivalent everywhere on the map. As a result, the "
1245 "poles won't be generated."),
1246 NULL, NULL, MAP_DEFAULT_ALLTEMPERATE)
1248 GEN_INT("temperature", map.server.temperature,
1249 SSET_MAP_GEN, SSET_GEOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1250 N_("Average temperature of the planet"),
1251 N_("Small values will give a cold map, while larger values will "
1252 "give a hotter map.\n"
1253 "\n"
1254 "100 means a very dry and hot planet with no polar arctic "
1255 "zones, only tropical and dry zones.\n"
1256 " 70 means a hot planet with little polar ice.\n"
1257 " 50 means a temperate planet with normal polar, cold, "
1258 "temperate, and tropical zones; a desert zone overlaps "
1259 "tropical and temperate zones.\n"
1260 " 30 means a cold planet with small tropical zones.\n"
1261 " 0 means a very cold planet with large polar zones and no "
1262 "tropics."),
1263 NULL, NULL,
1264 MAP_MIN_TEMPERATURE, MAP_MAX_TEMPERATURE, MAP_DEFAULT_TEMPERATURE)
1266 GEN_INT("landmass", map.server.landpercent,
1267 SSET_MAP_GEN, SSET_GEOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1268 N_("Percentage of the map that is land"),
1269 N_("This setting gives the approximate percentage of the map "
1270 "that will be made into land."), NULL, NULL,
1271 MAP_MIN_LANDMASS, MAP_MAX_LANDMASS, MAP_DEFAULT_LANDMASS)
1273 GEN_INT("steepness", map.server.steepness,
1274 SSET_MAP_GEN, SSET_GEOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1275 N_("Amount of hills/mountains"),
1276 N_("Small values give flat maps, while higher values give a "
1277 "steeper map with more hills and mountains."), NULL, NULL,
1278 MAP_MIN_STEEPNESS, MAP_MAX_STEEPNESS, MAP_DEFAULT_STEEPNESS)
1280 GEN_INT("wetness", map.server.wetness,
1281 SSET_MAP_GEN, SSET_GEOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1282 N_("Amount of water on landmasses"),
1283 N_("Small values mean lots of dry, desert-like land; "
1284 "higher values give a wetter map with more swamps, "
1285 "jungles, and rivers."), NULL, NULL,
1286 MAP_MIN_WETNESS, MAP_MAX_WETNESS, MAP_DEFAULT_WETNESS)
1288 GEN_BOOL("globalwarming", game.info.global_warming,
1289 SSET_RULES, SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1290 N_("Global warming"),
1291 N_("If turned off, global warming will not occur "
1292 "as a result of pollution. This setting does not "
1293 "affect pollution."), NULL, NULL,
1294 GAME_DEFAULT_GLOBAL_WARMING)
1296 GEN_BOOL("nuclearwinter", game.info.nuclear_winter,
1297 SSET_RULES, SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1298 N_("Nuclear winter"),
1299 N_("If turned off, nuclear winter will not occur "
1300 "as a result of nuclear war."), NULL, NULL,
1301 GAME_DEFAULT_NUCLEAR_WINTER)
1303 GEN_INT("mapseed", map.server.seed,
1304 SSET_MAP_GEN, SSET_INTERNAL, SSET_RARE, SSET_SERVER_ONLY,
1305 N_("Map generation random seed"),
1306 N_("The same seed will always produce the same map; "
1307 "for zero (the default) a seed will be chosen based on "
1308 "the time to give a random map. This setting is usually "
1309 "only of interest while debugging the game."), NULL, NULL,
1310 MAP_MIN_SEED, MAP_MAX_SEED, MAP_DEFAULT_SEED)
1312 /* Map additional stuff: huts and specials. gameseed also goes here
1313 * because huts and specials are the first time the gameseed gets used (?)
1314 * These are done when the game starts, so these are historical and
1315 * fixed after the game has started.
1317 GEN_INT("gameseed", game.server.seed,
1318 SSET_MAP_ADD, SSET_INTERNAL, SSET_RARE, SSET_SERVER_ONLY,
1319 N_("Game random seed"),
1320 N_("For zero (the default) a seed will be chosen based "
1321 "on the current time. This setting is usually "
1322 "only of interest while debugging the game."), NULL, NULL,
1323 GAME_MIN_SEED, GAME_MAX_SEED, GAME_DEFAULT_SEED)
1325 GEN_INT("specials", map.server.riches,
1326 SSET_MAP_ADD, SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1327 N_("Amount of \"special\" resource tiles"),
1328 N_("Special resources improve the basic terrain type they "
1329 "are on. The server variable's scale is parts per "
1330 "thousand."), NULL, NULL,
1331 MAP_MIN_RICHES, MAP_MAX_RICHES, MAP_DEFAULT_RICHES)
1333 GEN_INT("huts", map.server.huts,
1334 SSET_MAP_ADD, SSET_GEOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1335 N_("Amount of huts (minor tribe villages)"),
1336 N_("This setting gives the exact number of huts that will be "
1337 "placed on the entire map. Huts are small tribal villages "
1338 "that may be investigated by units."), NULL, NULL,
1339 MAP_MIN_HUTS, MAP_MAX_HUTS, MAP_DEFAULT_HUTS)
1341 /* Options affecting numbers of players and AI players. These only
1342 * affect the start of the game and can not be adjusted after that.
1344 GEN_INT("minplayers", game.server.min_players,
1345 SSET_PLAYERS, SSET_INTERNAL, SSET_VITAL,
1346 SSET_TO_CLIENT,
1347 N_("Minimum number of players"),
1348 N_("There must be at least this many players (connected "
1349 "human players) before the game can start."),
1350 NULL, NULL,
1351 GAME_MIN_MIN_PLAYERS, GAME_MAX_MIN_PLAYERS, GAME_DEFAULT_MIN_PLAYERS)
1353 GEN_INT("maxplayers", game.server.max_players,
1354 SSET_PLAYERS, SSET_INTERNAL, SSET_VITAL, SSET_TO_CLIENT,
1355 N_("Maximum number of players"),
1356 N_("The maximal number of human and AI players who can be in "
1357 "the game. When this number of players are connected in "
1358 "the pregame state, any new players who try to connect "
1359 "will be rejected.\n"
1360 "When playing a scenario which defines player start positions, "
1361 "this setting cannot be set to greater than the number of "
1362 "defined start positions."),
1363 maxplayers_callback, NULL,
1364 GAME_MIN_MAX_PLAYERS, GAME_MAX_MAX_PLAYERS, GAME_DEFAULT_MAX_PLAYERS)
1366 GEN_INT("aifill", game.info.aifill,
1367 SSET_PLAYERS, SSET_INTERNAL, SSET_VITAL, SSET_TO_CLIENT,
1368 N_("Limited number of AI players"),
1369 N_("If set to a positive value, then AI players will be "
1370 "automatically created or removed to keep the total "
1371 "number of players at this amount. As more players join, "
1372 "these AI players will be replaced. When set to zero, "
1373 "all AI players will be removed."), NULL,
1374 aifill_action, GAME_MIN_AIFILL, GAME_MAX_AIFILL,
1375 GAME_DEFAULT_AIFILL)
1377 GEN_STRING("nationset", game.server.nationset,
1378 SSET_PLAYERS, SSET_INTERNAL, SSET_RARE, SSET_TO_CLIENT,
1379 N_("Set of nations to choose from"),
1380 /* TRANS: do not translate '/list nationsets' */
1381 N_("Controls the set of nations allowed in the game. The "
1382 "choices are defined by the ruleset.\n"
1383 "Only nations in the set selected here will be allowed in "
1384 "any circumstances, including new players and civil war; "
1385 "small sets may thus limit the number of players in a game.\n"
1386 "If this is left blank, the ruleset's default nation set is "
1387 "used.\n"
1388 "See '/list nationsets' for possible choices for the "
1389 "currently loaded ruleset."),
1390 nationset_callback, nationset_action, GAME_DEFAULT_NATIONSET)
1392 GEN_INT("ec_turns", game.server.event_cache.turns,
1393 SSET_RULES_FLEXIBLE, SSET_INTERNAL, SSET_SITUATIONAL,
1394 SSET_TO_CLIENT,
1395 N_("Event cache for this number of turns"),
1396 N_("Event messages are saved for this number of turns. A value of "
1397 "0 deactivates the event cache."),
1398 NULL, NULL, GAME_MIN_EVENT_CACHE_TURNS, GAME_MAX_EVENT_CACHE_TURNS,
1399 GAME_DEFAULT_EVENT_CACHE_TURNS)
1401 GEN_INT("ec_max_size", game.server.event_cache.max_size,
1402 SSET_RULES_FLEXIBLE, SSET_INTERNAL, SSET_SITUATIONAL,
1403 SSET_TO_CLIENT,
1404 N_("Size of the event cache"),
1405 N_("This defines the maximal number of events in the event cache."),
1406 NULL, NULL, GAME_MIN_EVENT_CACHE_MAX_SIZE,
1407 GAME_MAX_EVENT_CACHE_MAX_SIZE, GAME_DEFAULT_EVENT_CACHE_MAX_SIZE)
1409 GEN_BOOL("ec_chat", game.server.event_cache.chat,
1410 SSET_RULES_FLEXIBLE, SSET_INTERNAL, SSET_SITUATIONAL,
1411 SSET_TO_CLIENT,
1412 N_("Save chat messages in the event cache"),
1413 N_("If turned on, chat messages will be saved in the event "
1414 "cache."), NULL, NULL, GAME_DEFAULT_EVENT_CACHE_CHAT)
1416 GEN_BOOL("ec_info", game.server.event_cache.info,
1417 SSET_RULES_FLEXIBLE, SSET_INTERNAL, SSET_SITUATIONAL, SSET_TO_CLIENT,
1418 N_("Print turn and time for each cached event"),
1419 /* TRANS: Don't translate the text between single quotes. */
1420 N_("If turned on, all cached events will be marked by the turn "
1421 "and time of the event like '(T2 - 15:29:52)'."),
1422 NULL, NULL, GAME_DEFAULT_EVENT_CACHE_INFO)
1424 /* Game initialization parameters (only affect the first start of the game,
1425 * and not reloads). Can not be changed after first start of game.
1427 /* TODO: Add this line back when we can support Ferry units */
1428 /* " f = Ferryboat (eg., Trireme)\n" */
1429 GEN_STRING("startunits", game.server.start_units,
1430 SSET_GAME_INIT, SSET_SOCIOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1431 N_("List of players' initial units"),
1432 N_("This should be a string of characters, each of which "
1433 "specifies a unit role. There must be at least one city "
1434 "founder in the string. The characters and their "
1435 "meanings are:\n"
1436 " c = City founder (eg., Settlers)\n"
1437 " w = Terrain worker (eg., Engineers)\n"
1438 " x = Explorer (eg., Explorer)\n"
1439 " k = Gameloss (eg., King)\n"
1440 " s = Diplomat (eg., Diplomat)\n"
1441 " d = Ok defense unit (eg., Warriors)\n"
1442 " D = Good defense unit (eg., Phalanx)\n"
1443 " a = Fast attack unit (eg., Horsemen)\n"
1444 " A = Strong attack unit (eg., Catapult)\n"),
1445 startunits_callback, NULL, GAME_DEFAULT_START_UNITS)
1447 GEN_BOOL("startcity", game.server.start_city,
1448 SSET_GAME_INIT, SSET_SOCIOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1449 N_("Whether player starts with a city"),
1450 N_("If this is set, game will start with player's first "
1451 "city already founded to starting location."),
1452 NULL, NULL, GAME_DEFAULT_START_CITY)
1454 GEN_INT("dispersion", game.server.dispersion,
1455 SSET_GAME_INIT, SSET_SOCIOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1456 N_("Area where initial units are located"),
1457 N_("This is the radius within "
1458 "which the initial units are dispersed."), NULL, NULL,
1459 GAME_MIN_DISPERSION, GAME_MAX_DISPERSION, GAME_DEFAULT_DISPERSION)
1461 GEN_INT("gold", game.info.gold,
1462 SSET_GAME_INIT, SSET_ECONOMICS, SSET_VITAL, SSET_TO_CLIENT,
1463 N_("Starting gold per player"),
1464 N_("At the beginning of the game, each player is given this "
1465 "much gold."), NULL, NULL,
1466 GAME_MIN_GOLD, GAME_MAX_GOLD, GAME_DEFAULT_GOLD)
1468 GEN_INT("techlevel", game.info.tech,
1469 SSET_GAME_INIT, SSET_SCIENCE, SSET_VITAL, SSET_TO_CLIENT,
1470 N_("Number of initial techs per player"),
1471 /* TRANS: The string between single quotes is a setting name and
1472 * should not be translated. */
1473 N_("At the beginning of the game, each player is given this "
1474 "many technologies. The technologies chosen are random for "
1475 "each player. Depending on the value of tech_cost_style in "
1476 "the ruleset, a big value for 'techlevel' can make the next "
1477 "techs really expensive."), NULL, NULL,
1478 GAME_MIN_TECHLEVEL, GAME_MAX_TECHLEVEL, GAME_DEFAULT_TECHLEVEL)
1480 GEN_INT("sciencebox", game.info.sciencebox,
1481 SSET_RULES, SSET_SCIENCE, SSET_SITUATIONAL, SSET_TO_CLIENT,
1482 N_("Technology cost multiplier percentage"),
1483 N_("This affects how quickly players can research new "
1484 "technology. All tech costs are multiplied by this amount "
1485 "(as a percentage). The base tech costs are determined by "
1486 "the ruleset or other game settings."),
1487 NULL, NULL, GAME_MIN_SCIENCEBOX, GAME_MAX_SCIENCEBOX,
1488 GAME_DEFAULT_SCIENCEBOX)
1490 GEN_INT("techpenalty", game.server.techpenalty,
1491 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1492 N_("Percentage penalty when changing tech"),
1493 N_("If you change your current research technology, and you have "
1494 "positive research points, you lose this percentage of those "
1495 "research points. This does not apply when you have just gained "
1496 "a technology this turn."), NULL, NULL,
1497 GAME_MIN_TECHPENALTY, GAME_MAX_TECHPENALTY,
1498 GAME_DEFAULT_TECHPENALTY)
1500 GEN_INT("techlost_recv", game.server.techlost_recv,
1501 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1502 N_("Chance to lose an invention while receiving it"),
1503 N_("If you receive an invention via a treaty, this setting "
1504 "defines the chance that the invention is lost during the "
1505 "transfer."),
1506 NULL, NULL, GAME_MIN_TECHLOST_RECV, GAME_MAX_TECHLOST_RECV,
1507 GAME_DEFAULT_TECHLOST_RECV)
1509 GEN_INT("techlost_donor", game.server.techlost_donor,
1510 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1511 N_("Chance to lose an invention while giving it"),
1512 N_("If you give an invention via a treaty, this setting "
1513 "defines the chance that the invention is lost for your "
1514 "civilization during the transfer."),
1515 NULL, NULL, GAME_MIN_TECHLOST_DONOR, GAME_MAX_TECHLOST_DONOR,
1516 GAME_DEFAULT_TECHLOST_DONOR)
1518 GEN_BOOL("team_pooled_research", game.info.team_pooled_research,
1519 SSET_RULES, SSET_SCIENCE, SSET_VITAL, SSET_TO_CLIENT,
1520 N_("Team pooled research"),
1521 N_("If this setting is turned on, then the team mates will share "
1522 "the science research. Else, every player of the team will "
1523 "have to make its own."),
1524 NULL, NULL, GAME_DEFAULT_TEAM_POOLED_RESEARCH)
1526 GEN_INT("diplcost", game.server.diplcost,
1527 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1528 N_("Penalty when getting tech or gold from treaty"),
1529 N_("For each technology you gain from a diplomatic treaty, you "
1530 "lose research points equal to this percentage of the cost to "
1531 "research a new technology. If this is non-zero, you can end up "
1532 "with negative research points. Also applies to gold "
1533 "transfers in diplomatic treaties."),
1534 NULL, NULL,
1535 GAME_MIN_DIPLCOST, GAME_MAX_DIPLCOST, GAME_DEFAULT_DIPLCOST)
1537 GEN_INT("conquercost", game.server.conquercost,
1538 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1539 N_("Penalty when getting tech from conquering"),
1540 N_("For each technology you gain by conquering an enemy city, you "
1541 "lose research points equal to this percentage of the cost to "
1542 "research a new technology. If this is non-zero, you can end up "
1543 "with negative research points."),
1544 NULL, NULL,
1545 GAME_MIN_CONQUERCOST, GAME_MAX_CONQUERCOST,
1546 GAME_DEFAULT_CONQUERCOST)
1548 GEN_INT("freecost", game.server.freecost,
1549 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1550 N_("Penalty when getting a free tech"),
1551 /* TRANS: The strings between single quotes are setting names and
1552 * shouldn't be translated. */
1553 N_("For each technology you gain \"for free\" (other than "
1554 "covered by 'diplcost' or 'conquercost': for instance, from huts "
1555 "or from Great Library effects), you lose research points "
1556 "equal to this percentage of the cost to research a new "
1557 "technology. If this is non-zero, you can end up "
1558 "with negative research points."),
1559 NULL, NULL,
1560 GAME_MIN_FREECOST, GAME_MAX_FREECOST, GAME_DEFAULT_FREECOST)
1562 GEN_INT("techlossforgiveness", game.server.techloss_forgiveness,
1563 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1564 N_("Research point debt threshold for losing tech"),
1565 N_("When you have negative research points, and your shortfall is "
1566 "greater than this percentage of the cost of your current "
1567 "research, you forget a technology you already knew.\n"
1568 "The special value -1 prevents loss of technology regardless of "
1569 "research points."),
1570 NULL, NULL,
1571 GAME_MIN_TECHLOSSFG, GAME_MAX_TECHLOSSFG,
1572 GAME_DEFAULT_TECHLOSSFG)
1574 GEN_INT("techlossrestore", game.server.techloss_restore,
1575 SSET_RULES, SSET_SCIENCE, SSET_RARE, SSET_TO_CLIENT,
1576 N_("Research points restored after losing a tech"),
1577 N_("When you lose a technology due to a negative research balance "
1578 "(see 'techlossforgiveness'), this percentage of its research "
1579 "cost is credited to your research balance (this may not be "
1580 "sufficient to make it positive).\n"
1581 "The special value -1 means that your research balance is always "
1582 "restored to zero, regardless of your previous shortfall."),
1583 NULL, NULL,
1584 GAME_MIN_TECHLOSSREST, GAME_MAX_TECHLOSSREST,
1585 GAME_DEFAULT_TECHLOSSREST)
1587 GEN_INT("foodbox", game.info.foodbox,
1588 SSET_RULES, SSET_ECONOMICS, SSET_SITUATIONAL, SSET_TO_CLIENT,
1589 N_("Food required for a city to grow"),
1590 N_("This is the base amount of food required to grow a city. "
1591 "This value is multiplied by another factor that comes from "
1592 "the ruleset and is dependent on the size of the city."),
1593 NULL, NULL,
1594 GAME_MIN_FOODBOX, GAME_MAX_FOODBOX, GAME_DEFAULT_FOODBOX)
1596 GEN_INT("aqueductloss", game.server.aqueductloss,
1597 SSET_RULES, SSET_ECONOMICS, SSET_RARE, SSET_TO_CLIENT,
1598 N_("Percentage food lost when building needed"),
1599 N_("If a city would expand, but it can't because it needs "
1600 "an Aqueduct (or Sewer System), it loses this percentage "
1601 "of its foodbox (or half that amount when it has a "
1602 "Granary)."), NULL, NULL,
1603 GAME_MIN_AQUEDUCTLOSS, GAME_MAX_AQUEDUCTLOSS,
1604 GAME_DEFAULT_AQUEDUCTLOSS)
1606 GEN_INT("shieldbox", game.info.shieldbox,
1607 SSET_RULES, SSET_ECONOMICS, SSET_SITUATIONAL, SSET_TO_CLIENT,
1608 N_("Multiplier percentage for production costs"),
1609 N_("This affects how quickly units and buildings can be "
1610 "produced. The base costs are multiplied by this value (as "
1611 "a percentage)."),
1612 NULL, NULL, GAME_MIN_SHIELDBOX, GAME_MAX_SHIELDBOX,
1613 GAME_DEFAULT_SHIELDBOX)
1615 /* Notradesize and fulltradesize used to have callbacks to prevent them
1616 * from being set illegally (notradesize > fulltradesize). However this
1617 * provided a problem when setting them both through the client's settings
1618 * dialog, since they cannot both be set atomically. So the callbacks were
1619 * removed and instead the game now knows how to deal with invalid
1620 * settings. */
1621 GEN_INT("fulltradesize", game.info.fulltradesize,
1622 SSET_RULES, SSET_ECONOMICS, SSET_RARE, SSET_TO_CLIENT,
1623 N_("Minimum city size to get full trade"),
1624 /* TRANS: The strings between single quotes are setting names and
1625 * shouldn't be translated. */
1626 N_("There is a trade penalty in all cities smaller than this. "
1627 "The penalty is 100% (no trade at all) for sizes up to "
1628 "'notradesize', and decreases gradually to 0% (no penalty "
1629 "except the normal corruption) for size='fulltradesize'. "
1630 "See also 'notradesize'."), NULL, NULL,
1631 GAME_MIN_FULLTRADESIZE, GAME_MAX_FULLTRADESIZE,
1632 GAME_DEFAULT_FULLTRADESIZE)
1634 GEN_INT("notradesize", game.info.notradesize,
1635 SSET_RULES, SSET_ECONOMICS, SSET_RARE, SSET_TO_CLIENT,
1636 N_("Maximum size of a city without trade"),
1637 /* TRANS: The strings between single quotes are setting names and
1638 * shouldn't be translated. */
1639 N_("Cities do not produce any trade at all unless their size "
1640 "is larger than this amount. The produced trade increases "
1641 "gradually for cities larger than 'notradesize' and smaller "
1642 "than 'fulltradesize'. See also 'fulltradesize'."), NULL, NULL,
1643 GAME_MIN_NOTRADESIZE, GAME_MAX_NOTRADESIZE,
1644 GAME_DEFAULT_NOTRADESIZE)
1646 GEN_INT("citymindist", game.info.citymindist,
1647 SSET_RULES, SSET_SOCIOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1648 N_("Minimum distance between cities"),
1649 N_("When a player attempts to found a new city, it is prevented "
1650 "if the distance from any existing city is less than this "
1651 "setting. For example, when this setting is 3, there must be "
1652 "at least two clear tiles in any direction between all existing "
1653 "cities and the new city site. A value of 1 removes any such "
1654 "restriction on city placement."),
1655 NULL, NULL,
1656 GAME_MIN_CITYMINDIST, GAME_MAX_CITYMINDIST,
1657 GAME_DEFAULT_CITYMINDIST)
1659 GEN_BOOL("trading_tech", game.info.trading_tech,
1660 SSET_RULES, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
1661 N_("Technology trading"),
1662 N_("If turned off, trading technologies in the diplomacy dialog "
1663 "is not allowed."), NULL, NULL,
1664 GAME_DEFAULT_TRADING_TECH)
1666 GEN_BOOL("trading_gold", game.info.trading_gold,
1667 SSET_RULES, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
1668 N_("Gold trading"),
1669 N_("If turned off, trading gold in the diplomacy dialog "
1670 "is not allowed."), NULL, NULL,
1671 GAME_DEFAULT_TRADING_GOLD)
1673 GEN_BOOL("trading_city", game.info.trading_city,
1674 SSET_RULES, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
1675 N_("City trading"),
1676 N_("If turned off, trading cities in the diplomacy dialog "
1677 "is not allowed."), NULL, NULL,
1678 GAME_DEFAULT_TRADING_CITY)
1680 GEN_INT("trademindist", game.info.trademindist,
1681 SSET_RULES, SSET_ECONOMICS, SSET_RARE, SSET_TO_CLIENT,
1682 N_("Minimum distance for trade routes"),
1683 N_("In order for two cities in the same civilization to establish "
1684 "a trade route, they must be at least this far apart on the "
1685 "map. For square grids, the distance is calculated as "
1686 "\"Manhattan distance\", that is, the sum of the displacements "
1687 "along the x and y directions."), NULL, NULL,
1688 GAME_MIN_TRADEMINDIST, GAME_MAX_TRADEMINDIST,
1689 GAME_DEFAULT_TRADEMINDIST)
1691 GEN_INT("rapturedelay", game.info.rapturedelay,
1692 SSET_RULES, SSET_SOCIOLOGY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1693 N_("Number of turns between rapture effect"),
1694 N_("Sets the number of turns between rapture growth of a city. "
1695 "If set to n a city will grow after celebrating for n+1 "
1696 "turns."),
1697 NULL, NULL,
1698 GAME_MIN_RAPTUREDELAY, GAME_MAX_RAPTUREDELAY,
1699 GAME_DEFAULT_RAPTUREDELAY)
1701 GEN_INT("disasters", game.info.disasters,
1702 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_VITAL, SSET_TO_CLIENT,
1703 N_("Frequency of disasters"),
1704 N_("Sets frequency of disasters occurring to cities."),
1705 NULL, NULL,
1706 GAME_MIN_DISASTERS, GAME_MAX_DISASTERS,
1707 GAME_DEFAULT_DISASTERS)
1709 GEN_INT("razechance", game.server.razechance,
1710 SSET_RULES, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1711 N_("Chance for conquered building destruction"),
1712 N_("When a player conquers a city, each city improvement has this "
1713 "percentage chance to be destroyed."), NULL, NULL,
1714 GAME_MIN_RAZECHANCE, GAME_MAX_RAZECHANCE, GAME_DEFAULT_RAZECHANCE)
1716 GEN_INT("occupychance", game.server.occupychance,
1717 SSET_RULES, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1718 N_("Chance of moving into tile after attack"),
1719 N_("If set to 0, combat is Civ1/2-style (when you attack, "
1720 "you remain in place). If set to 100, attacking units "
1721 "will always move into the tile they attacked when they win "
1722 "the combat (and no enemy units remain in the tile). If "
1723 "set to a value between 0 and 100, this will be used as "
1724 "the percent chance of \"occupying\" territory."), NULL, NULL,
1725 GAME_MIN_OCCUPYCHANCE, GAME_MAX_OCCUPYCHANCE,
1726 GAME_DEFAULT_OCCUPYCHANCE)
1728 GEN_BOOL("autoattack", game.server.autoattack, SSET_RULES_FLEXIBLE, SSET_MILITARY,
1729 SSET_SITUATIONAL, SSET_TO_CLIENT,
1730 N_("Turn on/off server-side autoattack"),
1731 N_("If set to on, units with moves left will automatically "
1732 "consider attacking enemy units that move adjacent to them."),
1733 NULL, NULL, GAME_DEFAULT_AUTOATTACK)
1735 GEN_BOOL("killstack", game.info.killstack, SSET_RULES, SSET_MILITARY,
1736 SSET_RARE, SSET_TO_CLIENT,
1737 N_("Do all units in tile die with defender"),
1738 N_("If this is enabled, each time a defender unit loses in combat, "
1739 "and is not inside a city or suitable base, all units in the same "
1740 "tile are destroyed along with the defender. If this is disabled, "
1741 "only the defender unit is destroyed."),
1742 NULL, NULL, GAME_DEFAULT_KILLSTACK)
1744 GEN_BOOL("killcitizen", game.info.killcitizen,
1745 SSET_RULES, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1746 N_("Reduce city population after attack"),
1747 N_("This flag indicates whether a city's population is reduced "
1748 "after a successful attack by an enemy unit. If this is "
1749 "disabled, population is never reduced. Even when this is "
1750 "enabled, only some units may kill citizens."),
1751 NULL, NULL, GAME_DEFAULT_KILLCITIZEN)
1753 GEN_INT("killunhomed", game.server.killunhomed,
1754 SSET_RULES, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1755 N_("Slowly kill units without home cities (e.g., starting units)"),
1756 N_("If greater than 0, then every unit without a homecity will "
1757 "lose hitpoints each turn. The number of hitpoints lost is "
1758 "given by 'killunhomed' percent of the hitpoints of the unit "
1759 "type. At least one hitpoint is lost every turn until the "
1760 "death of the unit."),
1761 NULL, NULL, GAME_MIN_KILLUNHOMED, GAME_MAX_KILLUNHOMED,
1762 GAME_DEFAULT_KILLUNHOMED)
1764 GEN_ENUM("borders", game.info.borders,
1765 SSET_RULES, SSET_MILITARY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1766 N_("National borders"),
1767 N_("If this is not disabled, then any land tiles around a "
1768 "fortress or city will be owned by that nation."),
1769 NULL, NULL, borders_name, GAME_DEFAULT_BORDERS)
1771 GEN_BOOL("happyborders", game.info.happyborders,
1772 SSET_RULES, SSET_MILITARY, SSET_SITUATIONAL,
1773 SSET_TO_CLIENT,
1774 N_("Units inside borders cause no unhappiness"),
1775 N_("If this is set, units will not cause unhappiness when "
1776 "inside your own borders."), NULL, NULL,
1777 GAME_DEFAULT_HAPPYBORDERS)
1779 GEN_ENUM("diplomacy", game.info.diplomacy,
1780 SSET_RULES, SSET_MILITARY, SSET_SITUATIONAL, SSET_TO_CLIENT,
1781 N_("Ability to do diplomacy with other players"),
1782 N_("This setting controls the ability to do diplomacy with "
1783 "other players."),
1784 NULL, NULL, diplomacy_name, GAME_DEFAULT_DIPLOMACY)
1786 GEN_ENUM("citynames", game.server.allowed_city_names,
1787 SSET_RULES, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
1788 N_("Allowed city names"),
1789 /* TRANS: The strings between double quotes are also translated
1790 * separately (they must match!). The strings between parentheses
1791 * and in uppercase must not be translated. */
1792 N_("- \"No restrictions\" (NO_RESTRICTIONS): players can have "
1793 "multiple cities with the same names.\n"
1794 "- \"Unique to a player\" (PLAYER_UNIQUE): one player can't "
1795 "have multiple cities with the same name.\n"
1796 "- \"Globally unique\" (GLOBAL_UNIQUE): all cities in a game "
1797 "have to have different names.\n"
1798 "- \"No city name stealing\" (NO_STEALING): like "
1799 "\"Globally unique\", but a player isn't allowed to use a "
1800 "default city name of another nation unless it is a default "
1801 "for their nation also."),
1802 NULL, NULL, citynames_name, GAME_DEFAULT_ALLOWED_CITY_NAMES)
1804 GEN_ENUM("plrcolormode", game.server.plrcolormode,
1805 SSET_RULES, SSET_INTERNAL, SSET_RARE, SSET_TO_CLIENT,
1806 N_("How to pick player colors"),
1807 /* TRANS: The strings between double quotes are also translated
1808 * separately (they must match!). The strings between single quotes
1809 * are setting names and shouldn't be translated. The strings
1810 * between parentheses and in uppercase must not be translated. */
1811 N_("This setting determines how player colors are chosen. Player "
1812 "colors are used in the Nations report, for national borders on "
1813 "the map, and so on.\n"
1814 "- \"Per-player, in order\" (PLR_ORDER): colors are assigned to "
1815 "individual players in order from a list defined by the "
1816 "ruleset.\n"
1817 "- \"Per-player, random\" (PLR_RANDOM): colors are assigned "
1818 "to invididual players randomly from the set defined by the "
1819 "ruleset.\n"
1820 "- \"Set manually\" (PLR_SET): colors can be set with the "
1821 "'playercolor' command before the game starts; these are not "
1822 "restricted to the ruleset colors. Any players for which no "
1823 "color is set when the game starts get a random color from the "
1824 "ruleset.\n"
1825 "- \"Per-team, in order\" (TEAM_ORDER): colors are assigned to "
1826 "teams from the list in the ruleset. Every player on the same "
1827 "team gets the same color.\n"
1828 "- \"Per-nation, in order\" (NATION_ORDER): if the ruleset "
1829 "defines a color for a player's nation, the player takes that "
1830 "color. Any players whose nations don't have associated colors "
1831 "get a random color from the list in the ruleset.\n"
1832 "Regardless of this setting, individual player colors can be "
1833 "changed after the game starts with the 'playercolor' command."),
1834 plrcol_validate, plrcol_action, plrcol_name,
1835 GAME_DEFAULT_PLRCOLORMODE)
1837 /* Flexible rules: these can be changed after the game has started.
1839 * The distinction between "rules" and "flexible rules" is not always
1840 * clearcut, and some existing cases may be largely historical or
1841 * accidental. However some generalizations can be made:
1843 * -- Low-level game mechanics should not be flexible (eg, rulesets).
1844 * -- Options which would affect the game "state" (city production etc)
1845 * should not be flexible (eg, foodbox).
1846 * -- Options which are explicitly sent to the client (eg, in
1847 * packet_game_info) should probably not be flexible, or at
1848 * least need extra care to be flexible.
1850 GEN_ENUM("barbarians", game.server.barbarianrate,
1851 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_VITAL, SSET_TO_CLIENT,
1852 N_("Barbarian appearance frequency"),
1853 /* TRANS: The string between single quotes is a setting name and
1854 * should not be translated. */
1855 N_("This setting controls how frequently the barbarians appear "
1856 "in the game. See also the 'onsetbarbs' setting."),
1857 NULL, NULL, barbarians_name, GAME_DEFAULT_BARBARIANRATE)
1859 GEN_INT("onsetbarbs", game.server.onsetbarbarian,
1860 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_VITAL, SSET_TO_CLIENT,
1861 N_("Barbarian onset turn"),
1862 N_("Barbarians will not appear before this turn."), NULL, NULL,
1863 GAME_MIN_ONSETBARBARIAN, GAME_MAX_ONSETBARBARIAN,
1864 GAME_DEFAULT_ONSETBARBARIAN)
1866 GEN_INT("revolen", game.server.revolution_length,
1867 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
1868 N_("Length in turns of revolution"),
1869 N_("When changing governments, a period of anarchy lasting this "
1870 "many turns will occur. "
1871 "Setting this value to 0 will give a random "
1872 "length of 1-5 turns."), NULL, NULL,
1873 GAME_MIN_REVOLUTION_LENGTH, GAME_MAX_REVOLUTION_LENGTH,
1874 GAME_DEFAULT_REVOLUTION_LENGTH)
1876 GEN_BOOL("fogofwar", game.info.fogofwar,
1877 SSET_RULES, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1878 N_("Whether to enable fog of war"),
1879 N_("If this is enabled, only those units and cities within "
1880 "the vision range of your own units and cities will be "
1881 "revealed to you. You will not see new cities or terrain "
1882 "changes in tiles not observed."),
1883 NULL, NULL, GAME_DEFAULT_FOGOFWAR)
1885 GEN_BOOL("foggedborders", game.server.foggedborders,
1886 SSET_RULES, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1887 N_("Whether fog of war applies to border changes"),
1888 N_("If this setting is enabled, players will not be able "
1889 "to see changes in tile ownership if they do not have "
1890 "direct sight of the affected tiles. Otherwise, players "
1891 "can see any or all changes to borders as long as they "
1892 "have previously seen the tiles."),
1893 NULL, NULL, GAME_DEFAULT_FOGGEDBORDERS)
1895 GEN_BITWISE("airliftingstyle", game.info.airlifting_style,
1896 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_SITUATIONAL,
1897 SSET_TO_CLIENT, N_("Airlifting style"),
1898 /* TRANS: The strings between double quotes are also
1899 * translated separately (they must match!). The strings
1900 * between parenthesis and in uppercase must not be
1901 * translated. */
1902 N_("This setting affects airlifting units between cities. It "
1903 "can be a set of the following values:\n"
1904 "- \"Allows units to be airlifted from allied cities\" "
1905 "(FROM_ALLIES).\n"
1906 "- \"Allows units to be airlifted to allied cities\" "
1907 "(TO_ALLIES).\n"
1908 "- \"Unlimited units from source city\" (SRC_UNLIMITED): "
1909 "note that airlifting from a city doesn't reduce the "
1910 "airlifted counter, but still needs at least 1.\n"
1911 "- \"Unlimited units to destination city\" "
1912 "(DEST_UNLIMITED): note that airlifting to a city doesn't "
1913 "reduce the airlifted counter, and doesn't need any."),
1914 NULL, NULL, airliftingstyle_name, GAME_DEFAULT_AIRLIFTINGSTYLE)
1916 GEN_INT("diplchance", game.server.diplchance,
1917 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_SITUATIONAL,
1918 SSET_TO_CLIENT,
1919 N_("Base chance for diplomats and spies to succeed"),
1920 N_("The base chance of a spy returning from a successful mission and "
1921 "the base chance of success for diplomats and spies."),
1922 NULL, NULL,
1923 GAME_MIN_DIPLCHANCE, GAME_MAX_DIPLCHANCE, GAME_DEFAULT_DIPLCHANCE)
1925 GEN_BOOL("spacerace", game.info.spacerace,
1926 SSET_RULES_FLEXIBLE, SSET_SCIENCE, SSET_VITAL, SSET_TO_CLIENT,
1927 N_("Whether to allow space race"),
1928 N_("If this option is enabled, players can build spaceships."),
1929 NULL, NULL, GAME_DEFAULT_SPACERACE)
1931 GEN_BOOL("endspaceship", game.server.endspaceship, SSET_RULES_FLEXIBLE,
1932 SSET_SCIENCE, SSET_VITAL, SSET_TO_CLIENT,
1933 N_("Should the game end if the spaceship arrives?"),
1934 N_("If this option is turned on, the game will end with the "
1935 "arrival of a spaceship at Alpha Centauri."),
1936 NULL, NULL, GAME_DEFAULT_END_SPACESHIP)
1938 GEN_INT("civilwarsize", game.server.civilwarsize,
1939 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
1940 N_("Minimum number of cities for civil war"),
1941 N_("A civil war is triggered when a player has at least this "
1942 "many cities and the player's capital is captured. If "
1943 "this option is set to the maximum value, civil wars are "
1944 "turned off altogether."), NULL, NULL,
1945 GAME_MIN_CIVILWARSIZE, GAME_MAX_CIVILWARSIZE,
1946 GAME_DEFAULT_CIVILWARSIZE)
1948 GEN_BOOL("restrictinfra", game.info.restrictinfra,
1949 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1950 N_("Restrict the use of the infrastructure for enemy units"),
1951 N_("If this option is enabled, the use of roads and rails "
1952 "will be restricted for enemy units."), NULL, NULL,
1953 GAME_DEFAULT_RESTRICTINFRA)
1955 GEN_BOOL("unreachableprotects", game.info.unreachable_protects,
1956 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1957 N_("Does unreachable unit protect reachable ones"),
1958 N_("This option controls whether tiles with both unreachable "
1959 "and reachable units can be attacked. If disabled, any "
1960 "tile with reachable units can be attacked. If enabled, "
1961 "tiles with an unreachable unit in them cannot be attacked."),
1962 NULL, NULL, GAME_DEFAULT_UNRPROTECTS)
1964 GEN_INT("contactturns", game.server.contactturns,
1965 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1966 N_("Turns until player contact is lost"),
1967 N_("Players may meet for diplomacy this number of turns "
1968 "after their units have last met, even when they do not have "
1969 "an embassy. If set to zero, then players cannot meet unless "
1970 "they have an embassy."),
1971 NULL, NULL,
1972 GAME_MIN_CONTACTTURNS, GAME_MAX_CONTACTTURNS,
1973 GAME_DEFAULT_CONTACTTURNS)
1975 GEN_BOOL("savepalace", game.server.savepalace,
1976 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1977 N_("Rebuild palace whenever capital is conquered"),
1978 N_("If this is turned on, when the capital is conquered the "
1979 "palace is automatically rebuilt for free in another randomly "
1980 "chosen city. This is significant because the technology "
1981 "requirement for building a palace will be ignored. (In "
1982 "some rulesets, buildings other than the palace are affected "
1983 "by this setting.)"),
1984 NULL, NULL, GAME_DEFAULT_SAVEPALACE)
1986 GEN_BOOL("homecaughtunits", game.server.homecaughtunits,
1987 SSET_RULES_FLEXIBLE, SSET_MILITARY, SSET_RARE, SSET_TO_CLIENT,
1988 N_("Give caught units a homecity"),
1989 /* TRANS: The string between single quotes is a setting name and
1990 * should not be translated. */
1991 N_("If unset, caught units will have no homecity and will be "
1992 "subject to the 'killunhomed' option."),
1993 NULL, NULL, GAME_DEFAULT_HOMECAUGHTUNITS)
1995 GEN_BOOL("alliedvictory", game.server.allied_victory,
1996 SSET_RULES_FLEXIBLE, SSET_MILITARY,
1997 SSET_SITUATIONAL, SSET_TO_CLIENT,
1998 N_("Whether allied players can win together"),
1999 N_("If this option is turned on and a point is reached where "
2000 "all the players still able to win the game are allies, and "
2001 "at least one defeated player is not part of this alliance, "
2002 "then the game will end in an immediate shared victory for "
2003 "the allied players."),
2004 NULL, NULL, GAME_DEFAULT_ALLIED_VICTORY)
2006 GEN_BOOL("naturalcitynames", game.server.natural_city_names,
2007 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
2008 N_("Whether to use natural city names"),
2009 N_("If enabled, the default city names will be determined based "
2010 "on the surrounding terrain."),
2011 NULL, NULL, GAME_DEFAULT_NATURALCITYNAMES)
2013 GEN_BOOL("migration", game.server.migration,
2014 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
2015 N_("Whether to enable citizen migration"),
2016 /* TRANS: The strings between single quotes are setting names
2017 * and should not be translated. */
2018 N_("This is the master setting that controls whether citizen "
2019 "migration is active in the game. If enabled, citizens may "
2020 "automatically move from less desirable cities to more "
2021 "desirable ones. The \"desirability\" of a given city is "
2022 "calculated from a number of factors. In general larger "
2023 "cities with more income and improvements will be preferred. "
2024 "Citizens will never migrate out of the capital, or cause "
2025 "a wonder to be lost by disbanding a city. A number of other "
2026 "settings control how migration behaves:\n"
2027 " 'mgr_turninterval' - How often citizens try to migrate.\n"
2028 " 'mgr_foodneeded' - Whether destination food is checked.\n"
2029 " 'mgr_distance' - How far citizens will migrate.\n"
2030 " 'mgr_worldchance' - Chance for inter-nation migration.\n"
2031 " 'mgr_nationchance' - Chance for intra-nation migration."),
2032 NULL, NULL, GAME_DEFAULT_MIGRATION)
2034 GEN_INT("mgr_turninterval", game.server.mgr_turninterval,
2035 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
2036 N_("Number of turns between migrations from a city"),
2037 /* TRANS: Do not translate 'migration' setting name. */
2038 N_("This setting controls the number of turns between migration "
2039 "checks for a given city. The interval is calculated from "
2040 "the founding turn of the city. So for example if this "
2041 "setting is 5, citizens will look for a suitable migration "
2042 "destination every five turns from the founding of their "
2043 "current city. Migration will never occur the same turn "
2044 "that a city is built. This setting has no effect unless "
2045 "migration is enabled by the 'migration' setting."), NULL,
2046 NULL, GAME_MIN_MGR_TURNINTERVAL, GAME_MAX_MGR_TURNINTERVAL,
2047 GAME_DEFAULT_MGR_TURNINTERVAL)
2049 GEN_BOOL("mgr_foodneeded", game.server.mgr_foodneeded,
2050 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
2051 N_("Whether migration is limited by food"),
2052 /* TRANS: Do not translate 'migration' setting name. */
2053 N_("If this setting is enabled, citizens will not migrate to "
2054 "cities which would not have enough food to support them. "
2055 "This setting has no effect unless migration is enabled by "
2056 "the 'migration' setting."), NULL, NULL,
2057 GAME_DEFAULT_MGR_FOODNEEDED)
2059 GEN_INT("mgr_distance", game.server.mgr_distance,
2060 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
2061 N_("Maximum distance citizens may migrate"),
2062 /* TRANS: Do not translate 'migration' setting name. */
2063 N_("This setting controls how far citizens may look for a "
2064 "suitable migration destination when deciding which city "
2065 "to migrate to. The value is added to the current city radius "
2066 "and compared to the distance between the two cities. If "
2067 "the distance is lower or equal, migration is possible. This "
2068 "setting has no effect unless migration is activated by the "
2069 "'migration' setting."),
2070 NULL, NULL, GAME_MIN_MGR_DISTANCE, GAME_MAX_MGR_DISTANCE,
2071 GAME_DEFAULT_MGR_DISTANCE)
2073 GEN_INT("mgr_nationchance", game.server.mgr_nationchance,
2074 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
2075 N_("Percent probability for migration within the same nation"),
2076 /* TRANS: Do not translate 'migration' setting name. */
2077 N_("This setting controls how likely it is for citizens to "
2078 "migrate between cities owned by the same player. Zero "
2079 "indicates migration will never occur, 100 means that "
2080 "migration will always occur if the citizens find a suitable "
2081 "destination. This setting has no effect unless migration "
2082 "is activated by the 'migration' setting."), NULL, NULL,
2083 GAME_MIN_MGR_NATIONCHANCE, GAME_MAX_MGR_NATIONCHANCE,
2084 GAME_DEFAULT_MGR_NATIONCHANCE)
2086 GEN_INT("mgr_worldchance", game.server.mgr_worldchance,
2087 SSET_RULES_FLEXIBLE, SSET_SOCIOLOGY, SSET_RARE, SSET_TO_CLIENT,
2088 N_("Percent probability for migration between foreign cities"),
2089 /* TRANS: Do not translate 'migration' setting name. */
2090 N_("This setting controls how likely it is for migration "
2091 "to occur between cities owned by different players. "
2092 "Zero indicates migration will never occur, 100 means "
2093 "that citizens will always migrate if they find a suitable "
2094 "destination. This setting has no effect if migration is "
2095 "not enabled by the 'migration' setting."), NULL, NULL,
2096 GAME_MIN_MGR_WORLDCHANCE, GAME_MAX_MGR_WORLDCHANCE,
2097 GAME_DEFAULT_MGR_WORLDCHANCE)
2099 /* Meta options: these don't affect the internal rules of the game, but
2100 * do affect players. Also options which only produce extra server
2101 * "output" and don't affect the actual game.
2102 * ("endturn" is here, and not RULES_FLEXIBLE, because it doesn't
2103 * affect what happens in the game, it just determines when the
2104 * players stop playing and look at the score.)
2106 GEN_STRING("allowtake", game.server.allow_take,
2107 SSET_META, SSET_NETWORK, SSET_RARE, SSET_TO_CLIENT,
2108 N_("Players that users are allowed to take"),
2109 /* TRANS: the strings in double quotes are server command names
2110 * and should not be translated. */
2111 N_("This should be a string of characters, each of which "
2112 "specifies a type or status of a civilization (player).\n"
2113 "Clients will only be permitted to take or observe those "
2114 "players which match one of the specified letters. This "
2115 "only affects future uses of the \"take\" or \"observe\" "
2116 "commands; it is not retroactive. The characters and their "
2117 "meanings are:\n"
2118 " o,O = Global observer\n"
2119 " b = Barbarian players\n"
2120 " d = Dead players\n"
2121 " a,A = AI players\n"
2122 " h,H = Human players\n"
2123 "The first description on this list which matches a "
2124 "player is the one which applies. Thus 'd' does not "
2125 "include dead barbarians, 'a' does not include dead AI "
2126 "players, and so on. Upper case letters apply before "
2127 "the game has started, lower case letters afterwards.\n"
2128 "Each character above may be followed by one of the "
2129 "following numbers to allow or restrict the manner "
2130 "of connection:\n"
2131 "(none) = Controller allowed, observers allowed, "
2132 "can displace connections. (Displacing a connection means "
2133 "that you may take over a player, even when another user "
2134 "already controls that player.)\n"
2135 " 1 = Controller allowed, observers allowed, "
2136 "can't displace connections;\n"
2137 " 2 = Controller allowed, no observers allowed, "
2138 "can displace connections;\n"
2139 " 3 = Controller allowed, no observers allowed, "
2140 "can't displace connections;\n"
2141 " 4 = No controller allowed, observers allowed"),
2142 allowtake_callback, NULL, GAME_DEFAULT_ALLOW_TAKE)
2144 GEN_BOOL("autotoggle", game.server.auto_ai_toggle,
2145 SSET_META, SSET_NETWORK, SSET_SITUATIONAL, SSET_TO_CLIENT,
2146 N_("Whether AI-status toggles with connection"),
2147 N_("If enabled, AI status is turned off when a player "
2148 "connects, and on when a player disconnects."),
2149 NULL, autotoggle_action, GAME_DEFAULT_AUTO_AI_TOGGLE)
2151 GEN_INT("endturn", game.server.end_turn,
2152 SSET_META, SSET_SOCIOLOGY, SSET_VITAL, SSET_TO_CLIENT,
2153 N_("Turn the game ends"),
2154 N_("The game will end at the end of the given turn."),
2155 endturn_callback, NULL,
2156 GAME_MIN_END_TURN, GAME_MAX_END_TURN, GAME_DEFAULT_END_TURN)
2158 GEN_BITWISE("revealmap", game.server.revealmap, SSET_GAME_INIT,
2159 SSET_MILITARY, SSET_SITUATIONAL, SSET_TO_CLIENT,
2160 N_("Reveal the map"),
2161 /* TRANS: The strings between double quotes are also translated
2162 * separately (they must match!). The strings between single
2163 * quotes are setting names and shouldn't be translated. The
2164 * strings between parentheses and in uppercase must not be
2165 * translated. */
2166 N_("If \"Reveal map at game start\" (START) is set, the "
2167 "initial state of the entire map will be known to all "
2168 "players from the start of the game, although it may "
2169 "still be fogged (depending on the 'fogofwar' setting). "
2170 "If \"Unfog map for dead players\" (DEAD) is set, dead "
2171 "players can see the entire map, if they are alone in "
2172 "their team."),
2173 NULL, NULL, revealmap_name, GAME_DEFAULT_REVEALMAP)
2175 GEN_INT("timeout", game.info.timeout,
2176 SSET_META, SSET_INTERNAL, SSET_VITAL, SSET_TO_CLIENT,
2177 N_("Maximum seconds per turn"),
2178 /* TRANS: \"Turn Done\" refers to the client button; it is also
2179 * translated separately, the translation should be the same.
2180 * \"timeoutincrease\" is a command name and must not to be
2181 * translated. */
2182 N_("If all players have not hit \"Turn Done\" before this "
2183 "time is up, then the turn ends automatically. Zero "
2184 "means there is no timeout. In servers compiled with "
2185 "debugging, a timeout of -1 sets the autogame test mode. "
2186 "Only connections with hack level access may set the "
2187 "timeout to lower than 30 seconds. Use this with the "
2188 "command \"timeoutincrease\" to have a dynamic timer. "
2189 "The first turn is treated as a special case and is controlled "
2190 "by the 'first_timeout' setting."),
2191 timeout_callback, timeout_action,
2192 GAME_MIN_TIMEOUT, GAME_MAX_TIMEOUT, GAME_DEFAULT_TIMEOUT)
2194 GEN_INT("first_timeout", game.server.first_timeout,
2195 SSET_META, SSET_INTERNAL, SSET_VITAL, SSET_TO_CLIENT,
2196 N_("First turn timeout"),
2197 /* TRANS: The strings between single quotes are setting names and
2198 * should not be translated. */
2199 N_("If greater than 0, T0 will last for 'first_timeout' seconds.\n"
2200 "If set to 0, T0 will not have a timeout.\n"
2201 "If set to -1, the special treatment of T0 will be disabled.\n"
2202 "See also 'timeout'."),
2203 NULL, NULL, GAME_MIN_FIRST_TIMEOUT, GAME_MAX_FIRST_TIMEOUT,
2204 GAME_DEFAULT_FIRST_TIMEOUT)
2206 GEN_INT("timeaddenemymove", game.server.timeoutaddenemymove,
2207 SSET_META, SSET_INTERNAL, SSET_VITAL, SSET_TO_CLIENT,
2208 N_("Timeout at least n seconds when enemy moved"),
2209 N_("Any time a unit moves while in sight of an enemy player, "
2210 "the remaining timeout is increased to this value."),
2211 NULL, NULL, 0, GAME_MAX_TIMEOUT, GAME_DEFAULT_TIMEOUTADDEMOVE)
2213 GEN_INT("unitwaittime", game.server.unitwaittime,
2214 SSET_RULES_FLEXIBLE, SSET_INTERNAL, SSET_VITAL, SSET_TO_CLIENT,
2215 N_("Time between unit moves over turn change"),
2216 /* TRANS: The string between single quotes is a setting name and
2217 * should not be translated. */
2218 N_("This setting gives the minimum amount of time in seconds "
2219 "between unit moves after a turn change occurs. For "
2220 "example, if this setting is set to 20 and a unit moves "
2221 "5 seconds before the turn change, it will not be able "
2222 "to move in the next turn for at least 15 seconds. Building "
2223 "cities is also affected by this setting, as well as units "
2224 "moving inside a transporter. This value is limited to "
2225 "a maximum value of 2/3 'timeout'."),
2226 unitwaittime_callback, NULL, GAME_MIN_UNITWAITTIME,
2227 GAME_MAX_UNITWAITTIME, GAME_DEFAULT_UNITWAITTIME)
2229 /* This setting points to the "stored" value; changing it won't have
2230 * an effect until the next synchronization point (i.e., the start of
2231 * the next turn). */
2232 GEN_ENUM("phasemode", game.server.phase_mode_stored,
2233 SSET_META, SSET_INTERNAL, SSET_SITUATIONAL, SSET_TO_CLIENT,
2234 N_("Control of simultaneous player/team phases"),
2235 N_("This setting controls whether players may make "
2236 "moves at the same time during a turn. Change "
2237 "in setting takes effect next turn."),
2238 NULL, NULL, phasemode_name, GAME_DEFAULT_PHASE_MODE)
2240 GEN_INT("nettimeout", game.server.tcptimeout,
2241 SSET_META, SSET_NETWORK, SSET_RARE, SSET_TO_CLIENT,
2242 N_("Seconds to let a client's network connection block"),
2243 N_("If a network connection is blocking for a time greater than "
2244 "this value, then the connection is closed. Zero "
2245 "means there is no timeout (although connections will be "
2246 "automatically disconnected eventually)."),
2247 NULL, NULL,
2248 GAME_MIN_TCPTIMEOUT, GAME_MAX_TCPTIMEOUT, GAME_DEFAULT_TCPTIMEOUT)
2250 GEN_INT("netwait", game.server.netwait,
2251 SSET_META, SSET_NETWORK, SSET_RARE, SSET_TO_CLIENT,
2252 N_("Max seconds for network buffers to drain"),
2253 N_("The server will wait for up to the value of this "
2254 "parameter in seconds, for all client connection network "
2255 "buffers to unblock. Zero means the server will not "
2256 "wait at all."), NULL, NULL,
2257 GAME_MIN_NETWAIT, GAME_MAX_NETWAIT, GAME_DEFAULT_NETWAIT)
2259 GEN_INT("pingtime", game.server.pingtime,
2260 SSET_META, SSET_NETWORK, SSET_RARE, SSET_TO_CLIENT,
2261 N_("Seconds between PINGs"),
2262 N_("The server will poll the clients with a PING request "
2263 "each time this period elapses."), NULL, NULL,
2264 GAME_MIN_PINGTIME, GAME_MAX_PINGTIME, GAME_DEFAULT_PINGTIME)
2266 GEN_INT("pingtimeout", game.server.pingtimeout,
2267 SSET_META, SSET_NETWORK, SSET_RARE,
2268 SSET_TO_CLIENT,
2269 N_("Time to cut a client"),
2270 N_("If a client doesn't reply to a PING in this time the "
2271 "client is disconnected."), NULL, NULL,
2272 GAME_MIN_PINGTIMEOUT, GAME_MAX_PINGTIMEOUT, GAME_DEFAULT_PINGTIMEOUT)
2274 GEN_BOOL("turnblock", game.server.turnblock,
2275 SSET_META, SSET_INTERNAL, SSET_SITUATIONAL, SSET_TO_CLIENT,
2276 N_("Turn-blocking game play mode"),
2277 N_("If this is turned on, the game turn is not advanced "
2278 "until all players have finished their turn, including "
2279 "disconnected players."),
2280 NULL, NULL, GAME_DEFAULT_TURNBLOCK)
2282 GEN_BOOL("fixedlength", game.server.fixedlength,
2283 SSET_META, SSET_INTERNAL, SSET_SITUATIONAL, SSET_TO_CLIENT,
2284 N_("Fixed-length turns play mode"),
2285 /* TRANS: \"Turn Done\" refers to the client button; it is also
2286 * translated separately, the translation should be the same. */
2287 N_("If this is turned on the game turn will not advance "
2288 "until the timeout has expired, even after all players "
2289 "have clicked on \"Turn Done\"."),
2290 NULL, NULL, FALSE)
2292 GEN_STRING("demography", game.server.demography,
2293 SSET_META, SSET_INTERNAL, SSET_SITUATIONAL, SSET_TO_CLIENT,
2294 N_("What is in the Demographics report"),
2295 /* TRANS: The strings between double quotes should be
2296 * translated. */
2297 N_("This should be a string of characters, each of which "
2298 "specifies the inclusion of a line of information "
2299 "in the Demographics report.\n"
2300 "The characters and their meanings are:\n"
2301 " N = include Population\n"
2302 " P = include Production\n"
2303 " A = include Land Area\n"
2304 " L = include Literacy\n"
2305 " R = include Research Speed\n"
2306 " S = include Settled Area\n"
2307 " E = include Economics\n"
2308 " M = include Military Service\n"
2309 " O = include Pollution\n"
2310 "Additionally, the following characters control whether "
2311 "or not certain columns are displayed in the report:\n"
2312 " q = display \"quantity\" column\n"
2313 " r = display \"rank\" column\n"
2314 " b = display \"best nation\" column\n"
2315 "The order of characters is not significant, but "
2316 "their capitalization is."),
2317 demography_callback, NULL, GAME_DEFAULT_DEMOGRAPHY)
2319 GEN_INT("saveturns", game.server.save_nturns,
2320 SSET_META, SSET_INTERNAL, SSET_VITAL, SSET_SERVER_ONLY,
2321 N_("Turns per auto-save"),
2322 /* TRANS: The string between double quotes is also translated
2323 * separately (it must match!). The string between single
2324 * quotes is a setting name and shouldn't be translated. */
2325 N_("How many turns elapse between automatic game saves. This "
2326 "setting only has an effect when the 'autosaves' setting "
2327 "includes \"New turn\"."), NULL, NULL,
2328 GAME_MIN_SAVETURNS, GAME_MAX_SAVETURNS, GAME_DEFAULT_SAVETURNS)
2330 GEN_BITWISE("autosaves", game.server.autosaves,
2331 SSET_META, SSET_INTERNAL, SSET_VITAL, SSET_SERVER_ONLY,
2332 N_("Which savegames are generated automatically"),
2333 /* TRANS: The strings between double quotes are also translated
2334 * separately (they must match!). The strings between single
2335 * quotes are setting names and shouldn't be translated. The
2336 * strings between parentheses and in uppercase must stay as
2337 * untranslated. */
2338 N_("This setting controls which autosave types get generated:\n"
2339 "- \"New turn\" (TURN): Save when turn begins, once every "
2340 "'saveturns' turns.\n"
2341 "- \"Game over\" (GAMEOVER): Final save when game ends.\n"
2342 "- \"No player connections\" (QUITIDLE): "
2343 "Save before server restarts due to lack of players.\n"
2344 "- \"Server interrupted\" (INTERRUPT): Save when server "
2345 "quits due to interrupt."),
2346 NULL, NULL, autosaves_name, GAME_DEFAULT_AUTOSAVES)
2348 GEN_INT("compress", game.server.save_compress_level,
2349 SSET_META, SSET_INTERNAL, SSET_RARE, SSET_SERVER_ONLY,
2350 N_("Savegame compression level"),
2351 /* TRANS: 'compresstype' setting name should not be translated. */
2352 N_("If non-zero, saved games will be compressed depending on the "
2353 "'compresstype' setting. Larger values will give better "
2354 "compression but take longer."),
2355 NULL, NULL, GAME_MIN_COMPRESS_LEVEL, GAME_MAX_COMPRESS_LEVEL,
2356 GAME_DEFAULT_COMPRESS_LEVEL)
2358 GEN_ENUM("compresstype", game.server.save_compress_type,
2359 SSET_META, SSET_INTERNAL, SSET_RARE, SSET_SERVER_ONLY,
2360 N_("Savegame compression algorithm"),
2361 N_("Compression library to use for savegames."),
2362 NULL, NULL, compresstype_name, GAME_DEFAULT_COMPRESS_TYPE)
2364 GEN_STRING("savename", game.server.save_name,
2365 SSET_META, SSET_INTERNAL, SSET_VITAL, SSET_SERVER_ONLY,
2366 N_("Definition of the save file name"),
2367 /* TRANS: %R, %S, %T and %Y must not be translated. The
2368 * strings (examples and setting names) between single quotes
2369 * neither. The strings between <> should be translated.
2370 * xgettext:no-c-format */
2371 N_("Within the string the following custom formats are "
2372 "allowed:\n"
2373 " %R = <reason>\n"
2374 " %S = <suffix>\n"
2375 " %T = <turn-number>\n"
2376 " %Y = <game-year>\n"
2377 "\n"
2378 "Example: 'freeciv-T%04T-Y%+05Y-%R' => "
2379 "'freeciv-T0100-Y00001-manual'\n"
2380 "\n"
2381 "Be careful to use at least one of %T and %Y, else newer "
2382 "savegames will overwrite old ones. If none of the formats "
2383 "is used '-T%04T-Y%05Y-%R' is appended to the value of "
2384 "'savename'."),
2385 savename_validate, NULL, GAME_DEFAULT_SAVE_NAME)
2387 GEN_BOOL("scorelog", game.server.scorelog,
2388 SSET_META, SSET_INTERNAL, SSET_SITUATIONAL, SSET_SERVER_ONLY,
2389 N_("Whether to log player statistics"),
2390 /* TRANS: The string between single quotes is a setting name and
2391 * should not be translated. */
2392 N_("If this is turned on, player statistics are appended to "
2393 "the file defined by the option 'scorefile' every turn. "
2394 "These statistics can be used to create power graphs after "
2395 "the game."), NULL, scorelog_action, GAME_DEFAULT_SCORELOG)
2397 GEN_STRING("scorefile", game.server.scorefile,
2398 SSET_META, SSET_INTERNAL, SSET_SITUATIONAL, SSET_SERVER_ONLY,
2399 N_("Name for the score log file"),
2400 /* TRANS: Don't translate the string in single quotes. */
2401 N_("The default name for the score log file is "
2402 "'freeciv-score.log'."),
2403 scorefile_validate, NULL, GAME_DEFAULT_SCOREFILE)
2405 GEN_INT("maxconnectionsperhost", game.server.maxconnectionsperhost,
2406 SSET_RULES_FLEXIBLE, SSET_NETWORK, SSET_RARE, SSET_TO_CLIENT,
2407 N_("Maximum number of connections to the server per host"),
2408 N_("New connections from a given host will be rejected if "
2409 "the total number of connections from the very same host "
2410 "equals or exceeds this value. A value of 0 means that "
2411 "there is no limit, at least up to the maximum number of "
2412 "connections supported by the server."), NULL, NULL,
2413 GAME_MIN_MAXCONNECTIONSPERHOST, GAME_MAX_MAXCONNECTIONSPERHOST,
2414 GAME_DEFAULT_MAXCONNECTIONSPERHOST)
2416 GEN_INT("kicktime", game.server.kick_time,
2417 SSET_RULES_FLEXIBLE, SSET_NETWORK, SSET_RARE, SSET_SERVER_ONLY,
2418 N_("Time before a kicked user can reconnect"),
2419 /* TRANS: the string in double quotes is a server command name and
2420 * should not be translated */
2421 N_("Gives the time in seconds before a user kicked using the "
2422 "\"kick\" command may reconnect. Changing this setting will "
2423 "affect users kicked in the past."), NULL, NULL,
2424 GAME_MIN_KICK_TIME, GAME_MAX_KICK_TIME, GAME_DEFAULT_KICK_TIME)
2427 #undef GEN_BOOL
2428 #undef GEN_INT
2429 #undef GEN_STRING
2430 #undef GEN_ENUM
2431 #undef GEN_BITWISE
2433 /* The number of settings, not including the END. */
2434 static const int SETTINGS_NUM = ARRAY_SIZE(settings);
2436 /****************************************************************************
2437 Returns the setting to the given id.
2438 ****************************************************************************/
2439 struct setting *setting_by_number(int id)
2441 return (0 <= id && id < SETTINGS_NUM ? settings + id : NULL);
2444 /****************************************************************************
2445 Returns the setting to the given name.
2446 ****************************************************************************/
2447 struct setting *setting_by_name(const char *name)
2449 fc_assert_ret_val(name, NULL);
2451 settings_iterate(SSET_ALL, pset) {
2452 if (0 == strcmp(name, pset->name)) {
2453 return pset;
2455 } settings_iterate_end;
2456 return NULL;
2459 /****************************************************************************
2460 Returns the id to the given setting.
2461 ****************************************************************************/
2462 int setting_number(const struct setting *pset)
2464 fc_assert_ret_val(pset != NULL, -1);
2465 return pset - settings;
2468 /****************************************************************************
2469 Access function for the setting name.
2470 ****************************************************************************/
2471 const char *setting_name(const struct setting *pset)
2473 return pset->name;
2476 /****************************************************************************
2477 Access function for the short help (not translated yet) of the setting.
2478 ****************************************************************************/
2479 const char *setting_short_help(const struct setting *pset)
2481 return pset->short_help;
2484 /****************************************************************************
2485 Access function for the long (extra) help (not translated yet) of
2486 the setting.
2487 ****************************************************************************/
2488 const char *setting_extra_help(const struct setting *pset)
2490 return pset->extra_help;
2493 /****************************************************************************
2494 Access function for the setting type.
2495 ****************************************************************************/
2496 enum sset_type setting_type(const struct setting *pset)
2498 return pset->stype;
2501 /****************************************************************************
2502 Access function for the setting level (used by the /show command).
2503 ****************************************************************************/
2504 enum sset_level setting_level(const struct setting *pset)
2506 return pset->slevel;
2509 /****************************************************************************
2510 Access function for the setting category.
2511 ****************************************************************************/
2512 enum sset_category setting_category(const struct setting *pset)
2514 return pset->scategory;
2517 /****************************************************************************
2518 Returns whether the specified server setting (option) can currently
2519 be changed by the caller. If it returns FALSE, the reason of the failure
2520 is available by the function setting_error().
2521 ****************************************************************************/
2522 bool setting_is_changeable(const struct setting *pset,
2523 struct connection *caller, char *reject_msg,
2524 size_t reject_msg_len)
2526 if (caller
2527 && (caller->access_level < ALLOW_BASIC
2528 || (caller->access_level < ALLOW_HACK && !pset->to_client))) {
2529 settings_snprintf(reject_msg, reject_msg_len,
2530 _("You are not allowed to change the setting '%s'."),
2531 setting_name(pset));
2532 return FALSE;
2535 if (setting_locked(pset)) {
2536 /* setting is locked by the ruleset */
2537 settings_snprintf(reject_msg, reject_msg_len,
2538 _("The setting '%s' is locked by the ruleset."),
2539 setting_name(pset));
2540 return FALSE;
2543 switch (pset->sclass) {
2544 case SSET_MAP_SIZE:
2545 case SSET_MAP_GEN:
2546 /* Only change map options if we don't yet have a map: */
2547 if (map_is_empty()) {
2548 return TRUE;
2551 settings_snprintf(reject_msg, reject_msg_len,
2552 _("The setting '%s' can't be modified after the map "
2553 "is fixed."), setting_name(pset));
2554 return FALSE;
2556 case SSET_MAP_ADD:
2557 case SSET_PLAYERS:
2558 case SSET_GAME_INIT:
2559 case SSET_RULES:
2560 /* Only change start params and most rules if we don't yet have a map,
2561 * or if we do have a map but its a scenario one (ie, the game has
2562 * never actually been started).
2564 if (map_is_empty() || game.info.is_new_game) {
2565 return TRUE;
2568 settings_snprintf(reject_msg, reject_msg_len,
2569 _("The setting '%s' can't be modified after the game "
2570 "has started."), setting_name(pset));
2571 return FALSE;
2573 case SSET_RULES_FLEXIBLE:
2574 case SSET_META:
2575 /* These can always be changed: */
2576 return TRUE;
2579 log_error("Wrong class variant for setting %s (%d): %d.",
2580 setting_name(pset), setting_number(pset), pset->sclass);
2581 settings_snprintf(reject_msg, reject_msg_len, _("Internal error."));
2583 return FALSE;
2586 /****************************************************************************
2587 Returns whether the specified server setting (option) can be seen by the
2588 caller.
2589 ****************************************************************************/
2590 bool setting_is_visible(const struct setting *pset,
2591 struct connection *caller)
2593 return (!caller
2594 || pset->to_client
2595 || caller->access_level >= ALLOW_HACK);
2598 /****************************************************************************
2599 Convert the string prefix to an integer representation.
2600 NB: This function is used for SSET_ENUM *and* SSET_BITWISE.
2602 FIXME: this mostly duplicate match_prefix_full().
2603 ****************************************************************************/
2604 static enum m_pre_result
2605 setting_match_prefix_base(const val_name_func_t name_fn,
2606 const char *prefix, int *ind_result,
2607 const char **matches, size_t max_matches,
2608 size_t *pnum_matches)
2610 const struct sset_val_name *name;
2611 size_t len = strlen(prefix);
2612 size_t num_matches;
2613 int i;
2615 *pnum_matches = 0;
2617 if (0 == len) {
2618 return M_PRE_EMPTY;
2621 for (i = 0, num_matches = 0; (name = name_fn(i)); i++) {
2622 if (0 == fc_strncasecmp(name->support, prefix, len)) {
2623 if (strlen(name->support) == len) {
2624 *ind_result = i;
2625 return M_PRE_EXACT;
2627 if (num_matches < max_matches) {
2628 matches[num_matches] = name->support;
2629 (*pnum_matches)++;
2631 if (0 == num_matches++) {
2632 *ind_result = i;
2637 if (1 == num_matches) {
2638 return M_PRE_ONLY;
2639 } else if (1 < num_matches) {
2640 return M_PRE_AMBIGUOUS;
2641 } else {
2642 return M_PRE_FAIL;
2646 /****************************************************************************
2647 Convert the string prefix to an integer representation.
2648 NB: This function is used for SSET_ENUM *and* SSET_BITWISE.
2649 ****************************************************************************/
2650 static bool setting_match_prefix(const val_name_func_t name_fn,
2651 const char *prefix, int *pvalue,
2652 char *reject_msg,
2653 size_t reject_msg_len)
2655 const char *matches[16];
2656 size_t num_matches;
2658 switch (setting_match_prefix_base(name_fn, prefix, pvalue, matches,
2659 ARRAY_SIZE(matches), &num_matches)) {
2660 case M_PRE_EXACT:
2661 case M_PRE_ONLY:
2662 return TRUE; /* Ok. */
2663 case M_PRE_AMBIGUOUS:
2665 struct astring astr = ASTRING_INIT;
2667 fc_assert(2 <= num_matches);
2668 settings_snprintf(reject_msg, reject_msg_len,
2669 _("\"%s\" prefix is ambiguous. Candidates are: %s."),
2670 prefix,
2671 astr_build_and_list(&astr, matches, num_matches));
2672 astr_free(&astr);
2674 return FALSE;
2675 case M_PRE_EMPTY:
2676 settings_snprintf(reject_msg, reject_msg_len, _("Missing value."));
2677 return FALSE;
2678 case M_PRE_LONG:
2679 case M_PRE_FAIL:
2680 case M_PRE_LAST:
2681 break;
2684 settings_snprintf(reject_msg, reject_msg_len,
2685 _("No match for \"%s\"."), prefix);
2686 return FALSE;
2689 /****************************************************************************
2690 Compute the string representation of the value for this boolean setting.
2691 ****************************************************************************/
2692 static const char *setting_bool_to_str(const struct setting *pset,
2693 bool value, bool pretty,
2694 char *buf, size_t buf_len)
2696 const struct sset_val_name *name = pset->boolean.name(value);
2698 if (pretty) {
2699 fc_snprintf(buf, buf_len, "%s", Q_(name->pretty));
2700 } else {
2701 fc_strlcpy(buf, name->support, buf_len);
2703 return buf;
2706 /****************************************************************************
2707 Returns TRUE if 'val' is a valid value for this setting. If it's not,
2708 the reason of the failure is available in the optionnal parameter
2709 'reject_msg'.
2711 FIXME: also check the access level of pconn.
2712 ****************************************************************************/
2713 static bool setting_bool_validate_base(const struct setting *pset,
2714 const char *val, int *pint_val,
2715 struct connection *caller,
2716 char *reject_msg,
2717 size_t reject_msg_len)
2719 char buf[256];
2721 if (SSET_BOOL != pset->stype) {
2722 settings_snprintf(reject_msg, reject_msg_len,
2723 _("This setting is not a boolean."));
2724 return FALSE;
2727 sz_strlcpy(buf, val);
2728 remove_leading_trailing_spaces(buf);
2730 return (setting_match_prefix(pset->boolean.name, buf, pint_val,
2731 reject_msg, reject_msg_len)
2732 && (NULL == pset->boolean.validate
2733 || pset->boolean.validate(0 != *pint_val, caller, reject_msg,
2734 reject_msg_len)));
2737 /****************************************************************************
2738 Set the setting to 'val'. Returns TRUE on success. If it's not,
2739 the reason of the failure is available in the optionnal parameter
2740 'reject_msg'.
2741 ****************************************************************************/
2742 bool setting_bool_set(struct setting *pset, const char *val,
2743 struct connection *caller, char *reject_msg,
2744 size_t reject_msg_len)
2746 int int_val;
2748 if (!setting_is_changeable(pset, caller, reject_msg, reject_msg_len)
2749 || !setting_bool_validate_base(pset, val, &int_val, caller,
2750 reject_msg, reject_msg_len)) {
2751 return FALSE;
2754 *pset->boolean.pvalue = (0 != int_val);
2755 return TRUE;
2758 /****************************************************************************
2759 Returns TRUE if 'val' is a valid value for this setting. If it's not,
2760 the reason of the failure is available in the optionnal parameter
2761 'reject_msg'.
2762 ****************************************************************************/
2763 bool setting_bool_validate(const struct setting *pset, const char *val,
2764 struct connection *caller, char *reject_msg,
2765 size_t reject_msg_len)
2767 int int_val;
2769 return setting_bool_validate_base(pset, val, &int_val, caller,
2770 reject_msg, reject_msg_len);
2773 /****************************************************************************
2774 Convert the integer to the long support string representation of a boolean
2775 setting. This function must match the secfile_enum_name_data_fn_t type.
2776 ****************************************************************************/
2777 static const char *setting_bool_secfile_str(secfile_data_t data, int val)
2779 const struct sset_val_name *name =
2780 ((const struct setting *) data)->boolean.name(val);
2782 return (NULL != name ? name->support : NULL);
2785 /****************************************************************************
2786 Compute the string representation of the value for this integer setting.
2787 ****************************************************************************/
2788 static const char *setting_int_to_str(const struct setting *pset,
2789 int value, bool pretty,
2790 char *buf, size_t buf_len)
2792 fc_snprintf(buf, buf_len, "%d", value);
2793 return buf;
2796 /****************************************************************************
2797 Returns the minimal integer value for this setting.
2798 ****************************************************************************/
2799 int setting_int_min(const struct setting *pset)
2801 fc_assert_ret_val(pset->stype == SSET_INT, 0);
2802 return pset->integer.min_value;
2805 /****************************************************************************
2806 Returns the maximal integer value for this setting.
2807 ****************************************************************************/
2808 int setting_int_max(const struct setting *pset)
2810 fc_assert_ret_val(pset->stype == SSET_INT, 0);
2811 return pset->integer.max_value;
2814 /****************************************************************************
2815 Set the setting to 'val'. Returns TRUE on success. If it fails, the
2816 reason of the failure is available by the function setting_error().
2817 ****************************************************************************/
2818 bool setting_int_set(struct setting *pset, int val,
2819 struct connection *caller, char *reject_msg,
2820 size_t reject_msg_len)
2822 if (!setting_is_changeable(pset, caller, reject_msg, reject_msg_len)
2823 || !setting_int_validate(pset, val, caller, reject_msg,
2824 reject_msg_len)) {
2825 return FALSE;
2828 *pset->integer.pvalue = val;
2829 return TRUE;
2832 /****************************************************************************
2833 Returns TRUE if 'val' is a valid value for this setting. If it's not,
2834 the reason of the failure is available by the function setting_error().
2836 FIXME: also check the access level of pconn.
2837 ****************************************************************************/
2838 bool setting_int_validate(const struct setting *pset, int val,
2839 struct connection *caller, char *reject_msg,
2840 size_t reject_msg_len)
2842 if (SSET_INT != pset->stype) {
2843 settings_snprintf(reject_msg, reject_msg_len,
2844 _("This setting is not an integer."));
2845 return FALSE;
2848 if (val < pset->integer.min_value || val > pset->integer.max_value) {
2849 settings_snprintf(reject_msg, reject_msg_len,
2850 _("Value out of range: %d (min: %d; max: %d)."),
2851 val, pset->integer.min_value, pset->integer.max_value);
2852 return FALSE;
2855 return (!pset->integer.validate
2856 || pset->integer.validate(val, caller, reject_msg,
2857 reject_msg_len));
2860 /****************************************************************************
2861 Compute the string representation of the value for this string setting.
2862 ****************************************************************************/
2863 static const char *setting_str_to_str(const struct setting *pset,
2864 const char *value, bool pretty,
2865 char *buf, size_t buf_len)
2867 if (pretty) {
2868 fc_snprintf(buf, buf_len, "\"%s\"", value);
2869 } else {
2870 fc_strlcpy(buf, value, buf_len);
2872 return buf;
2875 /****************************************************************************
2876 Set the setting to 'val'. Returns TRUE on success. If it fails, the
2877 reason of the failure is available by the function setting_error().
2878 ****************************************************************************/
2879 bool setting_str_set(struct setting *pset, const char *val,
2880 struct connection *caller, char *reject_msg,
2881 size_t reject_msg_len)
2883 if (!setting_is_changeable(pset, caller, reject_msg, reject_msg_len)
2884 || !setting_str_validate(pset, val, caller, reject_msg,
2885 reject_msg_len)) {
2886 return FALSE;
2889 fc_strlcpy(pset->string.value, val, pset->string.value_size);
2890 return TRUE;
2893 /****************************************************************************
2894 Returns TRUE if 'val' is a valid value for this setting. If it's not,
2895 the reason of the failure is available by the function setting_error().
2897 FIXME: also check the access level of pconn.
2898 ****************************************************************************/
2899 bool setting_str_validate(const struct setting *pset, const char *val,
2900 struct connection *caller, char *reject_msg,
2901 size_t reject_msg_len)
2903 if (SSET_STRING != pset->stype) {
2904 settings_snprintf(reject_msg, reject_msg_len,
2905 _("This setting is not a string."));
2906 return FALSE;
2909 if (strlen(val) >= pset->string.value_size) {
2910 settings_snprintf(reject_msg, reject_msg_len,
2911 _("String value too long (max length: %lu)."),
2912 (unsigned long) pset->string.value_size);
2913 return FALSE;
2916 return (!pset->string.validate
2917 || pset->string.validate(val, caller, reject_msg,
2918 reject_msg_len));
2921 /****************************************************************************
2922 Convert the integer to the long support string representation of an
2923 enumerator. This function must match the secfile_enum_name_data_fn_t type.
2924 ****************************************************************************/
2925 static const char *setting_enum_secfile_str(secfile_data_t data, int val)
2927 const struct sset_val_name *name =
2928 ((const struct setting *) data)->enumerator.name(val);
2930 return (NULL != name ? name->support : NULL);
2933 /****************************************************************************
2934 Convert the integer to the string representation of an enumerator.
2935 Return NULL if 'val' is not a valid enumerator.
2936 ****************************************************************************/
2937 const char *setting_enum_val(const struct setting *pset, int val,
2938 bool pretty)
2940 const struct sset_val_name *name;
2942 fc_assert_ret_val(SSET_ENUM == pset->stype, NULL);
2943 name = pset->enumerator.name(val);
2944 if (NULL == name) {
2945 return NULL;
2946 } else if (pretty) {
2947 return _(name->pretty);
2948 } else {
2949 return name->support;
2953 /****************************************************************************
2954 Compute the string representation of the value for this enumerator
2955 setting.
2956 ****************************************************************************/
2957 static const char *setting_enum_to_str(const struct setting *pset,
2958 int value, bool pretty,
2959 char *buf, size_t buf_len)
2961 const struct sset_val_name *name = pset->enumerator.name(value);
2963 if (pretty) {
2964 fc_snprintf(buf, buf_len, "\"%s\" (%s)",
2965 Q_(name->pretty), name->support);
2966 } else {
2967 fc_strlcpy(buf, name->support, buf_len);
2969 return buf;
2972 /****************************************************************************
2973 Returns TRUE if 'val' is a valid value for this setting. If it's not,
2974 the reason of the failure is available in the optionnal parameter
2975 'reject_msg'.
2977 FIXME: also check the access level of pconn.
2978 ****************************************************************************/
2979 static bool setting_enum_validate_base(const struct setting *pset,
2980 const char *val, int *pint_val,
2981 struct connection *caller,
2982 char *reject_msg,
2983 size_t reject_msg_len)
2985 char buf[256];
2987 if (SSET_ENUM != pset->stype) {
2988 settings_snprintf(reject_msg, reject_msg_len,
2989 _("This setting is not an enumerator."));
2990 return FALSE;
2993 sz_strlcpy(buf, val);
2994 remove_leading_trailing_spaces(buf);
2996 return (setting_match_prefix(pset->enumerator.name, buf, pint_val,
2997 reject_msg, reject_msg_len)
2998 && (NULL == pset->enumerator.validate
2999 || pset->enumerator.validate(*pint_val, caller, reject_msg,
3000 reject_msg_len)));
3003 /****************************************************************************
3004 Helper function to write value to enumerator setting
3005 ****************************************************************************/
3006 static bool set_enum_value(struct setting *pset, int val)
3008 switch(pset->enumerator.store_size) {
3009 case sizeof(int):
3011 int *to_int = pset->enumerator.pvalue;
3013 *to_int = val;
3015 break;
3016 case sizeof(char):
3018 char *to_char = pset->enumerator.pvalue;
3020 *to_char = (char) val;
3022 break;
3023 case sizeof(short):
3025 short *to_short = pset->enumerator.pvalue;
3027 *to_short = (short) val;
3029 break;
3030 default:
3031 return FALSE;
3034 return TRUE;
3037 /****************************************************************************
3038 Helper function to read value from enumerator setting
3039 ****************************************************************************/
3040 static int read_enum_value(const struct setting *pset)
3042 int val;
3044 switch(pset->enumerator.store_size) {
3045 case sizeof(int):
3046 val = *((int *)pset->enumerator.pvalue);
3047 break;
3048 case sizeof(char):
3049 val = *((char *)pset->enumerator.pvalue);
3050 break;
3051 case sizeof(short):
3052 val = *((short *)pset->enumerator.pvalue);
3053 break;
3054 default:
3055 log_error("Illegal enum store size %d, can't read value", pset->enumerator.store_size);
3056 return 0;
3059 return val;
3062 /****************************************************************************
3063 Set the setting to 'val'. Returns TRUE on success. If it fails, the
3064 reason of the failure is available in the optionnal parameter
3065 'reject_msg'.
3066 ****************************************************************************/
3067 bool setting_enum_set(struct setting *pset, const char *val,
3068 struct connection *caller, char *reject_msg,
3069 size_t reject_msg_len)
3071 int int_val;
3073 if (!setting_is_changeable(pset, caller, reject_msg, reject_msg_len)) {
3074 return FALSE;
3077 if (!setting_enum_validate_base(pset, val, &int_val, caller,
3078 reject_msg, reject_msg_len)) {
3079 return FALSE;
3082 if (!set_enum_value(pset, int_val)) {
3083 log_error("Illegal enumerator value size %d for %s",
3084 pset->enumerator.store_size, val);
3085 return FALSE;
3088 return TRUE;
3091 /****************************************************************************
3092 Returns TRUE if 'val' is a valid value for this setting. If it's not,
3093 the reason of the failure is available in the optionnal parameter
3094 'reject_msg'.
3095 ****************************************************************************/
3096 bool setting_enum_validate(const struct setting *pset, const char *val,
3097 struct connection *caller, char *reject_msg,
3098 size_t reject_msg_len)
3100 int int_val;
3102 return setting_enum_validate_base(pset, val, &int_val, caller,
3103 reject_msg, reject_msg_len);
3106 /****************************************************************************
3107 Convert the integer to the long support string representation of an
3108 enumerator. This function must match the secfile_enum_name_data_fn_t type.
3109 ****************************************************************************/
3110 static const char *setting_bitwise_secfile_str(secfile_data_t data, int bit)
3112 const struct sset_val_name *name =
3113 ((const struct setting *) data)->bitwise.name(bit);
3115 return (NULL != name ? name->support : NULL);
3118 /****************************************************************************
3119 Convert the bit number to its string representation.
3120 Return NULL if 'bit' is not a valid bit.
3121 ****************************************************************************/
3122 const char *setting_bitwise_bit(const struct setting *pset,
3123 int bit, bool pretty)
3125 const struct sset_val_name *name;
3127 fc_assert_ret_val(SSET_BITWISE == pset->stype, NULL);
3128 name = pset->bitwise.name(bit);
3129 if (NULL == name) {
3130 return NULL;
3131 } else if (pretty) {
3132 return _(name->pretty);
3133 } else {
3134 return name->support;
3138 /****************************************************************************
3139 Compute the string representation of the value for this bitwise setting.
3140 ****************************************************************************/
3141 static const char *setting_bitwise_to_str(const struct setting *pset,
3142 unsigned value, bool pretty,
3143 char *buf, size_t buf_len)
3145 const struct sset_val_name *name;
3146 char *old_buf = buf;
3147 int bit;
3149 if (pretty) {
3150 char buf2[64];
3151 struct astring astr = ASTRING_INIT;
3152 struct strvec *vec = strvec_new();
3153 size_t len;
3155 for (bit = 0; (name = pset->bitwise.name(bit)); bit++) {
3156 if ((1 << bit) & value) {
3157 /* TRANS: only emphasizing a string. */
3158 fc_snprintf(buf2, sizeof(buf2), _("\"%s\""), Q_(name->pretty));
3159 strvec_append(vec, buf2);
3163 if (0 == strvec_size(vec)) {
3164 /* No value. */
3165 fc_assert(0 == value);
3166 /* TRANS: Bitwise setting has no bits set. */
3167 fc_strlcpy(buf, _("empty value"), buf_len);
3168 strvec_destroy(vec);
3169 return buf;
3172 strvec_to_and_list(vec, &astr);
3173 strvec_destroy(vec);
3174 fc_strlcpy(buf, astr_str(&astr), buf_len);
3175 astr_free(&astr);
3176 fc_strlcat(buf, " (", buf_len);
3177 len = strlen(buf);
3178 buf += len;
3179 buf_len -= len;
3182 /* Long support part. */
3183 buf[0] = '\0';
3184 for (bit = 0; (name = pset->bitwise.name(bit)); bit++) {
3185 if ((1 << bit) & value) {
3186 if ('\0' != buf[0]) {
3187 fc_strlcat(buf, "|", buf_len);
3189 fc_strlcat(buf, name->support, buf_len);
3193 if (pretty) {
3194 fc_strlcat(buf, ")", buf_len);
3196 return old_buf;
3199 /****************************************************************************
3200 Returns TRUE if 'val' is a valid value for this setting. If it's not,
3201 the reason of the failure is available in the optionnal parameter
3202 'reject_msg'.
3204 FIXME: also check the access level of pconn.
3205 ****************************************************************************/
3206 static bool setting_bitwise_validate_base(const struct setting *pset,
3207 const char *val,
3208 unsigned *pint_val,
3209 struct connection *caller,
3210 char *reject_msg,
3211 size_t reject_msg_len)
3213 char buf[256];
3214 const char *p;
3215 int bit;
3217 if (SSET_BITWISE != pset->stype) {
3218 settings_snprintf(reject_msg, reject_msg_len,
3219 _("This setting is not a bitwise."));
3220 return FALSE;
3223 *pint_val = 0;
3225 /* Value names are separated by '|'. */
3226 do {
3227 p = strchr(val, '|');
3228 if (NULL != p) {
3229 p++;
3230 fc_strlcpy(buf, val, MIN(p - val, sizeof(buf)));
3231 } else {
3232 /* Last segment, full copy. */
3233 sz_strlcpy(buf, val);
3235 remove_leading_trailing_spaces(buf);
3236 if (NULL == p && '\0' == buf[0] && 0 == *pint_val) {
3237 /* Empty string = value 0. */
3238 break;
3239 } else if (!setting_match_prefix(pset->bitwise.name, buf, &bit,
3240 reject_msg, reject_msg_len)) {
3241 return FALSE;
3243 *pint_val |= 1 << bit;
3244 val = p;
3245 } while (NULL != p);
3247 return (NULL == pset->bitwise.validate
3248 || pset->bitwise.validate(*pint_val, caller,
3249 reject_msg, reject_msg_len));
3252 /****************************************************************************
3253 Set the setting to 'val'. Returns TRUE on success. If it fails, the
3254 reason of the failure is available in the optionnal parameter
3255 'reject_msg'.
3256 ****************************************************************************/
3257 bool setting_bitwise_set(struct setting *pset, const char *val,
3258 struct connection *caller, char *reject_msg,
3259 size_t reject_msg_len)
3261 unsigned int_val;
3263 if (!setting_is_changeable(pset, caller, reject_msg, reject_msg_len)
3264 || !setting_bitwise_validate_base(pset, val, &int_val, caller,
3265 reject_msg, reject_msg_len)) {
3266 return FALSE;
3269 *pset->bitwise.pvalue = int_val;
3270 return TRUE;
3273 /****************************************************************************
3274 Returns TRUE if 'val' is a valid value for this setting. If it's not,
3275 the reason of the failure is available in the optionnal parameter
3276 'reject_msg'.
3277 ****************************************************************************/
3278 bool setting_bitwise_validate(const struct setting *pset, const char *val,
3279 struct connection *caller, char *reject_msg,
3280 size_t reject_msg_len)
3282 unsigned int_val;
3284 return setting_bitwise_validate_base(pset, val, &int_val, caller,
3285 reject_msg, reject_msg_len);
3288 /****************************************************************************
3289 Compute the name of the current value of the setting.
3290 ****************************************************************************/
3291 const char *setting_value_name(const struct setting *pset, bool pretty,
3292 char *buf, size_t buf_len)
3294 fc_assert_ret_val(NULL != pset, NULL);
3295 fc_assert_ret_val(NULL != buf, NULL);
3296 fc_assert_ret_val(0 < buf_len, NULL);
3298 switch (pset->stype) {
3299 case SSET_BOOL:
3300 return setting_bool_to_str(pset, *pset->boolean.pvalue,
3301 pretty, buf, buf_len);
3302 case SSET_INT:
3303 return setting_int_to_str(pset, *pset->integer.pvalue,
3304 pretty, buf, buf_len);
3305 case SSET_STRING:
3306 return setting_str_to_str(pset, pset->string.value,
3307 pretty, buf, buf_len);
3308 case SSET_ENUM:
3309 return setting_enum_to_str(pset, read_enum_value(pset),
3310 pretty, buf, buf_len);
3311 case SSET_BITWISE:
3312 return setting_bitwise_to_str(pset, *pset->bitwise.pvalue,
3313 pretty, buf, buf_len);
3316 log_error("%s(): Setting \"%s\" (nb %d) not handled in switch statement.",
3317 __FUNCTION__, setting_name(pset), setting_number(pset));
3318 return NULL;
3321 /****************************************************************************
3322 Compute the name of the default value of the setting.
3323 ****************************************************************************/
3324 const char *setting_default_name(const struct setting *pset, bool pretty,
3325 char *buf, size_t buf_len)
3327 fc_assert_ret_val(NULL != pset, NULL);
3328 fc_assert_ret_val(NULL != buf, NULL);
3329 fc_assert_ret_val(0 < buf_len, NULL);
3331 switch (pset->stype) {
3332 case SSET_BOOL:
3333 return setting_bool_to_str(pset, pset->boolean.default_value,
3334 pretty, buf, buf_len);
3335 case SSET_INT:
3336 return setting_int_to_str(pset, pset->integer.default_value,
3337 pretty, buf, buf_len);
3338 case SSET_STRING:
3339 return setting_str_to_str(pset, pset->string.default_value,
3340 pretty, buf, buf_len);
3341 case SSET_ENUM:
3342 return setting_enum_to_str(pset, pset->enumerator.default_value,
3343 pretty, buf, buf_len);
3344 case SSET_BITWISE:
3345 return setting_bitwise_to_str(pset, pset->bitwise.default_value,
3346 pretty, buf, buf_len);
3349 log_error("%s(): Setting \"%s\" (nb %d) not handled in switch statement.",
3350 __FUNCTION__, setting_name(pset), setting_number(pset));
3351 return NULL;
3354 /****************************************************************************
3355 Update the setting to the default value
3356 ****************************************************************************/
3357 static void setting_set_to_default(struct setting *pset)
3359 switch (pset->stype) {
3360 case SSET_BOOL:
3361 (*pset->boolean.pvalue) = pset->boolean.default_value;
3362 break;
3363 case SSET_INT:
3364 (*pset->integer.pvalue) = pset->integer.default_value;
3365 break;
3366 case SSET_STRING:
3367 fc_strlcpy(pset->string.value, pset->string.default_value,
3368 pset->string.value_size);
3369 break;
3370 case SSET_ENUM:
3371 set_enum_value(pset, pset->enumerator.default_value);
3372 break;
3373 case SSET_BITWISE:
3374 (*pset->bitwise.pvalue) = pset->bitwise.default_value;
3375 break;
3379 /********************************************************************
3380 Execute the action callback if needed.
3381 *********************************************************************/
3382 void setting_action(const struct setting *pset)
3384 if (pset->action != NULL) {
3385 pset->action(pset);
3389 /**************************************************************************
3390 Load game settings from ruleset file 'game.ruleset'.
3391 **************************************************************************/
3392 bool settings_ruleset(struct section_file *file, const char *section,
3393 bool act)
3395 const char *name;
3396 int j;
3398 /* Unlock all settings. */
3399 settings_iterate(SSET_ALL, pset) {
3400 setting_lock_set(pset, FALSE);
3401 setting_set_to_default(pset);
3402 } settings_iterate_end;
3404 /* settings */
3405 if (NULL == secfile_section_by_name(file, section)) {
3406 /* no settings in ruleset file */
3407 log_verbose("no [%s] section for game settings in %s", section,
3408 secfile_name(file));
3409 return FALSE;
3412 for (j = 0; (name = secfile_lookup_str_default(file, NULL, "%s.set%d.name",
3413 section, j)); j++) {
3414 char path[256];
3415 fc_snprintf(path, sizeof(path), "%s.set%d", section, j);
3417 if (!setting_ruleset_one(file, name, path)) {
3418 log_error("unknown setting in '%s': %s", secfile_name(file), name);
3422 /* Execute all setting actions to consider actions due to the
3423 * default values. */
3424 if (act) {
3425 settings_iterate(SSET_ALL, pset) {
3426 setting_action(pset);
3427 } settings_iterate_end;
3430 /* send game settings */
3431 send_server_settings(NULL);
3433 return TRUE;
3436 /**************************************************************************
3437 Set one setting from the game.ruleset file.
3438 **************************************************************************/
3439 static bool setting_ruleset_one(struct section_file *file,
3440 const char *name, const char *path)
3442 struct setting *pset = NULL;
3443 char reject_msg[256], buf[256];
3444 bool lock;
3446 settings_iterate(SSET_ALL, pset_check) {
3447 if (0 == fc_strcasecmp(setting_name(pset_check), name)) {
3448 pset = pset_check;
3449 break;
3451 } settings_iterate_end;
3453 if (pset == NULL) {
3454 /* no setting found */
3455 return FALSE;
3458 switch (pset->stype) {
3459 case SSET_BOOL:
3461 int ival;
3462 bool val;
3464 /* Allow string with same boolean representation as accepted on
3465 * server command line */
3466 if (secfile_lookup_enum_data(file, &ival, FALSE,
3467 setting_bool_secfile_str, pset,
3468 "%s.value", path)) {
3469 val = (ival != 0);
3470 } else if (!secfile_lookup_bool(file, &val, "%s.value", path)) {
3471 log_error("Can't read value for setting '%s': %s", name,
3472 secfile_error());
3473 break;
3475 if (val != *pset->boolean.pvalue) {
3476 if (NULL == pset->boolean.validate
3477 || pset->boolean.validate(val, NULL, reject_msg,
3478 sizeof(reject_msg))) {
3479 *pset->boolean.pvalue = val;
3480 log_normal(_("Ruleset: '%s' has been set to %s."),
3481 setting_name(pset),
3482 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3483 } else {
3484 log_error("%s", reject_msg);
3488 break;
3490 case SSET_INT:
3492 int val;
3494 if (!secfile_lookup_int(file, &val, "%s.value", path)) {
3495 log_error("Can't read value for setting '%s': %s", name,
3496 secfile_error());
3497 } else if (val != *pset->integer.pvalue) {
3498 if (setting_int_set(pset, val, NULL, reject_msg,
3499 sizeof(reject_msg))) {
3500 log_normal(_("Ruleset: '%s' has been set to %s."),
3501 setting_name(pset),
3502 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3503 } else {
3504 log_error("%s", reject_msg);
3508 break;
3510 case SSET_STRING:
3512 const char *val = secfile_lookup_str(file, "%s.value", path);
3514 if (NULL == val) {
3515 log_error("Can't read value for setting '%s': %s", name,
3516 secfile_error());
3517 } else if (0 != strcmp(val, pset->string.value)) {
3518 if (setting_str_set(pset, val, NULL, reject_msg,
3519 sizeof(reject_msg))) {
3520 log_normal(_("Ruleset: '%s' has been set to %s."),
3521 setting_name(pset),
3522 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3523 } else {
3524 log_error("%s", reject_msg);
3528 break;
3530 case SSET_ENUM:
3532 int val;
3534 if (!secfile_lookup_enum_data(file, &val, FALSE,
3535 setting_enum_secfile_str, pset,
3536 "%s.value", path)) {
3537 log_error("Can't read value for setting '%s': %s",
3538 name, secfile_error());
3539 } else if (val != read_enum_value(pset)) {
3540 if (NULL == pset->enumerator.validate
3541 || pset->enumerator.validate(val, NULL, reject_msg,
3542 sizeof(reject_msg))) {
3543 set_enum_value(pset, val);
3544 log_normal(_("Ruleset: '%s' has been set to %s."),
3545 setting_name(pset),
3546 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3547 } else {
3548 log_error("%s", reject_msg);
3552 break;
3554 case SSET_BITWISE:
3556 int val;
3558 if (!secfile_lookup_enum_data(file, &val, TRUE,
3559 setting_bitwise_secfile_str, pset,
3560 "%s.value", path)) {
3561 log_error("Can't read value for setting '%s': %s",
3562 name, secfile_error());
3563 } else if (val != *pset->bitwise.pvalue) {
3564 if (NULL == pset->bitwise.validate
3565 || pset->bitwise.validate((unsigned) val, NULL,
3566 reject_msg, sizeof(reject_msg))) {
3567 *pset->bitwise.pvalue = val;
3568 log_normal(_("Ruleset: '%s' has been set to %s."),
3569 setting_name(pset),
3570 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3571 } else {
3572 log_error("%s", reject_msg);
3576 break;
3579 /* set lock */
3580 lock = secfile_lookup_bool_default(file, FALSE, "%s.lock", path);
3582 if (lock) {
3583 /* set lock */
3584 setting_lock_set(pset, lock);
3585 log_normal(_("Ruleset: '%s' has been locked by the ruleset."),
3586 setting_name(pset));
3589 return TRUE;
3592 /**************************************************************************
3593 Returns whether the setting has been changed (is not default).
3594 **************************************************************************/
3595 bool setting_changed(const struct setting *pset)
3597 switch (setting_type(pset)) {
3598 case SSET_BOOL:
3599 return (*pset->boolean.pvalue != pset->boolean.default_value);
3600 case SSET_INT:
3601 return (*pset->integer.pvalue != pset->integer.default_value);
3602 case SSET_STRING:
3603 return (0 != strcmp(pset->string.value, pset->string.default_value));
3604 case SSET_ENUM:
3605 return (read_enum_value(pset) != pset->enumerator.default_value);
3606 case SSET_BITWISE:
3607 return (*pset->bitwise.pvalue != pset->bitwise.default_value);
3610 log_error("%s(): Setting \"%s\" (nb %d) not handled in switch statement.",
3611 __FUNCTION__, setting_name(pset), setting_number(pset));
3612 return FALSE;
3615 /**************************************************************************
3616 Returns if the setting is locked by the ruleset.
3617 **************************************************************************/
3618 bool setting_locked(const struct setting *pset)
3620 return pset->locked;
3623 /**************************************************************************
3624 Set the value for the lock of a setting.
3625 **************************************************************************/
3626 void setting_lock_set(struct setting *pset, bool lock)
3628 pset->locked = lock;
3631 /**************************************************************************
3632 Save the setting value of the current game.
3633 **************************************************************************/
3634 static void setting_game_set(struct setting *pset, bool init)
3636 switch (setting_type(pset)) {
3637 case SSET_BOOL:
3638 pset->boolean.game_value = *pset->boolean.pvalue;
3639 break;
3641 case SSET_INT:
3642 pset->integer.game_value = *pset->integer.pvalue;
3643 break;
3645 case SSET_STRING:
3646 if (init) {
3647 pset->string.game_value
3648 = fc_calloc(1, pset->string.value_size
3649 * sizeof(pset->string.game_value));
3651 fc_strlcpy(pset->string.game_value, pset->string.value,
3652 pset->string.value_size);
3653 break;
3655 case SSET_ENUM:
3656 pset->enumerator.game_value = read_enum_value(pset);
3657 break;
3659 case SSET_BITWISE:
3660 pset->bitwise.game_value = *pset->bitwise.pvalue;
3661 break;
3665 /**************************************************************************
3666 Free the memory used for the settings at game start.
3667 **************************************************************************/
3668 static void setting_game_free(struct setting *pset)
3670 if (setting_type(pset) == SSET_STRING) {
3671 FC_FREE(pset->string.game_value);
3675 /**************************************************************************
3676 Restore the setting to the value used at the start of the current game.
3677 **************************************************************************/
3678 static void setting_game_restore(struct setting *pset)
3680 char reject_msg[256] = "", buf[256];
3681 bool res = FALSE;
3683 if (!setting_is_changeable(pset, NULL, reject_msg, sizeof(reject_msg))) {
3684 log_debug("Can't restore '%s': %s", setting_name(pset),
3685 reject_msg);
3686 return;
3689 switch (setting_type(pset)) {
3690 case SSET_BOOL:
3691 res = (NULL != setting_bool_to_str(pset, pset->boolean.game_value,
3692 FALSE, buf, sizeof(buf))
3693 && setting_bool_set(pset, buf, NULL, reject_msg,
3694 sizeof(reject_msg)));
3695 break;
3697 case SSET_INT:
3698 res = setting_int_set(pset, pset->integer.game_value, NULL, reject_msg,
3699 sizeof(reject_msg));
3700 break;
3702 case SSET_STRING:
3703 res = setting_str_set(pset, pset->string.game_value, NULL, reject_msg,
3704 sizeof(reject_msg));
3705 break;
3707 case SSET_ENUM:
3708 res = (NULL != setting_enum_to_str(pset, pset->enumerator.game_value,
3709 FALSE, buf, sizeof(buf))
3710 && setting_enum_set(pset, buf, NULL, reject_msg,
3711 sizeof(reject_msg)));
3712 break;
3714 case SSET_BITWISE:
3715 res = (NULL != setting_bitwise_to_str(pset, pset->bitwise.game_value,
3716 FALSE, buf, sizeof(buf))
3717 && setting_bitwise_set(pset, buf, NULL, reject_msg,
3718 sizeof(reject_msg)));
3719 break;
3722 if (!res) {
3723 log_error("Error restoring setting '%s' to the value from game start: "
3724 "%s", setting_name(pset), reject_msg);
3728 /**************************************************************************
3729 Save setting values at the start of the game.
3730 **************************************************************************/
3731 void settings_game_start(void)
3733 settings_iterate(SSET_ALL, pset) {
3734 setting_game_set(pset, FALSE);
3735 } settings_iterate_end;
3737 /* Settings from the start of the game are saved. */
3738 game.server.settings_gamestart_valid = TRUE;
3741 /********************************************************************
3742 Save game settings.
3743 *********************************************************************/
3744 void settings_game_save(struct section_file *file, const char *section)
3746 int set_count = 0;
3748 settings_iterate(SSET_ALL, pset) {
3749 secfile_insert_str(file, setting_name(pset),
3750 "%s.set%d.name", section, set_count);
3751 switch (setting_type(pset)) {
3752 case SSET_BOOL:
3753 secfile_insert_bool(file, *pset->boolean.pvalue,
3754 "%s.set%d.value", section, set_count);
3755 secfile_insert_bool(file, pset->boolean.game_value,
3756 "%s.set%d.gamestart", section, set_count);
3757 break;
3758 case SSET_INT:
3759 secfile_insert_int(file, *pset->integer.pvalue,
3760 "%s.set%d.value", section, set_count);
3761 secfile_insert_int(file, pset->integer.game_value,
3762 "%s.set%d.gamestart", section, set_count);
3763 break;
3764 case SSET_STRING:
3765 secfile_insert_str(file, pset->string.value,
3766 "%s.set%d.value", section, set_count);
3767 secfile_insert_str(file, pset->string.game_value,
3768 "%s.set%d.gamestart", section, set_count);
3769 break;
3770 case SSET_ENUM:
3771 secfile_insert_enum_data(file, read_enum_value(pset), FALSE,
3772 setting_enum_secfile_str, pset,
3773 "%s.set%d.value", section, set_count);
3774 secfile_insert_enum_data(file, pset->enumerator.game_value, FALSE,
3775 setting_enum_secfile_str, pset,
3776 "%s.set%d.gamestart", section, set_count);
3777 break;
3778 case SSET_BITWISE:
3779 secfile_insert_enum_data(file, *pset->bitwise.pvalue, TRUE,
3780 setting_bitwise_secfile_str, pset,
3781 "%s.set%d.value", section, set_count);
3782 secfile_insert_enum_data(file, pset->bitwise.game_value, TRUE,
3783 setting_bitwise_secfile_str, pset,
3784 "%s.set%d.gamestart", section, set_count);
3785 break;
3787 set_count++;
3788 } settings_iterate_end;
3790 secfile_insert_int(file, set_count, "%s.set_count", section);
3791 secfile_insert_bool(file, game.server.settings_gamestart_valid,
3792 "%s.gamestart_valid", section);
3795 /********************************************************************
3796 Restore all settings from a savegame.
3797 *********************************************************************/
3798 void settings_game_load(struct section_file *file, const char *section)
3800 const char *name;
3801 char reject_msg[256], buf[256];
3802 int i, set_count;
3803 int oldcitymindist = game.info.citymindist; /* backwards compat, see below */
3805 /* Compatibility with savegames created with older versions is usually
3806 * handled as conversions in savegame2.c compat_load_<version>() */
3808 if (!secfile_lookup_int(file, &set_count, "%s.set_count", section)) {
3809 /* Old savegames and scenarios doesn't contain this, not an error. */
3810 log_verbose("Can't read the number of settings in the save file.");
3811 return;
3814 /* Check if the saved settings are valid settings from game start. */
3815 game.server.settings_gamestart_valid
3816 = secfile_lookup_bool_default(file, FALSE, "%s.gamestart_valid",
3817 section);
3819 for (i = 0; i < set_count; i++) {
3820 name = secfile_lookup_str(file, "%s.set%d.name", section, i);
3822 settings_iterate(SSET_ALL, pset) {
3823 if (fc_strcasecmp(setting_name(pset), name) != 0) {
3824 continue;
3827 /* Load the current value of the setting. */
3828 switch (pset->stype) {
3829 case SSET_BOOL:
3831 bool val;
3833 if (!secfile_lookup_bool(file, &val, "%s.set%d.value", section,
3834 i)) {
3835 log_verbose("Option '%s' not defined in the savegame: %s", name,
3836 secfile_error());
3837 } else if (val != *pset->boolean.pvalue) {
3838 if (setting_is_changeable(pset, NULL, reject_msg,
3839 sizeof(reject_msg))
3840 && (NULL == pset->boolean.validate
3841 || pset->boolean.validate(val, NULL, reject_msg,
3842 sizeof(reject_msg)))) {
3843 *pset->boolean.pvalue = val;
3844 log_normal(_("Savegame: '%s' has been set to %s."),
3845 setting_name(pset),
3846 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3847 } else {
3848 log_error("Savegame: error restoring '%s' . (%s)",
3849 setting_name(pset), reject_msg);
3853 break;
3855 case SSET_INT:
3857 int val;
3859 if (!secfile_lookup_int(file, &val, "%s.set%d.value", section, i)) {
3860 log_verbose("Option '%s' not defined in the savegame: %s", name,
3861 secfile_error());
3862 } else if (val != *pset->integer.pvalue) {
3863 if (setting_is_changeable(pset, NULL, reject_msg,
3864 sizeof(reject_msg))
3865 && (NULL == pset->integer.validate
3866 || pset->integer.validate(val, NULL, reject_msg,
3867 sizeof(reject_msg)))) {
3868 *pset->integer.pvalue = val;
3869 log_normal(_("Savegame: '%s' has been set to %s."),
3870 setting_name(pset),
3871 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3872 } else {
3873 log_error("Savegame: error restoring '%s' . (%s)",
3874 setting_name(pset), reject_msg);
3878 break;
3880 case SSET_STRING:
3882 const char *val = secfile_lookup_str(file, "%s.set%d.value",
3883 section, i);
3885 if (NULL == val) {
3886 log_verbose("Option '%s' not defined in the savegame: %s", name,
3887 secfile_error());
3888 } else if (0 != strcmp(val, pset->string.value)) {
3889 if (setting_str_set(pset, val, NULL, reject_msg,
3890 sizeof(reject_msg))) {
3891 log_normal(_("Savegame: '%s' has been set to %s."),
3892 setting_name(pset),
3893 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3894 } else {
3895 log_error("Savegame: error restoring '%s' . (%s)",
3896 setting_name(pset), reject_msg);
3900 break;
3902 case SSET_ENUM:
3904 int val;
3906 if (!secfile_lookup_enum_data(file, &val, FALSE,
3907 setting_enum_secfile_str, pset,
3908 "%s.set%d.value", section, i)) {
3909 log_verbose("Option '%s' not defined in the savegame: %s", name,
3910 secfile_error());
3911 } else if (val != read_enum_value(pset)) {
3912 if (setting_is_changeable(pset, NULL, reject_msg,
3913 sizeof(reject_msg))
3914 && (NULL == pset->enumerator.validate
3915 || pset->enumerator.validate(val, NULL, reject_msg,
3916 sizeof(reject_msg)))) {
3917 set_enum_value(pset, val);
3918 log_normal(_("Savegame: '%s' has been set to %s."),
3919 setting_name(pset),
3920 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3921 } else {
3922 log_error("Savegame: error restoring '%s' . (%s)",
3923 setting_name(pset), reject_msg);
3927 break;
3929 case SSET_BITWISE:
3931 int val;
3933 if (!secfile_lookup_enum_data(file, &val, TRUE,
3934 setting_bitwise_secfile_str, pset,
3935 "%s.set%d.value", section, i)) {
3936 log_verbose("Option '%s' not defined in the savegame: %s", name,
3937 secfile_error());
3938 } else if (val != *pset->bitwise.pvalue) {
3939 if (setting_is_changeable(pset, NULL, reject_msg,
3940 sizeof(reject_msg))
3941 && (NULL == pset->bitwise.validate
3942 || pset->bitwise.validate(val, NULL, reject_msg,
3943 sizeof(reject_msg)))) {
3944 *pset->bitwise.pvalue = val;
3945 log_normal(_("Savegame: '%s' has been set to %s."),
3946 setting_name(pset),
3947 setting_value_name(pset, TRUE, buf, sizeof(buf)));
3948 } else {
3949 log_error("Savegame: error restoring '%s' . (%s)",
3950 setting_name(pset), reject_msg);
3954 break;
3957 if (game.server.settings_gamestart_valid) {
3958 /* Load the value of the setting at the start of the game. */
3959 switch (pset->stype) {
3960 case SSET_BOOL:
3961 pset->boolean.game_value =
3962 secfile_lookup_bool_default(file, *pset->boolean.pvalue,
3963 "%s.set%d.gamestart", section, i);
3964 break;
3966 case SSET_INT:
3967 pset->integer.game_value =
3968 secfile_lookup_int_default(file, *pset->integer.pvalue,
3969 "%s.set%d.gamestart", section, i);
3970 break;
3972 case SSET_STRING:
3973 fc_strlcpy(pset->string.game_value,
3974 secfile_lookup_str_default(file, pset->string.value,
3975 "%s.set%d.gamestart",
3976 section, i),
3977 pset->string.value_size);
3978 break;
3980 case SSET_ENUM:
3981 pset->enumerator.game_value =
3982 secfile_lookup_enum_default_data(file,
3983 read_enum_value(pset), FALSE, setting_enum_secfile_str,
3984 pset, "%s.set%d.gamestart", section, i);
3985 break;
3987 case SSET_BITWISE:
3988 pset->bitwise.game_value =
3989 secfile_lookup_enum_default_data(file,
3990 *pset->bitwise.pvalue, TRUE, setting_bitwise_secfile_str,
3991 pset, "%s.set%d.gamestart", section, i);
3992 break;
3995 } settings_iterate_end;
3998 /* Backwards compatibility for pre-2.4 savegames: citymindist=0 used to mean
3999 * take from ruleset min_dist_bw_cities, but that no longer exists.
4000 * This is here rather than in savegame2.c compat functions, as we need
4001 * to have loaded the relevant ruleset to know what to set it to (the
4002 * ruleset and any 'citymindist' setting it contains will have been loaded
4003 * before this function was called). */
4004 if (game.info.citymindist == 0) {
4005 game.info.citymindist = oldcitymindist;
4008 settings_iterate(SSET_ALL, pset) {
4009 /* Have to do this at the end due to dependencies ('aifill' and
4010 * 'maxplayer'). */
4011 setting_action(pset);
4012 } settings_iterate_end;
4015 /**************************************************************************
4016 Reset all settings to the values at game start.
4017 **************************************************************************/
4018 bool settings_game_reset(void)
4020 if (!game.server.settings_gamestart_valid) {
4021 log_debug("No saved settings from the game start available.");
4022 return FALSE;
4025 settings_iterate(SSET_ALL, pset) {
4026 setting_game_restore(pset);
4027 } settings_iterate_end;
4029 return TRUE;
4032 /**************************************************************************
4033 Initialize stuff related to this code module.
4034 **************************************************************************/
4035 void settings_init(bool act)
4037 settings_list_init();
4039 settings_iterate(SSET_ALL, pset) {
4040 setting_lock_set(pset, FALSE);
4041 setting_set_to_default(pset);
4042 setting_game_set(pset, TRUE);
4043 if (act) {
4044 setting_action(pset);
4046 } settings_iterate_end;
4048 settings_list_update();
4051 /********************************************************************
4052 Reset all settings iff they are changeable.
4053 *********************************************************************/
4054 void settings_reset(void)
4056 settings_iterate(SSET_ALL, pset) {
4057 if (setting_is_changeable(pset, NULL, NULL, 0)) {
4058 setting_set_to_default(pset);
4059 setting_action(pset);
4061 } settings_iterate_end;
4064 /**************************************************************************
4065 Update stuff every turn that is related to this code module. Run this
4066 on turn end.
4067 **************************************************************************/
4068 void settings_turn(void)
4070 /* Nothing at the moment. */
4073 /**************************************************************************
4074 Deinitialize stuff related to this code module.
4075 **************************************************************************/
4076 void settings_free(void)
4078 settings_iterate(SSET_ALL, pset) {
4079 setting_game_free(pset);
4080 } settings_iterate_end;
4082 settings_list_free();
4085 /****************************************************************************
4086 Returns the total number of settings.
4087 ****************************************************************************/
4088 int settings_number(void)
4090 return SETTINGS_NUM;
4093 /****************************************************************************
4094 Tell the client about just one server setting. Call this after a setting
4095 is saved.
4096 ****************************************************************************/
4097 void send_server_setting(struct conn_list *dest, const struct setting *pset)
4099 if (!dest) {
4100 dest = game.est_connections;
4103 #define PACKET_COMMON_INIT(packet, pset, pconn) \
4104 memset(&packet, 0, sizeof(packet)); \
4105 packet.id = setting_number(pset); \
4106 packet.is_visible = setting_is_visible(pset, pconn); \
4107 packet.is_changeable = setting_is_changeable(pset, pconn, NULL, 0); \
4108 packet.initial_setting = game.info.is_new_game;
4110 switch (setting_type(pset)) {
4111 case SSET_BOOL:
4113 struct packet_server_setting_bool packet;
4115 conn_list_iterate(dest, pconn) {
4116 PACKET_COMMON_INIT(packet, pset, pconn);
4117 if (packet.is_visible) {
4118 packet.val = *pset->boolean.pvalue;
4119 packet.default_val = pset->boolean.default_value;
4121 send_packet_server_setting_bool(pconn, &packet);
4122 } conn_list_iterate_end;
4124 break;
4125 case SSET_INT:
4127 struct packet_server_setting_int packet;
4129 conn_list_iterate(dest, pconn) {
4130 PACKET_COMMON_INIT(packet, pset, pconn);
4131 if (packet.is_visible) {
4132 packet.val = *pset->integer.pvalue;
4133 packet.default_val = pset->integer.default_value;
4134 packet.min_val = pset->integer.min_value;
4135 packet.max_val = pset->integer.max_value;
4137 send_packet_server_setting_int(pconn, &packet);
4138 } conn_list_iterate_end;
4140 break;
4141 case SSET_STRING:
4143 struct packet_server_setting_str packet;
4145 conn_list_iterate(dest, pconn) {
4146 PACKET_COMMON_INIT(packet, pset, pconn);
4147 if (packet.is_visible) {
4148 sz_strlcpy(packet.val, pset->string.value);
4149 sz_strlcpy(packet.default_val, pset->string.default_value);
4151 send_packet_server_setting_str(pconn, &packet);
4152 } conn_list_iterate_end;
4154 break;
4155 case SSET_ENUM:
4157 struct packet_server_setting_enum packet;
4158 const struct sset_val_name *val_name;
4159 int i;
4161 conn_list_iterate(dest, pconn) {
4162 PACKET_COMMON_INIT(packet, pset, pconn);
4163 if (packet.is_visible) {
4164 packet.val = read_enum_value(pset);
4165 packet.default_val = pset->enumerator.default_value;
4166 for (i = 0; (val_name = pset->enumerator.name(i)); i++) {
4167 sz_strlcpy(packet.support_names[i], val_name->support);
4168 /* Send untranslated string */
4169 sz_strlcpy(packet.pretty_names[i], val_name->pretty);
4171 packet.values_num = i;
4172 fc_assert(i <= ARRAY_SIZE(packet.support_names));
4173 fc_assert(i <= ARRAY_SIZE(packet.pretty_names));
4175 send_packet_server_setting_enum(pconn, &packet);
4176 } conn_list_iterate_end;
4178 break;
4179 case SSET_BITWISE:
4181 struct packet_server_setting_bitwise packet;
4182 const struct sset_val_name *val_name;
4183 int i;
4185 conn_list_iterate(dest, pconn) {
4186 PACKET_COMMON_INIT(packet, pset, pconn);
4187 if (packet.is_visible) {
4188 packet.val = *pset->bitwise.pvalue;
4189 packet.default_val = pset->bitwise.default_value;
4190 for (i = 0; (val_name = pset->bitwise.name(i)); i++) {
4191 sz_strlcpy(packet.support_names[i], val_name->support);
4192 /* Send untranslated string */
4193 sz_strlcpy(packet.pretty_names[i], val_name->pretty);
4195 packet.bits_num = i;
4196 fc_assert(i <= ARRAY_SIZE(packet.support_names));
4197 fc_assert(i <= ARRAY_SIZE(packet.pretty_names));
4199 send_packet_server_setting_bitwise(pconn, &packet);
4200 } conn_list_iterate_end;
4202 break;
4205 #undef PACKET_INIT
4208 /****************************************************************************
4209 Tell the client about all server settings.
4210 ****************************************************************************/
4211 void send_server_settings(struct conn_list *dest)
4213 settings_iterate(SSET_ALL, pset) {
4214 send_server_setting(dest, pset);
4215 } settings_iterate_end;
4218 /****************************************************************************
4219 Send the ALLOW_HACK server settings. Usually called when the access level
4220 of the user changes.
4221 ****************************************************************************/
4222 void send_server_hack_level_settings(struct conn_list *dest)
4224 settings_iterate(SSET_ALL, pset) {
4225 if (!pset->to_client) {
4226 send_server_setting(dest, pset);
4228 } settings_iterate_end;
4231 /****************************************************************************
4232 Tell the client about all server settings.
4233 ****************************************************************************/
4234 void send_server_setting_control(struct connection *pconn)
4236 struct packet_server_setting_control control;
4237 struct packet_server_setting_const setting;
4238 int i;
4240 control.settings_num = SETTINGS_NUM;
4242 /* Fill in the category strings. */
4243 fc_assert(SSET_NUM_CATEGORIES <= ARRAY_SIZE(control.category_names));
4244 control.categories_num = SSET_NUM_CATEGORIES;
4245 for (i = 0; i < SSET_NUM_CATEGORIES; i++) {
4246 /* Send untranslated name */
4247 sz_strlcpy(control.category_names[i], sset_category_name(i));
4250 /* Send off the control packet. */
4251 send_packet_server_setting_control(pconn, &control);
4253 /* Send the constant and common part of the settings. */
4254 settings_iterate(SSET_ALL, pset) {
4255 setting.id = setting_number(pset);
4256 sz_strlcpy(setting.name, setting_name(pset));
4257 /* Send untranslated strings to client */
4258 sz_strlcpy(setting.short_help, setting_short_help(pset));
4259 sz_strlcpy(setting.extra_help, setting_extra_help(pset));
4260 setting.category = pset->scategory;
4262 send_packet_server_setting_const(pconn, &setting);
4263 } settings_iterate_end;
4266 /*****************************************************************************
4267 Initialise sorted settings.
4268 *****************************************************************************/
4269 static void settings_list_init(void)
4271 struct setting *pset;
4272 int i;
4274 fc_assert_ret(setting_sorted.init == FALSE);
4276 /* Do it for all values of enum sset_level. */
4277 for (i = 0; i < OLEVELS_NUM; i++) {
4278 setting_sorted.level[i] = setting_list_new();
4281 for (i = 0; (pset = setting_by_number(i)); i++) {
4282 /* Add the setting to the list of all settings. */
4283 setting_list_append(setting_sorted.level[SSET_ALL], pset);
4285 switch (setting_level(pset)) {
4286 case SSET_NONE:
4287 /* No setting should be in this level. */
4288 fc_assert_msg(setting_level(pset) != SSET_NONE,
4289 "No setting level defined for '%s'.", setting_name(pset));
4290 break;
4291 case SSET_ALL:
4292 /* Done above - list of all settings. */
4293 break;
4294 case SSET_VITAL:
4295 setting_list_append(setting_sorted.level[SSET_VITAL], pset);
4296 break;
4297 case SSET_SITUATIONAL:
4298 setting_list_append(setting_sorted.level[SSET_SITUATIONAL], pset);
4299 break;
4300 case SSET_RARE:
4301 setting_list_append(setting_sorted.level[SSET_RARE], pset);
4302 break;
4303 case SSET_CHANGED:
4304 case SSET_LOCKED:
4305 /* This is done in settings_list_update. */
4306 break;
4307 case OLEVELS_NUM:
4308 /* No setting should be in this level. */
4309 fc_assert_msg(setting_level(pset) != OLEVELS_NUM,
4310 "Invalid setting level for '%s' (%s).",
4311 setting_name(pset), sset_level_name(setting_level(pset)));
4312 break;
4316 /* Sort the lists. */
4317 for (i = 0; i < OLEVELS_NUM; i++) {
4318 setting_list_sort(setting_sorted.level[i], settings_list_cmp);
4321 setting_sorted.init = TRUE;
4324 /*****************************************************************************
4325 Update sorted settings (changed and locked values).
4326 *****************************************************************************/
4327 void settings_list_update(void)
4329 struct setting *pset;
4330 int i;
4332 fc_assert_ret(setting_sorted.init == TRUE);
4334 /* Clear the lists for changed and locked values. */
4335 setting_list_clear(setting_sorted.level[SSET_CHANGED]);
4336 setting_list_clear(setting_sorted.level[SSET_LOCKED]);
4338 /* Refill them. */
4339 for (i = 0; (pset = setting_by_number(i)); i++) {
4340 if (setting_changed(pset)) {
4341 setting_list_append(setting_sorted.level[SSET_CHANGED], pset);
4343 if (setting_locked(pset)) {
4344 setting_list_append(setting_sorted.level[SSET_LOCKED], pset);
4348 /* Sort them. */
4349 setting_list_sort(setting_sorted.level[SSET_CHANGED], settings_list_cmp);
4350 setting_list_sort(setting_sorted.level[SSET_LOCKED], settings_list_cmp);
4353 /*****************************************************************************
4354 Update sorted settings (changed and locked values).
4355 *****************************************************************************/
4356 int settings_list_cmp(const struct setting *const *ppset1,
4357 const struct setting *const *ppset2)
4359 const struct setting *pset1 = *ppset1;
4360 const struct setting *pset2 = *ppset2;
4362 return fc_strcasecmp(setting_name(pset1), setting_name(pset2));
4365 /*****************************************************************************
4366 Get a settings list of a certain level. Call settings_list_update() before
4367 if something was changed.
4368 *****************************************************************************/
4369 struct setting_list *settings_list_get(enum sset_level level)
4371 fc_assert_ret_val(setting_sorted.init == TRUE, NULL);
4372 fc_assert_ret_val(setting_sorted.level[level] != NULL, NULL);
4373 fc_assert_ret_val(sset_level_is_valid(level), NULL);
4375 return setting_sorted.level[level];
4378 /*****************************************************************************
4379 Free sorted settings.
4380 *****************************************************************************/
4381 static void settings_list_free(void)
4383 int i;
4385 fc_assert_ret(setting_sorted.init == TRUE);
4387 /* Free the lists. */
4388 for (i = 0; i < OLEVELS_NUM; i++) {
4389 setting_list_destroy(setting_sorted.level[i]);
4392 setting_sorted.init = FALSE;