xref: /src/sys/contrib/zstd/programs/benchzstd.c (revision 5ff13fbc199bdf5f0572845351c68ee5ca828e71)
1902c8ce7SBaptiste Daroussin /*
2b3392d84SAllan Jude  * Copyright (c) Yann Collet, Facebook, Inc.
3a19eddc3SBaptiste Daroussin  * All rights reserved.
4a19eddc3SBaptiste Daroussin  *
5902c8ce7SBaptiste Daroussin  * This source code is licensed under both the BSD-style license (found in the
6902c8ce7SBaptiste Daroussin  * LICENSE file in the root directory of this source tree) and the GPLv2 (found
7902c8ce7SBaptiste Daroussin  * in the COPYING file in the root directory of this source tree).
8653667f9SBaptiste Daroussin  * You may select, at your option, one of the above-listed licenses.
9a19eddc3SBaptiste Daroussin  */
10a19eddc3SBaptiste Daroussin 
11a19eddc3SBaptiste Daroussin 
12a19eddc3SBaptiste Daroussin /* **************************************
13a19eddc3SBaptiste Daroussin *  Tuning parameters
14a19eddc3SBaptiste Daroussin ****************************************/
15a19eddc3SBaptiste Daroussin #ifndef BMK_TIMETEST_DEFAULT_S   /* default minimum time per test */
16a19eddc3SBaptiste Daroussin #define BMK_TIMETEST_DEFAULT_S 3
17a19eddc3SBaptiste Daroussin #endif
18a19eddc3SBaptiste Daroussin 
19a19eddc3SBaptiste Daroussin 
20a19eddc3SBaptiste Daroussin /* *************************************
21a19eddc3SBaptiste Daroussin *  Includes
22a19eddc3SBaptiste Daroussin ***************************************/
23a19eddc3SBaptiste Daroussin #include "platform.h"    /* Large Files support */
24a19eddc3SBaptiste Daroussin #include "util.h"        /* UTIL_getFileSize, UTIL_sleep */
25a19eddc3SBaptiste Daroussin #include <stdlib.h>      /* malloc, free */
26af73257bSConrad Meyer #include <string.h>      /* memset, strerror */
27a19eddc3SBaptiste Daroussin #include <stdio.h>       /* fprintf, fopen */
28af73257bSConrad Meyer #include <errno.h>
2942239e68SConrad Meyer #include <assert.h>      /* assert */
30a19eddc3SBaptiste Daroussin 
313f774a5eSConrad Meyer #include "timefn.h"      /* UTIL_time_t */
32af73257bSConrad Meyer #include "benchfn.h"
33bc64b5ceSConrad Meyer #include "../lib/common/mem.h"
34b3392d84SAllan Jude #ifndef ZSTD_STATIC_LINKING_ONLY
35a19eddc3SBaptiste Daroussin #define ZSTD_STATIC_LINKING_ONLY
36b3392d84SAllan Jude #endif
37bc64b5ceSConrad Meyer #include "../lib/zstd.h"
38a19eddc3SBaptiste Daroussin #include "datagen.h"     /* RDG_genBuffer */
39b3392d84SAllan Jude #ifndef XXH_INLINE_ALL
40b3392d84SAllan Jude #define XXH_INLINE_ALL
41b3392d84SAllan Jude #endif
42bc64b5ceSConrad Meyer #include "../lib/common/xxhash.h"
43af73257bSConrad Meyer #include "benchzstd.h"
44b3392d84SAllan Jude #include "../lib/zstd_errors.h"
45a19eddc3SBaptiste Daroussin 
46a19eddc3SBaptiste Daroussin 
47a19eddc3SBaptiste Daroussin /* *************************************
48a19eddc3SBaptiste Daroussin *  Constants
49a19eddc3SBaptiste Daroussin ***************************************/
50a19eddc3SBaptiste Daroussin #ifndef ZSTD_GIT_COMMIT
51a19eddc3SBaptiste Daroussin #  define ZSTD_GIT_COMMIT_STRING ""
52a19eddc3SBaptiste Daroussin #else
53a19eddc3SBaptiste Daroussin #  define ZSTD_GIT_COMMIT_STRING ZSTD_EXPAND_AND_QUOTE(ZSTD_GIT_COMMIT)
54a19eddc3SBaptiste Daroussin #endif
55a19eddc3SBaptiste Daroussin 
5642239e68SConrad Meyer #define TIMELOOP_MICROSEC     (1*1000000ULL) /* 1 second */
5742239e68SConrad Meyer #define TIMELOOP_NANOSEC      (1*1000000000ULL) /* 1 second */
5842239e68SConrad Meyer #define ACTIVEPERIOD_MICROSEC (70*TIMELOOP_MICROSEC) /* 70 seconds */
59a19eddc3SBaptiste Daroussin #define COOLPERIOD_SEC        10
60a19eddc3SBaptiste Daroussin 
61a19eddc3SBaptiste Daroussin #define KB *(1 <<10)
62a19eddc3SBaptiste Daroussin #define MB *(1 <<20)
63a19eddc3SBaptiste Daroussin #define GB *(1U<<30)
64a19eddc3SBaptiste Daroussin 
65706cfae4SConrad Meyer #define BMK_RUNTEST_DEFAULT_MS 1000
66a19eddc3SBaptiste Daroussin 
67706cfae4SConrad Meyer static const size_t maxMemory = (sizeof(size_t)==4)  ?
68706cfae4SConrad Meyer                     /* 32-bit */ (2 GB - 64 MB) :
69706cfae4SConrad Meyer                     /* 64-bit */ (size_t)(1ULL << ((sizeof(size_t)*8)-31));
70a19eddc3SBaptiste Daroussin 
71a19eddc3SBaptiste Daroussin 
72a19eddc3SBaptiste Daroussin /* *************************************
73a19eddc3SBaptiste Daroussin *  console display
74a19eddc3SBaptiste Daroussin ***************************************/
75b3392d84SAllan Jude #define DISPLAY(...)         { fprintf(stderr, __VA_ARGS__); fflush(NULL); }
76706cfae4SConrad Meyer #define DISPLAYLEVEL(l, ...) if (displayLevel>=l) { DISPLAY(__VA_ARGS__); }
77706cfae4SConrad Meyer /* 0 : no display;   1: errors;   2 : + result + interaction + warnings;   3 : + progression;   4 : + information */
78b3392d84SAllan Jude #define OUTPUT(...)          { fprintf(stdout, __VA_ARGS__); fflush(NULL); }
79b3392d84SAllan Jude #define OUTPUTLEVEL(l, ...)  if (displayLevel>=l) { OUTPUT(__VA_ARGS__); }
80a19eddc3SBaptiste Daroussin 
81a19eddc3SBaptiste Daroussin 
82a19eddc3SBaptiste Daroussin /* *************************************
83a19eddc3SBaptiste Daroussin *  Exceptions
84a19eddc3SBaptiste Daroussin ***************************************/
85a19eddc3SBaptiste Daroussin #ifndef DEBUG
86a19eddc3SBaptiste Daroussin #  define DEBUG 0
87a19eddc3SBaptiste Daroussin #endif
88affe9eafSBaptiste Daroussin #define DEBUGOUTPUT(...) { if (DEBUG) DISPLAY(__VA_ARGS__); }
89706cfae4SConrad Meyer 
90ea684039SConrad Meyer #define RETURN_ERROR_INT(errorNum, ...)  {               \
91ffcbc2d7SBaptiste Daroussin     DEBUGOUTPUT("%s: %i: \n", __FILE__, __LINE__);    \
92706cfae4SConrad Meyer     DISPLAYLEVEL(1, "Error %i : ", errorNum);         \
93a19eddc3SBaptiste Daroussin     DISPLAYLEVEL(1, __VA_ARGS__);                     \
94a19eddc3SBaptiste Daroussin     DISPLAYLEVEL(1, " \n");                           \
95706cfae4SConrad Meyer     return errorNum;                                  \
96a19eddc3SBaptiste Daroussin }
97a19eddc3SBaptiste Daroussin 
98af73257bSConrad Meyer #define CHECK_Z(zf) {              \
99af73257bSConrad Meyer     size_t const zerr = zf;        \
100af73257bSConrad Meyer     if (ZSTD_isError(zerr)) {      \
101af73257bSConrad Meyer         DEBUGOUTPUT("%s: %i: \n", __FILE__, __LINE__);  \
102af73257bSConrad Meyer         DISPLAY("Error : ");       \
103af73257bSConrad Meyer         DISPLAY("%s failed : %s",  \
104af73257bSConrad Meyer                 #zf, ZSTD_getErrorName(zerr));   \
105af73257bSConrad Meyer         DISPLAY(" \n");            \
106af73257bSConrad Meyer         exit(1);                   \
107af73257bSConrad Meyer     }                              \
108af73257bSConrad Meyer }
109af73257bSConrad Meyer 
110706cfae4SConrad Meyer #define RETURN_ERROR(errorNum, retType, ...)  {       \
111706cfae4SConrad Meyer     retType r;                                        \
112706cfae4SConrad Meyer     memset(&r, 0, sizeof(retType));                   \
113706cfae4SConrad Meyer     DEBUGOUTPUT("%s: %i: \n", __FILE__, __LINE__);    \
114706cfae4SConrad Meyer     DISPLAYLEVEL(1, "Error %i : ", errorNum);         \
115706cfae4SConrad Meyer     DISPLAYLEVEL(1, __VA_ARGS__);                     \
116706cfae4SConrad Meyer     DISPLAYLEVEL(1, " \n");                           \
117706cfae4SConrad Meyer     r.tag = errorNum;                                 \
118706cfae4SConrad Meyer     return r;                                         \
119706cfae4SConrad Meyer }
120706cfae4SConrad Meyer 
121a19eddc3SBaptiste Daroussin 
122a19eddc3SBaptiste Daroussin /* *************************************
123a19eddc3SBaptiste Daroussin *  Benchmark Parameters
124a19eddc3SBaptiste Daroussin ***************************************/
125a19eddc3SBaptiste Daroussin 
BMK_initAdvancedParams(void)126706cfae4SConrad Meyer BMK_advancedParams_t BMK_initAdvancedParams(void) {
127706cfae4SConrad Meyer     BMK_advancedParams_t const res = {
128706cfae4SConrad Meyer         BMK_both, /* mode */
129706cfae4SConrad Meyer         BMK_TIMETEST_DEFAULT_S, /* nbSeconds */
130706cfae4SConrad Meyer         0, /* blockSize */
131706cfae4SConrad Meyer         0, /* nbWorkers */
132706cfae4SConrad Meyer         0, /* realTime */
133706cfae4SConrad Meyer         0, /* additionalParam */
134706cfae4SConrad Meyer         0, /* ldmFlag */
135706cfae4SConrad Meyer         0, /* ldmMinMatch */
136706cfae4SConrad Meyer         0, /* ldmHashLog */
137706cfae4SConrad Meyer         0, /* ldmBuckSizeLog */
1383f774a5eSConrad Meyer         0,  /* ldmHashRateLog */
139b3392d84SAllan Jude         ZSTD_ps_auto, /* literalCompressionMode */
140b3392d84SAllan Jude         0 /* useRowMatchFinder */
141706cfae4SConrad Meyer     };
142706cfae4SConrad Meyer     return res;
143653667f9SBaptiste Daroussin }
144a19eddc3SBaptiste Daroussin 
145a19eddc3SBaptiste Daroussin 
146a19eddc3SBaptiste Daroussin /* ********************************************************
147a19eddc3SBaptiste Daroussin *  Bench functions
148a19eddc3SBaptiste Daroussin **********************************************************/
149a19eddc3SBaptiste Daroussin typedef struct {
150a19eddc3SBaptiste Daroussin     const void* srcPtr;
151a19eddc3SBaptiste Daroussin     size_t srcSize;
152a19eddc3SBaptiste Daroussin     void*  cPtr;
153a19eddc3SBaptiste Daroussin     size_t cRoom;
154a19eddc3SBaptiste Daroussin     size_t cSize;
155a19eddc3SBaptiste Daroussin     void*  resPtr;
156a19eddc3SBaptiste Daroussin     size_t resSize;
157a19eddc3SBaptiste Daroussin } blockParam_t;
158a19eddc3SBaptiste Daroussin 
159ffcbc2d7SBaptiste Daroussin #undef MIN
160ffcbc2d7SBaptiste Daroussin #undef MAX
161a19eddc3SBaptiste Daroussin #define MIN(a,b)    ((a) < (b) ? (a) : (b))
162a19eddc3SBaptiste Daroussin #define MAX(a,b)    ((a) > (b) ? (a) : (b))
163a19eddc3SBaptiste Daroussin 
1643f774a5eSConrad Meyer static void
BMK_initCCtx(ZSTD_CCtx * ctx,const void * dictBuffer,size_t dictBufferSize,int cLevel,const ZSTD_compressionParameters * comprParams,const BMK_advancedParams_t * adv)1653f774a5eSConrad Meyer BMK_initCCtx(ZSTD_CCtx* ctx,
1663f774a5eSConrad Meyer             const void* dictBuffer, size_t dictBufferSize,
1673f774a5eSConrad Meyer             int cLevel,
1683f774a5eSConrad Meyer             const ZSTD_compressionParameters* comprParams,
1693f774a5eSConrad Meyer             const BMK_advancedParams_t* adv)
1703f774a5eSConrad Meyer {
171af73257bSConrad Meyer     ZSTD_CCtx_reset(ctx, ZSTD_reset_session_and_parameters);
172706cfae4SConrad Meyer     if (adv->nbWorkers==1) {
173af73257bSConrad Meyer         CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_nbWorkers, 0));
17442239e68SConrad Meyer     } else {
175af73257bSConrad Meyer         CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_nbWorkers, adv->nbWorkers));
17642239e68SConrad Meyer     }
177af73257bSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_compressionLevel, cLevel));
178b3392d84SAllan Jude     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_useRowMatchFinder, adv->useRowMatchFinder));
179af73257bSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_enableLongDistanceMatching, adv->ldmFlag));
180af73257bSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_ldmMinMatch, adv->ldmMinMatch));
181af73257bSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_ldmHashLog, adv->ldmHashLog));
182af73257bSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_ldmBucketSizeLog, adv->ldmBucketSizeLog));
183af73257bSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_ldmHashRateLog, adv->ldmHashRateLog));
1843f774a5eSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_windowLog, (int)comprParams->windowLog));
1853f774a5eSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_hashLog, (int)comprParams->hashLog));
1863f774a5eSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_chainLog, (int)comprParams->chainLog));
1873f774a5eSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_searchLog, (int)comprParams->searchLog));
1883f774a5eSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_minMatch, (int)comprParams->minMatch));
1893f774a5eSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_targetLength, (int)comprParams->targetLength));
1903f774a5eSConrad Meyer     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_literalCompressionMode, (int)adv->literalCompressionMode));
191b3392d84SAllan Jude     CHECK_Z(ZSTD_CCtx_setParameter(ctx, ZSTD_c_strategy, (int)comprParams->strategy));
192af73257bSConrad Meyer     CHECK_Z(ZSTD_CCtx_loadDictionary(ctx, dictBuffer, dictBufferSize));
193706cfae4SConrad Meyer }
19442239e68SConrad Meyer 
BMK_initDCtx(ZSTD_DCtx * dctx,const void * dictBuffer,size_t dictBufferSize)195706cfae4SConrad Meyer static void BMK_initDCtx(ZSTD_DCtx* dctx,
196706cfae4SConrad Meyer     const void* dictBuffer, size_t dictBufferSize) {
197af73257bSConrad Meyer     CHECK_Z(ZSTD_DCtx_reset(dctx, ZSTD_reset_session_and_parameters));
198af73257bSConrad Meyer     CHECK_Z(ZSTD_DCtx_loadDictionary(dctx, dictBuffer, dictBufferSize));
199706cfae4SConrad Meyer }
200706cfae4SConrad Meyer 
201706cfae4SConrad Meyer 
202706cfae4SConrad Meyer typedef struct {
203706cfae4SConrad Meyer     ZSTD_CCtx* cctx;
204706cfae4SConrad Meyer     const void* dictBuffer;
205706cfae4SConrad Meyer     size_t dictBufferSize;
206706cfae4SConrad Meyer     int cLevel;
207706cfae4SConrad Meyer     const ZSTD_compressionParameters* comprParams;
208706cfae4SConrad Meyer     const BMK_advancedParams_t* adv;
209706cfae4SConrad Meyer } BMK_initCCtxArgs;
210706cfae4SConrad Meyer 
local_initCCtx(void * payload)211706cfae4SConrad Meyer static size_t local_initCCtx(void* payload) {
212706cfae4SConrad Meyer     BMK_initCCtxArgs* ag = (BMK_initCCtxArgs*)payload;
213706cfae4SConrad Meyer     BMK_initCCtx(ag->cctx, ag->dictBuffer, ag->dictBufferSize, ag->cLevel, ag->comprParams, ag->adv);
214706cfae4SConrad Meyer     return 0;
215706cfae4SConrad Meyer }
216706cfae4SConrad Meyer 
217706cfae4SConrad Meyer typedef struct {
218706cfae4SConrad Meyer     ZSTD_DCtx* dctx;
219706cfae4SConrad Meyer     const void* dictBuffer;
220706cfae4SConrad Meyer     size_t dictBufferSize;
221706cfae4SConrad Meyer } BMK_initDCtxArgs;
222706cfae4SConrad Meyer 
local_initDCtx(void * payload)223706cfae4SConrad Meyer static size_t local_initDCtx(void* payload) {
224706cfae4SConrad Meyer     BMK_initDCtxArgs* ag = (BMK_initDCtxArgs*)payload;
225706cfae4SConrad Meyer     BMK_initDCtx(ag->dctx, ag->dictBuffer, ag->dictBufferSize);
226706cfae4SConrad Meyer     return 0;
227706cfae4SConrad Meyer }
228706cfae4SConrad Meyer 
229706cfae4SConrad Meyer 
230706cfae4SConrad Meyer /* `addArgs` is the context */
local_defaultCompress(const void * srcBuffer,size_t srcSize,void * dstBuffer,size_t dstSize,void * addArgs)231706cfae4SConrad Meyer static size_t local_defaultCompress(
232706cfae4SConrad Meyer                     const void* srcBuffer, size_t srcSize,
233706cfae4SConrad Meyer                     void* dstBuffer, size_t dstSize,
234706cfae4SConrad Meyer                     void* addArgs)
235706cfae4SConrad Meyer {
236706cfae4SConrad Meyer     ZSTD_CCtx* const cctx = (ZSTD_CCtx*)addArgs;
237af73257bSConrad Meyer     return ZSTD_compress2(cctx, dstBuffer, dstSize, srcBuffer, srcSize);
238706cfae4SConrad Meyer }
239a19eddc3SBaptiste Daroussin 
240706cfae4SConrad Meyer /* `addArgs` is the context */
local_defaultDecompress(const void * srcBuffer,size_t srcSize,void * dstBuffer,size_t dstCapacity,void * addArgs)241706cfae4SConrad Meyer static size_t local_defaultDecompress(
242706cfae4SConrad Meyer                     const void* srcBuffer, size_t srcSize,
243706cfae4SConrad Meyer                     void* dstBuffer, size_t dstCapacity,
244706cfae4SConrad Meyer                     void* addArgs)
245706cfae4SConrad Meyer {
246706cfae4SConrad Meyer     size_t moreToFlush = 1;
247706cfae4SConrad Meyer     ZSTD_DCtx* const dctx = (ZSTD_DCtx*)addArgs;
248706cfae4SConrad Meyer     ZSTD_inBuffer in;
249706cfae4SConrad Meyer     ZSTD_outBuffer out;
250706cfae4SConrad Meyer     in.src = srcBuffer; in.size = srcSize; in.pos = 0;
251706cfae4SConrad Meyer     out.dst = dstBuffer; out.size = dstCapacity; out.pos = 0;
252706cfae4SConrad Meyer     while (moreToFlush) {
253706cfae4SConrad Meyer         if(out.pos == out.size) {
254706cfae4SConrad Meyer             return (size_t)-ZSTD_error_dstSize_tooSmall;
255706cfae4SConrad Meyer         }
256af73257bSConrad Meyer         moreToFlush = ZSTD_decompressStream(dctx, &out, &in);
257706cfae4SConrad Meyer         if (ZSTD_isError(moreToFlush)) {
258706cfae4SConrad Meyer             return moreToFlush;
259706cfae4SConrad Meyer         }
260706cfae4SConrad Meyer     }
261706cfae4SConrad Meyer     return out.pos;
262a19eddc3SBaptiste Daroussin 
263706cfae4SConrad Meyer }
264706cfae4SConrad Meyer 
265706cfae4SConrad Meyer 
266706cfae4SConrad Meyer /* ================================================================= */
267706cfae4SConrad Meyer /*      Benchmark Zstandard, mem-to-mem scenarios                    */
268706cfae4SConrad Meyer /* ================================================================= */
269706cfae4SConrad Meyer 
BMK_isSuccessful_benchOutcome(BMK_benchOutcome_t outcome)270706cfae4SConrad Meyer int BMK_isSuccessful_benchOutcome(BMK_benchOutcome_t outcome)
271706cfae4SConrad Meyer {
272706cfae4SConrad Meyer     return outcome.tag == 0;
273706cfae4SConrad Meyer }
274706cfae4SConrad Meyer 
BMK_extract_benchResult(BMK_benchOutcome_t outcome)275706cfae4SConrad Meyer BMK_benchResult_t BMK_extract_benchResult(BMK_benchOutcome_t outcome)
276706cfae4SConrad Meyer {
277706cfae4SConrad Meyer     assert(outcome.tag == 0);
278706cfae4SConrad Meyer     return outcome.internal_never_use_directly;
279706cfae4SConrad Meyer }
280706cfae4SConrad Meyer 
BMK_benchOutcome_error(void)281706cfae4SConrad Meyer static BMK_benchOutcome_t BMK_benchOutcome_error(void)
282706cfae4SConrad Meyer {
283706cfae4SConrad Meyer     BMK_benchOutcome_t b;
284706cfae4SConrad Meyer     memset(&b, 0, sizeof(b));
285706cfae4SConrad Meyer     b.tag = 1;
286706cfae4SConrad Meyer     return b;
287706cfae4SConrad Meyer }
288706cfae4SConrad Meyer 
BMK_benchOutcome_setValidResult(BMK_benchResult_t result)289706cfae4SConrad Meyer static BMK_benchOutcome_t BMK_benchOutcome_setValidResult(BMK_benchResult_t result)
290706cfae4SConrad Meyer {
291706cfae4SConrad Meyer     BMK_benchOutcome_t b;
292706cfae4SConrad Meyer     b.tag = 0;
293706cfae4SConrad Meyer     b.internal_never_use_directly = result;
294706cfae4SConrad Meyer     return b;
295706cfae4SConrad Meyer }
296706cfae4SConrad Meyer 
297706cfae4SConrad Meyer 
298706cfae4SConrad Meyer /* benchMem with no allocation */
299af73257bSConrad Meyer static BMK_benchOutcome_t
BMK_benchMemAdvancedNoAlloc(const void ** srcPtrs,size_t * srcSizes,void ** cPtrs,size_t * cCapacities,size_t * cSizes,void ** resPtrs,size_t * resSizes,void ** resultBufferPtr,void * compressedBuffer,size_t maxCompressedSize,BMK_timedFnState_t * timeStateCompress,BMK_timedFnState_t * timeStateDecompress,const void * srcBuffer,size_t srcSize,const size_t * fileSizes,unsigned nbFiles,const int cLevel,const ZSTD_compressionParameters * comprParams,const void * dictBuffer,size_t dictBufferSize,ZSTD_CCtx * cctx,ZSTD_DCtx * dctx,int displayLevel,const char * displayName,const BMK_advancedParams_t * adv)300af73257bSConrad Meyer BMK_benchMemAdvancedNoAlloc(
301706cfae4SConrad Meyer                     const void** srcPtrs, size_t* srcSizes,
302706cfae4SConrad Meyer                     void** cPtrs, size_t* cCapacities, size_t* cSizes,
303706cfae4SConrad Meyer                     void** resPtrs, size_t* resSizes,
304706cfae4SConrad Meyer                     void** resultBufferPtr, void* compressedBuffer,
305706cfae4SConrad Meyer                     size_t maxCompressedSize,
306706cfae4SConrad Meyer                     BMK_timedFnState_t* timeStateCompress,
307706cfae4SConrad Meyer                     BMK_timedFnState_t* timeStateDecompress,
308706cfae4SConrad Meyer 
309706cfae4SConrad Meyer                     const void* srcBuffer, size_t srcSize,
310706cfae4SConrad Meyer                     const size_t* fileSizes, unsigned nbFiles,
311af73257bSConrad Meyer                     const int cLevel,
312af73257bSConrad Meyer                     const ZSTD_compressionParameters* comprParams,
313706cfae4SConrad Meyer                     const void* dictBuffer, size_t dictBufferSize,
314706cfae4SConrad Meyer                     ZSTD_CCtx* cctx, ZSTD_DCtx* dctx,
315706cfae4SConrad Meyer                     int displayLevel, const char* displayName,
316706cfae4SConrad Meyer                     const BMK_advancedParams_t* adv)
317706cfae4SConrad Meyer {
318706cfae4SConrad Meyer     size_t const blockSize = ((adv->blockSize>=32 && (adv->mode != BMK_decodeOnly)) ? adv->blockSize : srcSize) + (!srcSize);  /* avoid div by 0 */
319706cfae4SConrad Meyer     BMK_benchResult_t benchResult;
320706cfae4SConrad Meyer     size_t const loadedCompressedSize = srcSize;
321706cfae4SConrad Meyer     size_t cSize = 0;
322706cfae4SConrad Meyer     double ratio = 0.;
323706cfae4SConrad Meyer     U32 nbBlocks;
324706cfae4SConrad Meyer 
325706cfae4SConrad Meyer     assert(cctx != NULL); assert(dctx != NULL);
326706cfae4SConrad Meyer 
327706cfae4SConrad Meyer     /* init */
328706cfae4SConrad Meyer     memset(&benchResult, 0, sizeof(benchResult));
329706cfae4SConrad Meyer     if (strlen(displayName)>17) displayName += strlen(displayName) - 17;   /* display last 17 characters */
330706cfae4SConrad Meyer     if (adv->mode == BMK_decodeOnly) {  /* benchmark only decompression : source must be already compressed */
331706cfae4SConrad Meyer         const char* srcPtr = (const char*)srcBuffer;
332706cfae4SConrad Meyer         U64 totalDSize64 = 0;
333706cfae4SConrad Meyer         U32 fileNb;
334706cfae4SConrad Meyer         for (fileNb=0; fileNb<nbFiles; fileNb++) {
335706cfae4SConrad Meyer             U64 const fSize64 = ZSTD_findDecompressedSize(srcPtr, fileSizes[fileNb]);
336706cfae4SConrad Meyer             if (fSize64==0) RETURN_ERROR(32, BMK_benchOutcome_t, "Impossible to determine original size ");
337706cfae4SConrad Meyer             totalDSize64 += fSize64;
338706cfae4SConrad Meyer             srcPtr += fileSizes[fileNb];
339706cfae4SConrad Meyer         }
340706cfae4SConrad Meyer         {   size_t const decodedSize = (size_t)totalDSize64;
341706cfae4SConrad Meyer             assert((U64)decodedSize == totalDSize64);   /* check overflow */
342706cfae4SConrad Meyer             free(*resultBufferPtr);
343706cfae4SConrad Meyer             *resultBufferPtr = malloc(decodedSize);
344706cfae4SConrad Meyer             if (!(*resultBufferPtr)) {
345706cfae4SConrad Meyer                 RETURN_ERROR(33, BMK_benchOutcome_t, "not enough memory");
346706cfae4SConrad Meyer             }
347706cfae4SConrad Meyer             if (totalDSize64 > decodedSize) {  /* size_t overflow */
348706cfae4SConrad Meyer                 free(*resultBufferPtr);
349706cfae4SConrad Meyer                 RETURN_ERROR(32, BMK_benchOutcome_t, "original size is too large");
350706cfae4SConrad Meyer             }
351706cfae4SConrad Meyer             cSize = srcSize;
352706cfae4SConrad Meyer             srcSize = decodedSize;
353706cfae4SConrad Meyer             ratio = (double)srcSize / (double)cSize;
354706cfae4SConrad Meyer         }
355706cfae4SConrad Meyer     }
356706cfae4SConrad Meyer 
357706cfae4SConrad Meyer     /* Init data blocks  */
358706cfae4SConrad Meyer     {   const char* srcPtr = (const char*)srcBuffer;
359706cfae4SConrad Meyer         char* cPtr = (char*)compressedBuffer;
360706cfae4SConrad Meyer         char* resPtr = (char*)(*resultBufferPtr);
361706cfae4SConrad Meyer         U32 fileNb;
362706cfae4SConrad Meyer         for (nbBlocks=0, fileNb=0; fileNb<nbFiles; fileNb++) {
363706cfae4SConrad Meyer             size_t remaining = fileSizes[fileNb];
364706cfae4SConrad Meyer             U32 const nbBlocksforThisFile = (adv->mode == BMK_decodeOnly) ? 1 : (U32)((remaining + (blockSize-1)) / blockSize);
365706cfae4SConrad Meyer             U32 const blockEnd = nbBlocks + nbBlocksforThisFile;
366706cfae4SConrad Meyer             for ( ; nbBlocks<blockEnd; nbBlocks++) {
367706cfae4SConrad Meyer                 size_t const thisBlockSize = MIN(remaining, blockSize);
368706cfae4SConrad Meyer                 srcPtrs[nbBlocks] = srcPtr;
369706cfae4SConrad Meyer                 srcSizes[nbBlocks] = thisBlockSize;
370706cfae4SConrad Meyer                 cPtrs[nbBlocks] = cPtr;
371706cfae4SConrad Meyer                 cCapacities[nbBlocks] = (adv->mode == BMK_decodeOnly) ? thisBlockSize : ZSTD_compressBound(thisBlockSize);
372706cfae4SConrad Meyer                 resPtrs[nbBlocks] = resPtr;
373706cfae4SConrad Meyer                 resSizes[nbBlocks] = (adv->mode == BMK_decodeOnly) ? (size_t) ZSTD_findDecompressedSize(srcPtr, thisBlockSize) : thisBlockSize;
374706cfae4SConrad Meyer                 srcPtr += thisBlockSize;
375706cfae4SConrad Meyer                 cPtr += cCapacities[nbBlocks];
376706cfae4SConrad Meyer                 resPtr += thisBlockSize;
377706cfae4SConrad Meyer                 remaining -= thisBlockSize;
378af73257bSConrad Meyer                 if (adv->mode == BMK_decodeOnly) {
379af73257bSConrad Meyer                     cSizes[nbBlocks] = thisBlockSize;
380af73257bSConrad Meyer                     benchResult.cSize = thisBlockSize;
381b3392d84SAllan Jude     }   }   }   }
382706cfae4SConrad Meyer 
3833f774a5eSConrad Meyer     /* warming up `compressedBuffer` */
384706cfae4SConrad Meyer     if (adv->mode == BMK_decodeOnly) {
385706cfae4SConrad Meyer         memcpy(compressedBuffer, srcBuffer, loadedCompressedSize);
386706cfae4SConrad Meyer     } else {
387706cfae4SConrad Meyer         RDG_genBuffer(compressedBuffer, maxCompressedSize, 0.10, 0.50, 1);
388706cfae4SConrad Meyer     }
389706cfae4SConrad Meyer 
390706cfae4SConrad Meyer     /* Bench */
391706cfae4SConrad Meyer     {   U64 const crcOrig = (adv->mode == BMK_decodeOnly) ? 0 : XXH64(srcBuffer, srcSize, 0);
392706cfae4SConrad Meyer #       define NB_MARKS 4
393706cfae4SConrad Meyer         const char* marks[NB_MARKS] = { " |", " /", " =", " \\" };
394706cfae4SConrad Meyer         U32 markNb = 0;
395706cfae4SConrad Meyer         int compressionCompleted = (adv->mode == BMK_decodeOnly);
396706cfae4SConrad Meyer         int decompressionCompleted = (adv->mode == BMK_compressOnly);
397af73257bSConrad Meyer         BMK_benchParams_t cbp, dbp;
398706cfae4SConrad Meyer         BMK_initCCtxArgs cctxprep;
399706cfae4SConrad Meyer         BMK_initDCtxArgs dctxprep;
400af73257bSConrad Meyer 
401ea684039SConrad Meyer         cbp.benchFn = local_defaultCompress;   /* ZSTD_compress2 */
402af73257bSConrad Meyer         cbp.benchPayload = cctx;
403ea684039SConrad Meyer         cbp.initFn = local_initCCtx;   /* BMK_initCCtx */
404af73257bSConrad Meyer         cbp.initPayload = &cctxprep;
405af73257bSConrad Meyer         cbp.errorFn = ZSTD_isError;
406af73257bSConrad Meyer         cbp.blockCount = nbBlocks;
407af73257bSConrad Meyer         cbp.srcBuffers = srcPtrs;
408af73257bSConrad Meyer         cbp.srcSizes = srcSizes;
409af73257bSConrad Meyer         cbp.dstBuffers = cPtrs;
410af73257bSConrad Meyer         cbp.dstCapacities = cCapacities;
411af73257bSConrad Meyer         cbp.blockResults = cSizes;
412af73257bSConrad Meyer 
413706cfae4SConrad Meyer         cctxprep.cctx = cctx;
414706cfae4SConrad Meyer         cctxprep.dictBuffer = dictBuffer;
415706cfae4SConrad Meyer         cctxprep.dictBufferSize = dictBufferSize;
416706cfae4SConrad Meyer         cctxprep.cLevel = cLevel;
417706cfae4SConrad Meyer         cctxprep.comprParams = comprParams;
418706cfae4SConrad Meyer         cctxprep.adv = adv;
419af73257bSConrad Meyer 
420af73257bSConrad Meyer         dbp.benchFn = local_defaultDecompress;
421af73257bSConrad Meyer         dbp.benchPayload = dctx;
422af73257bSConrad Meyer         dbp.initFn = local_initDCtx;
423af73257bSConrad Meyer         dbp.initPayload = &dctxprep;
424af73257bSConrad Meyer         dbp.errorFn = ZSTD_isError;
425af73257bSConrad Meyer         dbp.blockCount = nbBlocks;
426af73257bSConrad Meyer         dbp.srcBuffers = (const void* const *) cPtrs;
427af73257bSConrad Meyer         dbp.srcSizes = cSizes;
428af73257bSConrad Meyer         dbp.dstBuffers = resPtrs;
429af73257bSConrad Meyer         dbp.dstCapacities = resSizes;
430af73257bSConrad Meyer         dbp.blockResults = NULL;
431af73257bSConrad Meyer 
432706cfae4SConrad Meyer         dctxprep.dctx = dctx;
433706cfae4SConrad Meyer         dctxprep.dictBuffer = dictBuffer;
434706cfae4SConrad Meyer         dctxprep.dictBufferSize = dictBufferSize;
435706cfae4SConrad Meyer 
436b3392d84SAllan Jude         OUTPUTLEVEL(2, "\r%70s\r", "");   /* blank line */
437b3392d84SAllan Jude         assert(srcSize < UINT_MAX);
438b3392d84SAllan Jude         OUTPUTLEVEL(2, "%2s-%-17.17s :%10u -> \r", marks[markNb], displayName, (unsigned)srcSize);
439706cfae4SConrad Meyer 
440706cfae4SConrad Meyer         while (!(compressionCompleted && decompressionCompleted)) {
441706cfae4SConrad Meyer             if (!compressionCompleted) {
442af73257bSConrad Meyer                 BMK_runOutcome_t const cOutcome = BMK_benchTimedFn( timeStateCompress, cbp);
443706cfae4SConrad Meyer 
444706cfae4SConrad Meyer                 if (!BMK_isSuccessful_runOutcome(cOutcome)) {
445706cfae4SConrad Meyer                     return BMK_benchOutcome_error();
446706cfae4SConrad Meyer                 }
447706cfae4SConrad Meyer 
448706cfae4SConrad Meyer                 {   BMK_runTime_t const cResult = BMK_extract_runTime(cOutcome);
449706cfae4SConrad Meyer                     cSize = cResult.sumOfReturn;
450b3392d84SAllan Jude                     ratio = (double)srcSize / (double)cSize;
451706cfae4SConrad Meyer                     {   BMK_benchResult_t newResult;
4523f774a5eSConrad Meyer                         newResult.cSpeed = (U64)((double)srcSize * TIMELOOP_NANOSEC / cResult.nanoSecPerRun);
453706cfae4SConrad Meyer                         benchResult.cSize = cSize;
454706cfae4SConrad Meyer                         if (newResult.cSpeed > benchResult.cSpeed)
455706cfae4SConrad Meyer                             benchResult.cSpeed = newResult.cSpeed;
456a19eddc3SBaptiste Daroussin                 }   }
457a19eddc3SBaptiste Daroussin 
4581767cc49SConrad Meyer                 {   int const ratioAccuracy = (ratio < 10.) ? 3 : 2;
459b3392d84SAllan Jude                     assert(cSize < UINT_MAX);
460b3392d84SAllan Jude                     OUTPUTLEVEL(2, "%2s-%-17.17s :%10u ->%10u (x%5.*f), %6.*f MB/s \r",
461706cfae4SConrad Meyer                             marks[markNb], displayName,
462af73257bSConrad Meyer                             (unsigned)srcSize, (unsigned)cSize,
4631767cc49SConrad Meyer                             ratioAccuracy, ratio,
464b3392d84SAllan Jude                             benchResult.cSpeed < (10 * MB_UNIT) ? 2 : 1, (double)benchResult.cSpeed / MB_UNIT);
4651767cc49SConrad Meyer                 }
466706cfae4SConrad Meyer                 compressionCompleted = BMK_isCompleted_TimedFn(timeStateCompress);
467706cfae4SConrad Meyer             }
468706cfae4SConrad Meyer 
469706cfae4SConrad Meyer             if(!decompressionCompleted) {
470af73257bSConrad Meyer                 BMK_runOutcome_t const dOutcome = BMK_benchTimedFn(timeStateDecompress, dbp);
471706cfae4SConrad Meyer 
472706cfae4SConrad Meyer                 if(!BMK_isSuccessful_runOutcome(dOutcome)) {
473706cfae4SConrad Meyer                     return BMK_benchOutcome_error();
474706cfae4SConrad Meyer                 }
475706cfae4SConrad Meyer 
476706cfae4SConrad Meyer                 {   BMK_runTime_t const dResult = BMK_extract_runTime(dOutcome);
4773f774a5eSConrad Meyer                     U64 const newDSpeed = (U64)((double)srcSize * TIMELOOP_NANOSEC / dResult.nanoSecPerRun);
478706cfae4SConrad Meyer                     if (newDSpeed > benchResult.dSpeed)
479706cfae4SConrad Meyer                         benchResult.dSpeed = newDSpeed;
480706cfae4SConrad Meyer                 }
481706cfae4SConrad Meyer 
482706cfae4SConrad Meyer                 {   int const ratioAccuracy = (ratio < 10.) ? 3 : 2;
483b3392d84SAllan Jude                     OUTPUTLEVEL(2, "%2s-%-17.17s :%10u ->%10u (x%5.*f), %6.*f MB/s, %6.1f MB/s\r",
484706cfae4SConrad Meyer                             marks[markNb], displayName,
485bc64b5ceSConrad Meyer                             (unsigned)srcSize, (unsigned)cSize,
486706cfae4SConrad Meyer                             ratioAccuracy, ratio,
487b3392d84SAllan Jude                             benchResult.cSpeed < (10 * MB_UNIT) ? 2 : 1, (double)benchResult.cSpeed / MB_UNIT,
488706cfae4SConrad Meyer                             (double)benchResult.dSpeed / MB_UNIT);
489706cfae4SConrad Meyer                 }
490706cfae4SConrad Meyer                 decompressionCompleted = BMK_isCompleted_TimedFn(timeStateDecompress);
491706cfae4SConrad Meyer             }
492af73257bSConrad Meyer             markNb = (markNb+1) % NB_MARKS;
493706cfae4SConrad Meyer         }   /* while (!(compressionCompleted && decompressionCompleted)) */
494a19eddc3SBaptiste Daroussin 
495a19eddc3SBaptiste Daroussin         /* CRC Checking */
496706cfae4SConrad Meyer         {   const BYTE* resultBuffer = (const BYTE*)(*resultBufferPtr);
497706cfae4SConrad Meyer             U64 const crcCheck = XXH64(resultBuffer, srcSize, 0);
498706cfae4SConrad Meyer             if ((adv->mode == BMK_both) && (crcOrig!=crcCheck)) {
499a19eddc3SBaptiste Daroussin                 size_t u;
500af73257bSConrad Meyer                 DISPLAY("!!! WARNING !!! %14s : Invalid Checksum : %x != %x   \n",
501af73257bSConrad Meyer                         displayName, (unsigned)crcOrig, (unsigned)crcCheck);
502a19eddc3SBaptiste Daroussin                 for (u=0; u<srcSize; u++) {
503706cfae4SConrad Meyer                     if (((const BYTE*)srcBuffer)[u] != resultBuffer[u]) {
504af73257bSConrad Meyer                         unsigned segNb, bNb, pos;
505a19eddc3SBaptiste Daroussin                         size_t bacc = 0;
506af73257bSConrad Meyer                         DISPLAY("Decoding error at pos %u ", (unsigned)u);
507a19eddc3SBaptiste Daroussin                         for (segNb = 0; segNb < nbBlocks; segNb++) {
508706cfae4SConrad Meyer                             if (bacc + srcSizes[segNb] > u) break;
509706cfae4SConrad Meyer                             bacc += srcSizes[segNb];
510a19eddc3SBaptiste Daroussin                         }
511a19eddc3SBaptiste Daroussin                         pos = (U32)(u - bacc);
512a19eddc3SBaptiste Daroussin                         bNb = pos / (128 KB);
513affe9eafSBaptiste Daroussin                         DISPLAY("(sample %u, block %u, pos %u) \n", segNb, bNb, pos);
5143f774a5eSConrad Meyer                         {   size_t const lowest = (u>5) ? 5 : u;
5153f774a5eSConrad Meyer                             size_t n;
5161767cc49SConrad Meyer                             DISPLAY("origin: ");
5173f774a5eSConrad Meyer                             for (n=lowest; n>0; n--)
5183f774a5eSConrad Meyer                                 DISPLAY("%02X ", ((const BYTE*)srcBuffer)[u-n]);
519a19eddc3SBaptiste Daroussin                             DISPLAY(" :%02X:  ", ((const BYTE*)srcBuffer)[u]);
5203f774a5eSConrad Meyer                             for (n=1; n<3; n++)
5213f774a5eSConrad Meyer                                 DISPLAY("%02X ", ((const BYTE*)srcBuffer)[u+n]);
522a19eddc3SBaptiste Daroussin                             DISPLAY(" \n");
5231767cc49SConrad Meyer                             DISPLAY("decode: ");
524b3392d84SAllan Jude                             for (n=lowest; n>0; n--)
5253f774a5eSConrad Meyer                                 DISPLAY("%02X ", resultBuffer[u-n]);
526706cfae4SConrad Meyer                             DISPLAY(" :%02X:  ", resultBuffer[u]);
5273f774a5eSConrad Meyer                             for (n=1; n<3; n++)
5283f774a5eSConrad Meyer                                 DISPLAY("%02X ", resultBuffer[u+n]);
529a19eddc3SBaptiste Daroussin                             DISPLAY(" \n");
530a19eddc3SBaptiste Daroussin                         }
531a19eddc3SBaptiste Daroussin                         break;
532a19eddc3SBaptiste Daroussin                     }
533a19eddc3SBaptiste Daroussin                     if (u==srcSize-1) {  /* should never happen */
534a19eddc3SBaptiste Daroussin                         DISPLAY("no difference detected\n");
535706cfae4SConrad Meyer                     }
536ea684039SConrad Meyer                 }   /* for (u=0; u<srcSize; u++) */
537ea684039SConrad Meyer             }   /* if ((adv->mode == BMK_both) && (crcOrig!=crcCheck)) */
538706cfae4SConrad Meyer         }   /* CRC Checking */
539a19eddc3SBaptiste Daroussin 
540706cfae4SConrad Meyer         if (displayLevel == 1) {   /* hidden display mode -q, used by python speed benchmark */
541706cfae4SConrad Meyer             double const cSpeed = (double)benchResult.cSpeed / MB_UNIT;
542706cfae4SConrad Meyer             double const dSpeed = (double)benchResult.dSpeed / MB_UNIT;
543706cfae4SConrad Meyer             if (adv->additionalParam) {
544b3392d84SAllan Jude                 OUTPUT("-%-3i%11i (%5.3f) %6.2f MB/s %6.1f MB/s  %s (param=%d)\n", cLevel, (int)cSize, ratio, cSpeed, dSpeed, displayName, adv->additionalParam);
545706cfae4SConrad Meyer             } else {
546b3392d84SAllan Jude                 OUTPUT("-%-3i%11i (%5.3f) %6.2f MB/s %6.1f MB/s  %s\n", cLevel, (int)cSize, ratio, cSpeed, dSpeed, displayName);
547a19eddc3SBaptiste Daroussin             }
548706cfae4SConrad Meyer         }
549706cfae4SConrad Meyer 
550b3392d84SAllan Jude         OUTPUTLEVEL(2, "%2i#\n", cLevel);
551a19eddc3SBaptiste Daroussin     }   /* Bench */
552a19eddc3SBaptiste Daroussin 
553706cfae4SConrad Meyer     benchResult.cMem = (1ULL << (comprParams->windowLog)) + ZSTD_sizeof_CCtx(cctx);
554706cfae4SConrad Meyer     return BMK_benchOutcome_setValidResult(benchResult);
555a19eddc3SBaptiste Daroussin }
556a19eddc3SBaptiste Daroussin 
BMK_benchMemAdvanced(const void * srcBuffer,size_t srcSize,void * dstBuffer,size_t dstCapacity,const size_t * fileSizes,unsigned nbFiles,int cLevel,const ZSTD_compressionParameters * comprParams,const void * dictBuffer,size_t dictBufferSize,int displayLevel,const char * displayName,const BMK_advancedParams_t * adv)557706cfae4SConrad Meyer BMK_benchOutcome_t BMK_benchMemAdvanced(const void* srcBuffer, size_t srcSize,
558706cfae4SConrad Meyer                         void* dstBuffer, size_t dstCapacity,
559706cfae4SConrad Meyer                         const size_t* fileSizes, unsigned nbFiles,
560706cfae4SConrad Meyer                         int cLevel, const ZSTD_compressionParameters* comprParams,
561706cfae4SConrad Meyer                         const void* dictBuffer, size_t dictBufferSize,
562706cfae4SConrad Meyer                         int displayLevel, const char* displayName, const BMK_advancedParams_t* adv)
563706cfae4SConrad Meyer 
564706cfae4SConrad Meyer {
565706cfae4SConrad Meyer     int const dstParamsError = !dstBuffer ^ !dstCapacity;  /* must be both NULL or none */
566706cfae4SConrad Meyer 
567706cfae4SConrad Meyer     size_t const blockSize = ((adv->blockSize>=32 && (adv->mode != BMK_decodeOnly)) ? adv->blockSize : srcSize) + (!srcSize) /* avoid div by 0 */ ;
568706cfae4SConrad Meyer     U32 const maxNbBlocks = (U32) ((srcSize + (blockSize-1)) / blockSize) + nbFiles;
569706cfae4SConrad Meyer 
570706cfae4SConrad Meyer     /* these are the blockTable parameters, just split up */
571706cfae4SConrad Meyer     const void ** const srcPtrs = (const void**)malloc(maxNbBlocks * sizeof(void*));
572706cfae4SConrad Meyer     size_t* const srcSizes = (size_t*)malloc(maxNbBlocks * sizeof(size_t));
573706cfae4SConrad Meyer 
574706cfae4SConrad Meyer 
575706cfae4SConrad Meyer     void ** const cPtrs = (void**)malloc(maxNbBlocks * sizeof(void*));
576706cfae4SConrad Meyer     size_t* const cSizes = (size_t*)malloc(maxNbBlocks * sizeof(size_t));
577706cfae4SConrad Meyer     size_t* const cCapacities = (size_t*)malloc(maxNbBlocks * sizeof(size_t));
578706cfae4SConrad Meyer 
579706cfae4SConrad Meyer     void ** const resPtrs = (void**)malloc(maxNbBlocks * sizeof(void*));
580706cfae4SConrad Meyer     size_t* const resSizes = (size_t*)malloc(maxNbBlocks * sizeof(size_t));
581706cfae4SConrad Meyer 
582706cfae4SConrad Meyer     BMK_timedFnState_t* timeStateCompress = BMK_createTimedFnState(adv->nbSeconds * 1000, BMK_RUNTEST_DEFAULT_MS);
583706cfae4SConrad Meyer     BMK_timedFnState_t* timeStateDecompress = BMK_createTimedFnState(adv->nbSeconds * 1000, BMK_RUNTEST_DEFAULT_MS);
584706cfae4SConrad Meyer 
585706cfae4SConrad Meyer     ZSTD_CCtx* const cctx = ZSTD_createCCtx();
586706cfae4SConrad Meyer     ZSTD_DCtx* const dctx = ZSTD_createDCtx();
587706cfae4SConrad Meyer 
588706cfae4SConrad Meyer     const size_t maxCompressedSize = dstCapacity ? dstCapacity : ZSTD_compressBound(srcSize) + (maxNbBlocks * 1024);
589706cfae4SConrad Meyer 
590706cfae4SConrad Meyer     void* const internalDstBuffer = dstBuffer ? NULL : malloc(maxCompressedSize);
591706cfae4SConrad Meyer     void* const compressedBuffer = dstBuffer ? dstBuffer : internalDstBuffer;
592706cfae4SConrad Meyer 
593706cfae4SConrad Meyer     BMK_benchOutcome_t outcome = BMK_benchOutcome_error();  /* error by default */
594706cfae4SConrad Meyer 
595706cfae4SConrad Meyer     void* resultBuffer = srcSize ? malloc(srcSize) : NULL;
596706cfae4SConrad Meyer 
597706cfae4SConrad Meyer     int allocationincomplete = !srcPtrs || !srcSizes || !cPtrs ||
598706cfae4SConrad Meyer         !cSizes || !cCapacities || !resPtrs || !resSizes ||
599706cfae4SConrad Meyer         !timeStateCompress || !timeStateDecompress ||
600706cfae4SConrad Meyer         !cctx || !dctx ||
601706cfae4SConrad Meyer         !compressedBuffer || !resultBuffer;
602706cfae4SConrad Meyer 
603706cfae4SConrad Meyer 
604706cfae4SConrad Meyer     if (!allocationincomplete && !dstParamsError) {
605706cfae4SConrad Meyer         outcome = BMK_benchMemAdvancedNoAlloc(srcPtrs, srcSizes,
606706cfae4SConrad Meyer                                             cPtrs, cCapacities, cSizes,
607706cfae4SConrad Meyer                                             resPtrs, resSizes,
608706cfae4SConrad Meyer                                             &resultBuffer,
609706cfae4SConrad Meyer                                             compressedBuffer, maxCompressedSize,
610706cfae4SConrad Meyer                                             timeStateCompress, timeStateDecompress,
611706cfae4SConrad Meyer                                             srcBuffer, srcSize,
612706cfae4SConrad Meyer                                             fileSizes, nbFiles,
613706cfae4SConrad Meyer                                             cLevel, comprParams,
614706cfae4SConrad Meyer                                             dictBuffer, dictBufferSize,
615706cfae4SConrad Meyer                                             cctx, dctx,
616706cfae4SConrad Meyer                                             displayLevel, displayName, adv);
617706cfae4SConrad Meyer     }
618706cfae4SConrad Meyer 
619706cfae4SConrad Meyer     /* clean up */
620706cfae4SConrad Meyer     BMK_freeTimedFnState(timeStateCompress);
621706cfae4SConrad Meyer     BMK_freeTimedFnState(timeStateDecompress);
622706cfae4SConrad Meyer 
623706cfae4SConrad Meyer     ZSTD_freeCCtx(cctx);
624706cfae4SConrad Meyer     ZSTD_freeDCtx(dctx);
625706cfae4SConrad Meyer 
626706cfae4SConrad Meyer     free(internalDstBuffer);
627706cfae4SConrad Meyer     free(resultBuffer);
628706cfae4SConrad Meyer 
629706cfae4SConrad Meyer     free((void*)srcPtrs);
630706cfae4SConrad Meyer     free(srcSizes);
631706cfae4SConrad Meyer     free(cPtrs);
632706cfae4SConrad Meyer     free(cSizes);
633706cfae4SConrad Meyer     free(cCapacities);
634706cfae4SConrad Meyer     free(resPtrs);
635706cfae4SConrad Meyer     free(resSizes);
636706cfae4SConrad Meyer 
637706cfae4SConrad Meyer     if(allocationincomplete) {
638706cfae4SConrad Meyer         RETURN_ERROR(31, BMK_benchOutcome_t, "allocation error : not enough memory");
639706cfae4SConrad Meyer     }
640706cfae4SConrad Meyer 
641706cfae4SConrad Meyer     if(dstParamsError) {
642706cfae4SConrad Meyer         RETURN_ERROR(32, BMK_benchOutcome_t, "Dst parameters not coherent");
643706cfae4SConrad Meyer     }
644706cfae4SConrad Meyer     return outcome;
645706cfae4SConrad Meyer }
646706cfae4SConrad Meyer 
BMK_benchMem(const void * srcBuffer,size_t srcSize,const size_t * fileSizes,unsigned nbFiles,int cLevel,const ZSTD_compressionParameters * comprParams,const void * dictBuffer,size_t dictBufferSize,int displayLevel,const char * displayName)647706cfae4SConrad Meyer BMK_benchOutcome_t BMK_benchMem(const void* srcBuffer, size_t srcSize,
648706cfae4SConrad Meyer                         const size_t* fileSizes, unsigned nbFiles,
649706cfae4SConrad Meyer                         int cLevel, const ZSTD_compressionParameters* comprParams,
650706cfae4SConrad Meyer                         const void* dictBuffer, size_t dictBufferSize,
651706cfae4SConrad Meyer                         int displayLevel, const char* displayName) {
652706cfae4SConrad Meyer 
653706cfae4SConrad Meyer     BMK_advancedParams_t const adv = BMK_initAdvancedParams();
654706cfae4SConrad Meyer     return BMK_benchMemAdvanced(srcBuffer, srcSize,
655706cfae4SConrad Meyer                                 NULL, 0,
656706cfae4SConrad Meyer                                 fileSizes, nbFiles,
657706cfae4SConrad Meyer                                 cLevel, comprParams,
658706cfae4SConrad Meyer                                 dictBuffer, dictBufferSize,
659706cfae4SConrad Meyer                                 displayLevel, displayName, &adv);
660706cfae4SConrad Meyer }
661706cfae4SConrad Meyer 
BMK_benchCLevel(const void * srcBuffer,size_t benchedSize,const size_t * fileSizes,unsigned nbFiles,int cLevel,const ZSTD_compressionParameters * comprParams,const void * dictBuffer,size_t dictBufferSize,int displayLevel,const char * displayName,BMK_advancedParams_t const * const adv)662706cfae4SConrad Meyer static BMK_benchOutcome_t BMK_benchCLevel(const void* srcBuffer, size_t benchedSize,
663706cfae4SConrad Meyer                             const size_t* fileSizes, unsigned nbFiles,
664706cfae4SConrad Meyer                             int cLevel, const ZSTD_compressionParameters* comprParams,
665706cfae4SConrad Meyer                             const void* dictBuffer, size_t dictBufferSize,
666706cfae4SConrad Meyer                             int displayLevel, const char* displayName,
667706cfae4SConrad Meyer                             BMK_advancedParams_t const * const adv)
668706cfae4SConrad Meyer {
669706cfae4SConrad Meyer     const char* pch = strrchr(displayName, '\\'); /* Windows */
670706cfae4SConrad Meyer     if (!pch) pch = strrchr(displayName, '/');    /* Linux */
671706cfae4SConrad Meyer     if (pch) displayName = pch+1;
672706cfae4SConrad Meyer 
673706cfae4SConrad Meyer     if (adv->realTime) {
674706cfae4SConrad Meyer         DISPLAYLEVEL(2, "Note : switching to real-time priority \n");
675706cfae4SConrad Meyer         SET_REALTIME_PRIORITY;
676706cfae4SConrad Meyer     }
677706cfae4SConrad Meyer 
678706cfae4SConrad Meyer     if (displayLevel == 1 && !adv->additionalParam)   /* --quiet mode */
679b3392d84SAllan Jude         OUTPUT("bench %s %s: input %u bytes, %u seconds, %u KB blocks\n",
680706cfae4SConrad Meyer                 ZSTD_VERSION_STRING, ZSTD_GIT_COMMIT_STRING,
681af73257bSConrad Meyer                 (unsigned)benchedSize, adv->nbSeconds, (unsigned)(adv->blockSize>>10));
682706cfae4SConrad Meyer 
683706cfae4SConrad Meyer     return BMK_benchMemAdvanced(srcBuffer, benchedSize,
684706cfae4SConrad Meyer                                 NULL, 0,
685706cfae4SConrad Meyer                                 fileSizes, nbFiles,
686706cfae4SConrad Meyer                                 cLevel, comprParams,
687706cfae4SConrad Meyer                                 dictBuffer, dictBufferSize,
688706cfae4SConrad Meyer                                 displayLevel, displayName, adv);
689706cfae4SConrad Meyer }
690706cfae4SConrad Meyer 
BMK_syntheticTest(int cLevel,double compressibility,const ZSTD_compressionParameters * compressionParams,int displayLevel,const BMK_advancedParams_t * adv)691706cfae4SConrad Meyer BMK_benchOutcome_t BMK_syntheticTest(int cLevel, double compressibility,
692706cfae4SConrad Meyer                           const ZSTD_compressionParameters* compressionParams,
693706cfae4SConrad Meyer                           int displayLevel, const BMK_advancedParams_t* adv)
694706cfae4SConrad Meyer {
695706cfae4SConrad Meyer     char name[20] = {0};
696706cfae4SConrad Meyer     size_t const benchedSize = 10000000;
697706cfae4SConrad Meyer     void* srcBuffer;
698706cfae4SConrad Meyer     BMK_benchOutcome_t res;
699706cfae4SConrad Meyer 
700706cfae4SConrad Meyer     if (cLevel > ZSTD_maxCLevel()) {
701706cfae4SConrad Meyer         RETURN_ERROR(15, BMK_benchOutcome_t, "Invalid Compression Level");
702706cfae4SConrad Meyer     }
703706cfae4SConrad Meyer 
704706cfae4SConrad Meyer     /* Memory allocation */
705706cfae4SConrad Meyer     srcBuffer = malloc(benchedSize);
706706cfae4SConrad Meyer     if (!srcBuffer) RETURN_ERROR(21, BMK_benchOutcome_t, "not enough memory");
707706cfae4SConrad Meyer 
708706cfae4SConrad Meyer     /* Fill input buffer */
709706cfae4SConrad Meyer     RDG_genBuffer(srcBuffer, benchedSize, compressibility, 0.0, 0);
710706cfae4SConrad Meyer 
711706cfae4SConrad Meyer     /* Bench */
712706cfae4SConrad Meyer     snprintf (name, sizeof(name), "Synthetic %2u%%", (unsigned)(compressibility*100));
713706cfae4SConrad Meyer     res = BMK_benchCLevel(srcBuffer, benchedSize,
714706cfae4SConrad Meyer                     &benchedSize /* ? */, 1 /* ? */,
715706cfae4SConrad Meyer                     cLevel, compressionParams,
716706cfae4SConrad Meyer                     NULL, 0,  /* dictionary */
717706cfae4SConrad Meyer                     displayLevel, name, adv);
718706cfae4SConrad Meyer 
719706cfae4SConrad Meyer     /* clean up */
720706cfae4SConrad Meyer     free(srcBuffer);
721706cfae4SConrad Meyer 
722706cfae4SConrad Meyer     return res;
723706cfae4SConrad Meyer }
724706cfae4SConrad Meyer 
725706cfae4SConrad Meyer 
726a19eddc3SBaptiste Daroussin 
BMK_findMaxMem(U64 requiredMem)727a19eddc3SBaptiste Daroussin static size_t BMK_findMaxMem(U64 requiredMem)
728a19eddc3SBaptiste Daroussin {
729a19eddc3SBaptiste Daroussin     size_t const step = 64 MB;
730a19eddc3SBaptiste Daroussin     BYTE* testmem = NULL;
731a19eddc3SBaptiste Daroussin 
732a19eddc3SBaptiste Daroussin     requiredMem = (((requiredMem >> 26) + 1) << 26);
733a19eddc3SBaptiste Daroussin     requiredMem += step;
734a19eddc3SBaptiste Daroussin     if (requiredMem > maxMemory) requiredMem = maxMemory;
735a19eddc3SBaptiste Daroussin 
736a19eddc3SBaptiste Daroussin     do {
737a19eddc3SBaptiste Daroussin         testmem = (BYTE*)malloc((size_t)requiredMem);
738a19eddc3SBaptiste Daroussin         requiredMem -= step;
739706cfae4SConrad Meyer     } while (!testmem && requiredMem > 0);
740a19eddc3SBaptiste Daroussin 
741a19eddc3SBaptiste Daroussin     free(testmem);
742a19eddc3SBaptiste Daroussin     return (size_t)(requiredMem);
743a19eddc3SBaptiste Daroussin }
744a19eddc3SBaptiste Daroussin 
745a19eddc3SBaptiste Daroussin /*! BMK_loadFiles() :
74642239e68SConrad Meyer  *  Loads `buffer` with content of files listed within `fileNamesTable`.
74742239e68SConrad Meyer  *  At most, fills `buffer` entirely. */
BMK_loadFiles(void * buffer,size_t bufferSize,size_t * fileSizes,const char * const * fileNamesTable,unsigned nbFiles,int displayLevel)748706cfae4SConrad Meyer static int BMK_loadFiles(void* buffer, size_t bufferSize,
749a19eddc3SBaptiste Daroussin                          size_t* fileSizes,
750706cfae4SConrad Meyer                          const char* const * fileNamesTable, unsigned nbFiles,
751706cfae4SConrad Meyer                          int displayLevel)
752a19eddc3SBaptiste Daroussin {
753a19eddc3SBaptiste Daroussin     size_t pos = 0, totalSize = 0;
754a19eddc3SBaptiste Daroussin     unsigned n;
755a19eddc3SBaptiste Daroussin     for (n=0; n<nbFiles; n++) {
756ea684039SConrad Meyer         U64 fileSize = UTIL_getFileSize(fileNamesTable[n]);  /* last file may be shortened */
757a19eddc3SBaptiste Daroussin         if (UTIL_isDirectory(fileNamesTable[n])) {
758a19eddc3SBaptiste Daroussin             DISPLAYLEVEL(2, "Ignoring %s directory...       \n", fileNamesTable[n]);
759a19eddc3SBaptiste Daroussin             fileSizes[n] = 0;
760a19eddc3SBaptiste Daroussin             continue;
761a19eddc3SBaptiste Daroussin         }
7621767cc49SConrad Meyer         if (fileSize == UTIL_FILESIZE_UNKNOWN) {
7631767cc49SConrad Meyer             DISPLAYLEVEL(2, "Cannot evaluate size of %s, ignoring ... \n", fileNamesTable[n]);
7641767cc49SConrad Meyer             fileSizes[n] = 0;
7651767cc49SConrad Meyer             continue;
7661767cc49SConrad Meyer         }
767ea684039SConrad Meyer         {   FILE* const f = fopen(fileNamesTable[n], "rb");
768ea684039SConrad Meyer             if (f==NULL) RETURN_ERROR_INT(10, "impossible to open file %s", fileNamesTable[n]);
769b3392d84SAllan Jude             OUTPUTLEVEL(2, "Loading %s...       \r", fileNamesTable[n]);
770a19eddc3SBaptiste Daroussin             if (fileSize > bufferSize-pos) fileSize = bufferSize-pos, nbFiles=n;   /* buffer too small - stop after this file */
771a19eddc3SBaptiste Daroussin             {   size_t const readSize = fread(((char*)buffer)+pos, 1, (size_t)fileSize, f);
772ea684039SConrad Meyer                 if (readSize != (size_t)fileSize) RETURN_ERROR_INT(11, "could not read %s", fileNamesTable[n]);
773706cfae4SConrad Meyer                 pos += readSize;
774706cfae4SConrad Meyer             }
775a19eddc3SBaptiste Daroussin             fileSizes[n] = (size_t)fileSize;
776a19eddc3SBaptiste Daroussin             totalSize += (size_t)fileSize;
777a19eddc3SBaptiste Daroussin             fclose(f);
778ea684039SConrad Meyer     }   }
779a19eddc3SBaptiste Daroussin 
780ea684039SConrad Meyer     if (totalSize == 0) RETURN_ERROR_INT(12, "no data to bench");
781706cfae4SConrad Meyer     return 0;
782a19eddc3SBaptiste Daroussin }
783a19eddc3SBaptiste Daroussin 
BMK_benchFilesAdvanced(const char * const * fileNamesTable,unsigned nbFiles,const char * dictFileName,int cLevel,const ZSTD_compressionParameters * compressionParams,int displayLevel,const BMK_advancedParams_t * adv)784706cfae4SConrad Meyer BMK_benchOutcome_t BMK_benchFilesAdvanced(
785706cfae4SConrad Meyer                         const char* const * fileNamesTable, unsigned nbFiles,
786706cfae4SConrad Meyer                         const char* dictFileName, int cLevel,
787706cfae4SConrad Meyer                         const ZSTD_compressionParameters* compressionParams,
788706cfae4SConrad Meyer                         int displayLevel, const BMK_advancedParams_t* adv)
789a19eddc3SBaptiste Daroussin {
790706cfae4SConrad Meyer     void* srcBuffer = NULL;
791a19eddc3SBaptiste Daroussin     size_t benchedSize;
792a19eddc3SBaptiste Daroussin     void* dictBuffer = NULL;
793a19eddc3SBaptiste Daroussin     size_t dictBufferSize = 0;
794706cfae4SConrad Meyer     size_t* fileSizes = NULL;
795706cfae4SConrad Meyer     BMK_benchOutcome_t res;
796a19eddc3SBaptiste Daroussin     U64 const totalSizeToLoad = UTIL_getTotalFileSize(fileNamesTable, nbFiles);
797a19eddc3SBaptiste Daroussin 
798706cfae4SConrad Meyer     if (!nbFiles) {
799706cfae4SConrad Meyer         RETURN_ERROR(14, BMK_benchOutcome_t, "No Files to Benchmark");
800706cfae4SConrad Meyer     }
801706cfae4SConrad Meyer 
802706cfae4SConrad Meyer     if (cLevel > ZSTD_maxCLevel()) {
803706cfae4SConrad Meyer         RETURN_ERROR(15, BMK_benchOutcome_t, "Invalid Compression Level");
804706cfae4SConrad Meyer     }
805706cfae4SConrad Meyer 
806b3392d84SAllan Jude     if (totalSizeToLoad == UTIL_FILESIZE_UNKNOWN) {
807b3392d84SAllan Jude         RETURN_ERROR(9, BMK_benchOutcome_t, "Error loading files");
808b3392d84SAllan Jude     }
809b3392d84SAllan Jude 
810706cfae4SConrad Meyer     fileSizes = (size_t*)calloc(nbFiles, sizeof(size_t));
811706cfae4SConrad Meyer     if (!fileSizes) RETURN_ERROR(12, BMK_benchOutcome_t, "not enough memory for fileSizes");
812a19eddc3SBaptiste Daroussin 
813a19eddc3SBaptiste Daroussin     /* Load dictionary */
814a19eddc3SBaptiste Daroussin     if (dictFileName != NULL) {
8151767cc49SConrad Meyer         U64 const dictFileSize = UTIL_getFileSize(dictFileName);
816af73257bSConrad Meyer         if (dictFileSize == UTIL_FILESIZE_UNKNOWN) {
817af73257bSConrad Meyer             DISPLAYLEVEL(1, "error loading %s : %s \n", dictFileName, strerror(errno));
818af73257bSConrad Meyer             free(fileSizes);
819af73257bSConrad Meyer             RETURN_ERROR(9, BMK_benchOutcome_t, "benchmark aborted");
820af73257bSConrad Meyer         }
821706cfae4SConrad Meyer         if (dictFileSize > 64 MB) {
822706cfae4SConrad Meyer             free(fileSizes);
823706cfae4SConrad Meyer             RETURN_ERROR(10, BMK_benchOutcome_t, "dictionary file %s too large", dictFileName);
824706cfae4SConrad Meyer         }
825a19eddc3SBaptiste Daroussin         dictBufferSize = (size_t)dictFileSize;
826a19eddc3SBaptiste Daroussin         dictBuffer = malloc(dictBufferSize);
827706cfae4SConrad Meyer         if (dictBuffer==NULL) {
828706cfae4SConrad Meyer             free(fileSizes);
829706cfae4SConrad Meyer             RETURN_ERROR(11, BMK_benchOutcome_t, "not enough memory for dictionary (%u bytes)",
830af73257bSConrad Meyer                             (unsigned)dictBufferSize);
831706cfae4SConrad Meyer         }
832706cfae4SConrad Meyer 
833706cfae4SConrad Meyer         {   int const errorCode = BMK_loadFiles(dictBuffer, dictBufferSize,
834706cfae4SConrad Meyer                                                 fileSizes, &dictFileName /*?*/,
835706cfae4SConrad Meyer                                                 1 /*?*/, displayLevel);
836706cfae4SConrad Meyer             if (errorCode) {
837706cfae4SConrad Meyer                 res = BMK_benchOutcome_error();
838706cfae4SConrad Meyer                 goto _cleanUp;
839706cfae4SConrad Meyer         }   }
840a19eddc3SBaptiste Daroussin     }
841a19eddc3SBaptiste Daroussin 
842a19eddc3SBaptiste Daroussin     /* Memory allocation & restrictions */
843a19eddc3SBaptiste Daroussin     benchedSize = BMK_findMaxMem(totalSizeToLoad * 3) / 3;
844a19eddc3SBaptiste Daroussin     if ((U64)benchedSize > totalSizeToLoad) benchedSize = (size_t)totalSizeToLoad;
845a19eddc3SBaptiste Daroussin     if (benchedSize < totalSizeToLoad)
846af73257bSConrad Meyer         DISPLAY("Not enough memory; testing %u MB only...\n", (unsigned)(benchedSize >> 20));
847706cfae4SConrad Meyer 
848706cfae4SConrad Meyer     srcBuffer = benchedSize ? malloc(benchedSize) : NULL;
849706cfae4SConrad Meyer     if (!srcBuffer) {
850706cfae4SConrad Meyer         free(dictBuffer);
851706cfae4SConrad Meyer         free(fileSizes);
852706cfae4SConrad Meyer         RETURN_ERROR(12, BMK_benchOutcome_t, "not enough memory");
853706cfae4SConrad Meyer     }
854a19eddc3SBaptiste Daroussin 
855a19eddc3SBaptiste Daroussin     /* Load input buffer */
856706cfae4SConrad Meyer     {   int const errorCode = BMK_loadFiles(srcBuffer, benchedSize,
857706cfae4SConrad Meyer                                         fileSizes, fileNamesTable, nbFiles,
858706cfae4SConrad Meyer                                         displayLevel);
859706cfae4SConrad Meyer         if (errorCode) {
860706cfae4SConrad Meyer             res = BMK_benchOutcome_error();
861706cfae4SConrad Meyer             goto _cleanUp;
8621767cc49SConrad Meyer     }   }
863a19eddc3SBaptiste Daroussin 
864706cfae4SConrad Meyer     /* Bench */
865706cfae4SConrad Meyer     {   char mfName[20] = {0};
866706cfae4SConrad Meyer         snprintf (mfName, sizeof(mfName), " %u files", nbFiles);
867706cfae4SConrad Meyer         {   const char* const displayName = (nbFiles > 1) ? mfName : fileNamesTable[0];
868706cfae4SConrad Meyer             res = BMK_benchCLevel(srcBuffer, benchedSize,
869706cfae4SConrad Meyer                                 fileSizes, nbFiles,
870706cfae4SConrad Meyer                                 cLevel, compressionParams,
871706cfae4SConrad Meyer                                 dictBuffer, dictBufferSize,
872706cfae4SConrad Meyer                                 displayLevel, displayName,
873706cfae4SConrad Meyer                                 adv);
874706cfae4SConrad Meyer     }   }
875706cfae4SConrad Meyer 
876706cfae4SConrad Meyer _cleanUp:
877a19eddc3SBaptiste Daroussin     free(srcBuffer);
878a19eddc3SBaptiste Daroussin     free(dictBuffer);
879a19eddc3SBaptiste Daroussin     free(fileSizes);
880706cfae4SConrad Meyer     return res;
881a19eddc3SBaptiste Daroussin }
882a19eddc3SBaptiste Daroussin 
883a19eddc3SBaptiste Daroussin 
BMK_benchFiles(const char * const * fileNamesTable,unsigned nbFiles,const char * dictFileName,int cLevel,const ZSTD_compressionParameters * compressionParams,int displayLevel)884706cfae4SConrad Meyer BMK_benchOutcome_t BMK_benchFiles(
885706cfae4SConrad Meyer                     const char* const * fileNamesTable, unsigned nbFiles,
8861767cc49SConrad Meyer                     const char* dictFileName,
887706cfae4SConrad Meyer                     int cLevel, const ZSTD_compressionParameters* compressionParams,
888706cfae4SConrad Meyer                     int displayLevel)
889a19eddc3SBaptiste Daroussin {
890706cfae4SConrad Meyer     BMK_advancedParams_t const adv = BMK_initAdvancedParams();
891706cfae4SConrad Meyer     return BMK_benchFilesAdvanced(fileNamesTable, nbFiles, dictFileName, cLevel, compressionParams, displayLevel, &adv);
892a19eddc3SBaptiste Daroussin }
893