]> git.ipfire.org Git - thirdparty/zstd.git/commitdiff
support for searchLength from 3 to 7 for optimal parser
authorinikep <inikep@gmail.com>
Mon, 22 Feb 2016 10:34:07 +0000 (11:34 +0100)
committerinikep <inikep@gmail.com>
Mon, 22 Feb 2016 10:34:07 +0000 (11:34 +0100)
lib/zstd_compress.c
lib/zstd_internal.h
lib/zstd_opt.h
lib/zstd_opt_internal.h [new file with mode: 0644]
lib/zstd_static.h

index 8c917752f4c7c96920d7619d9b1e58cea1e18f05..8e572b4ac595f2a257f5718e0975ab2784351a84 100644 (file)
@@ -1369,6 +1369,7 @@ static void ZSTD_updateTree_extDict(ZSTD_CCtx* zc, const BYTE* const ip, const B
     while (idx < target) idx += ZSTD_insertBt1(zc, base+idx, mls, iend, nbCompares, 1);
 }
 
+#include "zstd_opt_internal.h"
 
 /** Tree updater, providing best match */
 static size_t ZSTD_BtFindBestMatch_extDict (
@@ -1410,10 +1411,6 @@ static size_t ZSTD_BtFindBestMatch_selectMLS_extDict (
 FORCE_INLINE
 U32 ZSTD_insertAndFindFirstIndex (ZSTD_CCtx* zc, const BYTE* ip, U32 mls)
 {
-#if MINMATCH == 3
-    U32* const hashTable3  = zc->hashTable3;
-    const U32 hashLog3 = zc->params.hashLog3;
-#endif 
     U32* const hashTable  = zc->hashTable;
     const U32 hashLog = zc->params.hashLog;
     U32* const chainTable = zc->contentTable;
@@ -1426,9 +1423,6 @@ U32 ZSTD_insertAndFindFirstIndex (ZSTD_CCtx* zc, const BYTE* ip, U32 mls)
         size_t h = ZSTD_hashPtr(base+idx, hashLog, mls);
         NEXT_IN_CHAIN(idx, chainMask) = hashTable[h];
         hashTable[h] = idx;
-#if MINMATCH == 3
-        hashTable3[ZSTD_hash3Ptr(base+idx, hashLog3)] = idx;
-#endif 
         idx++;
     }
 
@@ -1436,8 +1430,6 @@ U32 ZSTD_insertAndFindFirstIndex (ZSTD_CCtx* zc, const BYTE* ip, U32 mls)
     return hashTable[ZSTD_hashPtr(ip, hashLog, mls)];
 }
 
-#include "zstd_opt.h"
-
 
 FORCE_INLINE /* inlining is important to hardwire a hot branch (template emulation) */
 size_t ZSTD_HcFindBestMatch_generic (
@@ -1659,7 +1651,10 @@ _storeSequence:
 
 static void ZSTD_compressBlock_btopt(ZSTD_CCtx* ctx, const void* src, size_t srcSize)
 {
-    ZSTD_compressBlock_opt_generic(ctx, src, srcSize, 2);
+    if (ctx->params.searchLength == 3)
+        ZSTD_compressBlock_opt_generic3(ctx, src, srcSize, 2);
+    else
+        ZSTD_compressBlock_opt_generic4(ctx, src, srcSize, 2);
 }
 
 static void ZSTD_compressBlock_btlazy2(ZSTD_CCtx* ctx, const void* src, size_t srcSize)
@@ -1878,7 +1873,10 @@ static void ZSTD_compressBlock_btlazy2_extDict(ZSTD_CCtx* ctx, const void* src,
 
 static void ZSTD_compressBlock_btopt_extDict(ZSTD_CCtx* ctx, const void* src, size_t srcSize)
 {
-    ZSTD_compressBlock_opt_extDict_generic(ctx, src, srcSize, 2);
+    if (ctx->params.searchLength == 3)
+        ZSTD_compressBlock_opt_extDict_generic3(ctx, src, srcSize, 2);
+    else
+        ZSTD_compressBlock_opt_extDict_generic4(ctx, src, srcSize, 2);
 }
 
 
@@ -2261,7 +2259,7 @@ size_t ZSTD_compress(void* dst, size_t maxDstSize, const void* src, size_t srcSi
 
 /*-=====  Pre-defined compression levels  =====-*/
 
-#define ZSTD_MAX_CLEVEL 21
+#define ZSTD_MAX_CLEVEL 22
 unsigned ZSTD_maxCLevel(void) { return ZSTD_MAX_CLEVEL; }
 
 
@@ -2290,6 +2288,7 @@ static const ZSTD_parameters ZSTD_defaultParameters[4][ZSTD_MAX_CLEVEL+1] = {
     {  0, 25, 25, 24, 16,  5,  4, 40, ZSTD_btopt   },  /* level 19 */
     {  0, 26, 26, 25, 16,  8,  4,256, ZSTD_btopt   },  /* level 20 */
     {  0, 26, 27, 25, 24, 10,  4,256, ZSTD_btopt   },  /* level 21 */
+    {  0, 26, 26, 25, 16,  8,  3,256, ZSTD_btopt   },  /* level 20+MM3 */
 },
 {   /* for srcSize <= 256 KB */
     /* l,  W,  C,  H, H3,  S,  L,  T, strat */
index 620572e516c7edf345639d23c9930d7d7f93043c..b9826aa7857506662b13f71c8d007b944014d42b 100644 (file)
@@ -79,7 +79,7 @@ static const size_t ZSTD_frameHeaderSize_min = 5;
 #define IS_RAW 2
 #define IS_RLE 3
 
-#define MINMATCH 3
+#define MINMATCH 4
 #define REPCODE_STARTVALUE 1
 
 #define Litbits  8
index 9b1fffd7d07a2be737fd0b5bdf8400cc2934cdf6..24343d6918513a392068b059c11b53918efa01f2 100644 (file)
        - Zstd source repository : https://www.zstd.net
 */
 
-/* Note : this file is intended to be included within zstd_compress.c */
-
-
-/*-  Local types  -*/
-typedef struct {
-    U32 off;
-    U32 len;
-    U32 back;
-} ZSTD_match_t;
-
-typedef struct {
-    U32 price;
-    U32 off;
-    U32 mlen;
-    U32 litlen;
-    U32 rep;
-    U32 rep2;
-} ZSTD_optimal_t;
-
-
-/*-  Constants  -*/
-#define ZSTD_OPT_NUM    (1<<12)
-#define ZSTD_FREQ_START 1
-#define ZSTD_FREQ_STEP  1
-#define ZSTD_FREQ_DIV   6
-
-/*-  Debug  -*/
-#if defined(ZSTD_OPT_DEBUG) && ZSTD_OPT_DEBUG>=9
-    #define ZSTD_LOG_PARSER(...) printf(__VA_ARGS__)
-    #define ZSTD_LOG_ENCODE(...) printf(__VA_ARGS__)
-    #define ZSTD_LOG_TRY_PRICE(...) printf(__VA_ARGS__)
-#else
-    #define ZSTD_LOG_PARSER(...)
-    #define ZSTD_LOG_ENCODE(...)
-    #define ZSTD_LOG_TRY_PRICE(...)
-#endif
-
-
-#if MINMATCH == 3
-    #define MEM_readMINMATCH(ptr) ((U32)(MEM_read32(ptr)<<8)) 
-#else
-    #define MEM_readMINMATCH(ptr) (U32)(MEM_read32(ptr)) 
-#endif
-
-
-FORCE_INLINE U32 ZSTD_getLiteralPrice(seqStore_t* seqStorePtr, U32 litLength, const BYTE* literals)
-{
-    U32 price, u;
-
-    /* literals */
-    price = litLength * ZSTD_highbit(seqStorePtr->litSum);
-    for (u=0; u < litLength; u++)
-        price -= ZSTD_highbit(seqStorePtr->litFreq[literals[u]]);
-
-    /* literal Length */
-    price += ((litLength >= MaxLL)<<3) + ((litLength >= 255+MaxLL)<<4) + ((litLength>=(1<<15))<<3);
-    if (litLength >= MaxLL) litLength = MaxLL;
-    price += ZSTD_highbit(seqStorePtr->litLengthSum) - ZSTD_highbit(seqStorePtr->litLengthFreq[litLength]);
-
-    return price;
-}
+/* Note : this file is intended to be included within zstd_opt_internal.h */
 
 
-FORCE_INLINE U32 ZSTD_getPrice(seqStore_t* seqStorePtr, U32 litLength, const BYTE* literals, U32 offset, U32 matchLength)
+FORCE_INLINE U32 ZSTD_GETPRICE(seqStore_t* seqStorePtr, U32 litLength, const BYTE* literals, U32 offset, U32 matchLength)
 {
     /* offset */
     BYTE offCode = offset ? (BYTE)ZSTD_highbit(offset) + 1 : 0;
     U32 price = offCode + ZSTD_highbit(seqStorePtr->offCodeSum) - ZSTD_highbit(seqStorePtr->offCodeFreq[offCode]);
 
     /* match Length */
-    matchLength -= MINMATCH;
+    matchLength -= MINMATCHOPT;
     price += ((matchLength >= MaxML)<<3) + ((matchLength >= 255+MaxML)<<4) + ((matchLength>=(1<<15))<<3);
     if (matchLength >= MaxML) matchLength = MaxML;
     price += ZSTD_highbit(seqStorePtr->matchLengthSum) - ZSTD_highbit(seqStorePtr->matchLengthFreq[matchLength]);
@@ -113,120 +53,10 @@ FORCE_INLINE U32 ZSTD_getPrice(seqStore_t* seqStorePtr, U32 litLength, const BYT
 }
 
 
-MEM_STATIC void ZSTD_rescaleFreqs(seqStore_t* ssPtr)
-{
-    unsigned u;
-    
- //   printf("matchLengthSum=%d litLengthSum=%d litSum=%d offCodeSum=%d\n", ssPtr->matchLengthSum, ssPtr->litLengthSum, ssPtr->litSum, ssPtr->offCodeSum);
-    
-    if (ssPtr->litLengthSum == 0) {
-        ssPtr->matchLengthSum = (1<<MLbits);
-        ssPtr->litLengthSum = (1<<LLbits);
-        ssPtr->litSum = (1<<Litbits);
-        ssPtr->offCodeSum = (1<<Offbits);
-
-        for (u=0; u<=MaxLit; u++)
-            ssPtr->litFreq[u] = 1;
-        for (u=0; u<=MaxLL; u++)
-            ssPtr->litLengthFreq[u] = 1;
-        for (u=0; u<=MaxML; u++)
-            ssPtr->matchLengthFreq[u] = 1;
-        for (u=0; u<=MaxOff; u++)
-            ssPtr->offCodeFreq[u] = 1;
-    } else {
-        ssPtr->matchLengthSum = 0;
-        ssPtr->litLengthSum = 0;
-        ssPtr->litSum = 0;
-        ssPtr->offCodeSum = 0;
-
-        for (u=0; u<=MaxLit; u++) {
-            ssPtr->litFreq[u] = ZSTD_FREQ_START + (ssPtr->litFreq[u]>>ZSTD_FREQ_DIV);
-            ssPtr->litSum += ssPtr->litFreq[u];
-        }
-        for (u=0; u<=MaxLL; u++) {
-            ssPtr->litLengthFreq[u] = ZSTD_FREQ_START + (ssPtr->litLengthFreq[u]>>ZSTD_FREQ_DIV);
-            ssPtr->litLengthSum += ssPtr->litLengthFreq[u];
-        }
-        for (u=0; u<=MaxML; u++) {
-            ssPtr->matchLengthFreq[u] = ZSTD_FREQ_START + (ssPtr->matchLengthFreq[u]>>ZSTD_FREQ_DIV);
-            ssPtr->matchLengthSum += ssPtr->matchLengthFreq[u];
-        }
-        for (u=0; u<=MaxOff; u++) {
-            ssPtr->offCodeFreq[u] = ZSTD_FREQ_START + (ssPtr->offCodeFreq[u]>>ZSTD_FREQ_DIV);
-            ssPtr->offCodeSum += ssPtr->offCodeFreq[u];
-        }
-    }
-}
-
-
-MEM_STATIC void ZSTD_updatePrice(seqStore_t* seqStorePtr, U32 litLength, const BYTE* literals, U32 offset, U32 matchLength)
-{
-    U32 u;
-
-    /* literals */
-    seqStorePtr->litSum += litLength * ZSTD_FREQ_STEP;
-    for (u=0; u < litLength; u++)
-        seqStorePtr->litFreq[literals[u]] += ZSTD_FREQ_STEP;
-
-    /* literal Length */
-    seqStorePtr->litLengthSum += ZSTD_FREQ_STEP;
-    if (litLength >= MaxLL)
-        seqStorePtr->litLengthFreq[MaxLL] += ZSTD_FREQ_STEP;
-    else
-        seqStorePtr->litLengthFreq[litLength] += ZSTD_FREQ_STEP;
-
-    /* match offset */
-    seqStorePtr->offCodeSum += ZSTD_FREQ_STEP;
-    BYTE offCode = offset ? (BYTE)ZSTD_highbit(offset) + 1 : 0;
-    seqStorePtr->offCodeFreq[offCode] += ZSTD_FREQ_STEP;
-
-    /* match Length */
-    seqStorePtr->matchLengthSum += ZSTD_FREQ_STEP;
-    if (matchLength >= MaxML)
-        seqStorePtr->matchLengthFreq[MaxML] += ZSTD_FREQ_STEP;
-    else
-        seqStorePtr->matchLengthFreq[matchLength] += ZSTD_FREQ_STEP;
-}
-
-
-#define SET_PRICE(pos, mlen_, offset_, litlen_, price_)   \
-    {                                                 \
-        while (last_pos < pos)  { opt[last_pos+1].price = 1<<30; last_pos++; } \
-        opt[pos].mlen = mlen_;                         \
-        opt[pos].off = offset_;                        \
-        opt[pos].litlen = litlen_;                     \
-        opt[pos].price = price_;                       \
-        ZSTD_LOG_PARSER("%d: SET price[%d/%d]=%d litlen=%d len=%d off=%d\n", (int)(inr-base), (int)pos, (int)last_pos, opt[pos].price, opt[pos].litlen, opt[pos].mlen, opt[pos].off); \
-    }
-
-
-
 /*-*************************************
 *  Binary Tree search
 ***************************************/
-/* Update hashTable3 up to ip (excluded)
-   Assumption : always within prefix (ie. not within extDict) */
-#if MINMATCH == 3
-static U32 ZSTD_insertAndFindFirstIndexHash3 (ZSTD_CCtx* zc, const BYTE* ip)
-{
-    U32* const hashTable3  = zc->hashTable3;
-    const U32 hashLog3 = zc->params.hashLog3;
-    const BYTE* const base = zc->base;
-    const U32 target = (U32)(ip - base);
-    U32 idx = zc->nextToUpdate3;
-
-    while(idx < target) {
-        hashTable3[ZSTD_hash3Ptr(base+idx, hashLog3)] = idx;
-        idx++;
-    }
-
-    zc->nextToUpdate3 = target;
-    return hashTable3[ZSTD_hash3Ptr(ip, hashLog3)];
-}
-#endif 
-
-
-static U32 ZSTD_insertBtAndGetAllMatches (
+static U32 ZSTD_INSERTBTANDGETALLMATCHES (
                         ZSTD_CCtx* zc,
                         const BYTE* const ip, const BYTE* const iLimit,
                         U32 nbCompares, const U32 mls,
@@ -254,10 +84,10 @@ static U32 ZSTD_insertBtAndGetAllMatches (
     U32 dummy32;   /* to be nullified at the end */
     U32 mnum = 0;
 
-    size_t bestLength = MINMATCH-1;
+    size_t bestLength = MINMATCHOPT-1;
     hashTable[h] = current;   /* Update Hash Table */
 
-#if MINMATCH == 3
+#if MINMATCHOPT == 3
     /* HC3 match finder */
     U32 matchIndex3 = ZSTD_insertAndFindFirstIndexHash3 (zc, ip);
 
@@ -266,12 +96,11 @@ static U32 ZSTD_insertBtAndGetAllMatches (
         size_t currentMl=0;
         if ((!extDict) || matchIndex3 >= dictLimit) {
             match = base + matchIndex3;
-            if (match[bestLength] == ip[bestLength]) currentMl = ZSTD_count(ip, match, iLimit);   // faster
-          //  if (MEM_readMINMATCH(match) == MEM_readMINMATCH(ip)) currentMl = ZSTD_count(ip+MINMATCH, match+MINMATCH, iLimit)+MINMATCH;  // stronger
+            if (match[bestLength] == ip[bestLength]) currentMl = ZSTD_count(ip, match, iLimit);
         } else {
             match = dictBase + matchIndex3;
             if (MEM_readMINMATCH(match) == MEM_readMINMATCH(ip))    /* assumption : matchIndex3 <= dictLimit-4 (by table construction) */
-                currentMl = ZSTD_count_2segments(ip+MINMATCH, match+MINMATCH, iLimit, dictEnd, prefixStart) + MINMATCH;
+                currentMl = ZSTD_count_2segments(ip+MINMATCHOPT, match+MINMATCHOPT, iLimit, dictEnd, prefixStart) + MINMATCHOPT;
         }
 
         /* save best solution */
@@ -342,18 +171,18 @@ static U32 ZSTD_insertBtAndGetAllMatches (
 
 
 /** Tree updater, providing best match */
-static U32 ZSTD_BtGetAllMatches (
+static U32 ZSTD_BTGETALLMATCHES (
                         ZSTD_CCtx* zc,
                         const BYTE* const ip, const BYTE* const iLimit,
                         const U32 maxNbAttempts, const U32 mls, ZSTD_match_t* matches)
 {
     if (ip < zc->base + zc->nextToUpdate) return 0;   /* skipped area */
     ZSTD_updateTree(zc, ip, iLimit, maxNbAttempts, mls);
-    return ZSTD_insertBtAndGetAllMatches(zc, ip, iLimit, maxNbAttempts, mls, 0, matches);
+    return ZSTD_INSERTBTANDGETALLMATCHES(zc, ip, iLimit, maxNbAttempts, mls, 0, matches);
 }
 
 
-static U32 ZSTD_BtGetAllMatches_selectMLS (
+static U32 ZSTD_BTGETALLMATCHES_SELECTMLS (
                         ZSTD_CCtx* zc,   /* Index table will be updated */
                         const BYTE* ip, const BYTE* const iLowLimit, const BYTE* const iHighLimit,
                         const U32 maxNbAttempts, const U32 matchLengthSearch, ZSTD_match_t* matches)
@@ -362,25 +191,25 @@ static U32 ZSTD_BtGetAllMatches_selectMLS (
     switch(matchLengthSearch)
     {
     default :
-    case 4 : return ZSTD_BtGetAllMatches(zc, ip, iHighLimit, maxNbAttempts, 4, matches);
-    case 5 : return ZSTD_BtGetAllMatches(zc, ip, iHighLimit, maxNbAttempts, 5, matches);
-    case 6 : return ZSTD_BtGetAllMatches(zc, ip, iHighLimit, maxNbAttempts, 6, matches);
+    case 4 : return ZSTD_BTGETALLMATCHES(zc, ip, iHighLimit, maxNbAttempts, 4, matches);
+    case 5 : return ZSTD_BTGETALLMATCHES(zc, ip, iHighLimit, maxNbAttempts, 5, matches);
+    case 6 : return ZSTD_BTGETALLMATCHES(zc, ip, iHighLimit, maxNbAttempts, 6, matches);
     }
 }
 
 /** Tree updater, providing best match */
-static U32 ZSTD_BtGetAllMatches_extDict (
+static U32 ZSTD_BTGETALLMATCHES_EXTDICT (
                         ZSTD_CCtx* zc,
                         const BYTE* const ip, const BYTE* const iLimit,
                         const U32 maxNbAttempts, const U32 mls, ZSTD_match_t* matches)
 {
     if (ip < zc->base + zc->nextToUpdate) return 0;   /* skipped area */
     ZSTD_updateTree_extDict(zc, ip, iLimit, maxNbAttempts, mls);
-    return ZSTD_insertBtAndGetAllMatches(zc, ip, iLimit, maxNbAttempts, mls, 1, matches);
+    return ZSTD_INSERTBTANDGETALLMATCHES(zc, ip, iLimit, maxNbAttempts, mls, 1, matches);
 }
 
 
-static U32 ZSTD_BtGetAllMatches_selectMLS_extDict (
+static U32 ZSTD_BTGETALLMATCHES_SELECTMLS_EXTDICT (
                         ZSTD_CCtx* zc,   /* Index table will be updated */
                         const BYTE* ip, const BYTE* const iLowLimit, const BYTE* const iHighLimit,
                         const U32 maxNbAttempts, const U32 matchLengthSearch, ZSTD_match_t* matches)
@@ -389,9 +218,9 @@ static U32 ZSTD_BtGetAllMatches_selectMLS_extDict (
     switch(matchLengthSearch)
     {
     default :
-    case 4 : return ZSTD_BtGetAllMatches_extDict(zc, ip, iHighLimit, maxNbAttempts, 4, matches);
-    case 5 : return ZSTD_BtGetAllMatches_extDict(zc, ip, iHighLimit, maxNbAttempts, 5, matches);
-    case 6 : return ZSTD_BtGetAllMatches_extDict(zc, ip, iHighLimit, maxNbAttempts, 6, matches);
+    case 4 : return ZSTD_BTGETALLMATCHES_EXTDICT(zc, ip, iHighLimit, maxNbAttempts, 4, matches);
+    case 5 : return ZSTD_BTGETALLMATCHES_EXTDICT(zc, ip, iHighLimit, maxNbAttempts, 5, matches);
+    case 6 : return ZSTD_BTGETALLMATCHES_EXTDICT(zc, ip, iHighLimit, maxNbAttempts, 6, matches);
     }
 }
 
@@ -400,7 +229,7 @@ static U32 ZSTD_BtGetAllMatches_selectMLS_extDict (
 *  Optimal parser
 *********************************/
 FORCE_INLINE
-void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
+void ZSTD_COMPRESSBLOCK_OPT_GENERIC(ZSTD_CCtx* ctx,
                                     const void* src, size_t srcSize,
                                     const U32 depth)
 {
@@ -416,14 +245,13 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
     U32 rep_2=REPCODE_STARTVALUE, rep_1=REPCODE_STARTVALUE;
     const U32 maxSearches = 1U << ctx->params.searchLog;
     const U32 mls = ctx->params.searchLength;
+    const U32 sufficient_len = ctx->params.targetLength;
 
-    ZSTD_optimal_t opt[ZSTD_OPT_NUM+4];
+    ZSTD_optimal_t opt[ZSTD_OPT_NUM+1];
     ZSTD_match_t matches[ZSTD_OPT_NUM+1];
     const BYTE* inr;
     U32 cur, match_num, last_pos, litlen, price;
 
-    const U32 sufficient_len = ctx->params.targetLength;
-
     /* init */
     ctx->nextToUpdate3 = ctx->nextToUpdate;
     ZSTD_resetSeqStore(seqStorePtr);
@@ -445,7 +273,7 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
         /* check repCode */
         if (MEM_readMINMATCH(ip+1) == MEM_readMINMATCH(ip+1 - rep_1)) {
             /* repcode : we take it */
-            mlen = (U32)ZSTD_count(ip+1+MINMATCH, ip+1+MINMATCH-rep_1, iend) + MINMATCH;
+            mlen = (U32)ZSTD_count(ip+1+MINMATCHOPT, ip+1+MINMATCHOPT-rep_1, iend) + MINMATCHOPT;
 
             ZSTD_LOG_PARSER("%d: start try REP rep=%d mlen=%d\n", (int)(ip-base), (int)rep_1, (int)mlen);
             if (depth==0 || mlen > sufficient_len || mlen >= ZSTD_OPT_NUM) {
@@ -455,14 +283,14 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
 
             litlen = opt[0].litlen + 1;
             do {
-                price = ZSTD_getPrice(seqStorePtr, litlen, litstart, 0, mlen);
+                price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, 0, mlen);
                 if (mlen + 1 > last_pos || price < opt[mlen + 1].price)
                     SET_PRICE(mlen + 1, mlen, 0, litlen, price);   /* note : macro modifies last_pos */
                 mlen--;
-            } while (mlen >= MINMATCH);
+            } while (mlen >= MINMATCHOPT);
         }
 
-        match_num = ZSTD_BtGetAllMatches_selectMLS_extDict(ctx, ip, ip, iend, maxSearches, mls, matches); /* first search (depth 0) */
+        match_num = ZSTD_BTGETALLMATCHES_SELECTMLS(ctx, ip, ip, iend, maxSearches, mls, matches); /* first search (depth 0) */
 
         ZSTD_LOG_PARSER("%d: match_num=%d last_pos=%d\n", (int)(ip-base), match_num, last_pos);
         if (!last_pos && !match_num) { ip++; continue; }
@@ -479,7 +307,7 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
             goto _storeSequence;
         }
 
-       best_mlen = (last_pos) ? last_pos : MINMATCH;
+       best_mlen = (last_pos) ? last_pos : MINMATCHOPT;
 
        // set prices using matches at position = 0
        for (u = 0; u < match_num; u++) {
@@ -488,13 +316,13 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
            ZSTD_LOG_PARSER("%d: start Found mlen=%d off=%d best_mlen=%d last_pos=%d\n", (int)(ip-base), matches[u].len, matches[u].off, (int)best_mlen, (int)last_pos);
            litlen = opt[0].litlen;
            while (mlen <= best_mlen) {
-                price = ZSTD_getPrice(seqStorePtr, litlen, litstart, matches[u].off, mlen);
+                price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, matches[u].off, mlen);
                 if (mlen > last_pos || price < opt[mlen].price)
                     SET_PRICE(mlen, mlen, matches[u].off, litlen, price);
                 mlen++;
         }  }
 
-        if (last_pos < MINMATCH) { ip++; continue; }
+        if (last_pos < MINMATCHOPT) { ip++; continue; }
 
          /* check further positions */
         for (cur = 1; cur <= last_pos; cur++) {
@@ -554,7 +382,7 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
            }
 
            if (MEM_readMINMATCH(inr) == MEM_readMINMATCH(inr - cur_rep)) {  // check rep
-               mlen = (U32)ZSTD_count(inr+MINMATCH, inr+MINMATCH - cur_rep, iend) + MINMATCH;
+               mlen = (U32)ZSTD_count(inr+MINMATCHOPT, inr+MINMATCHOPT - cur_rep, iend) + MINMATCHOPT;
                ZSTD_LOG_PARSER("%d: Found REP mlen=%d off=%d rep=%d opt[%d].off=%d\n", (int)(inr-base), mlen, 0, opt[cur].rep, cur, opt[cur].off);
 
                if (mlen > sufficient_len || cur + mlen >= ZSTD_OPT_NUM) {
@@ -568,14 +396,14 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
                if (opt[cur].mlen == 1) {
                     litlen = opt[cur].litlen;
                     if (cur > litlen) {
-                        price = opt[cur - litlen].price + ZSTD_getPrice(seqStorePtr, litlen, inr-litlen, 0, mlen);
+                        price = opt[cur - litlen].price + ZSTD_GETPRICE(seqStorePtr, litlen, inr-litlen, 0, mlen);
                         ZSTD_LOG_TRY_PRICE("%d: TRY5 opt[%d].price=%d price=%d cur=%d litlen=%d\n", (int)(inr-base), cur - litlen, opt[cur - litlen].price, price, cur, litlen);
                     } else
-                        price = ZSTD_getPrice(seqStorePtr, litlen, litstart, 0, mlen);
+                        price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, 0, mlen);
                 } else {
                     litlen = 0;
-                    price = opt[cur].price + ZSTD_getPrice(seqStorePtr, 0, NULL, 0, mlen);
-                    ZSTD_LOG_TRY_PRICE("%d: TRY7 price=%d cur=%d litlen=0 getprice=%d\n", (int)(inr-base), price, cur, (int)ZSTD_getPrice(seqStorePtr, 0, NULL, 0, mlen));
+                    price = opt[cur].price + ZSTD_GETPRICE(seqStorePtr, 0, NULL, 0, mlen);
+                    ZSTD_LOG_TRY_PRICE("%d: TRY7 price=%d cur=%d litlen=0 getprice=%d\n", (int)(inr-base), price, cur, (int)ZSTD_GETPRICE(seqStorePtr, 0, NULL, 0, mlen));
                 }
 
                 best_mlen = mlen;
@@ -585,10 +413,10 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
                     if (cur + mlen > last_pos || price <= opt[cur + mlen].price)
                         SET_PRICE(cur + mlen, mlen, 0, litlen, price);
                     mlen--;
-                } while (mlen >= MINMATCH);
+                } while (mlen >= MINMATCHOPT);
             }
 
-            match_num = ZSTD_BtGetAllMatches_selectMLS_extDict(ctx, inr, ip, iend, maxSearches, mls, matches);
+            match_num = ZSTD_BTGETALLMATCHES_SELECTMLS(ctx, inr, ip, iend, maxSearches, mls, matches);
             ZSTD_LOG_PARSER("%d: ZSTD_GetAllMatches match_num=%d\n", (int)(inr-base), match_num);
 
             if (match_num > 0 && matches[match_num-1].len > sufficient_len) {
@@ -598,7 +426,7 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
                 goto _storeSequence;
             }
 
-            best_mlen = (best_mlen > MINMATCH) ? best_mlen : MINMATCH;
+            best_mlen = (best_mlen > MINMATCHOPT) ? best_mlen : MINMATCHOPT;
 
             /* set prices using matches at position = cur */
             for (u = 0; u < match_num; u++) {
@@ -611,12 +439,12 @@ void ZSTD_compressBlock_opt_generic(ZSTD_CCtx* ctx,
                     if (opt[cur].mlen == 1) {
                         litlen = opt[cur].litlen;
                         if (cur > litlen)
-                            price = opt[cur - litlen].price + ZSTD_getPrice(seqStorePtr, litlen, ip+cur-litlen, matches[u].off, mlen);
+                            price = opt[cur - litlen].price + ZSTD_GETPRICE(seqStorePtr, litlen, ip+cur-litlen, matches[u].off, mlen);
                         else
-                            price = ZSTD_getPrice(seqStorePtr, litlen, litstart, matches[u].off, mlen);
+                            price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, matches[u].off, mlen);
                     } else {
                         litlen = 0;
-                        price = opt[cur].price + ZSTD_getPrice(seqStorePtr, 0, NULL, matches[u].off, mlen);
+                        price = opt[cur].price + ZSTD_GETPRICE(seqStorePtr, 0, NULL, matches[u].off, mlen);
                     }
 
                     ZSTD_LOG_PARSER("%d: Found2 mlen=%d best_mlen=%d off=%d price=%d litlen=%d\n", (int)(inr-base), mlen, best_mlen, matches[u].off, price, litlen);
@@ -688,7 +516,7 @@ _storeSequence:   /* cur, last_pos, best_mlen, best_off have to be set */
             else
                 ml2 = (U32)ZSTD_count(ip, ip-rep_1, iend);
             if (offset == 0 || offset >= 8)
-            if (ml2 < mlen && ml2 < MINMATCH) {
+            if (ml2 < mlen && ml2 < MINMATCHOPT) {
                 printf("%d: ERROR iend=%d mlen=%d offset=%d ml2=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset, (int)ml2); exit(0); }
             if (ip < anchor) {
                 printf("%d: ERROR ip < anchor iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
@@ -696,14 +524,14 @@ _storeSequence:   /* cur, last_pos, best_mlen, best_off have to be set */
                 printf("%d: ERROR ip - offset < base iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
             if ((int)offset >= (1 << ctx->params.windowLog)) {
                 printf("%d: offset >= (1 << params.windowLog) iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
-            if (mlen < MINMATCH) {
-                printf("%d: ERROR mlen < MINMATCH iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
+            if (mlen < MINMATCHOPT) {
+                printf("%d: ERROR mlen < MINMATCHOPT iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
             if (ip + mlen > iend) {
                 printf("%d: ERROR ip + mlen >= iend iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
 #endif
 
-            ZSTD_updatePrice(seqStorePtr, litLength, anchor, offset, mlen-MINMATCH);
-            ZSTD_storeSeq(seqStorePtr, litLength, anchor, offset, mlen-MINMATCH);
+            ZSTD_updatePrice(seqStorePtr, litLength, anchor, offset, mlen-MINMATCHOPT);
+            ZSTD_storeSeq(seqStorePtr, litLength, anchor, offset, mlen-MINMATCHOPT);
             anchor = ip = ip + mlen;
         }   /* for (cur=0; cur < last_pos; ) */
 
@@ -711,14 +539,14 @@ _storeSequence:   /* cur, last_pos, best_mlen, best_off have to be set */
         while ( (anchor <= ilimit)
              && (MEM_readMINMATCH(anchor) == MEM_readMINMATCH(anchor - rep_2)) ) {
             /* store sequence */
-            best_mlen = (U32)ZSTD_count(anchor+MINMATCH, anchor+MINMATCH-rep_2, iend);
+            best_mlen = (U32)ZSTD_count(anchor+MINMATCHOPT, anchor+MINMATCHOPT-rep_2, iend);
             best_off = rep_2;
             rep_2 = rep_1;
             rep_1 = best_off;
             ZSTD_LOG_ENCODE("%d/%d: ENCODE REP literals=%d mlen=%d off=%d rep1=%d rep2=%d\n", (int)(anchor-base), (int)(iend-base), (int)(0), (int)best_mlen, (int)(0), (int)rep_1, (int)rep_2);
             ZSTD_updatePrice(seqStorePtr, 0, anchor, 0, best_mlen);
             ZSTD_storeSeq(seqStorePtr, 0, anchor, 0, best_mlen);
-            anchor += best_mlen+MINMATCH;
+            anchor += best_mlen+MINMATCHOPT;
             continue;   /* faster when present ... (?) */
         }
         if (anchor > ip) ip = anchor;
@@ -734,7 +562,7 @@ _storeSequence:   /* cur, last_pos, best_mlen, best_off have to be set */
 
 
 FORCE_INLINE
-void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
+void ZSTD_COMPRESSBLOCK_OPT_EXTDICT_GENERIC(ZSTD_CCtx* ctx,
                                      const void* src, size_t srcSize,
                                      const U32 depth)
 {
@@ -754,14 +582,13 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
     U32 rep_2=REPCODE_STARTVALUE, rep_1=REPCODE_STARTVALUE;
     const U32 maxSearches = 1U << ctx->params.searchLog;
     const U32 mls = ctx->params.searchLength;
+    const U32 sufficient_len = ctx->params.targetLength;
 
-    ZSTD_optimal_t opt[ZSTD_OPT_NUM+4];
+    ZSTD_optimal_t opt[ZSTD_OPT_NUM+1];
     ZSTD_match_t matches[ZSTD_OPT_NUM+1];
     const BYTE* inr;
     U32 cur, match_num, last_pos, litlen, price;
 
-    const U32 sufficient_len = ctx->params.targetLength;
-
     /* init */
     ctx->nextToUpdate3 = ctx->nextToUpdate;
     ZSTD_resetSeqStore(seqStorePtr);
@@ -788,7 +615,7 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
                && (MEM_readMINMATCH(ip+1) == MEM_readMINMATCH(repMatch)) ) {
                 /* repcode detected we should take it */
                 const BYTE* const repEnd = repIndex < dictLimit ? dictEnd : iend;
-                mlen = (U32)ZSTD_count_2segments(ip+1+MINMATCH, repMatch+MINMATCH, iend, repEnd, prefixStart) + MINMATCH;
+                mlen = (U32)ZSTD_count_2segments(ip+1+MINMATCHOPT, repMatch+MINMATCHOPT, iend, repEnd, prefixStart) + MINMATCHOPT;
 
                 ZSTD_LOG_PARSER("%d: start try REP rep=%d mlen=%d\n", (int)(ip-base), (int)rep_1, (int)mlen);
                 if (depth==0 || mlen > sufficient_len || mlen >= ZSTD_OPT_NUM) {
@@ -798,16 +625,16 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
 
                 litlen = opt[0].litlen + 1;
                 do {
-                    price = ZSTD_getPrice(seqStorePtr, litlen, litstart, 0, mlen);
+                    price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, 0, mlen);
                     if (mlen + 1 > last_pos || price < opt[mlen + 1].price)
                         SET_PRICE(mlen + 1, mlen, 0, litlen, price);
                     mlen--;
-                } while (mlen >= MINMATCH);
+                } while (mlen >= MINMATCHOPT);
         }   }
 
-       best_mlen = (last_pos) ? last_pos : MINMATCH;
+       best_mlen = (last_pos) ? last_pos : MINMATCHOPT;
 
-       match_num = ZSTD_BtGetAllMatches_selectMLS_extDict(ctx, ip, ip, iend, maxSearches, mls, matches);  /* first search (depth 0) */
+       match_num = ZSTD_BTGETALLMATCHES_SELECTMLS_EXTDICT(ctx, ip, ip, iend, maxSearches, mls, matches);  /* first search (depth 0) */
 
        ZSTD_LOG_PARSER("%d: match_num=%d last_pos=%d\n", (int)(ip-base), match_num, last_pos);
        if (!last_pos && !match_num) { ip++; continue; }
@@ -831,13 +658,13 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
             ZSTD_LOG_PARSER("%d: start Found mlen=%d off=%d best_mlen=%d last_pos=%d\n", (int)(ip-base), matches[u].len, matches[u].off, (int)best_mlen, (int)last_pos);
             litlen = opt[0].litlen;
             while (mlen <= best_mlen) {
-                price = ZSTD_getPrice(seqStorePtr, litlen, litstart, matches[u].off, mlen);
+                price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, matches[u].off, mlen);
                 if (mlen > last_pos || price < opt[mlen].price)
                     SET_PRICE(mlen, mlen, matches[u].off, litlen, price);
                 mlen++;
         }   }
 
-        if (last_pos < MINMATCH) {
+        if (last_pos < MINMATCHOPT) {
             // ip += ((ip-anchor) >> g_searchStrength) + 1;   /* jump faster over incompressible sections */
             ip++; continue;
         }
@@ -906,7 +733,7 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
               &&(MEM_readMINMATCH(inr) == MEM_readMINMATCH(repMatch)) ) {
                 /* repcode detected */
                 const BYTE* const repEnd = repIndex < dictLimit ? dictEnd : iend;
-                mlen = (U32)ZSTD_count_2segments(inr+MINMATCH, repMatch+MINMATCH, iend, repEnd, prefixStart) + MINMATCH;
+                mlen = (U32)ZSTD_count_2segments(inr+MINMATCHOPT, repMatch+MINMATCHOPT, iend, repEnd, prefixStart) + MINMATCHOPT;
                 ZSTD_LOG_PARSER("%d: Found REP mlen=%d off=%d rep=%d opt[%d].off=%d\n", (int)(inr-base), mlen, 0, opt[cur].rep, cur, opt[cur].off);
 
                 if (mlen > sufficient_len || cur + mlen >= ZSTD_OPT_NUM) {
@@ -920,14 +747,14 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
                 if (opt[cur].mlen == 1) {
                     litlen = opt[cur].litlen;
                     if (cur > litlen) {
-                        price = opt[cur - litlen].price + ZSTD_getPrice(seqStorePtr, litlen, inr-litlen, 0, mlen);
+                        price = opt[cur - litlen].price + ZSTD_GETPRICE(seqStorePtr, litlen, inr-litlen, 0, mlen);
                         ZSTD_LOG_TRY_PRICE("%d: TRY5 opt[%d].price=%d price=%d cur=%d litlen=%d\n", (int)(inr-base), cur - litlen, opt[cur - litlen].price, price, cur, litlen);
                     } else
-                        price = ZSTD_getPrice(seqStorePtr, litlen, litstart, 0, mlen);
+                        price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, 0, mlen);
                 } else {
                     litlen = 0;
-                    price = opt[cur].price + ZSTD_getPrice(seqStorePtr, 0, NULL, 0, mlen);
-                    ZSTD_LOG_TRY_PRICE("%d: TRY7 price=%d cur=%d litlen=0 getprice=%d\n", (int)(inr-base), price, cur, (int)ZSTD_getPrice(seqStorePtr, 0, NULL, 0, mlen));
+                    price = opt[cur].price + ZSTD_GETPRICE(seqStorePtr, 0, NULL, 0, mlen);
+                    ZSTD_LOG_TRY_PRICE("%d: TRY7 price=%d cur=%d litlen=0 getprice=%d\n", (int)(inr-base), price, cur, (int)ZSTD_GETPRICE(seqStorePtr, 0, NULL, 0, mlen));
                 }
 
                 best_mlen = mlen;
@@ -938,12 +765,12 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
                     if (cur + mlen > last_pos || price <= opt[cur + mlen].price) // || ((price == opt[cur + mlen].price) && (opt[cur].mlen == 1) && (cur != litlen))) // at equal price prefer REP instead of MATCH
                         SET_PRICE(cur + mlen, mlen, 0, litlen, price);
                     mlen--;
-                } while (mlen >= MINMATCH);
+                } while (mlen >= MINMATCHOPT);
             }
 
-            best_mlen = (best_mlen > MINMATCH) ? best_mlen : MINMATCH;
+            best_mlen = (best_mlen > MINMATCHOPT) ? best_mlen : MINMATCHOPT;
 
-            match_num = ZSTD_BtGetAllMatches_selectMLS_extDict(ctx, inr, ip, iend, maxSearches, mls, matches);
+            match_num = ZSTD_BTGETALLMATCHES_SELECTMLS_EXTDICT(ctx, inr, ip, iend, maxSearches, mls, matches);
             ZSTD_LOG_PARSER("%d: ZSTD_GetAllMatches match_num=%d\n", (int)(inr-base), match_num);
 
             if (match_num > 0 && matches[match_num-1].len > sufficient_len) {
@@ -964,12 +791,12 @@ void ZSTD_compressBlock_opt_extDict_generic(ZSTD_CCtx* ctx,
                     if (opt[cur].mlen == 1) {
                         litlen = opt[cur].litlen;
                         if (cur > litlen)
-                            price = opt[cur - litlen].price + ZSTD_getPrice(seqStorePtr, litlen, ip+cur-litlen, matches[u].off, mlen);
+                            price = opt[cur - litlen].price + ZSTD_GETPRICE(seqStorePtr, litlen, ip+cur-litlen, matches[u].off, mlen);
                         else
-                            price = ZSTD_getPrice(seqStorePtr, litlen, litstart, matches[u].off, mlen);
+                            price = ZSTD_GETPRICE(seqStorePtr, litlen, litstart, matches[u].off, mlen);
                     } else {
                         litlen = 0;
-                        price = opt[cur].price + ZSTD_getPrice(seqStorePtr, 0, NULL, matches[u].off, mlen);
+                        price = opt[cur].price + ZSTD_GETPRICE(seqStorePtr, 0, NULL, matches[u].off, mlen);
                     }
 
                     ZSTD_LOG_PARSER("%d: Found2 mlen=%d best_mlen=%d off=%d price=%d litlen=%d\n", (int)(inr-base), mlen, best_mlen, matches[u].off, price, litlen);
@@ -1040,7 +867,7 @@ _storeSequence: // cur, last_pos, best_mlen, best_off have to be set
                 ml2 = (U32)ZSTD_count(ip, ip-offset, iend);
             else
                 ml2 = (U32)ZSTD_count(ip, ip-rep_1, iend);
-            if (ml2 < mlen && ml2 < MINMATCH) {
+            if (ml2 < mlen && ml2 < MINMATCHOPT) {
                 printf("%d: ERROR iend=%d mlen=%d offset=%d ml2=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset, (int)ml2); exit(0); }
             if (ip < anchor) {
                 printf("%d: ERROR ip < anchor iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
@@ -1048,14 +875,14 @@ _storeSequence: // cur, last_pos, best_mlen, best_off have to be set
                 printf("%d: ERROR ip - offset < base iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
             if ((int)offset >= (1 << ctx->params.windowLog)) {
                 printf("%d: offset >= (1 << params.windowLog) iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
-            if (mlen < MINMATCH) {
-                printf("%d: ERROR mlen < MINMATCH iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
+            if (mlen < MINMATCHOPT) {
+                printf("%d: ERROR mlen < MINMATCHOPT iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
             if (ip + mlen > iend) {
                 printf("%d: ERROR ip + mlen >= iend iend=%d mlen=%d offset=%d\n", (int)(ip - base), (int)(iend - ip), (int)mlen, (int)offset); exit(0); }
 #endif
 
-            ZSTD_updatePrice(seqStorePtr, litLength, anchor, offset, mlen-MINMATCH);
-            ZSTD_storeSeq(seqStorePtr, litLength, anchor, offset, mlen-MINMATCH);
+            ZSTD_updatePrice(seqStorePtr, litLength, anchor, offset, mlen-MINMATCHOPT);
+            ZSTD_storeSeq(seqStorePtr, litLength, anchor, offset, mlen-MINMATCHOPT);
             anchor = ip = ip + mlen;
         }
 
@@ -1068,11 +895,11 @@ _storeSequence: // cur, last_pos, best_mlen, best_off have to be set
                && (MEM_readMINMATCH(anchor) == MEM_readMINMATCH(repMatch)) ) {
                 /* repcode detected, let's take it */
                 const BYTE* const repEnd = repIndex < dictLimit ? dictEnd : iend;
-                mlen = (U32)ZSTD_count_2segments(anchor+MINMATCH, repMatch+MINMATCH, iend, repEnd, prefixStart) + MINMATCH;
+                mlen = (U32)ZSTD_count_2segments(anchor+MINMATCHOPT, repMatch+MINMATCHOPT, iend, repEnd, prefixStart) + MINMATCHOPT;
                 offset = rep_2; rep_2 = rep_1; rep_1 = offset;   /* swap offset history */
                 ZSTD_LOG_ENCODE("%d/%d: ENCODE REP literals=%d mlen=%d off=%d rep1=%d rep2=%d\n", (int)(anchor-base), (int)(iend-base), (int)(0), (int)best_mlen, (int)(0), (int)rep_1, (int)rep_2);
-                ZSTD_updatePrice(seqStorePtr, 0, anchor, 0, mlen-MINMATCH);
-                ZSTD_storeSeq(seqStorePtr, 0, anchor, 0, mlen-MINMATCH);
+                ZSTD_updatePrice(seqStorePtr, 0, anchor, 0, mlen-MINMATCHOPT);
+                ZSTD_storeSeq(seqStorePtr, 0, anchor, 0, mlen-MINMATCHOPT);
                 anchor += mlen;
                 continue;   /* faster when present ... (?) */
             }
diff --git a/lib/zstd_opt_internal.h b/lib/zstd_opt_internal.h
new file mode 100644 (file)
index 0000000..29e936d
--- /dev/null
@@ -0,0 +1,231 @@
+/*
+    zstd_opt_internal - common optimal parser functions to include
+    Header File for include
+    Copyright (C) 2016, Przemyslaw Skibinski, Yann Collet.
+
+    BSD 2-Clause License (http://www.opensource.org/licenses/bsd-license.php)
+
+    Redistribution and use in source and binary forms, with or without
+    modification, are permitted provided that the following conditions are
+    met:
+    * Redistributions of source code must retain the above copyright
+    notice, this list of conditions and the following disclaimer.
+    * Redistributions in binary form must reproduce the above
+    copyright notice, this list of conditions and the following disclaimer
+    in the documentation and/or other materials provided with the
+    distribution.
+    THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+    "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+    LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+    A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+    OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+    SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+    LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+    DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+    THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+    (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+    OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+
+    You can contact the author at :
+    - zstd source repository : https://github.com/Cyan4973/zstd
+*/
+
+/* Note : this file is intended to be included within zstd_compress.c */
+
+#ifndef ZSTD_OPT_INTERNAL_H_MODULE
+#define ZSTD_OPT_INTERNAL_H_MODULE
+
+
+/*-*******************************************
+*  The optimal parser
+*********************************************/
+/*-  Constants  -*/
+#define ZSTD_OPT_NUM    (1<<12)
+#define ZSTD_FREQ_START 1
+#define ZSTD_FREQ_STEP  1
+#define ZSTD_FREQ_DIV   6
+
+/*-  Debug  -*/
+#if defined(ZSTD_OPT_DEBUG) && ZSTD_OPT_DEBUG>=9
+    #define ZSTD_LOG_PARSER(...) printf(__VA_ARGS__)
+    #define ZSTD_LOG_ENCODE(...) printf(__VA_ARGS__)
+    #define ZSTD_LOG_TRY_PRICE(...) printf(__VA_ARGS__)
+#else
+    #define ZSTD_LOG_PARSER(...)
+    #define ZSTD_LOG_ENCODE(...)
+    #define ZSTD_LOG_TRY_PRICE(...)
+#endif
+
+
+typedef struct {
+    U32 off;
+    U32 len;
+} ZSTD_match_t;
+
+typedef struct {
+    U32 price;
+    U32 off;
+    U32 mlen;
+    U32 litlen;
+    U32 rep;
+    U32 rep2;
+} ZSTD_optimal_t;
+
+
+MEM_STATIC void ZSTD_rescaleFreqs(seqStore_t* ssPtr)
+{
+    unsigned u;
+    
+ //   printf("matchLengthSum=%d litLengthSum=%d litSum=%d offCodeSum=%d\n", ssPtr->matchLengthSum, ssPtr->litLengthSum, ssPtr->litSum, ssPtr->offCodeSum);
+    
+    if (ssPtr->litLengthSum == 0) {
+        ssPtr->matchLengthSum = (1<<MLbits);
+        ssPtr->litLengthSum = (1<<LLbits);
+        ssPtr->litSum = (1<<Litbits);
+        ssPtr->offCodeSum = (1<<Offbits);
+
+        for (u=0; u<=MaxLit; u++)
+            ssPtr->litFreq[u] = 1;
+        for (u=0; u<=MaxLL; u++)
+            ssPtr->litLengthFreq[u] = 1;
+        for (u=0; u<=MaxML; u++)
+            ssPtr->matchLengthFreq[u] = 1;
+        for (u=0; u<=MaxOff; u++)
+            ssPtr->offCodeFreq[u] = 1;
+    } else {
+        ssPtr->matchLengthSum = 0;
+        ssPtr->litLengthSum = 0;
+        ssPtr->litSum = 0;
+        ssPtr->offCodeSum = 0;
+
+        for (u=0; u<=MaxLit; u++) {
+            ssPtr->litFreq[u] = ZSTD_FREQ_START + (ssPtr->litFreq[u]>>ZSTD_FREQ_DIV);
+            ssPtr->litSum += ssPtr->litFreq[u];
+        }
+        for (u=0; u<=MaxLL; u++) {
+            ssPtr->litLengthFreq[u] = ZSTD_FREQ_START + (ssPtr->litLengthFreq[u]>>ZSTD_FREQ_DIV);
+            ssPtr->litLengthSum += ssPtr->litLengthFreq[u];
+        }
+        for (u=0; u<=MaxML; u++) {
+            ssPtr->matchLengthFreq[u] = ZSTD_FREQ_START + (ssPtr->matchLengthFreq[u]>>ZSTD_FREQ_DIV);
+            ssPtr->matchLengthSum += ssPtr->matchLengthFreq[u];
+        }
+        for (u=0; u<=MaxOff; u++) {
+            ssPtr->offCodeFreq[u] = ZSTD_FREQ_START + (ssPtr->offCodeFreq[u]>>ZSTD_FREQ_DIV);
+            ssPtr->offCodeSum += ssPtr->offCodeFreq[u];
+        }
+    }
+}
+
+MEM_STATIC void ZSTD_updatePrice(seqStore_t* seqStorePtr, U32 litLength, const BYTE* literals, U32 offset, U32 matchLength)
+{
+    U32 u;
+
+    /* literals */
+    seqStorePtr->litSum += litLength * ZSTD_FREQ_STEP;
+    for (u=0; u < litLength; u++)
+        seqStorePtr->litFreq[literals[u]] += ZSTD_FREQ_STEP;
+
+    /* literal Length */
+    seqStorePtr->litLengthSum += ZSTD_FREQ_STEP;
+    if (litLength >= MaxLL)
+        seqStorePtr->litLengthFreq[MaxLL] += ZSTD_FREQ_STEP;
+    else
+        seqStorePtr->litLengthFreq[litLength] += ZSTD_FREQ_STEP;
+
+    /* match offset */
+    seqStorePtr->offCodeSum += ZSTD_FREQ_STEP;
+    BYTE offCode = offset ? (BYTE)ZSTD_highbit(offset) + 1 : 0;
+    seqStorePtr->offCodeFreq[offCode] += ZSTD_FREQ_STEP;
+
+    /* match Length */
+    seqStorePtr->matchLengthSum += ZSTD_FREQ_STEP;
+    if (matchLength >= MaxML)
+        seqStorePtr->matchLengthFreq[MaxML] += ZSTD_FREQ_STEP;
+    else
+        seqStorePtr->matchLengthFreq[matchLength] += ZSTD_FREQ_STEP;
+}
+
+FORCE_INLINE U32 ZSTD_getLiteralPrice(seqStore_t* seqStorePtr, U32 litLength, const BYTE* literals)
+{
+    U32 price, u;
+
+    /* literals */
+    price = litLength * ZSTD_highbit(seqStorePtr->litSum);
+    for (u=0; u < litLength; u++)
+        price -= ZSTD_highbit(seqStorePtr->litFreq[literals[u]]);
+
+    /* literal Length */
+    price += ((litLength >= MaxLL)<<3) + ((litLength >= 255+MaxLL)<<4) + ((litLength>=(1<<15))<<3);
+    if (litLength >= MaxLL) litLength = MaxLL;
+    price += ZSTD_highbit(seqStorePtr->litLengthSum) - ZSTD_highbit(seqStorePtr->litLengthFreq[litLength]);
+
+    return price;
+}
+
+#define SET_PRICE(pos, mlen_, offset_, litlen_, price_)   \
+    {                                                 \
+        while (last_pos < pos)  { opt[last_pos+1].price = 1<<30; last_pos++; } \
+        opt[pos].mlen = mlen_;                         \
+        opt[pos].off = offset_;                        \
+        opt[pos].litlen = litlen_;                     \
+        opt[pos].price = price_;                       \
+        ZSTD_LOG_PARSER("%d: SET price[%d/%d]=%d litlen=%d len=%d off=%d\n", (int)(inr-base), (int)pos, (int)last_pos, opt[pos].price, opt[pos].litlen, opt[pos].mlen, opt[pos].off); \
+    }
+
+/* Update hashTable3 up to ip (excluded)
+   Assumption : always within prefix (ie. not within extDict) */
+static U32 ZSTD_insertAndFindFirstIndexHash3 (ZSTD_CCtx* zc, const BYTE* ip)
+{
+    U32* const hashTable3  = zc->hashTable3;
+    const U32 hashLog3 = zc->params.hashLog3;
+    const BYTE* const base = zc->base;
+    const U32 target = (U32)(ip - base);
+    U32 idx = zc->nextToUpdate3;
+
+    while(idx < target) {
+        hashTable3[ZSTD_hash3Ptr(base+idx, hashLog3)] = idx;
+        idx++;
+    }
+
+    zc->nextToUpdate3 = target;
+    return hashTable3[ZSTD_hash3Ptr(ip, hashLog3)];
+}
+
+
+#define MINMATCHOPT 4
+#define MEM_readMINMATCH(ptr) (U32)(MEM_read32(ptr)) 
+#define ZSTD_GETPRICE ZSTD_getPrice4
+#define ZSTD_INSERTBTANDGETALLMATCHES ZSTD_insertBtAndGetAllMatches4
+#define ZSTD_BTGETALLMATCHES ZSTD_BtGetAllMatches4
+#define ZSTD_BTGETALLMATCHES_SELECTMLS ZSTD_BtGetAllMatches_selectMLS4
+#define ZSTD_BTGETALLMATCHES_EXTDICT ZSTD_BtGetAllMatches_extDict4
+#define ZSTD_BTGETALLMATCHES_SELECTMLS_EXTDICT ZSTD_BtGetAllMatches_selectMLS_extDict4
+#define ZSTD_COMPRESSBLOCK_OPT_GENERIC ZSTD_compressBlock_opt_generic4
+#define ZSTD_COMPRESSBLOCK_OPT_EXTDICT_GENERIC ZSTD_compressBlock_opt_extDict_generic4
+#include "zstd_opt.h"
+#undef MINMATCHOPT
+#undef MEM_readMINMATCH
+#undef ZSTD_GETPRICE
+#undef ZSTD_INSERTBTANDGETALLMATCHES
+#undef ZSTD_BTGETALLMATCHES
+#undef ZSTD_BTGETALLMATCHES_SELECTMLS
+#undef ZSTD_BTGETALLMATCHES_EXTDICT
+#undef ZSTD_BTGETALLMATCHES_SELECTMLS_EXTDICT
+#undef ZSTD_COMPRESSBLOCK_OPT_GENERIC
+#undef ZSTD_COMPRESSBLOCK_OPT_EXTDICT_GENERIC
+
+#define MINMATCHOPT 3
+#define MEM_readMINMATCH(ptr) ((U32)(MEM_read32(ptr)<<8)) 
+#define ZSTD_GETPRICE ZSTD_getPrice3
+#define ZSTD_INSERTBTANDGETALLMATCHES ZSTD_insertBtAndGetAllMatches3
+#define ZSTD_BTGETALLMATCHES ZSTD_BtGetAllMatches3
+#define ZSTD_BTGETALLMATCHES_SELECTMLS ZSTD_BtGetAllMatches_selectMLS3
+#define ZSTD_BTGETALLMATCHES_EXTDICT ZSTD_BtGetAllMatches_extDict3
+#define ZSTD_BTGETALLMATCHES_SELECTMLS_EXTDICT ZSTD_BtGetAllMatches_selectMLS_extDict3
+#define ZSTD_COMPRESSBLOCK_OPT_GENERIC ZSTD_compressBlock_opt_generic3
+#define ZSTD_COMPRESSBLOCK_OPT_EXTDICT_GENERIC ZSTD_compressBlock_opt_extDict_generic3
+#include "zstd_opt.h"
+
+
+#endif   /* ZSTD_OPT_INTERNAL_H_MODULE */
index 692b147d16fc6dde5dec9e03dfa20592d4d27038..0e280ceff6aeedbf1cdf69513bc069e9354cf9ff 100644 (file)
@@ -69,7 +69,7 @@ extern "C" {
 #define ZSTD_SEARCHLOG_MAX (ZSTD_CONTENTLOG_MAX-1)
 #define ZSTD_SEARCHLOG_MIN 1
 #define ZSTD_SEARCHLENGTH_MAX 7
-#define ZSTD_SEARCHLENGTH_MIN 4
+#define ZSTD_SEARCHLENGTH_MIN 3
 #define ZSTD_TARGETLENGTH_MIN 4
 #define ZSTD_TARGETLENGTH_MAX 999