contrib/python-zstandard/c-ext/compressionparams.c
changeset 42070 675775c33ab6
parent 40121 73fef626dae3
child 42937 69de49c4e39c
equal deleted inserted replaced
42069:668eff08387f 42070:675775c33ab6
     8 
     8 
     9 #include "python-zstandard.h"
     9 #include "python-zstandard.h"
    10 
    10 
    11 extern PyObject* ZstdError;
    11 extern PyObject* ZstdError;
    12 
    12 
    13 int set_parameter(ZSTD_CCtx_params* params, ZSTD_cParameter param, unsigned value) {
    13 int set_parameter(ZSTD_CCtx_params* params, ZSTD_cParameter param, int value) {
    14 	size_t zresult = ZSTD_CCtxParam_setParameter(params, param, value);
    14 	size_t zresult = ZSTD_CCtxParam_setParameter(params, param, value);
    15 	if (ZSTD_isError(zresult)) {
    15 	if (ZSTD_isError(zresult)) {
    16 		PyErr_Format(ZstdError, "unable to set compression context parameter: %s",
    16 		PyErr_Format(ZstdError, "unable to set compression context parameter: %s",
    17 			ZSTD_getErrorName(zresult));
    17 			ZSTD_getErrorName(zresult));
    18 		return 1;
    18 		return 1;
    21 	return 0;
    21 	return 0;
    22 }
    22 }
    23 
    23 
    24 #define TRY_SET_PARAMETER(params, param, value) if (set_parameter(params, param, value)) return -1;
    24 #define TRY_SET_PARAMETER(params, param, value) if (set_parameter(params, param, value)) return -1;
    25 
    25 
       
    26 #define TRY_COPY_PARAMETER(source, dest, param) { \
       
    27 	int result; \
       
    28 	size_t zresult = ZSTD_CCtxParam_getParameter(source, param, &result); \
       
    29 	if (ZSTD_isError(zresult)) { \
       
    30 		return 1; \
       
    31 	} \
       
    32 	zresult = ZSTD_CCtxParam_setParameter(dest, param, result); \
       
    33 	if (ZSTD_isError(zresult)) { \
       
    34 		return 1; \
       
    35 	} \
       
    36 }
       
    37 
    26 int set_parameters(ZSTD_CCtx_params* params, ZstdCompressionParametersObject* obj) {
    38 int set_parameters(ZSTD_CCtx_params* params, ZstdCompressionParametersObject* obj) {
    27 	TRY_SET_PARAMETER(params, ZSTD_p_format, obj->format);
    39 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_nbWorkers);
    28 	TRY_SET_PARAMETER(params, ZSTD_p_compressionLevel, (unsigned)obj->compressionLevel);
    40 
    29 	TRY_SET_PARAMETER(params, ZSTD_p_windowLog, obj->windowLog);
    41 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_format);
    30 	TRY_SET_PARAMETER(params, ZSTD_p_hashLog, obj->hashLog);
    42 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_compressionLevel);
    31 	TRY_SET_PARAMETER(params, ZSTD_p_chainLog, obj->chainLog);
    43 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_windowLog);
    32 	TRY_SET_PARAMETER(params, ZSTD_p_searchLog, obj->searchLog);
    44 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_hashLog);
    33 	TRY_SET_PARAMETER(params, ZSTD_p_minMatch, obj->minMatch);
    45 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_chainLog);
    34 	TRY_SET_PARAMETER(params, ZSTD_p_targetLength, obj->targetLength);
    46 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_searchLog);
    35 	TRY_SET_PARAMETER(params, ZSTD_p_compressionStrategy, obj->compressionStrategy);
    47 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_minMatch);
    36 	TRY_SET_PARAMETER(params, ZSTD_p_contentSizeFlag, obj->contentSizeFlag);
    48 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_targetLength);
    37 	TRY_SET_PARAMETER(params, ZSTD_p_checksumFlag, obj->checksumFlag);
    49 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_strategy);
    38 	TRY_SET_PARAMETER(params, ZSTD_p_dictIDFlag, obj->dictIDFlag);
    50 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_contentSizeFlag);
    39 	TRY_SET_PARAMETER(params, ZSTD_p_nbWorkers, obj->threads);
    51 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_checksumFlag);
    40 	TRY_SET_PARAMETER(params, ZSTD_p_jobSize, obj->jobSize);
    52 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_dictIDFlag);
    41 	TRY_SET_PARAMETER(params, ZSTD_p_overlapSizeLog, obj->overlapSizeLog);
    53 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_jobSize);
    42 	TRY_SET_PARAMETER(params, ZSTD_p_forceMaxWindow, obj->forceMaxWindow);
    54 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_overlapLog);
    43 	TRY_SET_PARAMETER(params, ZSTD_p_enableLongDistanceMatching, obj->enableLongDistanceMatching);
    55 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_forceMaxWindow);
    44 	TRY_SET_PARAMETER(params, ZSTD_p_ldmHashLog, obj->ldmHashLog);
    56 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_enableLongDistanceMatching);
    45 	TRY_SET_PARAMETER(params, ZSTD_p_ldmMinMatch, obj->ldmMinMatch);
    57 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_ldmHashLog);
    46 	TRY_SET_PARAMETER(params, ZSTD_p_ldmBucketSizeLog, obj->ldmBucketSizeLog);
    58 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_ldmMinMatch);
    47 	TRY_SET_PARAMETER(params, ZSTD_p_ldmHashEveryLog, obj->ldmHashEveryLog);
    59 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_ldmBucketSizeLog);
       
    60 	TRY_COPY_PARAMETER(obj->params, params, ZSTD_c_ldmHashRateLog);
    48 
    61 
    49 	return 0;
    62 	return 0;
    50 }
    63 }
    51 
    64 
    52 int reset_params(ZstdCompressionParametersObject* params) {
    65 int reset_params(ZstdCompressionParametersObject* params) {
    60 			return 1;
    73 			return 1;
    61 		}
    74 		}
    62 	}
    75 	}
    63 
    76 
    64 	return set_parameters(params->params, params);
    77 	return set_parameters(params->params, params);
       
    78 }
       
    79 
       
    80 #define TRY_GET_PARAMETER(params, param, value) { \
       
    81     size_t zresult = ZSTD_CCtxParam_getParameter(params, param, value); \
       
    82     if (ZSTD_isError(zresult)) { \
       
    83         PyErr_Format(ZstdError, "unable to retrieve parameter: %s", ZSTD_getErrorName(zresult)); \
       
    84         return 1; \
       
    85     } \
       
    86 }
       
    87 
       
    88 int to_cparams(ZstdCompressionParametersObject* params, ZSTD_compressionParameters* cparams) {
       
    89 	int value;
       
    90 
       
    91 	TRY_GET_PARAMETER(params->params, ZSTD_c_windowLog, &value);
       
    92 	cparams->windowLog = value;
       
    93 
       
    94 	TRY_GET_PARAMETER(params->params, ZSTD_c_chainLog, &value);
       
    95 	cparams->chainLog = value;
       
    96 
       
    97 	TRY_GET_PARAMETER(params->params, ZSTD_c_hashLog, &value);
       
    98 	cparams->hashLog = value;
       
    99 
       
   100 	TRY_GET_PARAMETER(params->params, ZSTD_c_searchLog, &value);
       
   101 	cparams->searchLog = value;
       
   102 
       
   103 	TRY_GET_PARAMETER(params->params, ZSTD_c_minMatch, &value);
       
   104 	cparams->minMatch = value;
       
   105 
       
   106 	TRY_GET_PARAMETER(params->params, ZSTD_c_targetLength, &value);
       
   107 	cparams->targetLength = value;
       
   108 
       
   109 	TRY_GET_PARAMETER(params->params, ZSTD_c_strategy, &value);
       
   110 	cparams->strategy = value;
       
   111 
       
   112 	return 0;
    65 }
   113 }
    66 
   114 
    67 static int ZstdCompressionParameters_init(ZstdCompressionParametersObject* self, PyObject* args, PyObject* kwargs) {
   115 static int ZstdCompressionParameters_init(ZstdCompressionParametersObject* self, PyObject* args, PyObject* kwargs) {
    68 	static char* kwlist[] = {
   116 	static char* kwlist[] = {
    69 		"format",
   117 		"format",
    73 		"chain_log",
   121 		"chain_log",
    74 		"search_log",
   122 		"search_log",
    75 		"min_match",
   123 		"min_match",
    76 		"target_length",
   124 		"target_length",
    77 		"compression_strategy",
   125 		"compression_strategy",
       
   126 		"strategy",
    78 		"write_content_size",
   127 		"write_content_size",
    79 		"write_checksum",
   128 		"write_checksum",
    80 		"write_dict_id",
   129 		"write_dict_id",
    81 		"job_size",
   130 		"job_size",
       
   131 		"overlap_log",
    82 		"overlap_size_log",
   132 		"overlap_size_log",
    83 		"force_max_window",
   133 		"force_max_window",
    84 		"enable_ldm",
   134 		"enable_ldm",
    85 		"ldm_hash_log",
   135 		"ldm_hash_log",
    86 		"ldm_min_match",
   136 		"ldm_min_match",
    87 		"ldm_bucket_size_log",
   137 		"ldm_bucket_size_log",
       
   138 		"ldm_hash_rate_log",
    88 		"ldm_hash_every_log",
   139 		"ldm_hash_every_log",
    89 		"threads",
   140 		"threads",
    90 		NULL
   141 		NULL
    91 	};
   142 	};
    92 
   143 
    93 	unsigned format = 0;
   144 	int format = 0;
    94 	int compressionLevel = 0;
   145 	int compressionLevel = 0;
    95 	unsigned windowLog = 0;
   146 	int windowLog = 0;
    96 	unsigned hashLog = 0;
   147 	int hashLog = 0;
    97 	unsigned chainLog = 0;
   148 	int chainLog = 0;
    98 	unsigned searchLog = 0;
   149 	int searchLog = 0;
    99 	unsigned minMatch = 0;
   150 	int minMatch = 0;
   100 	unsigned targetLength = 0;
   151 	int targetLength = 0;
   101 	unsigned compressionStrategy = 0;
   152 	int compressionStrategy = -1;
   102 	unsigned contentSizeFlag = 1;
   153 	int strategy = -1;
   103 	unsigned checksumFlag = 0;
   154 	int contentSizeFlag = 1;
   104 	unsigned dictIDFlag = 0;
   155 	int checksumFlag = 0;
   105 	unsigned jobSize = 0;
   156 	int dictIDFlag = 0;
   106 	unsigned overlapSizeLog = 0;
   157 	int jobSize = 0;
   107 	unsigned forceMaxWindow = 0;
   158 	int overlapLog = -1;
   108 	unsigned enableLDM = 0;
   159 	int overlapSizeLog = -1;
   109 	unsigned ldmHashLog = 0;
   160 	int forceMaxWindow = 0;
   110 	unsigned ldmMinMatch = 0;
   161 	int enableLDM = 0;
   111 	unsigned ldmBucketSizeLog = 0;
   162 	int ldmHashLog = 0;
   112 	unsigned ldmHashEveryLog = 0;
   163 	int ldmMinMatch = 0;
       
   164 	int ldmBucketSizeLog = 0;
       
   165 	int ldmHashRateLog = -1;
       
   166 	int ldmHashEveryLog = -1;
   113 	int threads = 0;
   167 	int threads = 0;
   114 
   168 
   115 	if (!PyArg_ParseTupleAndKeywords(args, kwargs,
   169 	if (!PyArg_ParseTupleAndKeywords(args, kwargs,
   116 		"|IiIIIIIIIIIIIIIIIIIIi:CompressionParameters",
   170 		"|iiiiiiiiiiiiiiiiiiiiiiii:CompressionParameters",
   117 		kwlist, &format, &compressionLevel, &windowLog, &hashLog, &chainLog,
   171 		kwlist, &format, &compressionLevel, &windowLog, &hashLog, &chainLog,
   118 		&searchLog, &minMatch, &targetLength, &compressionStrategy,
   172 		&searchLog, &minMatch, &targetLength, &compressionStrategy, &strategy,
   119 		&contentSizeFlag, &checksumFlag, &dictIDFlag, &jobSize, &overlapSizeLog,
   173 		&contentSizeFlag, &checksumFlag, &dictIDFlag, &jobSize, &overlapLog,
   120 		&forceMaxWindow, &enableLDM, &ldmHashLog, &ldmMinMatch, &ldmBucketSizeLog,
   174 		&overlapSizeLog, &forceMaxWindow, &enableLDM, &ldmHashLog, &ldmMinMatch,
   121 		&ldmHashEveryLog, &threads)) {
   175 		&ldmBucketSizeLog, &ldmHashRateLog, &ldmHashEveryLog, &threads)) {
       
   176 		return -1;
       
   177 	}
       
   178 
       
   179 	if (reset_params(self)) {
   122 		return -1;
   180 		return -1;
   123 	}
   181 	}
   124 
   182 
   125 	if (threads < 0) {
   183 	if (threads < 0) {
   126 		threads = cpu_count();
   184 		threads = cpu_count();
   127 	}
   185 	}
   128 
   186 
   129 	self->format = format;
   187 	/* We need to set ZSTD_c_nbWorkers before ZSTD_c_jobSize and ZSTD_c_overlapLog
   130 	self->compressionLevel = compressionLevel;
   188 	 * because setting ZSTD_c_nbWorkers resets the other parameters. */
   131 	self->windowLog = windowLog;
   189 	TRY_SET_PARAMETER(self->params, ZSTD_c_nbWorkers, threads);
   132 	self->hashLog = hashLog;
   190 
   133 	self->chainLog = chainLog;
   191 	TRY_SET_PARAMETER(self->params, ZSTD_c_format, format);
   134 	self->searchLog = searchLog;
   192 	TRY_SET_PARAMETER(self->params, ZSTD_c_compressionLevel, compressionLevel);
   135 	self->minMatch = minMatch;
   193 	TRY_SET_PARAMETER(self->params, ZSTD_c_windowLog, windowLog);
   136 	self->targetLength = targetLength;
   194 	TRY_SET_PARAMETER(self->params, ZSTD_c_hashLog, hashLog);
   137 	self->compressionStrategy = compressionStrategy;
   195 	TRY_SET_PARAMETER(self->params, ZSTD_c_chainLog, chainLog);
   138 	self->contentSizeFlag = contentSizeFlag;
   196 	TRY_SET_PARAMETER(self->params, ZSTD_c_searchLog, searchLog);
   139 	self->checksumFlag = checksumFlag;
   197 	TRY_SET_PARAMETER(self->params, ZSTD_c_minMatch, minMatch);
   140 	self->dictIDFlag = dictIDFlag;
   198 	TRY_SET_PARAMETER(self->params, ZSTD_c_targetLength, targetLength);
   141 	self->threads = threads;
   199 
   142 	self->jobSize = jobSize;
   200 	if (compressionStrategy != -1 && strategy != -1) {
   143 	self->overlapSizeLog = overlapSizeLog;
   201 		PyErr_SetString(PyExc_ValueError, "cannot specify both compression_strategy and strategy");
   144 	self->forceMaxWindow = forceMaxWindow;
       
   145 	self->enableLongDistanceMatching = enableLDM;
       
   146 	self->ldmHashLog = ldmHashLog;
       
   147 	self->ldmMinMatch = ldmMinMatch;
       
   148 	self->ldmBucketSizeLog = ldmBucketSizeLog;
       
   149 	self->ldmHashEveryLog = ldmHashEveryLog;
       
   150 
       
   151 	if (reset_params(self)) {
       
   152 		return -1;
   202 		return -1;
   153 	}
   203     }
       
   204 
       
   205 	if (compressionStrategy != -1) {
       
   206 		strategy = compressionStrategy;
       
   207 	}
       
   208 	else if (strategy == -1) {
       
   209 		strategy = 0;
       
   210 	}
       
   211 
       
   212 	TRY_SET_PARAMETER(self->params, ZSTD_c_strategy, strategy);
       
   213 	TRY_SET_PARAMETER(self->params, ZSTD_c_contentSizeFlag, contentSizeFlag);
       
   214 	TRY_SET_PARAMETER(self->params, ZSTD_c_checksumFlag, checksumFlag);
       
   215 	TRY_SET_PARAMETER(self->params, ZSTD_c_dictIDFlag, dictIDFlag);
       
   216 	TRY_SET_PARAMETER(self->params, ZSTD_c_jobSize, jobSize);
       
   217 
       
   218 	if (overlapLog != -1 && overlapSizeLog != -1) {
       
   219 		PyErr_SetString(PyExc_ValueError, "cannot specify both overlap_log and overlap_size_log");
       
   220 		return -1;
       
   221 	}
       
   222 
       
   223 	if (overlapSizeLog != -1) {
       
   224 		overlapLog = overlapSizeLog;
       
   225 	}
       
   226 	else if (overlapLog == -1) {
       
   227 		overlapLog = 0;
       
   228 	}
       
   229 
       
   230 	TRY_SET_PARAMETER(self->params, ZSTD_c_overlapLog, overlapLog);
       
   231 	TRY_SET_PARAMETER(self->params, ZSTD_c_forceMaxWindow, forceMaxWindow);
       
   232 	TRY_SET_PARAMETER(self->params, ZSTD_c_enableLongDistanceMatching, enableLDM);
       
   233 	TRY_SET_PARAMETER(self->params, ZSTD_c_ldmHashLog, ldmHashLog);
       
   234 	TRY_SET_PARAMETER(self->params, ZSTD_c_ldmMinMatch, ldmMinMatch);
       
   235 	TRY_SET_PARAMETER(self->params, ZSTD_c_ldmBucketSizeLog, ldmBucketSizeLog);
       
   236 
       
   237 	if (ldmHashRateLog != -1 && ldmHashEveryLog != -1) {
       
   238 		PyErr_SetString(PyExc_ValueError, "cannot specify both ldm_hash_rate_log and ldm_hash_everyLog");
       
   239 		return -1;
       
   240 	}
       
   241 
       
   242 	if (ldmHashEveryLog != -1) {
       
   243 		ldmHashRateLog = ldmHashEveryLog;
       
   244 	}
       
   245 	else if (ldmHashRateLog == -1) {
       
   246 		ldmHashRateLog = 0;
       
   247 	}
       
   248 
       
   249 	TRY_SET_PARAMETER(self->params, ZSTD_c_ldmHashRateLog, ldmHashRateLog);
   154 
   250 
   155 	return 0;
   251 	return 0;
   156 }
   252 }
   157 
   253 
   158 PyDoc_STRVAR(ZstdCompressionParameters_from_level__doc__,
   254 PyDoc_STRVAR(ZstdCompressionParameters_from_level__doc__,
   257 		Py_DECREF(val);
   353 		Py_DECREF(val);
   258 	}
   354 	}
   259 
   355 
   260 	val = PyDict_GetItemString(kwargs, "min_match");
   356 	val = PyDict_GetItemString(kwargs, "min_match");
   261 	if (!val) {
   357 	if (!val) {
   262 		val = PyLong_FromUnsignedLong(params.searchLength);
   358 		val = PyLong_FromUnsignedLong(params.minMatch);
   263 		if (!val) {
   359 		if (!val) {
   264 			goto cleanup;
   360 			goto cleanup;
   265 		}
   361 		}
   266 		PyDict_SetItemString(kwargs, "min_match", val);
   362 		PyDict_SetItemString(kwargs, "min_match", val);
   267 		Py_DECREF(val);
   363 		Py_DECREF(val);
   333 		self->params = NULL;
   429 		self->params = NULL;
   334 	}
   430 	}
   335 
   431 
   336 	PyObject_Del(self);
   432 	PyObject_Del(self);
   337 }
   433 }
       
   434 
       
   435 #define PARAM_GETTER(name, param) PyObject* ZstdCompressionParameters_get_##name(PyObject* self, void* unused) { \
       
   436     int result; \
       
   437     size_t zresult; \
       
   438     ZstdCompressionParametersObject* p = (ZstdCompressionParametersObject*)(self); \
       
   439     zresult = ZSTD_CCtxParam_getParameter(p->params, param, &result); \
       
   440     if (ZSTD_isError(zresult)) { \
       
   441         PyErr_Format(ZstdError, "unable to get compression parameter: %s", \
       
   442             ZSTD_getErrorName(zresult)); \
       
   443         return NULL; \
       
   444     } \
       
   445     return PyLong_FromLong(result); \
       
   446 }
       
   447 
       
   448 PARAM_GETTER(format, ZSTD_c_format)
       
   449 PARAM_GETTER(compression_level, ZSTD_c_compressionLevel)
       
   450 PARAM_GETTER(window_log, ZSTD_c_windowLog)
       
   451 PARAM_GETTER(hash_log, ZSTD_c_hashLog)
       
   452 PARAM_GETTER(chain_log, ZSTD_c_chainLog)
       
   453 PARAM_GETTER(search_log, ZSTD_c_searchLog)
       
   454 PARAM_GETTER(min_match, ZSTD_c_minMatch)
       
   455 PARAM_GETTER(target_length, ZSTD_c_targetLength)
       
   456 PARAM_GETTER(compression_strategy, ZSTD_c_strategy)
       
   457 PARAM_GETTER(write_content_size, ZSTD_c_contentSizeFlag)
       
   458 PARAM_GETTER(write_checksum, ZSTD_c_checksumFlag)
       
   459 PARAM_GETTER(write_dict_id, ZSTD_c_dictIDFlag)
       
   460 PARAM_GETTER(job_size, ZSTD_c_jobSize)
       
   461 PARAM_GETTER(overlap_log, ZSTD_c_overlapLog)
       
   462 PARAM_GETTER(force_max_window, ZSTD_c_forceMaxWindow)
       
   463 PARAM_GETTER(enable_ldm, ZSTD_c_enableLongDistanceMatching)
       
   464 PARAM_GETTER(ldm_hash_log, ZSTD_c_ldmHashLog)
       
   465 PARAM_GETTER(ldm_min_match, ZSTD_c_ldmMinMatch)
       
   466 PARAM_GETTER(ldm_bucket_size_log, ZSTD_c_ldmBucketSizeLog)
       
   467 PARAM_GETTER(ldm_hash_rate_log, ZSTD_c_ldmHashRateLog)
       
   468 PARAM_GETTER(threads, ZSTD_c_nbWorkers)
   338 
   469 
   339 static PyMethodDef ZstdCompressionParameters_methods[] = {
   470 static PyMethodDef ZstdCompressionParameters_methods[] = {
   340 	{
   471 	{
   341 		"from_level",
   472 		"from_level",
   342 		(PyCFunction)CompressionParameters_from_level,
   473 		(PyCFunction)CompressionParameters_from_level,
   350 		ZstdCompressionParameters_estimated_compression_context_size__doc__
   481 		ZstdCompressionParameters_estimated_compression_context_size__doc__
   351 	},
   482 	},
   352 	{ NULL, NULL }
   483 	{ NULL, NULL }
   353 };
   484 };
   354 
   485 
   355 static PyMemberDef ZstdCompressionParameters_members[] = {
   486 #define GET_SET_ENTRY(name) { #name, ZstdCompressionParameters_get_##name, NULL, NULL, NULL }
   356 	{ "format", T_UINT,
   487 
   357 	  offsetof(ZstdCompressionParametersObject, format), READONLY,
   488 static PyGetSetDef ZstdCompressionParameters_getset[] = {
   358 	  "compression format" },
   489 	GET_SET_ENTRY(format),
   359 	{ "compression_level", T_INT,
   490 	GET_SET_ENTRY(compression_level),
   360 	  offsetof(ZstdCompressionParametersObject, compressionLevel), READONLY,
   491 	GET_SET_ENTRY(window_log),
   361 	  "compression level" },
   492 	GET_SET_ENTRY(hash_log),
   362 	{ "window_log", T_UINT,
   493 	GET_SET_ENTRY(chain_log),
   363 	  offsetof(ZstdCompressionParametersObject, windowLog), READONLY,
   494 	GET_SET_ENTRY(search_log),
   364 	  "window log" },
   495 	GET_SET_ENTRY(min_match),
   365 	{ "hash_log", T_UINT,
   496 	GET_SET_ENTRY(target_length),
   366 	  offsetof(ZstdCompressionParametersObject, hashLog), READONLY,
   497 	GET_SET_ENTRY(compression_strategy),
   367 	  "hash log" },
   498 	GET_SET_ENTRY(write_content_size),
   368 	{ "chain_log", T_UINT,
   499 	GET_SET_ENTRY(write_checksum),
   369 	  offsetof(ZstdCompressionParametersObject, chainLog), READONLY,
   500 	GET_SET_ENTRY(write_dict_id),
   370 	  "chain log" },
   501 	GET_SET_ENTRY(threads),
   371 	{ "search_log", T_UINT,
   502 	GET_SET_ENTRY(job_size),
   372 	  offsetof(ZstdCompressionParametersObject, searchLog), READONLY,
   503 	GET_SET_ENTRY(overlap_log),
   373 	  "search log" },
   504 	/* TODO remove this deprecated attribute */
   374 	{ "min_match", T_UINT,
   505 	{ "overlap_size_log", ZstdCompressionParameters_get_overlap_log, NULL, NULL, NULL },
   375 	  offsetof(ZstdCompressionParametersObject, minMatch), READONLY,
   506 	GET_SET_ENTRY(force_max_window),
   376 	  "search length" },
   507 	GET_SET_ENTRY(enable_ldm),
   377 	{ "target_length", T_UINT,
   508 	GET_SET_ENTRY(ldm_hash_log),
   378 	  offsetof(ZstdCompressionParametersObject, targetLength), READONLY,
   509 	GET_SET_ENTRY(ldm_min_match),
   379 	  "target length" },
   510 	GET_SET_ENTRY(ldm_bucket_size_log),
   380 	{ "compression_strategy", T_UINT,
   511 	GET_SET_ENTRY(ldm_hash_rate_log),
   381 	  offsetof(ZstdCompressionParametersObject, compressionStrategy), READONLY,
   512 	/* TODO remove this deprecated attribute */
   382 	  "compression strategy" },
   513 	{ "ldm_hash_every_log", ZstdCompressionParameters_get_ldm_hash_rate_log, NULL, NULL, NULL },
   383 	{ "write_content_size", T_UINT,
       
   384 	  offsetof(ZstdCompressionParametersObject, contentSizeFlag), READONLY,
       
   385 	  "whether to write content size in frames" },
       
   386 	{ "write_checksum", T_UINT,
       
   387 	  offsetof(ZstdCompressionParametersObject, checksumFlag), READONLY,
       
   388 	  "whether to write checksum in frames" },
       
   389 	{ "write_dict_id", T_UINT,
       
   390 	  offsetof(ZstdCompressionParametersObject, dictIDFlag), READONLY,
       
   391 	  "whether to write dictionary ID in frames" },
       
   392 	{ "threads", T_UINT,
       
   393 	  offsetof(ZstdCompressionParametersObject, threads), READONLY,
       
   394 	  "number of threads to use" },
       
   395 	{ "job_size", T_UINT,
       
   396 	  offsetof(ZstdCompressionParametersObject, jobSize), READONLY,
       
   397 	  "size of compression job when using multiple threads" },
       
   398 	{ "overlap_size_log", T_UINT,
       
   399 	  offsetof(ZstdCompressionParametersObject, overlapSizeLog), READONLY,
       
   400 	  "Size of previous input reloaded at the beginning of each job" },
       
   401 	{ "force_max_window", T_UINT,
       
   402 	  offsetof(ZstdCompressionParametersObject, forceMaxWindow), READONLY,
       
   403 	  "force back references to remain smaller than window size" },
       
   404 	{ "enable_ldm", T_UINT,
       
   405 	  offsetof(ZstdCompressionParametersObject, enableLongDistanceMatching), READONLY,
       
   406 	  "whether to enable long distance matching" },
       
   407 	{ "ldm_hash_log", T_UINT,
       
   408 	  offsetof(ZstdCompressionParametersObject, ldmHashLog), READONLY,
       
   409 	  "Size of the table for long distance matching, as a power of 2" },
       
   410 	{ "ldm_min_match", T_UINT,
       
   411 	  offsetof(ZstdCompressionParametersObject, ldmMinMatch), READONLY,
       
   412 	  "minimum size of searched matches for long distance matcher" },
       
   413 	{ "ldm_bucket_size_log", T_UINT,
       
   414 	  offsetof(ZstdCompressionParametersObject, ldmBucketSizeLog), READONLY,
       
   415 	  "log size of each bucket in the LDM hash table for collision resolution" },
       
   416 	{ "ldm_hash_every_log", T_UINT,
       
   417 	  offsetof(ZstdCompressionParametersObject, ldmHashEveryLog), READONLY,
       
   418 	  "frequency of inserting/looking up entries in the LDM hash table" },
       
   419 	{ NULL }
   514 	{ NULL }
   420 };
   515 };
   421 
   516 
   422 PyTypeObject ZstdCompressionParametersType = {
   517 PyTypeObject ZstdCompressionParametersType = {
   423 	PyVarObject_HEAD_INIT(NULL, 0)
   518 	PyVarObject_HEAD_INIT(NULL, 0)
   446 	0,                         /* tp_richcompare */
   541 	0,                         /* tp_richcompare */
   447 	0,                         /* tp_weaklistoffset */
   542 	0,                         /* tp_weaklistoffset */
   448 	0,                         /* tp_iter */
   543 	0,                         /* tp_iter */
   449 	0,                         /* tp_iternext */
   544 	0,                         /* tp_iternext */
   450 	ZstdCompressionParameters_methods, /* tp_methods */
   545 	ZstdCompressionParameters_methods, /* tp_methods */
   451 	ZstdCompressionParameters_members, /* tp_members */
   546 	0,                          /* tp_members */
   452 	0,                         /* tp_getset */
   547 	ZstdCompressionParameters_getset,  /* tp_getset */
   453 	0,                         /* tp_base */
   548 	0,                         /* tp_base */
   454 	0,                         /* tp_dict */
   549 	0,                         /* tp_dict */
   455 	0,                         /* tp_descr_get */
   550 	0,                         /* tp_descr_get */
   456 	0,                         /* tp_descr_set */
   551 	0,                         /* tp_descr_set */
   457 	0,                         /* tp_dictoffset */
   552 	0,                         /* tp_dictoffset */