shortened repcode match finder implementation

dev
Yann Collet 2017-11-15 14:37:40 -08:00
parent d7e9805028
commit 61c2d70c86
1 changed files with 28 additions and 51 deletions

View File

@ -265,59 +265,36 @@ FORCE_INLINE_TEMPLATE
size_t bestLength = minMatchLen-1; size_t bestLength = minMatchLen-1;
/* check repCode */ /* check repCode */
#if 1 { U32 const lastR = ZSTD_REP_NUM + ll0;
if (!extDict) /*static*/ {
U32 const lastR = ZSTD_REP_NUM + ll0;
U32 repCode; U32 repCode;
for (repCode = ll0; repCode < lastR; repCode++) { for (repCode = ll0; repCode < lastR; repCode++) {
S32 const repOffset = (repCode==ZSTD_REP_NUM) ? (rep[0] - 1) : rep[repCode]; U32 const repOffset = (repCode==ZSTD_REP_NUM) ? (rep[0] - 1) : rep[repCode];
if ( (repOffset > 0) U32 const repIndex = current - repOffset;
&& (repOffset < (S32)(ip-prefixStart)) /* within current mem segment */ U32 repLen = 0;
&& (ZSTD_readMINMATCH(ip, minMatch) == ZSTD_readMINMATCH(ip - repOffset, minMatch))) { assert(repOffset <= current);
U32 const repLen = (U32)ZSTD_count(ip+minMatch, ip+minMatch-repOffset, iLimit) + minMatch; assert(current >= dictLimit);
/* save longer solution */ if (!extDict /*static*/ || (repIndex>=dictLimit)) {
if (repLen > bestLength) { if ( (repOffset-1 /* intentional overflow, discards 0 and -1 */ < current-dictLimit) /* within current mem segment */
DEBUGLOG(8, "current %u : found rep%u match of size%3u", && (ZSTD_readMINMATCH(ip, minMatch) == ZSTD_readMINMATCH(ip - repOffset, minMatch))) {
current, repCode - ll0, repLen); repLen = (U32)ZSTD_count(ip+minMatch, ip+minMatch-repOffset, iLimit) + minMatch;
bestLength = repLen; }
matches[mnum].off = repCode - ll0; } else { /* extDict */
matches[mnum].len = (U32)repLen; const BYTE* const repMatch = dictBase + repIndex;
mnum++; if ( ((repOffset-1) /*intentional overflow*/ < current)
if ( (repLen > ZSTD_OPT_NUM) & (((U32)((dictLimit-1) - repIndex) >= 3) /* intentional overflow */ & (repIndex > windowLow))
| (ip+repLen == iLimit) ) { /* best possible */ && (ZSTD_readMINMATCH(ip, minMatch) == ZSTD_readMINMATCH(repMatch, minMatch)) ) {
return mnum; repLen = (U32)ZSTD_count_2segments(ip+minMatch, repMatch+minMatch, iLimit, dictEnd, prefixStart) + minMatch;
} } } } } }
} else { /* extDict */ /* save longer solution */
U32 const lastR = ZSTD_REP_NUM + ll0; if (repLen > bestLength) {
U32 repCode; bestLength = repLen;
for (repCode=ll0; repCode<lastR; repCode++) { matches[mnum].off = repCode - ll0;
const S32 repCur = (repCode==ZSTD_REP_NUM) ? (rep[0] - 1) : rep[repCode]; matches[mnum].len = (U32)repLen;
const U32 repIndex = (U32)(current - repCur); mnum++;
const BYTE* const repBase = repIndex < dictLimit ? dictBase : base; if ( (repLen > ZSTD_OPT_NUM)
const BYTE* const repMatch = repBase + repIndex; | (ip+repLen == iLimit) ) { /* best possible */
if ( (repCur > 0 && repCur <= (S32)current) return mnum;
&& (((U32)((dictLimit-1) - repIndex) >= 3) & (repIndex>windowLow)) /* intentional overflow */ } } } }
&& (ZSTD_readMINMATCH(ip, minMatch) == ZSTD_readMINMATCH(repMatch, minMatch)) ) {
/* repcode detected we should take it */
const BYTE* const repEnd = repIndex < dictLimit ? dictEnd : iLimit;
U32 const repLen = (U32)ZSTD_count_2segments(ip+minMatch, repMatch+minMatch, iLimit, repEnd, prefixStart) + minMatch;
/* save longer solution */
if (repLen > bestLength) {
DEBUGLOG(8, "current %u : found rep%u match of size%3u",
current, repCode - ll0, repLen);
bestLength = repLen;
matches[mnum].off = repCode - ll0;
matches[mnum].len = (U32)repLen;
mnum++;
if ( (repLen > ZSTD_OPT_NUM)
| (ip+repLen == iLimit) ) { /* best possible */
return mnum;
} } } }
}
#else
(void)ll0; (void)rep; (void)minMatch;
#endif
/* HC3 match finder */ /* HC3 match finder */
if ((mls == 3) /*static*/ && (bestLength < mls)) { if ((mls == 3) /*static*/ && (bestLength < mls)) {