1 /*
2 * Copyright (c) 2016, Alliance for Open Media. All rights reserved
3 *
4 * This source code is subject to the terms of the BSD 2 Clause License and
5 * the Alliance for Open Media Patent License 1.0. If the BSD 2 Clause License
6 * was not distributed with this source code in the LICENSE file, you can
7 * obtain it at www.aomedia.org/license/software. If the Alliance for Open
8 * Media Patent License 1.0 was not distributed with this source code in the
9 * PATENTS file, you can obtain it at www.aomedia.org/license/patent.
10 */
11
12 #ifndef AOM_AOM_DSP_BITREADER_H_
13 #define AOM_AOM_DSP_BITREADER_H_
14
15 #include <assert.h>
16 #include <limits.h>
17
18 #include "config/aom_config.h"
19
20 #include "aom/aomdx.h"
21 #include "aom/aom_integer.h"
22 #include "aom_dsp/daalaboolreader.h"
23 #include "aom_dsp/prob.h"
24 #include "av1/common/odintrin.h"
25
26 #if CONFIG_ACCOUNTING
27 #include "av1/decoder/accounting.h"
28 #define ACCT_STR_NAME acct_str
29 #define ACCT_STR_PARAM , const char *ACCT_STR_NAME
30 #define ACCT_STR_ARG(s) , s
31 #else
32 #define ACCT_STR_PARAM
33 #define ACCT_STR_ARG(s)
34 #endif
35
36 #define aom_read(r, prob, ACCT_STR_NAME) \
37 aom_read_(r, prob ACCT_STR_ARG(ACCT_STR_NAME))
38 #define aom_read_bit(r, ACCT_STR_NAME) \
39 aom_read_bit_(r ACCT_STR_ARG(ACCT_STR_NAME))
40 #define aom_read_tree(r, tree, probs, ACCT_STR_NAME) \
41 aom_read_tree_(r, tree, probs ACCT_STR_ARG(ACCT_STR_NAME))
42 #define aom_read_literal(r, bits, ACCT_STR_NAME) \
43 aom_read_literal_(r, bits ACCT_STR_ARG(ACCT_STR_NAME))
44 #define aom_read_cdf(r, cdf, nsymbs, ACCT_STR_NAME) \
45 aom_read_cdf_(r, cdf, nsymbs ACCT_STR_ARG(ACCT_STR_NAME))
46 #define aom_read_symbol(r, cdf, nsymbs, ACCT_STR_NAME) \
47 aom_read_symbol_(r, cdf, nsymbs ACCT_STR_ARG(ACCT_STR_NAME))
48
49 #ifdef __cplusplus
50 extern "C" {
51 #endif
52
53 typedef struct daala_reader aom_reader;
54
aom_reader_init(aom_reader * r,const uint8_t * buffer,size_t size)55 static INLINE int aom_reader_init(aom_reader *r, const uint8_t *buffer,
56 size_t size) {
57 return aom_daala_reader_init(r, buffer, (int)size);
58 }
59
aom_reader_find_begin(aom_reader * r)60 static INLINE const uint8_t *aom_reader_find_begin(aom_reader *r) {
61 return aom_daala_reader_find_begin(r);
62 }
63
aom_reader_find_end(aom_reader * r)64 static INLINE const uint8_t *aom_reader_find_end(aom_reader *r) {
65 return aom_daala_reader_find_end(r);
66 }
67
68 // Returns true if the bit reader has tried to decode more data from the buffer
69 // than was actually provided.
aom_reader_has_overflowed(const aom_reader * r)70 static INLINE int aom_reader_has_overflowed(const aom_reader *r) {
71 return aom_daala_reader_has_overflowed(r);
72 }
73
74 // Returns the position in the bit reader in bits.
aom_reader_tell(const aom_reader * r)75 static INLINE uint32_t aom_reader_tell(const aom_reader *r) {
76 return aom_daala_reader_tell(r);
77 }
78
79 // Returns the position in the bit reader in 1/8th bits.
aom_reader_tell_frac(const aom_reader * r)80 static INLINE uint32_t aom_reader_tell_frac(const aom_reader *r) {
81 return aom_daala_reader_tell_frac(r);
82 }
83
84 #if CONFIG_ACCOUNTING
aom_process_accounting(const aom_reader * r ACCT_STR_PARAM)85 static INLINE void aom_process_accounting(const aom_reader *r ACCT_STR_PARAM) {
86 if (r->accounting != NULL) {
87 uint32_t tell_frac;
88 tell_frac = aom_reader_tell_frac(r);
89 aom_accounting_record(r->accounting, ACCT_STR_NAME,
90 tell_frac - r->accounting->last_tell_frac);
91 r->accounting->last_tell_frac = tell_frac;
92 }
93 }
94
aom_update_symb_counts(const aom_reader * r,int is_binary)95 static INLINE void aom_update_symb_counts(const aom_reader *r, int is_binary) {
96 if (r->accounting != NULL) {
97 r->accounting->syms.num_multi_syms += !is_binary;
98 r->accounting->syms.num_binary_syms += !!is_binary;
99 }
100 }
101 #endif
102
aom_read_(aom_reader * r,int prob ACCT_STR_PARAM)103 static INLINE int aom_read_(aom_reader *r, int prob ACCT_STR_PARAM) {
104 int ret;
105 ret = aom_daala_read(r, prob);
106 #if CONFIG_ACCOUNTING
107 if (ACCT_STR_NAME) aom_process_accounting(r, ACCT_STR_NAME);
108 aom_update_symb_counts(r, 1);
109 #endif
110 return ret;
111 }
112
aom_read_bit_(aom_reader * r ACCT_STR_PARAM)113 static INLINE int aom_read_bit_(aom_reader *r ACCT_STR_PARAM) {
114 int ret;
115 ret = aom_read(r, 128, NULL); // aom_prob_half
116 #if CONFIG_ACCOUNTING
117 if (ACCT_STR_NAME) aom_process_accounting(r, ACCT_STR_NAME);
118 #endif
119 return ret;
120 }
121
aom_read_literal_(aom_reader * r,int bits ACCT_STR_PARAM)122 static INLINE int aom_read_literal_(aom_reader *r, int bits ACCT_STR_PARAM) {
123 int literal = 0, bit;
124
125 for (bit = bits - 1; bit >= 0; bit--) literal |= aom_read_bit(r, NULL) << bit;
126 #if CONFIG_ACCOUNTING
127 if (ACCT_STR_NAME) aom_process_accounting(r, ACCT_STR_NAME);
128 #endif
129 return literal;
130 }
131
aom_read_cdf_(aom_reader * r,const aom_cdf_prob * cdf,int nsymbs ACCT_STR_PARAM)132 static INLINE int aom_read_cdf_(aom_reader *r, const aom_cdf_prob *cdf,
133 int nsymbs ACCT_STR_PARAM) {
134 int ret;
135 ret = daala_read_symbol(r, cdf, nsymbs);
136
137 #if CONFIG_ACCOUNTING
138 if (ACCT_STR_NAME) aom_process_accounting(r, ACCT_STR_NAME);
139 aom_update_symb_counts(r, (nsymbs == 2));
140 #endif
141 return ret;
142 }
143
aom_read_symbol_(aom_reader * r,aom_cdf_prob * cdf,int nsymbs ACCT_STR_PARAM)144 static INLINE int aom_read_symbol_(aom_reader *r, aom_cdf_prob *cdf,
145 int nsymbs ACCT_STR_PARAM) {
146 int ret;
147 ret = aom_read_cdf(r, cdf, nsymbs, ACCT_STR_NAME);
148 if (r->allow_update_cdf) update_cdf(cdf, ret, nsymbs);
149 return ret;
150 }
151
152 #ifdef __cplusplus
153 } // extern "C"
154 #endif
155
156 #endif // AOM_AOM_DSP_BITREADER_H_
157