mirror of
https://github.com/tmux/tmux.git
synced 2026-07-03 10:12:31 +00:00
Better way of working out any flag.
This commit is contained in:
43
client.c
43
client.c
@@ -69,40 +69,23 @@ static void client_dispatch_attached(struct imsg *);
|
|||||||
static void client_dispatch_wait(struct imsg *);
|
static void client_dispatch_wait(struct imsg *);
|
||||||
static const char *client_exit_message(void);
|
static const char *client_exit_message(void);
|
||||||
|
|
||||||
static int
|
/* Does any command have a flag? */
|
||||||
client_next_has_flag(int argc, char **argv, int flag)
|
|
||||||
{
|
|
||||||
struct args_value *values = args_from_vector(argc, argv);
|
|
||||||
struct cmd *cmd;
|
|
||||||
char *cause;
|
|
||||||
int result = 0;
|
|
||||||
|
|
||||||
cmd = cmd_parse(values, argc, NULL, 0, 0, &cause);
|
|
||||||
if (cmd == NULL)
|
|
||||||
free(cause);
|
|
||||||
else {
|
|
||||||
if (cmd_get_entry(cmd)->flags & flag)
|
|
||||||
result = 1;
|
|
||||||
cmd_free(cmd);
|
|
||||||
}
|
|
||||||
args_free_values(values, argc);
|
|
||||||
free(values);
|
|
||||||
return (result);
|
|
||||||
}
|
|
||||||
|
|
||||||
static int
|
static int
|
||||||
client_command_has_flag(int argc, char **argv, int flag)
|
client_command_has_flag(int argc, char **argv, int flag)
|
||||||
{
|
{
|
||||||
int start = 0, i;
|
struct args_value *values;
|
||||||
|
struct cmd_parse_tree *tree;
|
||||||
|
int found;
|
||||||
|
|
||||||
for (i = 0; i <= argc; i++) {
|
values = args_from_vector(argc, argv);
|
||||||
if (i != argc && strcmp(argv[i], ";") != 0)
|
tree = cmd_parse_from_arguments(values, argc);
|
||||||
continue;
|
found = cmd_parse_any_have(tree, flag);
|
||||||
if (i != start && client_next_has_flag(i - start, argv + start, flag))
|
|
||||||
return (1);
|
cmd_parse_free(tree);
|
||||||
start = i + 1;
|
args_free_values(values, argc);
|
||||||
}
|
free(values);
|
||||||
return (0);
|
|
||||||
|
return (found);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|||||||
117
cmd-parse.y
117
cmd-parse.y
@@ -1115,10 +1115,6 @@ cmd_parse_print_command(char **buf, struct cmd_parse_node *cmd, u_int depth)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* Emit a line break before a body line, or a space when printing on one
|
|
||||||
* line.
|
|
||||||
*/
|
|
||||||
static void
|
static void
|
||||||
cmd_parse_print_break(char **buf, u_int depth, int oneline)
|
cmd_parse_print_break(char **buf, u_int depth, int oneline)
|
||||||
{
|
{
|
||||||
@@ -1130,12 +1126,6 @@ cmd_parse_print_break(char **buf, u_int depth, int oneline)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
* An %if that shares a sequence with other commands must be printed on one
|
|
||||||
* line, because only an inline %if reparses in that position; such an %if
|
|
||||||
* always has single-sequence branch bodies, so this is lossless. An %if that
|
|
||||||
* is alone in its sequence is printed over multiple lines.
|
|
||||||
*/
|
|
||||||
static void
|
static void
|
||||||
cmd_parse_print_if(char **buf, struct cmd_parse_node *node, u_int depth,
|
cmd_parse_print_if(char **buf, struct cmd_parse_node *node, u_int depth,
|
||||||
int oneline)
|
int oneline)
|
||||||
@@ -1208,11 +1198,15 @@ static void
|
|||||||
cmd_parse_print_sequence(char **buf, struct cmd_parse_node *seq, u_int depth)
|
cmd_parse_print_sequence(char **buf, struct cmd_parse_node *seq, u_int depth)
|
||||||
{
|
{
|
||||||
struct cmd_parse_node *child;
|
struct cmd_parse_node *child;
|
||||||
int first = 1, oneline;
|
int first = 1, oneline = 0;
|
||||||
|
|
||||||
/* More than one item in a sequence forces everything onto one line. */
|
if (TAILQ_NEXT(TAILQ_FIRST(&seq->children), entry) != NULL) {
|
||||||
oneline = (TAILQ_FIRST(&seq->children) !=
|
/*
|
||||||
TAILQ_LAST(&seq->children, cmd_parse_nodes));
|
* If there is more than one item in a sequence, force
|
||||||
|
* everything on to one line.
|
||||||
|
*/
|
||||||
|
oneline = 1;
|
||||||
|
}
|
||||||
|
|
||||||
TAILQ_FOREACH(child, &seq->children, entry) {
|
TAILQ_FOREACH(child, &seq->children, entry) {
|
||||||
if (!first)
|
if (!first)
|
||||||
@@ -1240,6 +1234,101 @@ cmd_parse_print(struct cmd_parse_tree *tree)
|
|||||||
return (buf);
|
return (buf);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static char *
|
||||||
|
cmd_parse_make_string(struct cmd_parse_node *node)
|
||||||
|
{
|
||||||
|
struct cmd_parse_node *child;
|
||||||
|
char *s = NULL, *new;
|
||||||
|
|
||||||
|
if (node->type != CMD_PARSE_STRING)
|
||||||
|
return (NULL);
|
||||||
|
|
||||||
|
TAILQ_FOREACH(child, &node->children, entry) {
|
||||||
|
if (child->type != CMD_PARSE_TEXT) {
|
||||||
|
free(s);
|
||||||
|
return (NULL);
|
||||||
|
}
|
||||||
|
if (s == NULL)
|
||||||
|
s = xstrdup(child->value);
|
||||||
|
else {
|
||||||
|
xasprintf(&new, "%s%s", s, child->value);
|
||||||
|
free(s);
|
||||||
|
s = new;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (s == NULL)
|
||||||
|
s = xstrdup("");
|
||||||
|
return (s);
|
||||||
|
}
|
||||||
|
|
||||||
|
static int
|
||||||
|
cmd_parse_command_any_have(struct cmd_parse_node *node, int flag)
|
||||||
|
{
|
||||||
|
struct cmd_parse_node *child;
|
||||||
|
struct args_value *values = NULL;
|
||||||
|
struct cmd *cmd;
|
||||||
|
char *cause = NULL;
|
||||||
|
u_int count = 0;
|
||||||
|
int found = 0;
|
||||||
|
|
||||||
|
if (node->type != CMD_PARSE_COMMAND)
|
||||||
|
return (0);
|
||||||
|
|
||||||
|
TAILQ_FOREACH(child, &node->children, entry) {
|
||||||
|
values = xreallocarray(values, count + 1, sizeof *values);
|
||||||
|
memset(&values[count], 0, sizeof values[count]);
|
||||||
|
|
||||||
|
switch (child->type) {
|
||||||
|
case CMD_PARSE_STRING:
|
||||||
|
values[count].type = ARGS_STRING;
|
||||||
|
values[count].string = cmd_parse_make_string(child);
|
||||||
|
if (values[count].string == NULL)
|
||||||
|
goto out;
|
||||||
|
break;
|
||||||
|
case CMD_PARSE_COMMANDS:
|
||||||
|
values[count].type = ARGS_COMMANDS;
|
||||||
|
values[count].cmd = cmd_parse_from_node(child);
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
fatalx("unexpected node type in command");
|
||||||
|
}
|
||||||
|
count++;
|
||||||
|
}
|
||||||
|
|
||||||
|
cmd = cmd_parse(values, count, NULL, node->line, 0, &cause);
|
||||||
|
if (cmd == NULL)
|
||||||
|
free(cause);
|
||||||
|
else {
|
||||||
|
if (cmd_get_entry(cmd)->flags & flag)
|
||||||
|
found = 1;
|
||||||
|
cmd_free(cmd);
|
||||||
|
}
|
||||||
|
|
||||||
|
out:
|
||||||
|
args_free_values(values, count);
|
||||||
|
free(values);
|
||||||
|
return (found);
|
||||||
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
cmd_parse_any_have(struct cmd_parse_tree *tree, int flag)
|
||||||
|
{
|
||||||
|
struct cmd_parse_node *seq, *node;
|
||||||
|
|
||||||
|
TAILQ_FOREACH(seq, &tree->root->children, entry) {
|
||||||
|
if (seq->type != CMD_PARSE_SEQUENCE)
|
||||||
|
continue;
|
||||||
|
|
||||||
|
TAILQ_FOREACH(node, &seq->children, entry) {
|
||||||
|
if (node->type != CMD_PARSE_COMMAND)
|
||||||
|
continue;
|
||||||
|
if (cmd_parse_command_any_have(node, flag))
|
||||||
|
return (1);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return (0);
|
||||||
|
}
|
||||||
|
|
||||||
static void printflike(1, 2)
|
static void printflike(1, 2)
|
||||||
yyerror(const char *fmt, ...)
|
yyerror(const char *fmt, ...)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -81,6 +81,7 @@ struct cmd_parse_tree *cmd_parse_from_string(const char *,
|
|||||||
struct cmd_parse_tree *cmd_parse_from_node(struct cmd_parse_node *);
|
struct cmd_parse_tree *cmd_parse_from_node(struct cmd_parse_node *);
|
||||||
struct cmd_parse_tree *cmd_parse_from_arguments(struct args_value *, u_int);
|
struct cmd_parse_tree *cmd_parse_from_arguments(struct args_value *, u_int);
|
||||||
struct cmd_parse_tree *cmd_parse_add_ref(struct cmd_parse_tree *);
|
struct cmd_parse_tree *cmd_parse_add_ref(struct cmd_parse_tree *);
|
||||||
|
int cmd_parse_any_have(struct cmd_parse_tree *, int);
|
||||||
void cmd_parse_free(struct cmd_parse_tree *);
|
void cmd_parse_free(struct cmd_parse_tree *);
|
||||||
struct cmd_parse_node *cmd_parse_root(struct cmd_parse_tree *);
|
struct cmd_parse_node *cmd_parse_root(struct cmd_parse_tree *);
|
||||||
char *cmd_parse_print(struct cmd_parse_tree *);
|
char *cmd_parse_print(struct cmd_parse_tree *);
|
||||||
|
|||||||
Reference in New Issue
Block a user