4 * Copyright (c) 2009 Tiago Cunha <me@tiagocunha.org>
6 * Permission to use, copy, modify, and distribute this software for any
7 * purpose with or without fee is hereby granted, provided that the above
8 * copyright notice and this permission notice appear in all copies.
10 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
11 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
12 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
13 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
14 * WHATSOEVER RESULTING FROM LOSS OF MIND, USE, DATA OR PROFITS, WHETHER
15 * IN AN ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING
16 * OUT OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
19 #include <sys/types.h>
28 * Asks for confirmation before executing a command.
31 static enum args_parse_type
cmd_confirm_before_args_parse(struct args
*,
33 static enum cmd_retval
cmd_confirm_before_exec(struct cmd
*,
36 static int cmd_confirm_before_callback(struct client
*, void *,
38 static void cmd_confirm_before_free(void *);
40 const struct cmd_entry cmd_confirm_before_entry
= {
41 .name
= "confirm-before",
44 .args
= { "bp:t:", 1, 1, cmd_confirm_before_args_parse
},
45 .usage
= "[-b] [-p prompt] " CMD_TARGET_CLIENT_USAGE
" command",
47 .flags
= CMD_CLIENT_TFLAG
,
48 .exec
= cmd_confirm_before_exec
51 struct cmd_confirm_before_data
{
52 struct cmdq_item
*item
;
53 struct cmd_list
*cmdlist
;
56 static enum args_parse_type
57 cmd_confirm_before_args_parse(__unused
struct args
*args
, __unused u_int idx
,
58 __unused
char **cause
)
60 return (ARGS_PARSE_COMMANDS_OR_STRING
);
63 static enum cmd_retval
64 cmd_confirm_before_exec(struct cmd
*self
, struct cmdq_item
*item
)
66 struct args
*args
= cmd_get_args(self
);
67 struct cmd_confirm_before_data
*cdata
;
68 struct client
*tc
= cmdq_get_target_client(item
);
69 struct cmd_find_state
*target
= cmdq_get_target(item
);
71 const char *prompt
, *cmd
;
72 int wait
= !args_has(args
, 'b');
74 cdata
= xcalloc(1, sizeof *cdata
);
75 cdata
->cmdlist
= args_make_commands_now(self
, item
, 0, 1);
76 if (cdata
->cmdlist
== NULL
)
77 return (CMD_RETURN_ERROR
);
82 if ((prompt
= args_get(args
, 'p')) != NULL
)
83 xasprintf(&new_prompt
, "%s ", prompt
);
85 cmd
= cmd_get_entry(cmd_list_first(cdata
->cmdlist
))->name
;
86 xasprintf(&new_prompt
, "Confirm '%s'? (y/n) ", cmd
);
89 status_prompt_set(tc
, target
, new_prompt
, NULL
,
90 cmd_confirm_before_callback
, cmd_confirm_before_free
, cdata
,
91 PROMPT_SINGLE
, PROMPT_TYPE_COMMAND
);
95 return (CMD_RETURN_NORMAL
);
96 return (CMD_RETURN_WAIT
);
100 cmd_confirm_before_callback(struct client
*c
, void *data
, const char *s
,
103 struct cmd_confirm_before_data
*cdata
= data
;
104 struct cmdq_item
*item
= cdata
->item
, *new_item
;
107 if (c
->flags
& CLIENT_DEAD
)
110 if (s
== NULL
|| *s
== '\0')
112 if (tolower((u_char
)s
[0]) != 'y' || s
[1] != '\0')
117 new_item
= cmdq_get_command(cdata
->cmdlist
, NULL
);
118 cmdq_append(c
, new_item
);
120 new_item
= cmdq_get_command(cdata
->cmdlist
,
121 cmdq_get_state(item
));
122 cmdq_insert_after(item
, new_item
);
127 if (cmdq_get_client(item
) != NULL
&&
128 cmdq_get_client(item
)->session
== NULL
)
129 cmdq_get_client(item
)->retval
= retcode
;
136 cmd_confirm_before_free(void *data
)
138 struct cmd_confirm_before_data
*cdata
= data
;
140 cmd_list_free(cdata
->cmdlist
);