Add eachfile and mkaliasbn builtins
This commit is contained in:
@ -8,7 +8,7 @@
|
|||||||
extern PID_t PID;
|
extern PID_t PID;
|
||||||
extern Dev_t ps2kbdev;
|
extern Dev_t ps2kbdev;
|
||||||
|
|
||||||
static InterpResult RES;
|
InterpResult RES;
|
||||||
|
|
||||||
void tz_init(Tokenizer *tz, char *str) {
|
void tz_init(Tokenizer *tz, char *str) {
|
||||||
tz->str = str;
|
tz->str = str;
|
||||||
@ -116,6 +116,8 @@ void tz_classify(Tokenizer *tz) {
|
|||||||
else IF_RTCMD(do)
|
else IF_RTCMD(do)
|
||||||
else IF_RTCMD(stackpush)
|
else IF_RTCMD(stackpush)
|
||||||
else IF_RTCMD(stackpop)
|
else IF_RTCMD(stackpop)
|
||||||
|
else IF_RTCMD(eachfile)
|
||||||
|
else IF_RTCMD(mkaliasbn)
|
||||||
else {
|
else {
|
||||||
tk->type = TOK_MISC;
|
tk->type = TOK_MISC;
|
||||||
}
|
}
|
||||||
|
|||||||
@ -11,6 +11,8 @@ typedef struct {
|
|||||||
char errmsg[INTERP_ERRMSG_BUF_MAX];
|
char errmsg[INTERP_ERRMSG_BUF_MAX];
|
||||||
} InterpResult;
|
} InterpResult;
|
||||||
|
|
||||||
|
extern InterpResult RES;
|
||||||
|
|
||||||
typedef struct Token {
|
typedef struct Token {
|
||||||
struct Token *next;
|
struct Token *next;
|
||||||
char *str;
|
char *str;
|
||||||
|
|||||||
@ -167,11 +167,124 @@ bool rt_stackpop(Token *tks) {
|
|||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void rt_init(void) {
|
typedef struct EachFileSkip {
|
||||||
RTCMD("%print", &rt_print);
|
struct EachFileSkip *next;
|
||||||
RTCMD("%mkalias", &rt_mkalias);
|
char *filename;
|
||||||
RTCMD("%PID", &rt_PID);
|
} EachFileSkip;
|
||||||
RTCMD("%do", &rt_do);
|
|
||||||
RTCMD("%stackpush", &rt_stackpush);
|
bool rt_eachfile(Token *tks) {
|
||||||
RTCMD("%stackpop", &rt_stackpop);
|
EachFileSkip *skips = NULL;
|
||||||
|
|
||||||
|
Token *tk = tks;
|
||||||
|
char *dirpath;
|
||||||
|
|
||||||
|
while (tk && tk->str[0] == '!') {
|
||||||
|
EachFileSkip *skip = (EachFileSkip *)umalloc(sizeof(*skip));
|
||||||
|
skip->filename = tk->str + 1;
|
||||||
|
LL_APPEND(skips, skip);
|
||||||
|
tk = tk->next;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (tk != NULL) {
|
||||||
|
dirpath = tk->str;
|
||||||
|
tk = tk->next;
|
||||||
|
}
|
||||||
|
|
||||||
|
FsStat statbuf; ZERO(&statbuf);
|
||||||
|
if (fs_stat(dirpath, &statbuf) != E_OK || statbuf.type != FSSTAT_DIR) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
FsDirent *dirents = (FsDirent *)umalloc(statbuf.size * sizeof(*dirents));
|
||||||
|
|
||||||
|
for (size_t i = 0; i < statbuf.size; i++) {
|
||||||
|
fs_fetchdirent(dirpath, &dirents[i], i);
|
||||||
|
FsDirent *dirent = &dirents[i];
|
||||||
|
|
||||||
|
if (string_strcmp(dirent->name, ".") == 0 || string_strcmp(dirent->name, "..") == 0) {
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
EachFileSkip *skip1, *skip1tmp;
|
||||||
|
LL_FOREACH_SAFE(skips, skip1, skip1tmp) {
|
||||||
|
if (string_strcmp(skip1->filename, dirent->name) == 0) {
|
||||||
|
goto nextiter;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
char tmpbuf[1024]; ZERO(tmpbuf);
|
||||||
|
string_strcpy(tmpbuf, dirpath);
|
||||||
|
if (dirpath[string_len(dirpath) - 1] != '/') {
|
||||||
|
string_combine(tmpbuf, "/");
|
||||||
|
}
|
||||||
|
string_combine(tmpbuf, dirent->name);
|
||||||
|
|
||||||
|
#define EACHFILE_MAX_STRING 1024
|
||||||
|
char *s = umalloc(EACHFILE_MAX_STRING);
|
||||||
|
string_memset(s, 0, EACHFILE_MAX_STRING);
|
||||||
|
size_t cursor = 0;
|
||||||
|
Token *argtk, *argtktmp;
|
||||||
|
LL_FOREACH_SAFE(tk, argtk, argtktmp) {
|
||||||
|
if (string_strcmp(argtk->str, "&EF-ELEM") == 0) {
|
||||||
|
size_t len = string_len(tmpbuf);
|
||||||
|
string_memcpy(&s[cursor], tmpbuf, len);
|
||||||
|
cursor += len;
|
||||||
|
s[cursor] = ' ';
|
||||||
|
cursor++;
|
||||||
|
} else {
|
||||||
|
size_t len = string_len(argtk->str);
|
||||||
|
string_memcpy(&s[cursor], argtk->str, len);
|
||||||
|
cursor += len;
|
||||||
|
s[cursor] = ' ';
|
||||||
|
cursor++;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
InterpResult save; string_memcpy(&save, &RES, sizeof(save));
|
||||||
|
InterpResult *res;
|
||||||
|
interp_runstring(s, &res, false, false);
|
||||||
|
string_memcpy(&RES, &save, sizeof(save));
|
||||||
|
|
||||||
|
/* ufree(s); */
|
||||||
|
|
||||||
|
nextiter:
|
||||||
|
}
|
||||||
|
|
||||||
|
ufree(dirents);
|
||||||
|
|
||||||
|
EachFileSkip *skip1, *skip1tmp;
|
||||||
|
LL_FOREACH_SAFE(skips, skip1, skip1tmp) {
|
||||||
|
ufree(skip1);
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool rt_mkaliasbn(Token *tks) {
|
||||||
|
Token *tk = tks;
|
||||||
|
|
||||||
|
if (tk == NULL) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
RtAlias *alias = umalloc(sizeof(*alias));
|
||||||
|
string_memset(alias, 0, sizeof(*alias));
|
||||||
|
|
||||||
|
char *basename = (char *)path_basename(tk->str);
|
||||||
|
string_memcpy(alias->namebuf, basename, MIN(string_len(basename), RTALIAS_NAMEBUF_MAX));
|
||||||
|
string_memcpy(alias->valbuf, tk->str, MIN(string_len(tk->str), RTALIAS_VALBUF_MAX));
|
||||||
|
|
||||||
|
LL_APPEND(RTALIASES, alias);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
void rt_init(void) {
|
||||||
|
RTCMD("print", &rt_print);
|
||||||
|
RTCMD("mkalias", &rt_mkalias);
|
||||||
|
RTCMD("PID", &rt_PID);
|
||||||
|
RTCMD("do", &rt_do);
|
||||||
|
RTCMD("stackpush", &rt_stackpush);
|
||||||
|
RTCMD("stackpop", &rt_stackpop);
|
||||||
|
RTCMD("eachfile", &rt_eachfile);
|
||||||
|
RTCMD("mkaliasbn", &rt_mkaliasbn);
|
||||||
}
|
}
|
||||||
|
|||||||
@ -36,6 +36,8 @@ bool rt_PID(struct Token *);
|
|||||||
bool rt_do(struct Token *);
|
bool rt_do(struct Token *);
|
||||||
bool rt_stackpush(struct Token *);
|
bool rt_stackpush(struct Token *);
|
||||||
bool rt_stackpop(struct Token *);
|
bool rt_stackpop(struct Token *);
|
||||||
|
bool rt_eachfile(struct Token *);
|
||||||
|
bool rt_mkaliasbn(struct Token *);
|
||||||
|
|
||||||
void rtstringv_stackpushcopy(char *s, size_t len);
|
void rtstringv_stackpushcopy(char *s, size_t len);
|
||||||
char *rtstringv_stackpop(void);
|
char *rtstringv_stackpop(void);
|
||||||
|
|||||||
Reference in New Issue
Block a user