Merge pull request #1459 from terrelln/destroy

[zstdcli] Refuse to overwrite input file
This commit is contained in:
Nick Terrell 2018-12-18 17:03:54 -08:00 committed by GitHub
commit 3a4634f2af
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 18 additions and 5 deletions

View File

@ -404,7 +404,7 @@ static FILE* FIO_openSrcFile(const char* srcFileName)
/** FIO_openDstFile() :
* condition : `dstFileName` must be non-NULL.
* @result : FILE* to `dstFileName`, or NULL if it fails */
static FILE* FIO_openDstFile(const char* dstFileName)
static FILE* FIO_openDstFile(const char* srcFileName, const char* dstFileName)
{
assert(dstFileName != NULL);
if (!strcmp (dstFileName, stdoutmark)) {
@ -416,6 +416,16 @@ static FILE* FIO_openDstFile(const char* dstFileName)
}
return stdout;
}
if (srcFileName != NULL) {
stat_t srcStat;
stat_t dstStat;
if (UTIL_getFileStat(srcFileName, &srcStat) && UTIL_getFileStat(dstFileName, &dstStat)) {
if (srcStat.st_dev == dstStat.st_dev && srcStat.st_ino == dstStat.st_ino) {
DISPLAYLEVEL(1, "zstd: Refusing to open a output file which will overwrite the input file \n");
return NULL;
}
}
}
if (g_sparseFileSupport == 1) {
g_sparseFileSupport = ZSTD_SPARSE_DEFAULT;
@ -1114,7 +1124,7 @@ static int FIO_compressFilename_dstFile(cRess_t ress,
if (ress.dstFile == NULL) {
closeDstFile = 1;
DISPLAYLEVEL(6, "FIO_compressFilename_dstFile: opening dst: %s", dstFileName);
ress.dstFile = FIO_openDstFile(dstFileName);
ress.dstFile = FIO_openDstFile(srcFileName, dstFileName);
if (ress.dstFile==NULL) return 1; /* could not open dstFileName */
/* Must only be added after FIO_openDstFile() succeeds.
* Otherwise we may delete the destination file if it already exists,
@ -1264,7 +1274,7 @@ int FIO_compressMultipleFilenames(const char** inFileNamesTable, unsigned nbFile
assert(outFileName != NULL || suffix != NULL);
if (outFileName != NULL) { /* output into a single destination (stdout typically) */
ress.dstFile = FIO_openDstFile(outFileName);
ress.dstFile = FIO_openDstFile(NULL, outFileName);
if (ress.dstFile == NULL) { /* could not open outFileName */
error = 1;
} else {
@ -1880,7 +1890,7 @@ static int FIO_decompressDstFile(dRess_t ress, FILE* srcFile,
if (ress.dstFile == NULL) {
releaseDstFile = 1;
ress.dstFile = FIO_openDstFile(dstFileName);
ress.dstFile = FIO_openDstFile(srcFileName, dstFileName);
if (ress.dstFile==0) return 1;
/* Must only be added after FIO_openDstFile() succeeds.
@ -2057,7 +2067,7 @@ FIO_decompressMultipleFilenames(const char* srcNamesTable[], unsigned nbFiles,
if (outFileName) {
unsigned u;
ress.dstFile = FIO_openDstFile(outFileName);
ress.dstFile = FIO_openDstFile(NULL, outFileName);
if (ress.dstFile == 0) EXM_THROW(71, "cannot open %s", outFileName);
for (u=0; u<nbFiles; u++)
error |= FIO_decompressSrcFile(ress, outFileName, srcNamesTable[u]);

View File

@ -183,6 +183,9 @@ $ECHO "test: --no-progress flag"
$ZSTD tmpro -c --no-progress | $ZSTD -d -o "$INTOVOID" --no-progress
$ZSTD tmpro -cv --no-progress | $ZSTD -dv -o "$INTOVOID" --no-progress
rm -f tmpro tmpro.zst
$ECHO "test: overwrite input file (must fail)"
$ZSTD tmp -fo tmp && die "zstd overwrote the input file"
$ZSTD tmp.zst -dfo tmp.zst && die "zstd overwrote the input file"
$ECHO "test : file removal"