gh-115988: Add ARM64 and RISCV BCJ filters constants in lzma module (GH-115989)

---------

Signed-off-by: Chien Wong <m@xv97.com>
Co-authored-by: Gregory P. Smith <greg@krypto.org>
This commit is contained in:
Chien Wong 2026-05-28 23:05:03 +08:00 committed by GitHub
parent f386f1feed
commit cf2cd0be82
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
6 changed files with 57 additions and 7 deletions

View file

@ -356,12 +356,26 @@ options. Valid filter IDs are as follows:
* Branch-Call-Jump (BCJ) filters:
* :const:`FILTER_X86`
* :const:`FILTER_IA64`
* :const:`FILTER_ARM`
* :const:`FILTER_ARMTHUMB`
* :const:`FILTER_POWERPC`
* :const:`FILTER_SPARC`
* :const:`!FILTER_X86`
* :const:`!FILTER_IA64`
* :const:`!FILTER_ARM`
* :const:`!FILTER_ARMTHUMB`
* :const:`!FILTER_POWERPC`
* :const:`!FILTER_SPARC`
The above work on all lzma runtime library versions.
* :const:`!FILTER_ARM64`
Only works if the lzma version is 5.4.0 or later.
.. versionadded:: next
* :const:`!FILTER_RISCV`
Only works if the lzma version is 5.6.0 or later.
.. versionadded:: next
A filter chain can consist of up to 4 filters, and cannot be empty. The last
filter in the chain must be a compression filter, and any other filters must be

View file

@ -93,6 +93,15 @@ gzip
which is passed on to the constructor of the :class:`~gzip.GzipFile` class.
(Contributed by Marin Misur in :gh:`91372`.)
lzma
----
* Add support of new BCJ filters ARM64 and RISC-V via
:const:`!lzma.FILTER_ARM64` and :const:`!lzma.FILTER_RISCV`. Note that the
new filters will work only if runtime library supports them. ARM64 filter
requires ``lzma`` 5.4.0 or newer while RISC-V requires 5.6.0 or newer.
(Contributed by Chien Wong in :gh:`115988`.)
os
--

View file

@ -13,6 +13,7 @@
"CHECK_ID_MAX", "CHECK_UNKNOWN",
"FILTER_LZMA1", "FILTER_LZMA2", "FILTER_DELTA", "FILTER_X86", "FILTER_IA64",
"FILTER_ARM", "FILTER_ARMTHUMB", "FILTER_POWERPC", "FILTER_SPARC",
"FILTER_ARM64", "FILTER_RISCV",
"FORMAT_AUTO", "FORMAT_XZ", "FORMAT_ALONE", "FORMAT_RAW",
"MF_HC3", "MF_HC4", "MF_BT2", "MF_BT3", "MF_BT4",
"MODE_FAST", "MODE_NORMAL", "PRESET_DEFAULT", "PRESET_EXTREME",

View file

@ -383,6 +383,12 @@ def test_uninitialized_LZMADecompressor_crash(self):
self.assertEqual(LZMADecompressor.__new__(LZMADecompressor).
decompress(bytes()), b'')
def test_riscv_filter_constant_exists(self):
self.assertTrue(lzma.FILTER_RISCV)
def test_arm64_filter_constant_exists(self):
self.assertTrue(lzma.FILTER_ARM64)
class CompressDecompressFunctionTestCase(unittest.TestCase):

View file

@ -0,0 +1 @@
:mod:`lzma` adds constants to support the newer BCJ filters for ARM64 and RISC-V.

View file

@ -26,6 +26,19 @@
#error "The maximum block size accepted by liblzma is SIZE_MAX."
#endif
/*
* If the lzma.h we're building against is so old as not to define these, this
* provides their equivalent values so that the names remain defined in Python
* regardless of the header versions used at build time.
*/
#ifndef LZMA_FILTER_ARM64
#define LZMA_FILTER_ARM64 LZMA_VLI_C(0x0A)
#endif
#ifndef LZMA_FILTER_RISCV
#define LZMA_FILTER_RISCV LZMA_VLI_C(0x0B)
#endif
/* On success, return value >= 0
On failure, return -1 */
static inline Py_ssize_t
@ -373,6 +386,8 @@ lzma_filter_converter(_lzma_state *state, PyObject *spec, void *ptr)
case LZMA_FILTER_ARM:
case LZMA_FILTER_ARMTHUMB:
case LZMA_FILTER_SPARC:
case LZMA_FILTER_ARM64:
case LZMA_FILTER_RISCV:
f->options = parse_filter_spec_bcj(state, spec);
return f->options != NULL;
default:
@ -491,7 +506,9 @@ build_filter_spec(const lzma_filter *f)
case LZMA_FILTER_IA64:
case LZMA_FILTER_ARM:
case LZMA_FILTER_ARMTHUMB:
case LZMA_FILTER_SPARC: {
case LZMA_FILTER_SPARC:
case LZMA_FILTER_ARM64:
case LZMA_FILTER_RISCV: {
lzma_options_bcj *options = f->options;
if (options) {
ADD_FIELD(options, start_offset);
@ -1544,6 +1561,8 @@ lzma_exec(PyObject *module)
ADD_INT_PREFIX_MACRO(module, FILTER_ARMTHUMB);
ADD_INT_PREFIX_MACRO(module, FILTER_SPARC);
ADD_INT_PREFIX_MACRO(module, FILTER_POWERPC);
ADD_INT_PREFIX_MACRO(module, FILTER_ARM64);
ADD_INT_PREFIX_MACRO(module, FILTER_RISCV);
ADD_INT_PREFIX_MACRO(module, MF_HC3);
ADD_INT_PREFIX_MACRO(module, MF_HC4);
ADD_INT_PREFIX_MACRO(module, MF_BT2);