Add buffer overflow check in Ppmd compression routines.

Fix pipe mode encryption check.
Change file difference check in tests.
Add more tests.
This commit is contained in:
Moinak Ghosh 2012-11-09 20:05:13 +05:30
parent da9083ae12
commit 77db54e712
11 changed files with 145 additions and 20 deletions

View file

@ -69,7 +69,7 @@ typedef struct
UInt32 Code; UInt32 Code;
UInt32 Low; UInt32 Low;
Byte *buf; Byte *buf;
UInt32 bufUsed, bufLen; UInt32 bufUsed, bufLen, overflow;
Byte Indx2Units[PPMD_NUM_INDEXES]; Byte Indx2Units[PPMD_NUM_INDEXES];
Byte Units2Indx[128]; Byte Units2Indx[128];

View file

@ -13,8 +13,12 @@ void Ppmd8_RangeEnc_FlushData(CPpmd8 *p)
{ {
unsigned i; unsigned i;
for (i = 0; i < 4; i++, p->Low <<= 8 ) { for (i = 0; i < 4; i++, p->Low <<= 8 ) {
p->buf[p->bufUsed] = (Byte)(p->Low >> 24); if (p->bufUsed < p->bufLen) {
p->bufUsed++; p->buf[p->bufUsed] = (Byte)(p->Low >> 24);
p->bufUsed++;
} else {
p->overflow = 1;
}
} }
// p->Stream.Out->Write(p->Stream.Out, (Byte)(p->Low >> 24)); // p->Stream.Out->Write(p->Stream.Out, (Byte)(p->Low >> 24));
} }
@ -24,9 +28,13 @@ static void RangeEnc_Normalize(CPpmd8 *p)
while ((p->Low ^ (p->Low + p->Range)) < kTop || while ((p->Low ^ (p->Low + p->Range)) < kTop ||
(p->Range < kBot && ((p->Range = (0 - p->Low) & (kBot - 1)), 1))) (p->Range < kBot && ((p->Range = (0 - p->Low) & (kBot - 1)), 1)))
{ {
p->buf[p->bufUsed] = (Byte)(p->Low >> 24); if (p->bufUsed < p->bufLen) {
p->bufUsed++; p->buf[p->bufUsed] = (Byte)(p->Low >> 24);
//p->Stream.Out->Write(p->Stream.Out, (Byte)(p->Low >> 24)); p->bufUsed++;
//p->Stream.Out->Write(p->Stream.Out, (Byte)(p->Low >> 24));
} else {
p->overflow = 1;
}
p->Range <<= 8; p->Range <<= 8;
p->Low <<= 8; p->Low <<= 8;
} }

3
main.c
View file

@ -1171,7 +1171,6 @@ plain_compress:
*/ */
*(tdat->compressed_chunk) = type; *(tdat->compressed_chunk) = type;
printf("type: %d\n", type);
/* /*
* If encrypting, compute HMAC for chunk header and trailer. * If encrypting, compute HMAC for chunk header and trailer.
*/ */
@ -2049,7 +2048,7 @@ main(int argc, char *argv[])
fprintf(stderr, "Encryption only makes sense when compressing!\n"); fprintf(stderr, "Encryption only makes sense when compressing!\n");
exit(1); exit(1);
} else if (pipe_mode && !pwd_file) { } else if (pipe_mode && encrypt_type && !pwd_file) {
fprintf(stderr, "Pipe mode requires password to be provided in a file.\n"); fprintf(stderr, "Pipe mode requires password to be provided in a file.\n");
exit(1); exit(1);
} }

View file

@ -111,11 +111,13 @@ ppmd_compress(void *src, size_t srclen, void *dst,
_ppmd->buf = (Byte *)dst; _ppmd->buf = (Byte *)dst;
_ppmd->bufLen = *dstlen; _ppmd->bufLen = *dstlen;
_ppmd->bufUsed = 0; _ppmd->bufUsed = 0;
_ppmd->overflow = 0;
Ppmd8_EncodeBuffer(_ppmd, _src, srclen); Ppmd8_EncodeBuffer(_ppmd, _src, srclen);
Ppmd8_EncodeSymbol(_ppmd, -1); Ppmd8_EncodeSymbol(_ppmd, -1);
Ppmd8_RangeEnc_FlushData(_ppmd); Ppmd8_RangeEnc_FlushData(_ppmd);
if (_ppmd->overflow) return (-1);
*dstlen = _ppmd->bufUsed; *dstlen = _ppmd->bufUsed;
return (0); return (0);
} }
@ -133,6 +135,7 @@ ppmd_decompress(void *src, size_t srclen, void *dst,
_ppmd->buf = (Byte *)_src; _ppmd->buf = (Byte *)_src;
_ppmd->bufLen = srclen; _ppmd->bufLen = srclen;
_ppmd->bufUsed = 0; _ppmd->bufUsed = 0;
_ppmd->overflow = 0;
Ppmd8_RangeDec_Init(_ppmd); Ppmd8_RangeDec_Init(_ppmd);
Ppmd8_Init(_ppmd, _ppmd->Order, PPMD8_RESTORE_METHOD_RESTART); Ppmd8_Init(_ppmd, _ppmd->Order, PPMD8_RESTORE_METHOD_RESTART);
@ -143,7 +146,7 @@ ppmd_decompress(void *src, size_t srclen, void *dst,
i++; i++;
} }
if (i < *dstlen) if (i < *dstlen || _ppmd->overflow)
return (-1); return (-1);
return (0); return (0);
} }

