<URL: http://bugs.freeciv.org/Ticket/Display.html?id=39614 >
First step: clean up in stdinhand. /aitoggle, /remove, /cmdlevel and
/cut support the arguments between quote marks.
Patch attached.
Index: server/stdinhand.c
===================================================================
--- server/stdinhand.c (révision 13752)
+++ server/stdinhand.c (copie de travail)
@@ -810,20 +810,29 @@
/**************************************************************************
...
**************************************************************************/
-static bool toggle_ai_player(struct connection *caller, char *arg, bool check)
+static bool toggle_ai_player(struct connection *caller, char *str, bool check)
{
enum m_pre_result match_result;
struct player *pplayer;
+ char *arg;
+ bool ret = TRUE;
+ if (get_tokens(str, &arg, 1, TOKEN_DELIMITERS) == 0) {
+ cmd_reply_no_such_player(CMD_AITOGGLE, caller, NULL, M_PRE_EMPTY);
+ return FALSE;
+ }
+
pplayer = find_player_by_name_prefix(arg, &match_result);
if (!pplayer) {
cmd_reply_no_such_player(CMD_AITOGGLE, caller, arg, match_result);
- return FALSE;
+ ret = FALSE;
} else if (!check) {
toggle_ai_player_direct(caller, pplayer);
}
- return TRUE;
+
+ free(arg);
+ return ret;
}
/**************************************************************************
@@ -940,26 +949,35 @@
/**************************************************************************
...
**************************************************************************/
-static bool remove_player(struct connection *caller, char *arg, bool check)
+static bool remove_player(struct connection *caller, char *str, bool check)
{
enum m_pre_result match_result;
struct player *pplayer;
char name[MAX_LEN_NAME];
+ bool ret = FALSE;
+ char *arg;
- pplayer=find_player_by_name_prefix(arg, &match_result);
-
- if(!pplayer) {
- cmd_reply_no_such_player(CMD_REMOVE, caller, arg, match_result);
- return FALSE;
- }
-
if (!(game.info.is_new_game && server_state == PRE_GAME_STATE)) {
cmd_reply(CMD_REMOVE, caller, C_FAIL,
_("Players cannot be removed once the game has started."));
return FALSE;
}
+
+ if (get_tokens(str, &arg, 1, TOKEN_DELIMITERS) == 0) {
+ cmd_reply_no_such_player(CMD_AITOGGLE, caller, NULL, M_PRE_EMPTY);
+ return FALSE;
+ }
+
+ pplayer = find_player_by_name_prefix(arg, &match_result);
+
+ if (!pplayer) {
+ cmd_reply_no_such_player(CMD_REMOVE, caller, arg, match_result);
+ goto end;
+ }
+
+ ret = TRUE;
if (check) {
- return TRUE;
+ goto end;
}
sz_strlcpy(name, pplayer->name);
@@ -969,7 +987,10 @@
_("Removed player %s from the game."), name);
}
aifill(game.info.aifill);
- return TRUE;
+
+end:
+ free(arg);
+ return ret;
}
/**************************************************************************
@@ -1159,8 +1180,8 @@
set ptarget's cmdlevel to level if caller is allowed to do so
**************************************************************************/
static bool set_cmdlevel(struct connection *caller,
- struct connection *ptarget,
- enum cmdlevel_id level)
+ struct connection *ptarget,
+ enum cmdlevel_id level)
{
assert(ptarget != NULL); /* only ever call me for specific connection */
@@ -1240,142 +1261,132 @@
**************************************************************************/
static bool cmdlevel_command(struct connection *caller, char *str, bool check)
{
- char arg_level[MAX_LEN_CONSOLE_LINE]; /* info, ctrl etc */
- char arg_name[MAX_LEN_CONSOLE_LINE]; /* a player name, or "new" */
- char *cptr_s, *cptr_d; /* used for string ops */
-
+ char *args[2]; /* [0]: level name [1]: "new", "first" or a connection name */
+ int i, ntokens;
enum m_pre_result match_result;
enum cmdlevel_id level;
struct connection *ptarget;
+ bool ret = FALSE;
- /* find the start of the level: */
- for (cptr_s = str; *cptr_s != '\0' && !my_isalnum(*cptr_s); cptr_s++) {
- /* nothing */
- }
+ ntokens = get_tokens(str, args, 2, TOKEN_DELIMITERS);
- /* copy the level into arg_level[] */
- for(cptr_d=arg_level; *cptr_s != '\0' && my_isalnum(*cptr_s); cptr_s++, cptr_d++) {
- *cptr_d=*cptr_s;
- }
- *cptr_d='\0';
-
- if (arg_level[0] == '\0') {
+ if (ntokens == 0) {
/* no level name supplied; list the levels */
- cmd_reply(CMD_CMDLEVEL, caller, C_COMMENT, _("Command access levels in effect:"));
+ cmd_reply(CMD_CMDLEVEL, caller, C_COMMENT,
+ _("Command access levels in effect:"));
conn_list_iterate(game.est_connections, pconn) {
cmd_reply(CMD_CMDLEVEL, caller, C_COMMENT, "cmdlevel %s %s",
cmdlevel_name(pconn->access_level), pconn->username);
- }
- conn_list_iterate_end;
+ } conn_list_iterate_end;
cmd_reply(CMD_CMDLEVEL, caller, C_COMMENT,
_("Command access level for new connections: %s"),
cmdlevel_name(default_access_level));
cmd_reply(CMD_CMDLEVEL, caller, C_COMMENT,
_("Command access level for first player to take it: %s"),
cmdlevel_name(first_access_level));
- return TRUE;
+ return TRUE; /* No need to free 0 strings */
}
/* a level name was supplied; set the level */
- if ((level = cmdlevel_named(arg_level)) == ALLOW_UNRECOGNIZED) {
+ if ((level = cmdlevel_named(args[0])) == ALLOW_UNRECOGNIZED) {
cmd_reply(CMD_CMDLEVEL, caller, C_SYNTAX,
_("Error: command access level must be one of"
" 'none', 'info', 'ctrl', or 'hack'."));
- return FALSE;
+ goto end;
} else if (caller && level > caller->access_level) {
cmd_reply(CMD_CMDLEVEL, caller, C_FAIL,
_("Cannot increase command access level to '%s';"
" you only have '%s' yourself."),
- arg_level, cmdlevel_name(caller->access_level));
- return FALSE;
+ cmdlevel_name(level), cmdlevel_name(caller->access_level));
+ goto end;
}
- if (check) {
- return TRUE; /* looks good */
- }
- /* find the start of the name: */
- for (; *cptr_s != '\0' && !my_isalnum(*cptr_s); cptr_s++) {
- /* nothing */
- }
+ if (ntokens == 1) {
+ /* no playername supplied: set for all connections, and set the default */
- /* copy the name into arg_name[] */
- for(cptr_d=arg_name;
- *cptr_s != '\0' && (*cptr_s == '-' || *cptr_s == ' ' || my_isalnum(*cptr_s));
- cptr_s++ , cptr_d++) {
- *cptr_d=*cptr_s;
- }
- *cptr_d='\0';
-
- if (arg_name[0] == '\0') {
- /* no playername supplied: set for all connections, and set the default */
- conn_list_iterate(game.est_connections, pconn) {
- if (set_cmdlevel(caller, pconn, level)) {
- cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for connection %s."),
- cmdlevel_name(level), pconn->username);
- } else {
- cmd_reply(CMD_CMDLEVEL, caller, C_FAIL,
- _("Command access level could not be set to '%s' for "
- "connection %s."),
- cmdlevel_name(level), pconn->username);
- return FALSE;
- }
- }
- conn_list_iterate_end;
-
- default_access_level = level;
- cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for new players."),
- cmdlevel_name(level));
- first_access_level = level;
- cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for first player to grab it."),
- cmdlevel_name(level));
- }
- else if (strcmp(arg_name,"new") == 0) {
- default_access_level = level;
- cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for new players."),
- cmdlevel_name(level));
- if (level > first_access_level) {
+ if (!check) {
+ conn_list_iterate(game.est_connections, pconn) {
+ if (set_cmdlevel(caller, pconn, level)) {
+ cmd_reply(CMD_CMDLEVEL, caller, C_OK,
+ _("Command access level set to '%s' for connection %s."),
+ cmdlevel_name(level), pconn->username);
+ } else {
+ cmd_reply(CMD_CMDLEVEL, caller, C_FAIL,
+ _("Command access level could not be set to '%s'"
+ " for connection %s."),
+ cmdlevel_name(level), pconn->username);
+ /* Don't stop here, maybe other connection can get it */
+ }
+ } conn_list_iterate_end;
+
+ default_access_level = level;
+ cmd_reply(CMD_CMDLEVEL, caller, C_OK,
+ _("Command access level set to '%s' for new players."),
+ cmdlevel_name(level));
first_access_level = level;
cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for first player to grab it."),
- cmdlevel_name(level));
+ _("Command access level set to '%s'"
+ " for first player to grab it."),
+ cmdlevel_name(level));
}
- }
- else if (strcmp(arg_name,"first") == 0) {
- first_access_level = level;
- cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for first player to grab it."),
- cmdlevel_name(level));
- if (level < default_access_level) {
+ } else if (strcmp(args[1], "new") == 0) {
+ if (!check) {
default_access_level = level;
cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for new players."),
- cmdlevel_name(level));
+ _("Command access level set to '%s'"
+ " for new players."),
+ cmdlevel_name(level));
+ if (level > first_access_level) {
+ first_access_level = level;
+ cmd_reply(CMD_CMDLEVEL, caller, C_OK,
+ _("Command access level set to '%s'"
+ " for first player to grab it."),
+ cmdlevel_name(level));
+ }
}
- }
- else if ((ptarget = find_conn_by_user_prefix(arg_name, &match_result))) {
- if (set_cmdlevel(caller, ptarget, level)) {
+ } else if (strcmp(args[1], "first") == 0) {
+ if (!check) {
+ first_access_level = level;
cmd_reply(CMD_CMDLEVEL, caller, C_OK,
- _("Command access level set to '%s' for connection %s."),
- cmdlevel_name(level), ptarget->username);
- } else {
- cmd_reply(CMD_CMDLEVEL, caller, C_FAIL,
- _("Command access level could not be set to '%s'"
- " for connection %s."),
- cmdlevel_name(level), ptarget->username);
- return FALSE;
+ _("Command access level set to '%s'"
+ " for first player to grab it."),
+ cmdlevel_name(level));
+ if (level < default_access_level) {
+ default_access_level = level;
+ cmd_reply(CMD_CMDLEVEL, caller, C_OK,
+ _("Command access level set to '%s'"
+ " for new players."),
+ cmdlevel_name(level));
+ }
}
+ } else if ((ptarget = find_conn_by_user_prefix(args[1], &match_result))) {
+ if (!check) {
+ if (set_cmdlevel(caller, ptarget, level)) {
+ cmd_reply(CMD_CMDLEVEL, caller, C_OK,
+ _("Command access level set to '%s' for connection %s."),
+ cmdlevel_name(level), ptarget->username);
+ } else {
+ cmd_reply(CMD_CMDLEVEL, caller, C_FAIL,
+ _("Command access level could not be set to '%s'"
+ " for connection %s."),
+ cmdlevel_name(level), ptarget->username);
+ goto end;
+ }
+ }
} else {
- cmd_reply_no_such_conn(CMD_CMDLEVEL, caller, arg_name, match_result);
- return FALSE;
+ cmd_reply_no_such_conn(CMD_CMDLEVEL, caller, args[1], match_result);
+ goto end;
}
- return TRUE;
+ ret = TRUE;
+
+end:
+ for (i = 0; i < ntokens; i++) {
+ free(args[i]);
+ }
+ return ret;
}
/**************************************************************************
@@ -3636,7 +3647,7 @@
return TRUE;
}
notify_conn(game.est_connections, NULL, E_GAME_END,
- _("Game ended in a draw."));
+ _("Game ended in a draw."));
server_state = GAME_OVER_STATE;
force_end_of_sniff = TRUE;
cmd_reply(CMD_END_GAME, caller, C_OK,
@@ -3746,34 +3757,48 @@
/**************************************************************************
...
**************************************************************************/
-static bool cut_client_connection(struct connection *caller, char *name,
+static bool cut_client_connection(struct connection *caller, char *str,
bool check)
{
enum m_pre_result match_result;
struct connection *ptarget;
struct player *pplayer;
+ char *name;
+ bool was_connected, ret = FALSE;
+
+ if (get_tokens(str, &name, 1, TOKEN_DELIMITERS) == 0) {
+ cmd_reply_no_such_conn(CMD_CUT, caller, NULL, M_PRE_EMPTY);
+ return FALSE;
+ }
ptarget = find_conn_by_user_prefix(name, &match_result);
if (!ptarget) {
cmd_reply_no_such_conn(CMD_CUT, caller, name, match_result);
- return FALSE;
- } else if (check) {
- return TRUE;
+ goto end;
}
- pplayer = !ptarget->observer ? ptarget->player : NULL;
+ ret = TRUE;
+ if (check) {
+ goto end;
+ }
+ pplayer = ptarget->player;
+ was_connected = pplayer ? pplayer->is_connected : FALSE;
+
cmd_reply(CMD_CUT, caller, C_DISCONNECTED,
_("Cutting connection %s."), ptarget->username);
lost_connection_to_client(ptarget);
close_connection(ptarget);
/* if we cut the connection, unassign the login name */
- if (pplayer) {
+ if (pplayer && was_connected && !pplayer->is_connected) {
sz_strlcpy(pplayer->username, ANON_USER_NAME);
}
- return TRUE;
+
+end:
+ free(name);
+ return ret;
}
/**************************************************************************
@@ -4667,4 +4692,3 @@
}
#endif /* HAVE_LIBREADLINE */
-
_______________________________________________
Freeciv-dev mailing list
[email protected]
https://mail.gna.org/listinfo/freeciv-dev