Don't try to clean up .. segments in fteqcc's include paths. Its buggy, and doesn't handle symlink weirdness properly.
git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@5805 fc73d0e0-1445-4013-8a0c-d673dee63da5
This commit is contained in:
parent
193d14a931
commit
e26f26e170
2 changed files with 28 additions and 51 deletions
|
@ -9,7 +9,7 @@
|
||||||
#include <dirent.h>
|
#include <dirent.h>
|
||||||
#include <sys/stat.h>
|
#include <sys/stat.h>
|
||||||
#endif
|
#endif
|
||||||
void QCC_Canonicalize(char *fullname, size_t fullnamesize, const char *newfile, const char *base);
|
void QCC_JoinPaths(char *fullname, size_t fullnamesize, const char *newfile, const char *base);
|
||||||
|
|
||||||
//package formats:
|
//package formats:
|
||||||
//pakzip - files are uncompressed, with both a pak header and a zip trailer, allowing it to be read as either type of file.
|
//pakzip - files are uncompressed, with both a pak header and a zip trailer, allowing it to be read as either type of file.
|
||||||
|
@ -376,7 +376,7 @@ static void PKG_CreateOutput(struct pkgctx_s *ctx, struct dataset_s *s, const ch
|
||||||
memset(o, 0, sizeof(*o));
|
memset(o, 0, sizeof(*o));
|
||||||
strcpy(o->code, code);
|
strcpy(o->code, code);
|
||||||
o->usediffs = diff;
|
o->usediffs = diff;
|
||||||
QCC_Canonicalize(o->filename, sizeof(o->filename), path, ctx->gamepath);
|
QCC_JoinPaths(o->filename, sizeof(o->filename), path, ctx->gamepath);
|
||||||
o->next = s->outputs;
|
o->next = s->outputs;
|
||||||
s->outputs = o;
|
s->outputs = o;
|
||||||
|
|
||||||
|
@ -679,7 +679,7 @@ static void PKG_AddClassFiles(struct pkgctx_s *ctx, struct class_s *c, const cha
|
||||||
char basepath[MAX_OSPATH], tmppath[MAX_OSPATH];
|
char basepath[MAX_OSPATH], tmppath[MAX_OSPATH];
|
||||||
struct stat statbuf;
|
struct stat statbuf;
|
||||||
|
|
||||||
QCC_Canonicalize(basepath, sizeof(basepath), fname, ctx->sourcepath);
|
QCC_JoinPaths(basepath, sizeof(basepath), fname, ctx->sourcepath);
|
||||||
QC_strlcat(basepath, "/", sizeof(basepath));
|
QC_strlcat(basepath, "/", sizeof(basepath));
|
||||||
dir = opendir(basepath);
|
dir = opendir(basepath);
|
||||||
if (!dir)
|
if (!dir)
|
||||||
|
@ -691,8 +691,8 @@ static void PKG_AddClassFiles(struct pkgctx_s *ctx, struct class_s *c, const cha
|
||||||
{
|
{
|
||||||
if (*ent->d_name == '.')
|
if (*ent->d_name == '.')
|
||||||
continue;
|
continue;
|
||||||
QCC_Canonicalize(basepath, sizeof(basepath), ent->d_name, fname);
|
QCC_JoinPaths(basepath, sizeof(basepath), ent->d_name, fname);
|
||||||
QCC_Canonicalize(tmppath, sizeof(tmppath), basepath, ctx->sourcepath);
|
QCC_JoinPaths(tmppath, sizeof(tmppath), basepath, ctx->sourcepath);
|
||||||
if (stat(tmppath, &statbuf)!=0)
|
if (stat(tmppath, &statbuf)!=0)
|
||||||
continue;
|
continue;
|
||||||
|
|
||||||
|
@ -958,7 +958,7 @@ static void *PKG_OpenSourceFile(struct pkgctx_s *ctx, struct file_s *file, size_
|
||||||
|
|
||||||
*fsize = 0;
|
*fsize = 0;
|
||||||
|
|
||||||
QCC_Canonicalize(fullname, sizeof(fullname), file->name, ctx->sourcepath);
|
QCC_JoinPaths(fullname, sizeof(fullname), file->name, ctx->sourcepath);
|
||||||
strcpy(file->write.name, file->name);
|
strcpy(file->write.name, file->name);
|
||||||
|
|
||||||
//WIN32 FIXME: use the utf16 version because microsoft suck and don't allow utf-8
|
//WIN32 FIXME: use the utf16 version because microsoft suck and don't allow utf-8
|
||||||
|
@ -996,7 +996,7 @@ static void *PKG_OpenSourceFile(struct pkgctx_s *ctx, struct file_s *file, size_
|
||||||
//delete temp file...
|
//delete temp file...
|
||||||
fclose(f);
|
fclose(f);
|
||||||
|
|
||||||
QCC_Canonicalize(tempname, sizeof(tempname), file->write.name, ctx->sourcepath);
|
QCC_JoinPaths(tempname, sizeof(tempname), file->write.name, ctx->sourcepath);
|
||||||
f = fopen(tempname, "rb");
|
f = fopen(tempname, "rb");
|
||||||
if (f)
|
if (f)
|
||||||
{
|
{
|
||||||
|
@ -1702,7 +1702,7 @@ void Packager_ParseText(struct pkgctx_s *ctx, char *scripttext)
|
||||||
if (PKG_GetStringToken(ctx, cmd, sizeof(cmd)))
|
if (PKG_GetStringToken(ctx, cmd, sizeof(cmd)))
|
||||||
{
|
{
|
||||||
QC_strlcat(cmd, "/", sizeof(cmd));
|
QC_strlcat(cmd, "/", sizeof(cmd));
|
||||||
QCC_Canonicalize(ctx->sourcepath, sizeof(ctx->sourcepath), cmd, old);
|
QCC_JoinPaths(ctx->sourcepath, sizeof(ctx->sourcepath), cmd, old);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (!strcmp(cmd, "rule"))
|
else if (!strcmp(cmd, "rule"))
|
||||||
|
|
|
@ -218,56 +218,33 @@ pbool QCC_PR_UnInclude(void)
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
void QCC_Canonicalize(char *fullname, size_t fullnamesize, const char *newfile, const char *base)
|
//expresses a relative path relative to an existing FILEname. any directories in base must be / terminated properly.
|
||||||
|
void QCC_JoinPaths(char *fullname, size_t fullnamesize, const char *newfile, const char *base)
|
||||||
{
|
{
|
||||||
int doubledots;
|
char *end;
|
||||||
char *end = fullname;
|
|
||||||
|
|
||||||
doubledots = 0;
|
|
||||||
|
|
||||||
/*count how far up we need to go*/
|
if (*newfile == '/' || *newfile == '\\')
|
||||||
while(1)
|
{ //its an absolute path...
|
||||||
{
|
QC_strlcpy(fullname, newfile, fullnamesize);
|
||||||
if (!strncmp(newfile, "./", 2) || !strncmp(newfile, ".\\", 2))
|
return;
|
||||||
newfile+=2;
|
|
||||||
else if(!strncmp(newfile, "../", 3) || !strncmp(newfile, "..\\", 3))
|
|
||||||
{
|
|
||||||
newfile+=3;
|
|
||||||
doubledots++;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
break;
|
|
||||||
}
|
}
|
||||||
|
QC_strlcpy(fullname, base, fullnamesize);
|
||||||
//FIXME: length validation!
|
|
||||||
if (base)
|
|
||||||
strcpy(fullname, base);
|
|
||||||
else
|
|
||||||
*fullname = 0;
|
|
||||||
end = fullname+strlen(fullname);
|
end = fullname+strlen(fullname);
|
||||||
|
|
||||||
while (end > fullname)
|
while (end > fullname)
|
||||||
{
|
{
|
||||||
end--;
|
end--;
|
||||||
/*stop at the slash, unless we're meant to go further*/
|
|
||||||
if (*end == '/' || *end == '\\')
|
if (*end == '/' || *end == '\\')
|
||||||
{
|
{
|
||||||
if (!doubledots)
|
end++;
|
||||||
{
|
break;
|
||||||
end++;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
doubledots--;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
QC_strlcpy(end, newfile, fullnamesize - (end-fullname));
|
||||||
|
|
||||||
while (doubledots-- > 0)
|
//FIXME: do we want to convert /segment/../ into just / ?
|
||||||
{
|
//fteqw might insist on it for its filesystem sandboxing.
|
||||||
strcpy(end, "../");
|
//but it breaks symlink weirdness (itself a possible security hole).
|
||||||
end += 3;
|
//should probably be a separate function.
|
||||||
}
|
|
||||||
|
|
||||||
strcpy(end, newfile);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
extern char qccmsourcedir[];
|
extern char qccmsourcedir[];
|
||||||
|
@ -291,7 +268,7 @@ void QCC_FindBestInclude(char *newfile, char *currentfile, pbool verbose)
|
||||||
currentfile = qccincludedir[includepath-1];
|
currentfile = qccincludedir[includepath-1];
|
||||||
}
|
}
|
||||||
|
|
||||||
QCC_Canonicalize(fullname, sizeof(fullname), newfile, currentfile);
|
QCC_JoinPaths(fullname, sizeof(fullname), newfile, currentfile);
|
||||||
|
|
||||||
{
|
{
|
||||||
extern progfuncs_t *qccprogfuncs;
|
extern progfuncs_t *qccprogfuncs;
|
||||||
|
@ -954,7 +931,7 @@ static pbool QCC_PR_Precompiler(void)
|
||||||
QCC_ImportProgs(pr_token);
|
QCC_ImportProgs(pr_token);
|
||||||
if (!*destfile && !destfile_explicit)
|
if (!*destfile && !destfile_explicit)
|
||||||
{
|
{
|
||||||
QCC_Canonicalize(destfile, sizeof(destfile), pr_token, compilingfile);
|
QCC_JoinPaths(destfile, sizeof(destfile), pr_token, compilingfile);
|
||||||
externs->Printf("Outputfile: %s\n", destfile);
|
externs->Printf("Outputfile: %s\n", destfile);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1079,7 +1056,7 @@ static pbool QCC_PR_Precompiler(void)
|
||||||
QCC_PR_SimpleGetString();
|
QCC_PR_SimpleGetString();
|
||||||
if (!destfile_explicit)
|
if (!destfile_explicit)
|
||||||
{
|
{
|
||||||
QCC_Canonicalize(destfile, sizeof(destfile), pr_token, compilingfile);
|
QCC_JoinPaths(destfile, sizeof(destfile), pr_token, compilingfile);
|
||||||
externs->Printf("Outputfile: %s\n", pr_token);
|
externs->Printf("Outputfile: %s\n", pr_token);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1213,7 +1190,7 @@ static pbool QCC_PR_Precompiler(void)
|
||||||
QC_strlcat(qcc_token, "/", sizeof(qcc_token));
|
QC_strlcat(qcc_token, "/", sizeof(qcc_token));
|
||||||
}
|
}
|
||||||
|
|
||||||
QCC_Canonicalize(newinc, sizeof(newinc), qcc_token, compilingfile);
|
QCC_JoinPaths(newinc, sizeof(newinc), qcc_token, compilingfile);
|
||||||
QCC_PR_AddIncludePath(newinc);
|
QCC_PR_AddIncludePath(newinc);
|
||||||
}
|
}
|
||||||
else if (!QC_strcasecmp(qcc_token, "noref"))
|
else if (!QC_strcasecmp(qcc_token, "noref"))
|
||||||
|
@ -1332,7 +1309,7 @@ static pbool QCC_PR_Precompiler(void)
|
||||||
QCC_COM_Parse(msg);
|
QCC_COM_Parse(msg);
|
||||||
|
|
||||||
if (!destfile_explicit) //if output file is named on the commandline, don't change it mid-compile
|
if (!destfile_explicit) //if output file is named on the commandline, don't change it mid-compile
|
||||||
QCC_Canonicalize(destfile, sizeof(destfile), qcc_token, compilingfile);
|
QCC_JoinPaths(destfile, sizeof(destfile), qcc_token, compilingfile);
|
||||||
|
|
||||||
if (strcmp(destfile, olddest))
|
if (strcmp(destfile, olddest))
|
||||||
externs->Printf("Outputfile: %s\n", destfile);
|
externs->Printf("Outputfile: %s\n", destfile);
|
||||||
|
|
Loading…
Reference in a new issue