Skip to content

Commit

Permalink
Use a single list of internal commands instead of 3
Browse files Browse the repository at this point in the history
  • Loading branch information
leo-arch committed Dec 5, 2024
1 parent 42dbe92 commit 0b218c8
Show file tree
Hide file tree
Showing 13 changed files with 238 additions and 381 deletions.
2 changes: 1 addition & 1 deletion src/aux.c
Original file line number Diff line number Diff line change
Expand Up @@ -359,7 +359,7 @@ should_expand_eln(const char *text, char *cmd_name)
if (p) /* Either space of fused ELN. */
*p = '\0';
flags |= STATE_COMPLETING;
const int ret = (is_internal_c(l) && !is_internal_f(l)) ? 0 : 1;
const int ret = (is_internal_cmd(l, NO_FNAME_NUM, 1, 1)) ? 0 : 1;
flags &= ~STATE_COMPLETING;
if (p)
*p = t;
Expand Down
1 change: 0 additions & 1 deletion src/bulk_remove.c
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,6 @@
#include <errno.h>

#include "aux.h" /* xnmalloc, open_fwrite(), is_cmd_in_path(), count_dir() */
#include "checks.h" /* is_internal() */
#include "file_operations.h" // open_file() */
#include "messages.h" /* RR_USAGE */
#include "misc.h" /* xerror() */
Expand Down
232 changes: 38 additions & 194 deletions src/checks.c
Original file line number Diff line number Diff line change
Expand Up @@ -414,8 +414,8 @@ is_number(const char *restrict str)
}

/* Check if command STR contains a digit and this digit is not the first
* char of STR. Used by find_cmd() (called by is_internal_c()) to check
* for fused parameters in internal commands.
* char of STR. Used by is_internal_cmd() to check for fused parameters in
* internal commands.
* Returns the index of the digit in STR or -1 if no digit is found. */
static int
contains_digit(const char *str)
Expand All @@ -435,35 +435,6 @@ contains_digit(const char *str)
return (-1);
}

/* Return 1 if CMD is found in CMDS_LIST or zero otherwise. */
static int
find_cmd(const struct cmdslist_t *cmds_list, const size_t list_size, char *cmd)
{
int found = 0;
int i = (int)list_size;
char c = 0;
const int d = contains_digit(cmd);

if (d != -1) {
c = cmd[d];
cmd[d] = '\0';
}

const size_t cmd_len = strlen(cmd);
while (--i >= 0) {
if (*cmd == *cmds_list[i].name && cmd_len == cmds_list[i].len
&& strcmp(cmd, cmds_list[i].name) == 0) {
found = 1;
break;
}
}

if (d != -1)
cmd[d] = c;

return found;
}

/* Check whether S is an action name.
* Returns 1 if true or 0 otherwise. */
int
Expand All @@ -481,180 +452,53 @@ is_action_name(const char *s)
return 0;
}

/* Return 1 if CMD is an internal command, or zero otherwise. */
int
is_internal_c(char *restrict cmd)
{
if (find_cmd(internal_cmds, internal_cmds_n, cmd))
return 1;

/* Check for the search and history functions as well */
if ((*cmd == '/' && access(cmd, F_OK) != 0) || (*cmd == '!'
&& (IS_DIGIT(cmd[1]) || (cmd[1] == '-' && IS_DIGIT(cmd[2]))
|| cmd[1] == '!')))
return 1;

return 0;
}

/* Check cmd against a list of internal commands. Used by parse_input_str()
* to know whether it should perform additional expansions, like glob, regex,
* tilde, and so on. Only internal commands dealing with ELN/filenames
* should be checked here. */
/* Return 1 if CMD is an internal command matching the flags in FLAG.
* Otherwise, return 0. */
int
is_internal(char *restrict cmd)
is_internal_cmd(char *cmd, const int flag, const int check_hist,
const int check_search)
{
static struct cmdslist_t const int_cmds[] = {
{"ac", 2},
{"ad", 2},
{"bb", 2},
{"bleach", 6},
{"bm", 2},
{"bookmarks", 9},
{"bl", 2},
{"br", 2},
{"bulk", 4},
{"c", 1},
{"cd", 2},
{"d", 1},
{"dup", 3},
{"exp", 3},
{"export", 6},
{"jc", 2},
{"jp", 2},
{"l", 1},
{"le", 2},
{"m", 1},
{"mm", 2},
{"mime", 4},
{"n", 1},
{"new", 3},
{"o", 1},
{"oc", 2},
{"open", 4},
{"paste", 5},
{"p", 1},
{"pc", 2},
{"pp", 2},
{"pr", 2},
{"prop", 4},
{"pin", 3},
{"r", 1},
{"s", 1},
{"sel", 3},
{"t", 1},
{"tr", 2},
{"trash", 5},
{"tag", 3},
{"ta", 2},
{"te", 2},
{"v", 1},
{"vv", 2},
{NULL, 0}
};

static size_t i = 0;
if (i == 0)
i = (sizeof(int_cmds) / sizeof(struct cmdslist_t)) - 1;

if (find_cmd(int_cmds, i, cmd))
return 1;

/* Check for the search function as well */
if (*cmd == '/' && access(cmd, F_OK) != 0)
return 1;

return 0;
}
if (!cmd || !*cmd)
return 0;

