vlc->table_size = 0;
return AVERROR(ENOMEM);
}
+ memset(vlc->table + vlc->table_allocated - (1 << vlc->bits), 0, sizeof(VLC_TYPE) * 2 << vlc->bits);
}
return index;
}
int table_size, table_index, index, code_prefix, symbol, subtable_bits;
int i, j, k, n, nb, inc;
uint32_t code;
- VLC_TYPE (*table)[2];
+ volatile VLC_TYPE (* volatile table)[2]; // the double volatile is needed to prevent a internal compiler error in gcc 4.2
table_size = 1 << table_nb_bits;
if (table_nb_bits > 30)
av_dlog(NULL, "new table index=%d size=%d\n", table_index, table_size);
if (table_index < 0)
return table_index;
- table = &vlc->table[table_index];
-
- for (i = 0; i < table_size; i++) {
- table[i][1] = 0; //bits
- table[i][0] = -1; //codes
- }
+ table = (volatile VLC_TYPE (*)[2])&vlc->table[table_index];
/* first pass: map codes and compute auxiliary table sizes */
for (i = 0; i < nb_codes; i++) {
inc = 1 << n;
}
for (k = 0; k < nb; k++) {
+ int bits = table[j][1];
av_dlog(NULL, "%4x: code=%d n=%d\n", j, i, n);
- if (table[j][1] /*bits*/ != 0) {
+ if (bits != 0 && bits != n) {
av_log(NULL, AV_LOG_ERROR, "incorrect codes\n");
return AVERROR_INVALIDDATA;
}
if (index < 0)
return index;
/* note: realloc has been done, so reload tables */
- table = &vlc->table[table_index];
+ table = (volatile VLC_TYPE (*)[2])&vlc->table[table_index];
table[j][0] = index; //code
- av_assert0(table[j][0] == index);
i = k-1;
}
}
+
+ for (i = 0; i < table_size; i++) {
+ if (table[i][1] == 0) //bits
+ table[i][0] = -1; //codes
+ }
+
return table_index;
}
'use_static' should be set to 1 for tables, which should be freed
with av_free_static(), 0 if ff_free_vlc() will be used.
*/
-int ff_init_vlc_sparse(VLC *vlc, int nb_bits, int nb_codes,
+int ff_init_vlc_sparse(VLC *vlc_arg, int nb_bits, int nb_codes,
const void *bits, int bits_wrap, int bits_size,
const void *codes, int codes_wrap, int codes_size,
const void *symbols, int symbols_wrap, int symbols_size,
VLCcode *buf;
int i, j, ret;
VLCcode localbuf[1500]; // the maximum currently needed is 1296 by rv34
- void *state;
+ VLC localvlc, *vlc;
+ vlc = vlc_arg;
vlc->bits = nb_bits;
if (flags & INIT_VLC_USE_NEW_STATIC) {
- while (state = avpriv_atomic_ptr_cas(&vlc->init_state, NULL, vlc)) {
- if (state == vlc + 1) {
- av_assert0(vlc->table_size && vlc->table_size == vlc->table_allocated);
- return 0;
- }
- }
- av_assert0(!vlc->table_size);
av_assert0(nb_codes + 1 <= FF_ARRAY_ELEMS(localbuf));
buf = localbuf;
+ localvlc = *vlc_arg;
+ vlc = &localvlc;
+ vlc->table_size = 0;
} else {
vlc->table = NULL;
vlc->table_allocated = 0;
if (flags & INIT_VLC_USE_NEW_STATIC) {
if(vlc->table_size != vlc->table_allocated)
av_log(NULL, AV_LOG_ERROR, "needed %d had %d\n", vlc->table_size, vlc->table_allocated);
- state = avpriv_atomic_ptr_cas(&vlc->init_state, vlc, vlc+1);
- av_assert0(state == vlc);
+
av_assert0(ret >= 0);
+ *vlc_arg = *vlc;
} else {
av_free(buf);
if (ret < 0) {