[med-svn] [Git][med-team/htscodecs][master] 6 commits: New upstream version 1.5.2
Étienne Mollier (@emollier)
gitlab at salsa.debian.org
Mon Oct 23 20:54:32 BST 2023
Étienne Mollier pushed to branch master at Debian Med / htscodecs
Commits:
d6a42009 by Étienne Mollier at 2023-10-23T20:50:29+02:00
New upstream version 1.5.2
- - - - -
9a3603f0 by Étienne Mollier at 2023-10-23T20:50:29+02:00
routine-update: New upstream version
- - - - -
8ea79ae9 by Étienne Mollier at 2023-10-23T20:50:36+02:00
Update upstream source from tag 'upstream/1.5.2'
Update to upstream version '1.5.2'
with Debian dir e7a62c4d723084172f2aef95c9996ef5dfddbac6
- - - - -
b5081388 by Étienne Mollier at 2023-10-23T21:43:34+02:00
d/clean: cleanup multiple build artifacts.
Closes: #1048106
- - - - -
8723063d by Étienne Mollier at 2023-10-23T21:44:46+02:00
d/rules: make test artifacts cleanup more targeted.
Closes: #1049483
- - - - -
35ef8a0b by Étienne Mollier at 2023-10-23T21:53:10+02:00
ready to upload to unstable.
- - - - -
21 changed files:
- .cirrus.yml
- NEWS.md
- configure.ac
- debian/changelog
- + debian/clean
- debian/rules
- htscodecs/arith_dynamic.c
- htscodecs/c_range_coder.h
- htscodecs/fqzcomp_qual.c
- htscodecs/htscodecs.h
- htscodecs/rANS_static.c
- htscodecs/rANS_static16_int.h
- htscodecs/rANS_static32x16pr_avx2.c
- htscodecs/rANS_static32x16pr_sse4.c
- htscodecs/rANS_static4x16pr.c
- htscodecs/tokenise_name3.c
- htscodecs/varint.h
- tests/arith_dynamic_test.c
- tests/rANS_static4x16pr_test.c
- tests/rANS_static_test.c
- tests/tokenise_name3_test.c
Changes:
=====================================
.cirrus.yml
=====================================
@@ -156,7 +156,7 @@ task:
task:
name: freebsd
freebsd_instance:
- image_family: freebsd-13-1
+ image_family: freebsd-13-2
pkginstall_script:
- pkg update -f
=====================================
NEWS.md
=====================================
@@ -1,3 +1,65 @@
+Release 1.5.2: 6th October 2023
+-------------------------------
+
+*** SECURITY FIXES ***
+
+This release contains multiple bug fixes, including a couple
+buffer overruns that could corrupt memory when used in specific
+scenarios. These have not been observed with real data, but could
+represent an attack vector for a malicious user. (We know of no
+exploit.)
+
+
+Changes
+
+- The range coder has been extended to do bounds checking if the
+ new RC_SetOutputEnd() is called. This has a small performance hit
+ for the encoder, depending on compiler, but tests showed within 10%
+ at worst.
+
+Bug fixes
+
+- Fix write-buffer overruns in fqzcomp and name tokeniser.
+
+ SECURITY ISSUE: FQZComp could overflow the computed maximum growth
+ size, causing writes beyond the ends of the allocated memory. This
+ is triggered by many very small 1bp reads. Fixed the maximum
+ bounds for compressed data.
+
+ SECURITY ISSUE: The name tokeniser using the maximum number of
+ tokens (128) would erroneously write a 129th token. This is a
+ restricted overflow of a few bytes.
+
+ (PR#97, reported by Shubham Chandak)
+
+- Fix an maximum 8-byte read overflow in the AVX2 rans decoder.
+ SECURITY ISSUE: This was only present when using gcc.
+ (PR#100, reported by Rob Davies)
+
+- The rANS Order-1 SSE4 decoder could decode incorrectly.
+ When a single symbol only occurs and we're using 12-bit freqs, the
+ frequency of 4096 was interpreted as freq 0. This only happens in
+ the non-SIMD tidy-up stage at the end of the decode, so at worst the
+ final 31 bytes may be incorrect. (PR#102)
+
+- Fixed a 1-byte heap read-buffer overflow. Existed since 6a87ead2
+ (Oct 2021). Low severity security due to size and high likelihood
+ it's just malloc meta-data. (PR#95; OSS-Fuzz 62270)
+
+- rans_compress_4x16 now works on zero length input.
+ Previously this was giving divide-by-zero errors.
+ (PR#101, reported by Shubham Chandak)
+
+- Remove asserts which caused warnings about unused variables when
+ building with -DNDEBUG.
+
+- Fix ARM builds when HWCAP_ASIMD is missing (on Conda) (PR#91)
+
+- Improve FreeBSD CI testing
+
+- Fix undefined behaviour from signed bit-shifting (PR#90).
+
+
Release 1.5.1: 19th July 2023
-----------------------------
=====================================
configure.ac
=====================================
@@ -1,5 +1,5 @@
dnl Process this file with autoconf to produce a configure script.
-AC_INIT(htscodecs, 1.5.1)
+AC_INIT(htscodecs, 1.5.2)
# Some functions benefit from -O3 optimisation, so if the user didn't
# explicitly set any compiler flags, we'll plump for O3.
@@ -61,7 +61,7 @@ AM_EXTRA_RECURSIVE_TARGETS([fuzz])
# libhtscodecs.so.1.1.0
VERS_CURRENT=3
-VERS_REVISION=3
+VERS_REVISION=4
VERS_AGE=1
AC_SUBST(VERS_CURRENT)
AC_SUBST(VERS_REVISION)
=====================================
debian/changelog
=====================================
@@ -1,3 +1,11 @@
+htscodecs (1.5.2-1) unstable; urgency=medium
+
+ * New upstream version 1.5.2
+ * d/clean: cleanup multiple build artifacts. (Closes: #1048106)
+ * d/rules: make test artifacts cleanup more targeted. (Closes: #1049483)
+
+ -- Étienne Mollier <emollier at debian.org> Mon, 23 Oct 2023 21:52:19 +0200
+
htscodecs (1.5.1-1) unstable; urgency=medium
* New upstream version
=====================================
debian/clean
=====================================
@@ -0,0 +1,10 @@
+htscodecs/Makefile
+htscodecs/version.h
+htscodecs/.libs/
+htscodecs/*.o
+htscodecs/*.la
+Makefile
+config.*
+libtool
+stamp-h1
+tests/*.trs
=====================================
debian/rules
=====================================
@@ -46,7 +46,8 @@ ifeq (,$(filter nocheck,$(DEB_BUILD_OPTIONS)))
endif
override_dh_installexamples:
- rm -Rf tests/.libs tests/tok* tests/test.out tests/*.o tests/*log \
+ rm -Rf tests/.libs tests/*.trs tests/tokenise_name3 \
+ tests/test.out tests/*.o tests/*log \
tests/Makefile tests/Makefile.in tests/arith_dynamic tests/fqzcomp_qual \
tests/rans4x16pr tests/rans4x8 tests/varint tests/entropy
dh_installexamples
=====================================
htscodecs/arith_dynamic.c
=====================================
@@ -98,10 +98,11 @@ static
unsigned char *arith_compress_O0(unsigned char *in, unsigned int in_size,
unsigned char *out, unsigned int *out_size) {
int i, bound = arith_compress_bound(in_size,0)-5; // -5 for order/size
+ unsigned char *out_free = NULL;
if (!out) {
*out_size = bound;
- out = malloc(*out_size);
+ out_free = out = malloc(*out_size);
}
if (!out || bound > *out_size)
return NULL;
@@ -118,12 +119,16 @@ unsigned char *arith_compress_O0(unsigned char *in, unsigned int in_size,
RangeCoder rc;
RC_SetOutput(&rc, (char *)out+1);
+ RC_SetOutputEnd(&rc, (char *)out + *out_size);
RC_StartEncode(&rc);
for (i = 0; i < in_size; i++)
SIMPLE_MODEL(256, _encodeSymbol)(&byte_model, &rc, in[i]);
- RC_FinishEncode(&rc);
+ if (RC_FinishEncode(&rc) < 0) {
+ free(out_free);
+ return NULL;
+ }
// Finalise block size and return it
*out_size = RC_OutSize(&rc)+1;
@@ -141,8 +146,9 @@ unsigned char *arith_uncompress_O0(unsigned char *in, unsigned int in_size,
SIMPLE_MODEL(256,_) byte_model;
SIMPLE_MODEL(256,_init)(&byte_model, m);
+ unsigned char *out_free = NULL;
if (!out)
- out = malloc(out_sz);
+ out_free = out = malloc(out_sz);
if (!out)
return NULL;
@@ -152,7 +158,10 @@ unsigned char *arith_uncompress_O0(unsigned char *in, unsigned int in_size,
for (i = 0; i < out_sz; i++)
out[i] = SIMPLE_MODEL(256, _decodeSymbol)(&byte_model, &rc);
- RC_FinishDecode(&rc);
+ if (RC_FinishDecode(&rc) < 0) {
+ free(out_free);
+ return NULL;
+ }
return out;
}
@@ -192,6 +201,7 @@ unsigned char *arith_compress_O1(unsigned char *in, unsigned int in_size,
RangeCoder rc;
RC_SetOutput(&rc, (char *)out+1);
+ RC_SetOutputEnd(&rc, (char *)out + *out_size);
RC_StartEncode(&rc);
uint8_t last = 0;
@@ -200,7 +210,11 @@ unsigned char *arith_compress_O1(unsigned char *in, unsigned int in_size,
last = in[i];
}
- RC_FinishEncode(&rc);
+ if (RC_FinishEncode(&rc) < 0) {
+ free(out_free);
+ htscodecs_tls_free(byte_model);
+ return NULL;
+ }
// Finalise block size and return it
*out_size = RC_OutSize(&rc)+1;
@@ -241,7 +255,11 @@ unsigned char *arith_uncompress_O1(unsigned char *in, unsigned int in_size,
last = out[i];
}
- RC_FinishDecode(&rc);
+ if (RC_FinishDecode(&rc) < 0) {
+ htscodecs_tls_free(byte_model);
+ free(out_free);
+ return NULL;
+ }
htscodecs_tls_free(byte_model);
return out;
@@ -259,10 +277,11 @@ unsigned char *arith_compress_O2(unsigned char *in, unsigned int in_size,
int i, j;
int bound = arith_compress_bound(in_size,0)-5; // -5 for order/size
+ unsigned char *out_free = NULL;
if (!out) {
*out_size = bound;
- out = malloc(*out_size);
+ out_free = out = malloc(*out_size);
}
if (!out || bound > *out_size)
return NULL;
@@ -285,6 +304,7 @@ unsigned char *arith_compress_O2(unsigned char *in, unsigned int in_size,
RangeCoder rc;
RC_SetOutput(&rc, (char *)out+1);
+ RC_SetOutputEnd(&rc, (char *)out + *out_size);
RC_StartEncode(&rc);
unsigned char last1 = 0, last2 = 0;
@@ -295,7 +315,10 @@ unsigned char *arith_compress_O2(unsigned char *in, unsigned int in_size,
}
free(byte_model);
- RC_FinishEncode(&rc);
+ if (RC_FinishEncode(&rc) < 0) {
+ free(out_free);
+ return NULL;
+ }
// Finalise block size and return it
*out_size = RC_OutSize(&rc)+1;
@@ -310,9 +333,10 @@ unsigned char *arith_compress_O2(unsigned char *in, unsigned int in_size,
int i, j;
int bound = arith_compress_bound(in_size,0)-5; // -5 for order/size
+ unsigned char *out_free = NULL;
if (!out) {
*out_size = bound;
- out = malloc(*out_size);
+ out_free = out = malloc(*out_size);
}
if (!out || bound > *out_size)
return NULL;
@@ -338,6 +362,7 @@ unsigned char *arith_compress_O2(unsigned char *in, unsigned int in_size,
RangeCoder rc;
RC_SetOutput(&rc, (char *)out+1);
+ RC_SetOutputEnd(&rc, (char *)out + *out_size);
RC_StartEncode(&rc);
unsigned char last1 = 0, last2 = 0;
@@ -355,7 +380,10 @@ unsigned char *arith_compress_O2(unsigned char *in, unsigned int in_size,
}
free(byte_model);
- RC_FinishEncode(&rc);
+ if (RC_FinishEncode(&rc) < 0) {
+ free(out_free);
+ return NULL;
+ }
// Finalise block size and return it
*out_size = RC_OutSize(&rc)+1;
@@ -375,8 +403,9 @@ unsigned char *arith_uncompress_O2(unsigned char *in, unsigned int in_size,
for (j = 0; j < 256; j++)
SIMPLE_MODEL(256,_init)(&byte_model[i*256+j], m);
+ unsigned char *out_free = NULL;
if (!out)
- out = malloc(out_sz);
+ out_free = out = malloc(out_sz);
if (!out)
return NULL;
@@ -391,7 +420,10 @@ unsigned char *arith_uncompress_O2(unsigned char *in, unsigned int in_size,
}
free(byte_model);
- RC_FinishDecode(&rc);
+ if (RC_FinishDecode(&rc) < 0) {
+ free(out_free);
+ return NULL;
+ }
return out;
}
@@ -440,6 +472,7 @@ unsigned char *arith_compress_O0_RLE(unsigned char *in, unsigned int in_size,
RangeCoder rc;
RC_SetOutput(&rc, (char *)out+1);
+ RC_SetOutputEnd(&rc, (char *)out + *out_size);
RC_StartEncode(&rc);
unsigned char last = 0;
@@ -466,7 +499,11 @@ unsigned char *arith_compress_O0_RLE(unsigned char *in, unsigned int in_size,
} while (run);
}
- RC_FinishEncode(&rc);
+ if (RC_FinishEncode(&rc) < 0) {
+ htscodecs_tls_free(run_model);
+ free(out_free);
+ return NULL;
+ }
// Finalise block size and return it
*out_size = RC_OutSize(&rc)+1;
@@ -524,7 +561,11 @@ unsigned char *arith_uncompress_O0_RLE(unsigned char *in, unsigned int in_size,
out[++i] = last;
}
- RC_FinishDecode(&rc);
+ if (RC_FinishDecode(&rc) < 0) {
+ htscodecs_tls_free(run_model);
+ free(out_free);
+ return NULL;
+ }
htscodecs_tls_free(run_model);
return out;
@@ -571,6 +612,7 @@ unsigned char *arith_compress_O1_RLE(unsigned char *in, unsigned int in_size,
RangeCoder rc;
RC_SetOutput(&rc, (char *)out+1);
+ RC_SetOutputEnd(&rc, (char *)out + *out_size);
RC_StartEncode(&rc);
unsigned char last = 0;
@@ -597,7 +639,12 @@ unsigned char *arith_compress_O1_RLE(unsigned char *in, unsigned int in_size,
} while (run);
}
- RC_FinishEncode(&rc);
+ if (RC_FinishEncode(&rc) < 0) {
+ htscodecs_tls_free(byte_model);
+ htscodecs_tls_free(run_model);
+ free(out_free);
+ return NULL;
+ }
// Finalise block size and return it
*out_size = RC_OutSize(&rc)+1;
@@ -663,7 +710,12 @@ unsigned char *arith_uncompress_O1_RLE(unsigned char *in, unsigned int in_size,
out[++i] = last;
}
- RC_FinishDecode(&rc);
+ if (RC_FinishDecode(&rc) < 0) {
+ htscodecs_tls_free(byte_model);
+ htscodecs_tls_free(run_model);
+ free(out_free);
+ return NULL;
+ }
htscodecs_tls_free(byte_model);
htscodecs_tls_free(run_model);
=====================================
htscodecs/c_range_coder.h
=====================================
@@ -31,13 +31,18 @@ typedef struct {
uc *in_buf;
uc *out_buf;
uc *in_end;
+ uc *out_end;
+ int err;
} RangeCoder;
static inline void RC_SetInput(RangeCoder *rc, char *in, char *in_end) {
rc->out_buf = rc->in_buf = (uc *)in;
rc->in_end = (uc *)in_end;
}
-static inline void RC_SetOutput(RangeCoder *rc, char *out) { rc->in_buf = rc->out_buf = (uc *)out; }
+
+// NB: call RC_SetOutput first, and then RC_SetOutputEnd
+static inline void RC_SetOutput(RangeCoder *rc, char *out) { rc->in_buf = rc->out_buf = (uc *)out; rc->out_end = NULL;}
+static inline void RC_SetOutputEnd(RangeCoder *rc, char *out_end) { rc->out_end = (uc *)out_end; }
static inline char *RC_GetInput(RangeCoder *rc) { return (char *)rc->in_buf; }
static inline char *RC_GetOutput(RangeCoder *rc) { return (char *)rc->out_buf; }
static inline size_t RC_OutSize(RangeCoder *rc) { return rc->out_buf - rc->in_buf; }
@@ -51,6 +56,7 @@ static inline void RC_StartEncode(RangeCoder *rc)
rc->Carry = 0;
rc->Cache = 0;
rc->code = 0;
+ rc->err = 0;
}
static inline void RC_StartDecode(RangeCoder *rc)
@@ -61,6 +67,7 @@ static inline void RC_StartDecode(RangeCoder *rc)
rc->Carry = 0;
rc->Cache = 0;
rc->code = 0;
+ rc->err = 0;
if (rc->in_buf+5 > rc->in_end) {
rc->in_buf = rc->in_end; // prevent decode
return;
@@ -68,6 +75,31 @@ static inline void RC_StartDecode(RangeCoder *rc)
DO(5) rc->code = (rc->code<<8) | *rc->in_buf++;
}
+static inline void RC_ShiftLowCheck(RangeCoder *rc) {
+ if (rc->low < Thres || rc->Carry) {
+ if (rc->out_end && rc->FFNum >= rc->out_end - rc->out_buf) {
+ rc->err = -1;
+ return;
+ }
+
+ *rc->out_buf++ = rc->Cache + rc->Carry;
+
+ // Flush any stored FFs
+ while (rc->FFNum) {
+ *rc->out_buf++ = rc->Carry-1; // (Carry-1)&255;
+ rc->FFNum--;
+ }
+
+ // Take copy of top byte ready for next flush
+ rc->Cache = rc->low >> 24;
+ rc->Carry = 0;
+ } else {
+ // Low if FFxx xxxx. Bump FF count and shift in as before
+ rc->FFNum++;
+ }
+ rc->low = rc->low<<8;
+}
+
static inline void RC_ShiftLow(RangeCoder *rc) {
if (rc->low < Thres || rc->Carry) {
*rc->out_buf++ = rc->Cache + rc->Carry;
@@ -88,12 +120,15 @@ static inline void RC_ShiftLow(RangeCoder *rc) {
rc->low = rc->low<<8;
}
-static inline void RC_FinishEncode(RangeCoder *rc)
+static inline int RC_FinishEncode(RangeCoder *rc)
{
- DO(5) RC_ShiftLow(rc);
+ DO(5) RC_ShiftLowCheck(rc);
+ return rc->err;
}
-static inline void RC_FinishDecode(RangeCoder *rc) {}
+static inline int RC_FinishDecode(RangeCoder *rc) {
+ return rc->err;
+}
static inline void RC_Encode (RangeCoder *rc, uint32_t cumFreq, uint32_t freq, uint32_t totFreq)
{
@@ -105,7 +140,7 @@ static inline void RC_Encode (RangeCoder *rc, uint32_t cumFreq, uint32_t freq, u
while (rc->range < TOP) {
rc->range <<= 8;
- RC_ShiftLow(rc);
+ RC_ShiftLowCheck(rc);
}
}
@@ -119,8 +154,10 @@ static inline void RC_Decode (RangeCoder *rc, uint32_t cumFreq, uint32_t freq, u
rc->code -= cumFreq * rc->range;
rc->range *= freq;
while (rc->range < TOP) {
- if (rc->in_buf >= rc->in_end)
- return; // FIXME: could signal error, instead of caller just generating nonsense
+ if (rc->in_buf >= rc->in_end) {
+ rc->err = -1;
+ return;
+ }
rc->code = (rc->code<<8) + *rc->in_buf++;
rc->range <<= 8;
}
=====================================
htscodecs/fqzcomp_qual.c
=====================================
@@ -1018,11 +1018,6 @@ unsigned char *compress_block_fqz2f(int vers,
int comp_idx = 0;
RangeCoder rc;
- unsigned char *comp = (unsigned char *)malloc(in_size*1.1+100000);
- unsigned char *compe = comp + (size_t)(in_size*1.1+100000);
- if (!comp)
- return NULL;
-
// Pick and store params
if (!gp) {
gp = &local_gp;
@@ -1031,6 +1026,36 @@ unsigned char *compress_block_fqz2f(int vers,
free_params = 1;
}
+ // Worst case scenario assuming random input data and no way to compress
+ // is NBytes*growth for some small growth factor (arith_dynamic uses 1.05),
+ // plus fixed overheads for the header / params. Growth can be high
+ // here as we're modelling things and pathological cases may trigger a
+ // bad probability model.
+ //
+ // Per read is 4-byte len if not fixed length (but less if avg smaller)
+ // up to 1 byte for selection state (log2(max_sel) bits)
+ // 1-bit for reverse flag
+ // 1-bit for dup-last flag (but then no quals)
+ // Per qual is 1-byte (assuming QMAX==256)
+ //
+ // Header size is total guess, as depends on params, but it's almost
+ // always tiny, so a few K extra should be sufficient.
+ //
+ // => Total of (s->num_records*4.25 + in_size)*growth + hdr
+ int sel_bits = 0, sel = gp->max_sel;
+ while (sel) {
+ sel_bits++;
+ sel >>= 1;
+ }
+ double len_sz = gp->p[0].fixed_len ? 0.25 : 4.25;
+ len_sz += sel_bits / 8.0;
+ size_t comp_sz = (s->num_records*len_sz + in_size)*1.1 + 10000;
+
+ unsigned char *comp = (unsigned char *)malloc(comp_sz);
+ unsigned char *compe = comp + (size_t)comp_sz;
+ if (!comp)
+ return NULL;
+
//dump_params(gp);
comp_idx = var_put_u32(comp, compe, in_size);
comp_idx += fqz_store_parameters(gp, comp+comp_idx);
@@ -1054,6 +1079,7 @@ unsigned char *compress_block_fqz2f(int vers,
return NULL;
RC_SetOutput(&rc, (char *)comp+comp_idx);
+ RC_SetOutputEnd(&rc, (char *)comp+comp_sz);
RC_StartEncode(&rc);
// For CRAM3.1, reverse upfront if needed
@@ -1151,7 +1177,12 @@ unsigned char *compress_block_fqz2f(int vers,
#endif
}
- RC_FinishEncode(&rc);
+ if (RC_FinishEncode(&rc) < 0) {
+ free(comp);
+ comp = NULL;
+ *out_size = 0;
+ goto err;
+ }
// For CRAM3.1, undo our earlier reversal step
rec = state.rec;
@@ -1186,6 +1217,7 @@ unsigned char *compress_block_fqz2f(int vers,
*out_size = comp_idx + RC_OutSize(&rc);
//fprintf(stderr, "%d -> %d\n", (int)in_size, (int)*out_size);
+ err:
fqz_destroy_models(&model);
if (free_params)
fqz_free_parameters(gp);
@@ -1550,7 +1582,9 @@ unsigned char *uncompress_block_fqz2f(fqz_slice *s,
}
}
- RC_FinishDecode(&rc);
+ if (RC_FinishDecode(&rc) < 0)
+ goto err;
+
fqz_destroy_models(&model);
free(rev_a);
free(len_a);
=====================================
htscodecs/htscodecs.h
=====================================
@@ -43,7 +43,7 @@
* Note currently this needs manually editing as it isn't automatically
* updated by autoconf.
*/
-#define HTSCODECS_VERSION 100501
+#define HTSCODECS_VERSION 100502
/*
* A const string form of the HTSCODECS_VERSION define.
=====================================
htscodecs/rANS_static.c
=====================================
@@ -96,7 +96,7 @@ unsigned char *rans_compress_O0(unsigned char *in, unsigned int in_size,
free(out_buf);
return NULL;
}
- tr = ((uint64_t)TOTFREQ<<31)/in_size + (1<<30)/in_size;
+ tr = in_size ? ((uint64_t)TOTFREQ<<31)/in_size + (1<<30)/in_size : 0;
normalise_harder:
// Normalise so T[i] == TOTFREQ
=====================================
htscodecs/rANS_static16_int.h
=====================================
@@ -294,8 +294,6 @@ static inline int encode_freq_d(uint8_t *cp, uint32_t *F0, uint32_t *F) {
dz++;
*cp++ = 0;
}
- } else {
- assert(F[j] == 0);
}
}
@@ -313,7 +311,7 @@ static inline int encode_freq_d(uint8_t *cp, uint32_t *F0, uint32_t *F) {
// Returns the desired TF_SHIFT; 10 or 12 bit, or -1 on error.
static inline int encode_freq1(uint8_t *in, uint32_t in_size, int Nway,
RansEncSymbol syms[256][256], uint8_t **cp_p) {
- int tab_size = 0, i, j, z;
+ int i, j, z;
uint8_t *out = *cp_p, *cp = out;
// Compute O1 frequency statistics
@@ -413,9 +411,6 @@ static inline int encode_freq1(uint8_t *in, uint32_t in_size, int Nway,
free(c_freq);
}
- tab_size = cp - out;
- assert(tab_size < 257*257*3);
-
*cp_p = cp;
htscodecs_tls_free(F);
return shift;
=====================================
htscodecs/rANS_static32x16pr_avx2.c
=====================================
@@ -526,7 +526,6 @@ unsigned char *rans_uncompress_O0_32x16_avx2(unsigned char *in,
Rv2 = _mm256_add_epi32(
_mm256_mullo_epi32(
_mm256_srli_epi32(Rv2,TF_SHIFT), fv2), bv2);
-
#ifdef __clang__
// Protect against running off the end of in buffer.
// We copy it to a worst-case local buffer when near the end.
@@ -649,6 +648,7 @@ unsigned char *rans_uncompress_O0_32x16_avx2(unsigned char *in,
Yv3 = _mm256_or_si256(Yv3, Vv3);
Vv4 = _mm256_permutevar8x32_epi32(Vv4, idx4);
Yv4 = _mm256_or_si256(Yv4, Vv4);
+ sp += _mm_popcnt_u32(imask4);
#ifndef __clang__
// 26% faster here than above for gcc10, but former location is
@@ -663,8 +663,6 @@ unsigned char *rans_uncompress_O0_32x16_avx2(unsigned char *in,
}
#endif
- sp += _mm_popcnt_u32(imask4);
-
// R[z] = c ? Y[z] : R[z];
Rv3 = _mm256_blendv_epi8(Rv3, Yv3, renorm_mask3);
Rv4 = _mm256_blendv_epi8(Rv4, Yv4, renorm_mask4);
=====================================
htscodecs/rANS_static32x16pr_sse4.c
=====================================
@@ -1414,8 +1414,10 @@ unsigned char *rans_uncompress_O1_32x16_sse4(unsigned char *in,
uint32_t S = s3[l[z]][m];
unsigned char c = S & 0xff;
out[i4[z]++] = c;
- R[z] = (S>>(TF_SHIFT_O1+8)) * (R[z]>>TF_SHIFT_O1) +
- ((S>>8) & ((1u<<TF_SHIFT_O1)-1));
+ int f = (S>>(TF_SHIFT_O1+8));
+ if (f == 0)
+ f = 4096;
+ R[z] = f * (R[z]>>TF_SHIFT_O1) + ((S>>8) & ((1u<<TF_SHIFT_O1)-1));
RansDecRenormSafe(&R[z], &ptr, ptr_end);
l[z] = c;
}
=====================================
htscodecs/rANS_static4x16pr.c
=====================================
@@ -1018,7 +1018,7 @@ unsigned char *(*rans_dec_func(int do_simd, int order))
static inline int have_neon() {
#if defined(__linux__) && defined(__arm__)
return (getauxval(AT_HWCAP) & HWCAP_NEON) != 0;
-#elif defined(__linux__) && defined(__aarch64__)
+#elif defined(__linux__) && defined(__aarch64__) && defined(HWCAP_ASIMD)
return (getauxval(AT_HWCAP) & HWCAP_ASIMD) != 0;
#elif defined(__APPLE__)
return 1;
@@ -1026,7 +1026,7 @@ static inline int have_neon() {
u_long cap;
if (elf_aux_info(AT_HWCAP, &cap, sizeof cap) != 0) return 0;
return (cap & HWCAP_NEON) != 0;
-#elif defined(__FreeBSD__) && defined(__aarch64__)
+#elif defined(__FreeBSD__) && defined(__aarch64__) && defined(HWCAP_ASIMD)
u_long cap;
if (elf_aux_info(AT_HWCAP, &cap, sizeof cap) != 0) return 0;
return (cap & HWCAP_ASIMD) != 0;
@@ -1267,7 +1267,8 @@ unsigned char *rans_compress_to_4x16(unsigned char *in, unsigned int in_size,
out[0] = RANS_ORDER_CAT;
c_meta_len = 1;
c_meta_len += var_put_u32(&out[1], out_end, in_size);
- memcpy(out+c_meta_len, in, in_size);
+ if (in_size)
+ memcpy(out+c_meta_len, in, in_size);
*out_size = c_meta_len + in_size;
return out;
}
@@ -1380,7 +1381,8 @@ unsigned char *rans_compress_to_4x16(unsigned char *in, unsigned int in_size,
if (*out_size >= in_size) {
out[0] &= ~3;
out[0] |= RANS_ORDER_CAT | no_size;
- memcpy(out+c_meta_len, in, in_size);
+ if (in_size)
+ memcpy(out+c_meta_len, in, in_size);
*out_size = in_size;
}
=====================================
htscodecs/tokenise_name3.c
=====================================
@@ -756,6 +756,8 @@ static int encode_name(name_context *ctx, char *name, int len, int mode) {
for (; i < len; i++) {
if (ntok >= ctx->max_tok) {
+ if (ctx->max_tok >= MAX_TOKENS)
+ return -1;
memset(&ctx->desc[ctx->max_tok << 4], 0, 16*sizeof(ctx->desc[0]));
memset(&ctx->token_dcount[ctx->max_tok], 0, sizeof(int));
memset(&ctx->token_icount[ctx->max_tok], 0, sizeof(int));
@@ -968,6 +970,8 @@ static int encode_name(name_context *ctx, char *name, int len, int mode) {
fprintf(stderr, "Tok %d (end)\n", N_END);
#endif
if (ntok >= ctx->max_tok) {
+ if (ctx->max_tok >= MAX_TOKENS)
+ return -1;
memset(&ctx->desc[ctx->max_tok << 4], 0, 16*sizeof(ctx->desc[0]));
memset(&ctx->token_dcount[ctx->max_tok], 0, sizeof(int));
memset(&ctx->token_icount[ctx->max_tok], 0, sizeof(int));
@@ -1464,11 +1468,17 @@ uint8_t *tok3_encode_names(char *blk, int len, int level, int use_arith,
// Encode name
for (i = j = 0; i < len; j=++i) {
- while (i < len && blk[i] > '\n')
+ while (i < len && (signed char)blk[i] >= ' ') // non-ASCII check
i++;
if (i >= len)
break;
+ if (blk[i] != '\0' && blk[i] != '\n') {
+ // Names must be 7-bit ASCII printable
+ free_context(ctx);
+ return NULL;
+ }
+
blk[i] = '\0';
// try both 0 and 1 and pick best?
if (encode_name(ctx, &blk[j], i-j, 1) < 0) {
=====================================
htscodecs/varint.h
=====================================
@@ -115,14 +115,14 @@ int var_put_u64(uint8_t *cp, const uint8_t *endp, uint64_t i) {
*cp++ = ((i>> 7) & 0x7f) | 128;
*cp++ = i & 0x7f;
return 4;
- } else if (i < (1LL<<35)) {
+ } else if (i < (1ULL<<35)) {
*cp++ = ((i>>28) & 0x7f) | 128;
*cp++ = ((i>>21) & 0x7f) | 128;
*cp++ = ((i>>14) & 0x7f) | 128;
*cp++ = ((i>> 7) & 0x7f) | 128;
*cp++ = i & 0x7f;
return 5;
- } else if (i < (1LL<<42)) {
+ } else if (i < (1ULL<<42)) {
*cp++ = ((i>>35) & 0x7f) | 128;
*cp++ = ((i>>28) & 0x7f) | 128;
*cp++ = ((i>>21) & 0x7f) | 128;
@@ -130,7 +130,7 @@ int var_put_u64(uint8_t *cp, const uint8_t *endp, uint64_t i) {
*cp++ = ((i>> 7) & 0x7f) | 128;
*cp++ = i & 0x7f;
return 6;
- } else if (i < (1LL<<49)) {
+ } else if (i < (1ULL<<49)) {
*cp++ = ((i>>42) & 0x7f) | 128;
*cp++ = ((i>>35) & 0x7f) | 128;
*cp++ = ((i>>28) & 0x7f) | 128;
@@ -139,7 +139,7 @@ int var_put_u64(uint8_t *cp, const uint8_t *endp, uint64_t i) {
*cp++ = ((i>> 7) & 0x7f) | 128;
*cp++ = i & 0x7f;
return 7;
- } else if (i < (1LL<<56)) {
+ } else if (i < (1ULL<<56)) {
*cp++ = ((i>>49) & 0x7f) | 128;
*cp++ = ((i>>42) & 0x7f) | 128;
*cp++ = ((i>>35) & 0x7f) | 128;
@@ -149,7 +149,7 @@ int var_put_u64(uint8_t *cp, const uint8_t *endp, uint64_t i) {
*cp++ = ((i>> 7) & 0x7f) | 128;
*cp++ = i & 0x7f;
return 8;
- } else if (i < (1LL<<63)) {
+ } else if (i < (1ULL<<63)) {
*cp++ = ((i>>56) & 0x7f) | 128;
*cp++ = ((i>>49) & 0x7f) | 128;
*cp++ = ((i>>42) & 0x7f) | 128;
@@ -241,7 +241,7 @@ int var_get_u64(uint8_t *cp, const uint8_t *endp, uint64_t *i) {
uint8_t *op = cp, c;
uint64_t j = 0;
- if (!endp || endp - cp >= 10) {
+ if (!endp || endp - cp >= 11) {
int n = 10;
do {
c = *cp++;
=====================================
tests/arith_dynamic_test.c
=====================================
@@ -266,12 +266,13 @@ int main(int argc, char **argv) {
bytes += out_size;
}
} else {
- for (;;) {
+ int loop = 0;
+ for (;;loop++) {
uint32_t in_size, out_size;
unsigned char *out;
in_size = fread(in_buf, 1, BLK_SIZE, infp);
- if (in_size <= 0)
+ if (loop && in_size <= 0)
break;
if (in_size < 4)
=====================================
tests/rANS_static4x16pr_test.c
=====================================
@@ -309,12 +309,13 @@ int main(int argc, char **argv) {
bytes += out_size;
}
} else {
- for (;;) {
+ int loop = 0;
+ for (;;loop++) {
uint32_t in_size, out_size;
unsigned char *out;
in_size = fread(in_buf, 1, blk_size, infp);
- if (in_size <= 0)
+ if (loop && in_size <= 0)
break;
if (in_size < 4)
=====================================
tests/rANS_static_test.c
=====================================
@@ -259,12 +259,13 @@ int main(int argc, char **argv) {
bytes += out_size;
}
} else {
- for (;;) {
+ int loop=0;
+ for (;;loop++) {
uint32_t in_size, out_size;
unsigned char *out;
in_size = fread(in_buf, 1, BLK_SIZE, infp);
- if (in_size <= 0)
+ if (loop && in_size <= 0)
break;
out = rans_compress(in_buf, in_size, &out_size,
=====================================
tests/tokenise_name3_test.c
=====================================
@@ -146,6 +146,10 @@ static int encode(int argc, char **argv) {
int out_len;
uint8_t *out = tok3_encode_names(blk, len, level, use_arith,
&out_len, &last_start);
+ if (!out) {
+ fprintf(stderr, "Couldn't encode names\n");
+ exit(1);
+ }
if (write(1, &out_len, 4) < 4) exit(1);
if (write(1, out, out_len) < out_len) exit(1); // encoded data
free(out);
View it on GitLab: https://salsa.debian.org/med-team/htscodecs/-/compare/f75629924d1634c3b43611642c17ba9d0fb2e4a7...35ef8a0b0be5e5cc14affc1df7a0800267c98124
--
View it on GitLab: https://salsa.debian.org/med-team/htscodecs/-/compare/f75629924d1634c3b43611642c17ba9d0fb2e4a7...35ef8a0b0be5e5cc14affc1df7a0800267c98124
You're receiving this email because of your account on salsa.debian.org.
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://alioth-lists.debian.net/pipermail/debian-med-commit/attachments/20231023/30074dde/attachment-0001.htm>
More information about the debian-med-commit
mailing list