/* Check CMD against a list of internal commands taking ELN's or numbers
* as parameters. Used by split_fusedcmd(). */
int
is_internal_f(const char *restrict cmd)
{
/* If we are completing/suggesting, do not take 'ws', 'mf', and 'st/sort'
* commands into account: they do not take ELN/filenames as parameters,
* but just numbers, in which case no ELN-filename completion should
* be made. */
if (flags & STATE_COMPLETING
/* Old is_internal_f() function */
if ((flags & STATE_COMPLETING) && (flag & PARAM_FNAME_NUM)
&& (*cmd == 'w' || (*cmd == 'm' && *(cmd + 1) == 'f')
|| (*cmd == 's' && (*(cmd + 1) == 't' || *(cmd + 1) == 'o')) ) )
return 0;

static struct cmdslist_t const int_cmds[] = {
{"ac", 2},
{"ad", 2},
{"alias", 5}, /* 'alias import' takes file names */
{"bb", 2},
{"dh", 2},
{"bl", 2},
{"bleach", 6},
{"bm", 2},
{"bookmarks", 9},
{"br", 2},
{"bulk", 4},
{"c", 1},
{"cd", 2},
{"d", 1},
{"dup", 3},
{"ds", 2},
{"desel", 5},
{"exp", 3},
{"l", 1},
{"ln", 2},
{"le", 2},
{"m", 1},
{"mime", 4},
{"mm", 2},
{"md", 2},
{"mf", 2},
{"n", 1},
{"new", 3},
{"o", 1},
{"oc", 2},
{"open", 4},
{"ow", 2},
{"p", 1},
{"pc", 2},
{"pp", 2},
{"pr", 2},
{"prop", 4},
{"paste", 5},
{"pin", 3},
{"r", 1},
{"rr", 2},
{"s", 1},
{"sel", 3},
{"st", 2},
{"sort", 4},
{"t", 1},
{"tr", 2},
{"trash", 5},
{"tag", 3},
{"ta", 2},
{"te", 2},
{"tl", 2},
{"v", 1},
{"vv", 2},
{"ws", 2},
{"x", 1},
{"X", 1},
{NULL, 0}
};

static int n = 0;
if (n == 0)
n = (int)(sizeof(int_cmds) / sizeof(struct cmdslist_t)) - 1;
const size_t cmd_len = strlen(cmd);

int i = n;
char c = 0;
const int d = contains_digit(cmd);

if (d != -1) {
c = cmd[d];
cmd[d] = '\0';
}

const size_t clen = strlen(cmd);
ssize_t i = (ssize_t)internal_cmds_n;
int found = 0;

while (--i >= 0) {
if (*cmd == *int_cmds[i].name && cmd_len == int_cmds[i].len
&& strcmp(cmd, int_cmds[i].name) == 0) {
return 1;
if (((flag & ALL_CMDS) || (internal_cmds[i].flag & flag))
&& clen == internal_cmds[i].len && *cmd == *internal_cmds[i].name
&& strcmp(cmd + 1, internal_cmds[i].name + 1) == 0) {
found = 1;
break;
}
}

if (d != -1)
cmd[d] = c;

if (found == 1)
return 1;

if ((check_search == 1 && (*cmd == '/' && access(cmd, F_OK) != 0))
|| (check_hist == 1 && (*cmd == '!' && (IS_DIGIT(cmd[1])
|| (cmd[1] == '-' && IS_DIGIT(cmd[2])) || cmd[1] == '!'))))
return 1;

return 0;
}

Expand Down
5 changes: 2 additions & 3 deletions src/checks.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,9 +43,8 @@ int is_bin_cmd(char *str);
int is_exec_cmd(const char *cmd);
int is_file_in_cwd(char *name);
int is_force_param(const char *s);
int is_internal(const char *restrict cmd);
int is_internal_c(const char *restrict cmd);
int is_internal_f(const char *restrict cmd);
int is_internal_cmd(char *cmd, const int flag, const int check_hist,
const int check_search);
int is_number(const char *restrict str);
int is_url(const char *url);
void truncate_file(char *file, const int max, const int check_dups);
Expand Down
10 changes: 5 additions & 5 deletions src/exec.c
Original file line number Diff line number Diff line change
Expand Up @@ -1211,7 +1211,7 @@ check_auto_first(char **args)
|| (args[1] && (*args[1] != '&' || args[1][1])))
return (-1);

if (!(flags & FIRST_WORD_IS_ELN) && is_internal_c(args[0]))
if (!(flags & FIRST_WORD_IS_ELN) && is_internal_cmd(args[0], ALL_CMDS, 1, 1))
return (-1);

char *deq_str = (char *)NULL;
Expand Down Expand Up @@ -1981,7 +1981,7 @@ check_fs_changes(void)
static int
is_write_cmd(const char *cmd)
{
static struct cmdslist_t const wcmds[] = {
static struct nameslist_t const wcmds[] = {
/* Internal commands */
{"ac", 2},
{"ad", 2},
Expand Down Expand Up @@ -2126,7 +2126,7 @@ exec_cmd(char **comm)
const int old_exit_code = exit_code;
exit_code = FUNC_SUCCESS;

int is_internal_cmd = 1;
int is_internal_command = 1;

if (dir_cmds.first_cmd_in_dir == UNSET && dir_cmds.last_cmd_ignored == 0)
dir_cmds.first_cmd_in_dir = (int)current_hist_n;
Expand Down Expand Up @@ -2679,11 +2679,11 @@ exec_cmd(char **comm)
if ((exit_code = run_shell_cmd(comm)) == FUNC_FAILURE)
return FUNC_FAILURE;
else
is_internal_cmd = 0;
is_internal_command = 0;
}

CHECK_EVENTS:
if (conf.autols == 0 || (is_internal_cmd == 0
if (conf.autols == 0 || (is_internal_command == 0
&& conf.clear_screen == CLEAR_INTERNAL_CMD_ONLY))
return exit_code;

Expand Down
20 changes: 18 additions & 2 deletions src/helpers.h
Original file line number Diff line number Diff line change
Expand Up @@ -1693,14 +1693,30 @@ struct props_t {
};
extern struct props_t prop_fields;

#define ALL_CMDS (1 << 0) // Check all commands (ignore parameters)
#define NO_PARAM (1 << 1) // Command takes no parameter
#define PARAM_STR (1 << 2) // Command takes a string (not file name)
#define PARAM_FNAME (1 << 3) // Command takes file names
#define PARAM_NUM (1 << 4) // Command takes numbers
#define NO_FNAME_NUM (NO_PARAM | PARAM_STR) // Neither file name nor number
#define PARAM_FNAME_NUM (PARAM_FNAME | PARAM_NUM) // Either file name or number

struct cmdslist_t {
char *name;
size_t len;
int flag;
int pad;
};

extern const struct cmdslist_t param_str[];
extern const struct cmdslist_t internal_cmds[];
extern const struct cmdslist_t kb_cmds[];

struct nameslist_t {
char *name;
size_t len;
};

extern const struct nameslist_t param_str[];
extern const struct nameslist_t kb_cmds[];

extern size_t internal_cmds_n;

Expand Down
2 changes: 1 addition & 1 deletion src/highlight.c
Original file line number Diff line number Diff line change
Expand Up @@ -104,7 +104,7 @@ rl_highlight(const char *str, const size_t pos, const int flag)
} else {
char cc = c;
*(str + pos) = '\0';
int ret = is_internal_f(str);
int ret = is_internal_cmd(str, PARAM_FNAME_NUM, 0, 0);
*(str + pos) = cc;
if (ret) {
cl = hn_c;
Expand Down
Loading

0 comments on commit 0b218c8

Please sign in to comment.