1
0
mirror of https://github.com/facebook/zstd.git synced 2025-03-06 16:56:49 +02:00

[lib] Skip the input window buffer when ZSTD_c_stableInBuffer is set

Compress directly from the `ZSTD_inBuffer`. We still allocate the input
buffer. A following commit will remove that allocation.
This commit is contained in:
Nick Terrell 2020-10-12 14:36:30 -07:00
parent 6bd6b6f7d3
commit 24f72789e2

View File

@ -4084,8 +4084,9 @@ static size_t ZSTD_compressStream_generic(ZSTD_CStream* zcs,
ZSTD_CCtx_reset(zcs, ZSTD_reset_session_only); ZSTD_CCtx_reset(zcs, ZSTD_reset_session_only);
someMoreWork = 0; break; someMoreWork = 0; break;
} }
/* complete loading into inBuffer */ /* complete loading into inBuffer in buffered mode */
{ size_t const toLoad = zcs->inBuffTarget - zcs->inBuffPos; if (zcs->appliedParams.inBufferMode == ZSTD_bm_buffered) {
size_t const toLoad = zcs->inBuffTarget - zcs->inBuffPos;
size_t const loaded = ZSTD_limitCopy( size_t const loaded = ZSTD_limitCopy(
zcs->inBuff + zcs->inBuffPos, toLoad, zcs->inBuff + zcs->inBuffPos, toLoad,
ip, iend-ip); ip, iend-ip);
@ -4105,31 +4106,49 @@ static size_t ZSTD_compressStream_generic(ZSTD_CStream* zcs,
} }
/* compress current block (note : this stage cannot be stopped in the middle) */ /* compress current block (note : this stage cannot be stopped in the middle) */
DEBUGLOG(5, "stream compression stage (flushMode==%u)", flushMode); DEBUGLOG(5, "stream compression stage (flushMode==%u)", flushMode);
{ void* cDst; { int const inputBuffered = (zcs->appliedParams.inBufferMode == ZSTD_bm_buffered);
void* cDst;
size_t cSize; size_t cSize;
size_t const iSize = zcs->inBuffPos - zcs->inToCompress;
size_t oSize = oend-op; size_t oSize = oend-op;
unsigned const lastBlock = (flushMode == ZSTD_e_end) && (ip==iend); size_t const iSize = inputBuffered
? zcs->inBuffPos - zcs->inToCompress
: MIN((size_t)(iend - ip), zcs->blockSize);
if (oSize >= ZSTD_compressBound(iSize) || zcs->appliedParams.outBufferMode == ZSTD_bm_stable) if (oSize >= ZSTD_compressBound(iSize) || zcs->appliedParams.outBufferMode == ZSTD_bm_stable)
cDst = op; /* compress into output buffer, to skip flush stage */ cDst = op; /* compress into output buffer, to skip flush stage */
else else
cDst = zcs->outBuff, oSize = zcs->outBuffSize; cDst = zcs->outBuff, oSize = zcs->outBuffSize;
cSize = lastBlock ? if (inputBuffered) {
ZSTD_compressEnd(zcs, cDst, oSize, unsigned const lastBlock = (flushMode == ZSTD_e_end) && (ip==iend);
zcs->inBuff + zcs->inToCompress, iSize) : cSize = lastBlock ?
ZSTD_compressContinue(zcs, cDst, oSize, ZSTD_compressEnd(zcs, cDst, oSize,
zcs->inBuff + zcs->inToCompress, iSize); zcs->inBuff + zcs->inToCompress, iSize) :
FORWARD_IF_ERROR(cSize, "%s", lastBlock ? "ZSTD_compressEnd failed" : "ZSTD_compressContinue failed"); ZSTD_compressContinue(zcs, cDst, oSize,
zcs->frameEnded = lastBlock; zcs->inBuff + zcs->inToCompress, iSize);
/* prepare next block */ FORWARD_IF_ERROR(cSize, "%s", lastBlock ? "ZSTD_compressEnd failed" : "ZSTD_compressContinue failed");
zcs->inBuffTarget = zcs->inBuffPos + zcs->blockSize; zcs->frameEnded = lastBlock;
if (zcs->inBuffTarget > zcs->inBuffSize) /* prepare next block */
zcs->inBuffPos = 0, zcs->inBuffTarget = zcs->blockSize; zcs->inBuffTarget = zcs->inBuffPos + zcs->blockSize;
DEBUGLOG(5, "inBuffTarget:%u / inBuffSize:%u", if (zcs->inBuffTarget > zcs->inBuffSize)
(unsigned)zcs->inBuffTarget, (unsigned)zcs->inBuffSize); zcs->inBuffPos = 0, zcs->inBuffTarget = zcs->blockSize;
if (!lastBlock) DEBUGLOG(5, "inBuffTarget:%u / inBuffSize:%u",
assert(zcs->inBuffTarget <= zcs->inBuffSize); (unsigned)zcs->inBuffTarget, (unsigned)zcs->inBuffSize);
zcs->inToCompress = zcs->inBuffPos; if (!lastBlock)
assert(zcs->inBuffTarget <= zcs->inBuffSize);
zcs->inToCompress = zcs->inBuffPos;
} else {
unsigned const lastBlock = (ip + iSize == iend);
assert(flushMode == ZSTD_e_end /* Already validated */);
cSize = lastBlock ?
ZSTD_compressEnd(zcs, cDst, oSize, ip, iSize) :
ZSTD_compressContinue(zcs, cDst, oSize, ip, iSize);
/* Consume the input prior to error checking to mirror buffered mode. */
if (iSize > 0)
ip += iSize;
FORWARD_IF_ERROR(cSize, "%s", lastBlock ? "ZSTD_compressEnd failed" : "ZSTD_compressContinue failed");
zcs->frameEnded = lastBlock;
if (lastBlock)
assert(ip == iend);
}
if (cDst == op) { /* no need to flush */ if (cDst == op) { /* no need to flush */
op += cSize; op += cSize;
if (zcs->frameEnded) { if (zcs->frameEnded) {