View file

@ -34,8 +34,8 @@ do
echo "${cmd} errored." echo "${cmd} errored."
exit 1 exit 1
fi fi
diff ${tf} ${tf}.1 | grep -i differ diff ${tf} ${tf}.1 > /dev/null
if [ $? -eq 0 ] if [ $? -ne 0 ]
then then
echo "${cmd}: Decompression was not correct" echo "${cmd}: Decompression was not correct"
exit 1 exit 1

View file

@ -28,8 +28,8 @@ do
exit 1 exit 1
fi fi
diff ${tf} ${tf}.1 | grep -i differ diff ${tf} ${tf}.1 > /dev/null
if [ $? -eq 0 ] if [ $? -ne 0 ]
then then
echo "${cmd}: Decompression was not correct" echo "${cmd}: Decompression was not correct"
exit 1 exit 1

View file

@ -3,7 +3,7 @@
# #
clean() { clean() {
for algo in lzfx lz4 zlib bzip2 lzma lzmaMt libbsc for algo in lzfx lz4 zlib bzip2 lzma lzmaMt libbsc ppmd adapt adapt2
do do
for tf in bin.dat share.dat inc.dat for tf in bin.dat share.dat inc.dat
do do
@ -65,8 +65,8 @@ do
echo "${cmd} errored." echo "${cmd} errored."
exit 1 exit 1
fi fi
diff ${tf}.${algo} ${tf}.${algo}.1 | grep -i differ diff ${tf}.${algo} ${tf}.${algo}.1 > /dev/null
if [ $? -eq 0 ] if [ $? -ne 0 ]
then then
echo "${cmd}: Decompression was not correct" echo "${cmd}: Decompression was not correct"
exit 1 exit 1

View file

@ -30,8 +30,8 @@ do
exit 1 exit 1
fi fi
diff ${tf} ${tf}.1 | grep -i differ diff ${tf} ${tf}.1 > /dev/null
if [ $? -eq 0 ] if [ $? -ne 0 ]
then then
echo "${cmd}: Decompression was not correct" echo "${cmd}: Decompression was not correct"
exit 1 exit 1

View file

@ -40,8 +40,8 @@ do
exit 1 exit 1
fi fi
diff ${tf} ${tf}.1 | grep -i differ diff ${tf} ${tf}.1 > /dev/null
if [ $? -eq 0 ] if [ $? -ne 0 ]
then then
echo "${cmd}: Decompression was not correct" echo "${cmd}: Decompression was not correct"
exit 1 exit 1

49
test/t6.tst Normal file
View file

@ -0,0 +1,49 @@
#
# Simple compress and decompress
#
echo "#################################################"
echo "# Simple pipe mode compress and decompress"
echo "#################################################"
for algo in lzfx lz4 adapt
do
../../pcompress 2>&1 | grep $algo > /dev/null
[ $? -ne 0 ] && continue
for level in 1 3
do
for tf in combined.dat
do
for seg in 1m 2m 3m
do
cmd="cat ${tf} | ../../pcompress -p -c ${algo} -l ${level} -s ${seg} > ${tf}.pz"
echo "Running $cmd"
eval $cmd
if [ $? -ne 0 ]
then
echo "${cmd} errored."
exit 1
fi
cmd="../../pcompress -d ${tf}.pz ${tf}.1"
echo "Running $cmd"
eval $cmd
if [ $? -ne 0 ]
then
echo "${cmd} errored."
exit 1
fi
diff ${tf} ${tf}.1 > /dev/null
if [ $? -ne 0 ]
then
echo "${cmd}: Decompression was not correct"
exit 1
fi
rm -f ${tf}.pz ${tf}.1
done
done
done
done
echo "#################################################"
echo ""

66
test/t7.tst Normal file
View file

@ -0,0 +1,66 @@
#
# Test crypto
#
echo "#################################################"
echo "# Pipe mode Crypto tests"
echo "#################################################"
for algo in lzfx adapt2
do
for tf in comb_d.dat
do
for feat in "-e" "-e -L" "-D -e" "-D -EE -L -e" "-e -S CRC64"
do
for seg in 2m 5m
do
echo "sillypassword" > /tmp/pwf
cmd="cat ${tf} | ../../pcompress -c${algo} -p -l3 -s${seg} $feat -w /tmp/pwf > ${tf}.pz"
echo "Running $cmd"
eval $cmd
if [ $? -ne 0 ]
then
echo "${cmd} errored."
exit 1
fi
pw=`cat /tmp/pwf`
if [ "$pw" = "sillypassword" ]
then
echo "ERROR: Password file /tmp/pwf not zeroed!"
exit 1
fi
echo "sillypassword" > /tmp/pwf
cmd="../../pcompress -d -w /tmp/pwf ${tf}.pz ${tf}.1"
echo "Running $cmd"
eval $cmd
if [ $? -ne 0 ]
then
echo "${cmd} errored."
exit 1
fi
diff ${tf} ${tf}.1 > /dev/null
if [ $? -ne 0 ]
then
echo "${cmd}: Decompression was not correct"
exit 1
fi
pw=`cat /tmp/pwf`
if [ "$pw" = "sillypassword" ]
then
echo "ERROR: Password file /tmp/pwf not zeroed!"
exit 1
fi
rm -f ${tf}.pz ${tf}.1
done
done
done
done
rm -f /tmp/pwf
echo "#################################################"
echo ""