mirror of
https://git.code.sf.net/p/quake/quakeforge
synced 2025-01-17 22:50:51 +00:00
Changed GIB_Arg* into macros. Cleaned up GIB file access a bit and added
file.move and file.delete builtins. Added Qremove to quakeio.[ch]. Did a little cleaning and commenting in gib_parse.c. Added support for \t and \r escape characters.
This commit is contained in:
parent
7542a2457f
commit
8c2afef44c
6 changed files with 125 additions and 61 deletions
|
@ -29,6 +29,8 @@
|
||||||
$Id$
|
$Id$
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "QF/cbuf.h" // For cbuf_active
|
||||||
|
|
||||||
typedef struct gib_builtin_s {
|
typedef struct gib_builtin_s {
|
||||||
struct dstring_s *name;
|
struct dstring_s *name;
|
||||||
void (*func) (void);
|
void (*func) (void);
|
||||||
|
@ -39,9 +41,11 @@ typedef struct gib_builtin_s {
|
||||||
} type;
|
} type;
|
||||||
} gib_builtin_t;
|
} gib_builtin_t;
|
||||||
|
|
||||||
unsigned int GIB_Argc (void);
|
#define GIB_Argc() (cbuf_active->args->argc)
|
||||||
const char *GIB_Argv (unsigned int arg);
|
#define GIB_Argv(x) ((x) < cbuf_active->args->argc ? cbuf_active->args->argv[(x)]->str : "")
|
||||||
const char *GIB_Args (unsigned int arg);
|
#define GIB_Args(x) ((x) < cbuf_active->args->argc ? cbuf_active->args->args[(x)] : "")
|
||||||
|
#define GIB_Argd(x) ((x) < cbuf_active->args->argc ? cbuf_active->args->argv[(x)] : NULL)
|
||||||
|
|
||||||
void GIB_Arg_Strip_Delim (unsigned int arg);
|
void GIB_Arg_Strip_Delim (unsigned int arg);
|
||||||
void GIB_Return (const char *str);
|
void GIB_Return (const char *str);
|
||||||
void GIB_Builtin_Add (const char *name, void (*func) (void), enum gib_builtin_type_e type);
|
void GIB_Builtin_Add (const char *name, void (*func) (void), enum gib_builtin_type_e type);
|
||||||
|
|
|
@ -38,6 +38,7 @@ typedef struct QFile_s QFile;
|
||||||
|
|
||||||
void Qexpand_squiggle(const char *path, char *dest);
|
void Qexpand_squiggle(const char *path, char *dest);
|
||||||
int Qrename(const char *old, const char *new);
|
int Qrename(const char *old, const char *new);
|
||||||
|
int Qremove(const char *path);
|
||||||
int Qfilesize (QFile *file);
|
int Qfilesize (QFile *file);
|
||||||
QFile *Qopen(const char *path, const char *mode);
|
QFile *Qopen(const char *path, const char *mode);
|
||||||
QFile *Qdopen(int fd, const char *mode);
|
QFile *Qdopen(int fd, const char *mode);
|
||||||
|
|
|
@ -114,46 +114,6 @@ GIB_Builtin_Find (const char *name)
|
||||||
return (gib_builtin_t *) Hash_Find (gib_builtins, name);
|
return (gib_builtin_t *) Hash_Find (gib_builtins, name);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
|
||||||
GIB_Argc
|
|
||||||
|
|
||||||
Returns the number of arguments available
|
|
||||||
in the current buffer.
|
|
||||||
*/
|
|
||||||
unsigned int
|
|
||||||
GIB_Argc (void)
|
|
||||||
{
|
|
||||||
return cbuf_active->args->argc;
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
Returns a specific argument in the current
|
|
||||||
buffer.
|
|
||||||
*/
|
|
||||||
const char *
|
|
||||||
GIB_Argv (unsigned int arg)
|
|
||||||
{
|
|
||||||
if (arg < cbuf_active->args->argc)
|
|
||||||
return cbuf_active->args->argv[arg]->str;
|
|
||||||
else
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
|
||||||
GIB_Args
|
|
||||||
|
|
||||||
Returns a pointer to the composite command
|
|
||||||
line starting at token arg.
|
|
||||||
*/
|
|
||||||
const char *
|
|
||||||
GIB_Args (unsigned int arg)
|
|
||||||
{
|
|
||||||
if (arg < cbuf_active->args->argc)
|
|
||||||
return cbuf_active->args->args[arg];
|
|
||||||
else
|
|
||||||
return "";
|
|
||||||
}
|
|
||||||
|
|
||||||
/*
|
/*
|
||||||
GIB_Arg_Strip_Delim
|
GIB_Arg_Strip_Delim
|
||||||
|
|
||||||
|
@ -554,7 +514,7 @@ GIB_File_Read_f (void)
|
||||||
"usage: file.read path_and_filename");
|
"usage: file.read path_and_filename");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
path = cbuf_active->args->argv[1]->str;
|
path = GIB_Argv (1);
|
||||||
if (!GIB_CollapsePath (path)) {
|
if (!GIB_CollapsePath (path)) {
|
||||||
Cbuf_Error ("access",
|
Cbuf_Error ("access",
|
||||||
"file.read: access to %s denied", path);
|
"file.read: access to %s denied", path);
|
||||||
|
@ -564,7 +524,7 @@ GIB_File_Read_f (void)
|
||||||
contents = (char *) COM_LoadHunkFile (path);
|
contents = (char *) COM_LoadHunkFile (path);
|
||||||
if (!contents) {
|
if (!contents) {
|
||||||
Cbuf_Error ("file",
|
Cbuf_Error ("file",
|
||||||
"file.read: could not open %s for reading: %s", path, strerror (errno));
|
"file.read: could not open %s/%s for reading: %s", com_gamedir, path, strerror (errno));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
GIB_Return (contents);
|
GIB_Return (contents);
|
||||||
|
@ -583,7 +543,7 @@ GIB_File_Write_f (void)
|
||||||
"usage: file.write path_and_filename data");
|
"usage: file.write path_and_filename data");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
path = cbuf_active->args->argv[1]->str;
|
path = GIB_Argv (1);
|
||||||
if (!GIB_CollapsePath (path)) {
|
if (!GIB_CollapsePath (path)) {
|
||||||
Cbuf_Error ("access",
|
Cbuf_Error ("access",
|
||||||
"file.write: access to %s denied", path);
|
"file.write: access to %s denied", path);
|
||||||
|
@ -591,7 +551,7 @@ GIB_File_Write_f (void)
|
||||||
}
|
}
|
||||||
if (!(file = Qopen (va ("%s/%s", com_gamedir, path), "w"))) {
|
if (!(file = Qopen (va ("%s/%s", com_gamedir, path), "w"))) {
|
||||||
Cbuf_Error ("file",
|
Cbuf_Error ("file",
|
||||||
"file.write: could not open %s for writing: %s", path, strerror (errno));
|
"file.write: could not open %s/%s for writing: %s", com_gamedir, path, strerror (errno));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
Qprintf (file, "%s", GIB_Argv (2));
|
Qprintf (file, "%s", GIB_Argv (2));
|
||||||
|
@ -613,19 +573,18 @@ GIB_File_Find_f (void)
|
||||||
"usage: file.find glob [path]");
|
"usage: file.find glob [path]");
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
path = GIB_Argv (2);
|
||||||
if (GIB_Argc () == 3) {
|
if (GIB_Argc () == 3) {
|
||||||
path = cbuf_active->args->argv[2]->str;
|
|
||||||
if (!GIB_CollapsePath (path)) {
|
if (!GIB_CollapsePath (path)) {
|
||||||
Cbuf_Error ("access",
|
Cbuf_Error ("access",
|
||||||
"file.find: access to %s denied", path);
|
"file.find: access to %s denied", path);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
directory = opendir (va ("%s/%s", com_gamedir, GIB_Argv (2)));
|
directory = opendir (va ("%s/%s", com_gamedir, path));
|
||||||
if (!directory) {
|
if (!directory) {
|
||||||
Cbuf_Error ("file",
|
Cbuf_Error ("file",
|
||||||
"file.find: could not open directory %s: %s", GIB_Argv (2), strerror (errno));
|
"file.find: could not open directory %s/%s: %s", com_gamedir, path, strerror (errno));
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
list = dstring_newstr ();
|
list = dstring_newstr ();
|
||||||
|
@ -645,7 +604,66 @@ GIB_File_Find_f (void)
|
||||||
GIB_Return ("");
|
GIB_Return ("");
|
||||||
dstring_delete (list);
|
dstring_delete (list);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
GIB_File_Move_f (void)
|
||||||
|
{
|
||||||
|
char *path1, *path2;
|
||||||
|
dstring_t *from, *to;
|
||||||
|
|
||||||
|
if (GIB_Argc () != 3) {
|
||||||
|
Cbuf_Error ("syntax",
|
||||||
|
"file.move: invalid syntax\n"
|
||||||
|
"usage: file.move from_file to_file");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
path1 = GIB_Argv (1);
|
||||||
|
path2 = GIB_Argv (2);
|
||||||
|
if (!GIB_CollapsePath (path1)) {
|
||||||
|
Cbuf_Error ("access",
|
||||||
|
"file.move: access to %s denied", path1);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (!GIB_CollapsePath (path2)) {
|
||||||
|
Cbuf_Error ("access",
|
||||||
|
"file.move: access to %s denied", path2);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
from = dstring_newstr ();
|
||||||
|
to = dstring_newstr ();
|
||||||
|
dsprintf (from, "%s/%s", com_gamedir, path1);
|
||||||
|
dsprintf (to, "%s/%s", com_gamedir, path2);
|
||||||
|
if (Qrename (from->str, to->str))
|
||||||
|
Cbuf_Error ("file",
|
||||||
|
"file.move: could not move %s to %s: %s",
|
||||||
|
from->str, to->str, strerror(errno));
|
||||||
|
dstring_delete (from);
|
||||||
|
dstring_delete (to);
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
GIB_File_Delete_f (void)
|
||||||
|
{
|
||||||
|
char *path;
|
||||||
|
|
||||||
|
if (GIB_Argc () != 2) {
|
||||||
|
Cbuf_Error ("syntax",
|
||||||
|
"file.delete: invalid syntax\n"
|
||||||
|
"usage: file.delete file");
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
path = GIB_Argv (1);
|
||||||
|
if (!GIB_CollapsePath (path)) {
|
||||||
|
Cbuf_Error ("access",
|
||||||
|
"file.delete: access to %s denied", path);
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (Qremove(va("%s/%s", com_gamedir, path)))
|
||||||
|
Cbuf_Error ("file",
|
||||||
|
"file.delete: could not delete %s/%s: %s",
|
||||||
|
com_gamedir, path, strerror(errno));
|
||||||
|
}
|
||||||
|
|
||||||
void
|
void
|
||||||
GIB_Range_f (void)
|
GIB_Range_f (void)
|
||||||
{
|
{
|
||||||
|
@ -714,6 +732,8 @@ GIB_Builtin_Init (void)
|
||||||
GIB_Builtin_Add ("file.read", GIB_File_Read_f, GIB_BUILTIN_NORMAL);
|
GIB_Builtin_Add ("file.read", GIB_File_Read_f, GIB_BUILTIN_NORMAL);
|
||||||
GIB_Builtin_Add ("file.write", GIB_File_Write_f, GIB_BUILTIN_NORMAL);
|
GIB_Builtin_Add ("file.write", GIB_File_Write_f, GIB_BUILTIN_NORMAL);
|
||||||
GIB_Builtin_Add ("file.find", GIB_File_Find_f, GIB_BUILTIN_NORMAL);
|
GIB_Builtin_Add ("file.find", GIB_File_Find_f, GIB_BUILTIN_NORMAL);
|
||||||
|
GIB_Builtin_Add ("file.move", GIB_File_Move_f, GIB_BUILTIN_NORMAL);
|
||||||
|
GIB_Builtin_Add ("file.delete", GIB_File_Delete_f, GIB_BUILTIN_NORMAL);
|
||||||
GIB_Builtin_Add ("range", GIB_Range_f, GIB_BUILTIN_NORMAL);
|
GIB_Builtin_Add ("range", GIB_Range_f, GIB_BUILTIN_NORMAL);
|
||||||
GIB_Builtin_Add ("print", GIB_Print_f, GIB_BUILTIN_NORMAL);
|
GIB_Builtin_Add ("print", GIB_Print_f, GIB_BUILTIN_NORMAL);
|
||||||
}
|
}
|
||||||
|
|
|
@ -63,6 +63,13 @@ cbuf_interpreter_t gib_interp = {
|
||||||
GIB_Buffer_Destruct,
|
GIB_Buffer_Destruct,
|
||||||
};
|
};
|
||||||
|
|
||||||
|
/*
|
||||||
|
GIB_Escaped
|
||||||
|
|
||||||
|
Returns true if character i in str is
|
||||||
|
escaped with a backslash (and the backslash
|
||||||
|
is not itself escaped).
|
||||||
|
*/
|
||||||
inline qboolean
|
inline qboolean
|
||||||
GIB_Escaped (const char *str, int i)
|
GIB_Escaped (const char *str, int i)
|
||||||
{
|
{
|
||||||
|
@ -181,6 +188,16 @@ GIB_Parse_Match_Backtick (const char *str, unsigned int *i)
|
||||||
return '`';
|
return '`';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
GIB_Parse_Match_Index
|
||||||
|
|
||||||
|
Progresses an index variable through a string
|
||||||
|
until a normal brace (]) is reached. Calls
|
||||||
|
other matching functions to skip areas of a
|
||||||
|
string it does not want to handle. Returns
|
||||||
|
0 on success, or the character it could not
|
||||||
|
match otherwise.
|
||||||
|
*/
|
||||||
char
|
char
|
||||||
GIB_Parse_Match_Index (const char *str, unsigned int *i)
|
GIB_Parse_Match_Index (const char *str, unsigned int *i)
|
||||||
{
|
{
|
||||||
|
@ -193,6 +210,14 @@ GIB_Parse_Match_Index (const char *str, unsigned int *i)
|
||||||
return '[';
|
return '[';
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/*
|
||||||
|
GIB_Parse_Strip_Comments
|
||||||
|
|
||||||
|
Finds instances of // comments in a cbuf
|
||||||
|
outside of double quotes and snips between
|
||||||
|
the // and the next newline or the end of
|
||||||
|
the string.
|
||||||
|
*/
|
||||||
void
|
void
|
||||||
GIB_Parse_Strip_Comments (struct cbuf_s *cbuf)
|
GIB_Parse_Strip_Comments (struct cbuf_s *cbuf)
|
||||||
{
|
{
|
||||||
|
@ -252,11 +277,9 @@ GIB_Parse_Extract_Line (struct cbuf_s *cbuf)
|
||||||
}
|
}
|
||||||
|
|
||||||
if (dstr->str[0]) { // If something is left in the buffer
|
if (dstr->str[0]) { // If something is left in the buffer
|
||||||
if (i) { // If we used any of it
|
if (i)// If we used any of it
|
||||||
dstring_insert (cbuf->line, 0, dstr->str, i);
|
dstring_insert (cbuf->line, 0, dstr->str, i);
|
||||||
Sys_DPrintf ("extracted line: %s\n", cbuf->line->str);
|
// Clip out what we used or any leftover newlines or ;s
|
||||||
}
|
|
||||||
// Clip out what we used or any leftover newlines or ;s
|
|
||||||
dstring_snip (dstr, 0, i + (dstr->str[i] == '\n' || dstr->str[i] == ';'));
|
dstring_snip (dstr, 0, i + (dstr->str[i] == '\n' || dstr->str[i] == ';'));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -348,7 +371,7 @@ GIB_Parse_Get_Token (const char *str, unsigned int *i, dstring_t *dstr, qboolean
|
||||||
of pointers to the beginnings of tokens
|
of pointers to the beginnings of tokens
|
||||||
within it.
|
within it.
|
||||||
*/
|
*/
|
||||||
void
|
inline static void
|
||||||
GIB_Parse_Generate_Composite (struct cbuf_s *cbuf)
|
GIB_Parse_Generate_Composite (struct cbuf_s *cbuf)
|
||||||
{
|
{
|
||||||
cbuf_args_t *args = cbuf->args;
|
cbuf_args_t *args = cbuf->args;
|
||||||
|
@ -379,7 +402,7 @@ GIB_Parse_Generate_Composite (struct cbuf_s *cbuf)
|
||||||
or concatenates it to the end of the last
|
or concatenates it to the end of the last
|
||||||
according to cat.
|
according to cat.
|
||||||
*/
|
*/
|
||||||
inline void
|
inline static void
|
||||||
GIB_Parse_Add_Token (struct cbuf_args_s *args, qboolean cat, dstring_t *token)
|
GIB_Parse_Add_Token (struct cbuf_args_s *args, qboolean cat, dstring_t *token)
|
||||||
{
|
{
|
||||||
if (cat) {
|
if (cat) {
|
||||||
|
|
|
@ -262,9 +262,17 @@ GIB_Process_Escapes (dstring_t *token)
|
||||||
int i;
|
int i;
|
||||||
for (i = 0; token->str[i]; i++) {
|
for (i = 0; token->str[i]; i++) {
|
||||||
if (token->str[i] == '\\') {
|
if (token->str[i] == '\\') {
|
||||||
dstring_snip (token, i, 1);
|
dstring_snip (token, i, 1); // Get rid of slash
|
||||||
if (token->str[i] == 'n')
|
switch (token->str[i]) {
|
||||||
token->str[i] = '\n';
|
case 'n':
|
||||||
|
token->str[i] = '\n';
|
||||||
|
break;
|
||||||
|
case 't':
|
||||||
|
token->str[i] = '\t';
|
||||||
|
break;
|
||||||
|
case 'r':
|
||||||
|
token->str[i] = '\r';
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -129,6 +129,14 @@ Qrename (const char *old, const char *new)
|
||||||
return rename (e_old, e_new);
|
return rename (e_old, e_new);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
int
|
||||||
|
Qremove (const char *path)
|
||||||
|
{
|
||||||
|
char e_path[PATH_MAX];
|
||||||
|
Qexpand_squiggle (path, e_path);
|
||||||
|
return remove (e_path);
|
||||||
|
}
|
||||||
|
|
||||||
int
|
int
|
||||||
Qfilesize (QFile *file)
|
Qfilesize (QFile *file)
|
||||||
{
|
{
|
||||||
|
|
Loading…
Reference in a new issue