1a28cd43dSSascha Wildner /* 2a28cd43dSSascha Wildner * Copyright (c) 2016-2020, Yann Collet, Facebook, Inc. 3a28cd43dSSascha Wildner * All rights reserved. 4a28cd43dSSascha Wildner * 5a28cd43dSSascha Wildner * This source code is licensed under both the BSD-style license (found in the 6a28cd43dSSascha Wildner * LICENSE file in the root directory of this source tree) and the GPLv2 (found 7a28cd43dSSascha Wildner * in the COPYING file in the root directory of this source tree). 8a28cd43dSSascha Wildner * You may select, at your option, one of the above-listed licenses. 9a28cd43dSSascha Wildner */ 10a28cd43dSSascha Wildner 11a28cd43dSSascha Wildner /* benchzstd : 12a28cd43dSSascha Wildner * benchmark Zstandard compression / decompression 13a28cd43dSSascha Wildner * over a set of files or buffers 14a28cd43dSSascha Wildner * and display progress result and final summary 15a28cd43dSSascha Wildner */ 16a28cd43dSSascha Wildner 17a28cd43dSSascha Wildner #if defined (__cplusplus) 18a28cd43dSSascha Wildner extern "C" { 19a28cd43dSSascha Wildner #endif 20a28cd43dSSascha Wildner 21a28cd43dSSascha Wildner #ifndef BENCH_ZSTD_H_3242387 22a28cd43dSSascha Wildner #define BENCH_ZSTD_H_3242387 23a28cd43dSSascha Wildner 24a28cd43dSSascha Wildner /* === Dependencies === */ 25a28cd43dSSascha Wildner #include <stddef.h> /* size_t */ 26a28cd43dSSascha Wildner #define ZSTD_STATIC_LINKING_ONLY /* ZSTD_compressionParameters */ 27a28cd43dSSascha Wildner #include "../lib/zstd.h" /* ZSTD_compressionParameters */ 28a28cd43dSSascha Wildner 29a28cd43dSSascha Wildner 30a28cd43dSSascha Wildner /* === Constants === */ 31a28cd43dSSascha Wildner 32a28cd43dSSascha Wildner #define MB_UNIT 1000000 33a28cd43dSSascha Wildner 34a28cd43dSSascha Wildner 35a28cd43dSSascha Wildner /* === Benchmark functions === */ 36a28cd43dSSascha Wildner 37a28cd43dSSascha Wildner /* Creates a variant `typeName`, able to express "error or valid result". 38a28cd43dSSascha Wildner * Functions with return type `typeName` 39a28cd43dSSascha Wildner * must first check if result is valid, using BMK_isSuccessful_*(), 40a28cd43dSSascha Wildner * and only then can extract `baseType`. 41a28cd43dSSascha Wildner */ 42a28cd43dSSascha Wildner #define VARIANT_ERROR_RESULT(baseType, variantName) \ 43a28cd43dSSascha Wildner \ 44a28cd43dSSascha Wildner typedef struct { \ 45a28cd43dSSascha Wildner baseType internal_never_use_directly; \ 46a28cd43dSSascha Wildner int tag; \ 47a28cd43dSSascha Wildner } variantName 48a28cd43dSSascha Wildner 49a28cd43dSSascha Wildner 50a28cd43dSSascha Wildner typedef struct { 51a28cd43dSSascha Wildner size_t cSize; 52a28cd43dSSascha Wildner unsigned long long cSpeed; /* bytes / sec */ 53a28cd43dSSascha Wildner unsigned long long dSpeed; 54a28cd43dSSascha Wildner size_t cMem; /* memory usage during compression */ 55a28cd43dSSascha Wildner } BMK_benchResult_t; 56a28cd43dSSascha Wildner 57a28cd43dSSascha Wildner VARIANT_ERROR_RESULT(BMK_benchResult_t, BMK_benchOutcome_t); 58a28cd43dSSascha Wildner 59a28cd43dSSascha Wildner /* check first if the return structure represents an error or a valid result */ 60a28cd43dSSascha Wildner int BMK_isSuccessful_benchOutcome(BMK_benchOutcome_t outcome); 61a28cd43dSSascha Wildner 62a28cd43dSSascha Wildner /* extract result from variant type. 63a28cd43dSSascha Wildner * note : this function will abort() program execution if result is not valid 64a28cd43dSSascha Wildner * check result validity first, by using BMK_isSuccessful_benchOutcome() 65a28cd43dSSascha Wildner */ 66a28cd43dSSascha Wildner BMK_benchResult_t BMK_extract_benchResult(BMK_benchOutcome_t outcome); 67a28cd43dSSascha Wildner 68a28cd43dSSascha Wildner 69a28cd43dSSascha Wildner /*! BMK_benchFiles() -- called by zstdcli */ 70a28cd43dSSascha Wildner /* Loads files from fileNamesTable into memory, 71a28cd43dSSascha Wildner * and an optional dictionary from dictFileName (can be NULL), 72a28cd43dSSascha Wildner * then uses benchMem(). 73a28cd43dSSascha Wildner * fileNamesTable - name of files to benchmark. 74a28cd43dSSascha Wildner * nbFiles - number of files (size of fileNamesTable), must be > 0. 75a28cd43dSSascha Wildner * dictFileName - name of dictionary file to load. 76a28cd43dSSascha Wildner * cLevel - compression level to benchmark, errors if invalid. 77a28cd43dSSascha Wildner * compressionParams - advanced compression Parameters. 78a28cd43dSSascha Wildner * displayLevel - what gets printed: 79a28cd43dSSascha Wildner * 0 : no display; 80a28cd43dSSascha Wildner * 1 : errors; 81a28cd43dSSascha Wildner * 2 : + result + interaction + warnings; 82a28cd43dSSascha Wildner * 3 : + information; 83a28cd43dSSascha Wildner * 4 : + debug 84a28cd43dSSascha Wildner * @return: 85a28cd43dSSascha Wildner * a variant, which expresses either an error, or a valid result. 86a28cd43dSSascha Wildner * Use BMK_isSuccessful_benchOutcome() to check if function was successful. 87a28cd43dSSascha Wildner * If yes, extract the valid result with BMK_extract_benchResult(), 88a28cd43dSSascha Wildner * it will contain : 89a28cd43dSSascha Wildner * .cSpeed: compression speed in bytes per second, 90a28cd43dSSascha Wildner * .dSpeed: decompression speed in bytes per second, 91a28cd43dSSascha Wildner * .cSize : compressed size, in bytes 92a28cd43dSSascha Wildner * .cMem : memory budget required for the compression context 93a28cd43dSSascha Wildner */ 94a28cd43dSSascha Wildner BMK_benchOutcome_t BMK_benchFiles( 95a28cd43dSSascha Wildner const char* const * fileNamesTable, unsigned nbFiles, 96a28cd43dSSascha Wildner const char* dictFileName, 97a28cd43dSSascha Wildner int cLevel, const ZSTD_compressionParameters* compressionParams, 98a28cd43dSSascha Wildner int displayLevel); 99a28cd43dSSascha Wildner 100a28cd43dSSascha Wildner 101a28cd43dSSascha Wildner typedef enum { 102a28cd43dSSascha Wildner BMK_both = 0, 103a28cd43dSSascha Wildner BMK_decodeOnly = 1, 104a28cd43dSSascha Wildner BMK_compressOnly = 2 105a28cd43dSSascha Wildner } BMK_mode_t; 106a28cd43dSSascha Wildner 107a28cd43dSSascha Wildner typedef struct { 108a28cd43dSSascha Wildner BMK_mode_t mode; /* 0: all, 1: compress only 2: decode only */ 109a28cd43dSSascha Wildner unsigned nbSeconds; /* default timing is in nbSeconds */ 110a28cd43dSSascha Wildner size_t blockSize; /* Maximum size of each block*/ 111a28cd43dSSascha Wildner int nbWorkers; /* multithreading */ 112a28cd43dSSascha Wildner unsigned realTime; /* real time priority */ 113a28cd43dSSascha Wildner int additionalParam; /* used by python speed benchmark */ 114a28cd43dSSascha Wildner int ldmFlag; /* enables long distance matching */ 115a28cd43dSSascha Wildner int ldmMinMatch; /* below: parameters for long distance matching, see zstd.1.md */ 116a28cd43dSSascha Wildner int ldmHashLog; 117a28cd43dSSascha Wildner int ldmBucketSizeLog; 118a28cd43dSSascha Wildner int ldmHashRateLog; 119a28cd43dSSascha Wildner ZSTD_literalCompressionMode_e literalCompressionMode; 120a28cd43dSSascha Wildner } BMK_advancedParams_t; 121a28cd43dSSascha Wildner 122a28cd43dSSascha Wildner /* returns default parameters used by nonAdvanced functions */ 123a28cd43dSSascha Wildner BMK_advancedParams_t BMK_initAdvancedParams(void); 124a28cd43dSSascha Wildner 125a28cd43dSSascha Wildner /*! BMK_benchFilesAdvanced(): 126a28cd43dSSascha Wildner * Same as BMK_benchFiles(), 127a28cd43dSSascha Wildner * with more controls, provided through advancedParams_t structure */ 128a28cd43dSSascha Wildner BMK_benchOutcome_t BMK_benchFilesAdvanced( 129a28cd43dSSascha Wildner const char* const * fileNamesTable, unsigned nbFiles, 130a28cd43dSSascha Wildner const char* dictFileName, 131a28cd43dSSascha Wildner int cLevel, const ZSTD_compressionParameters* compressionParams, 132a28cd43dSSascha Wildner int displayLevel, const BMK_advancedParams_t* adv); 133a28cd43dSSascha Wildner 134a28cd43dSSascha Wildner /*! BMK_syntheticTest() -- called from zstdcli */ 135a28cd43dSSascha Wildner /* Generates a sample with datagen, using compressibility argument */ 136a28cd43dSSascha Wildner /* cLevel - compression level to benchmark, errors if invalid 137a28cd43dSSascha Wildner * compressibility - determines compressibility of sample 138a28cd43dSSascha Wildner * compressionParams - basic compression Parameters 139a28cd43dSSascha Wildner * displayLevel - see benchFiles 140a28cd43dSSascha Wildner * adv - see advanced_Params_t 141a28cd43dSSascha Wildner * @return: 142a28cd43dSSascha Wildner * a variant, which expresses either an error, or a valid result. 143a28cd43dSSascha Wildner * Use BMK_isSuccessful_benchOutcome() to check if function was successful. 144a28cd43dSSascha Wildner * If yes, extract the valid result with BMK_extract_benchResult(), 145a28cd43dSSascha Wildner * it will contain : 146a28cd43dSSascha Wildner * .cSpeed: compression speed in bytes per second, 147a28cd43dSSascha Wildner * .dSpeed: decompression speed in bytes per second, 148a28cd43dSSascha Wildner * .cSize : compressed size, in bytes 149a28cd43dSSascha Wildner * .cMem : memory budget required for the compression context 150a28cd43dSSascha Wildner */ 151a28cd43dSSascha Wildner BMK_benchOutcome_t BMK_syntheticTest( 152a28cd43dSSascha Wildner int cLevel, double compressibility, 153a28cd43dSSascha Wildner const ZSTD_compressionParameters* compressionParams, 154a28cd43dSSascha Wildner int displayLevel, const BMK_advancedParams_t* adv); 155a28cd43dSSascha Wildner 156a28cd43dSSascha Wildner 157a28cd43dSSascha Wildner 158a28cd43dSSascha Wildner /* === Benchmark Zstandard in a memory-to-memory scenario === */ 159a28cd43dSSascha Wildner 160a28cd43dSSascha Wildner /** BMK_benchMem() -- core benchmarking function, called in paramgrill 161a28cd43dSSascha Wildner * applies ZSTD_compress_generic() and ZSTD_decompress_generic() on data in srcBuffer 162a28cd43dSSascha Wildner * with specific compression parameters provided by other arguments using benchFunction 163a28cd43dSSascha Wildner * (cLevel, comprParams + adv in advanced Mode) */ 164a28cd43dSSascha Wildner /* srcBuffer - data source, expected to be valid compressed data if in Decode Only Mode 165a28cd43dSSascha Wildner * srcSize - size of data in srcBuffer 166a28cd43dSSascha Wildner * fileSizes - srcBuffer is considered cut into 1+ segments, to compress separately. 167a28cd43dSSascha Wildner * note : sum(fileSizes) must be == srcSize. (<== ensure it's properly checked) 168a28cd43dSSascha Wildner * nbFiles - nb of segments 169a28cd43dSSascha Wildner * cLevel - compression level 170a28cd43dSSascha Wildner * comprParams - basic compression parameters 171a28cd43dSSascha Wildner * dictBuffer - a dictionary if used, null otherwise 172a28cd43dSSascha Wildner * dictBufferSize - size of dictBuffer, 0 otherwise 173a28cd43dSSascha Wildner * displayLevel - see BMK_benchFiles 174a28cd43dSSascha Wildner * displayName - name used by display 175a28cd43dSSascha Wildner * @return: 176a28cd43dSSascha Wildner * a variant, which expresses either an error, or a valid result. 177a28cd43dSSascha Wildner * Use BMK_isSuccessful_benchOutcome() to check if function was successful. 178a28cd43dSSascha Wildner * If yes, extract the valid result with BMK_extract_benchResult(), 179a28cd43dSSascha Wildner * it will contain : 180a28cd43dSSascha Wildner * .cSpeed: compression speed in bytes per second, 181a28cd43dSSascha Wildner * .dSpeed: decompression speed in bytes per second, 182a28cd43dSSascha Wildner * .cSize : compressed size, in bytes 183a28cd43dSSascha Wildner * .cMem : memory budget required for the compression context 184a28cd43dSSascha Wildner */ 185a28cd43dSSascha Wildner BMK_benchOutcome_t BMK_benchMem(const void* srcBuffer, size_t srcSize, 186a28cd43dSSascha Wildner const size_t* fileSizes, unsigned nbFiles, 187a28cd43dSSascha Wildner int cLevel, const ZSTD_compressionParameters* comprParams, 188a28cd43dSSascha Wildner const void* dictBuffer, size_t dictBufferSize, 189a28cd43dSSascha Wildner int displayLevel, const char* displayName); 190a28cd43dSSascha Wildner 191a28cd43dSSascha Wildner 192a28cd43dSSascha Wildner /* BMK_benchMemAdvanced() : same as BMK_benchMem() 193a28cd43dSSascha Wildner * with following additional options : 194a28cd43dSSascha Wildner * dstBuffer - destination buffer to write compressed output in, NULL if none provided. 195a28cd43dSSascha Wildner * dstCapacity - capacity of destination buffer, give 0 if dstBuffer = NULL 196a28cd43dSSascha Wildner * adv = see advancedParams_t 197a28cd43dSSascha Wildner */ 198a28cd43dSSascha Wildner BMK_benchOutcome_t BMK_benchMemAdvanced(const void* srcBuffer, size_t srcSize, 199a28cd43dSSascha Wildner void* dstBuffer, size_t dstCapacity, 200a28cd43dSSascha Wildner const size_t* fileSizes, unsigned nbFiles, 201a28cd43dSSascha Wildner int cLevel, const ZSTD_compressionParameters* comprParams, 202a28cd43dSSascha Wildner const void* dictBuffer, size_t dictBufferSize, 203a28cd43dSSascha Wildner int displayLevel, const char* displayName, 204a28cd43dSSascha Wildner const BMK_advancedParams_t* adv); 205a28cd43dSSascha Wildner 206a28cd43dSSascha Wildner 207a28cd43dSSascha Wildner 208a28cd43dSSascha Wildner #endif /* BENCH_ZSTD_H_3242387 */ 209a28cd43dSSascha Wildner 210a28cd43dSSascha Wildner #if defined (__cplusplus) 211a28cd43dSSascha Wildner } 212a28cd43dSSascha Wildner #endif 213