]> git.sesse.net Git - vlc/blob - src/ac3_decoder/ac3_exponent.c
Separation du decodeur ac3 et de la partie specifique a videolan
[vlc] / src / ac3_decoder / ac3_exponent.c
1 #include <stdio.h>                                           /* "intf_msg.h" */
2
3 #include "int_types.h"
4 #include "ac3_decoder.h"
5 #include "ac3_bit_stream.h"
6 #include "ac3_exponent.h"
7
8 static const s16 exps_1[128] =
9   { -2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,-2,
10     -1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,-1,
11      0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,
12      1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1,
13      2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2, 2,
14      0, 0, 0 };
15
16 static const s16 exps_2[128] =
17   { -2,-2,-2,-2,-2,-1,-1,-1,-1,-1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2,
18     -2,-2,-2,-2,-2,-1,-1,-1,-1,-1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2,
19     -2,-2,-2,-2,-2,-1,-1,-1,-1,-1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2,
20     -2,-2,-2,-2,-2,-1,-1,-1,-1,-1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2,
21     -2,-2,-2,-2,-2,-1,-1,-1,-1,-1, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 2, 2, 2, 2, 2,
22      0, 0, 0 };
23
24 static const s16 exps_3[128] =
25   { -2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,
26     -2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,
27     -2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,
28     -2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,
29     -2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,-2,-1, 0, 1, 2,
30      0, 0, 0 };
31
32 #define UNPACK_FBW 1 
33 #define UNPACK_CPL 2 
34 #define UNPACK_LFE 4
35
36 static __inline__ int exp_unpack_ch( ac3dec_t * p_ac3dec, u16 type, u16 expstr, u16 ngrps, u16 initial_exp, u16 exps[], u16 * dest )
37 {
38     u16 i,j;
39     s16 exp_acc;
40
41     if ( expstr == EXP_REUSE )
42     {
43         return 0;
44     }
45
46     /* Handle the initial absolute exponent */
47     exp_acc = initial_exp;
48     j = 0;
49
50     /* In the case of a fbw channel then the initial absolute values is
51      * also an exponent */
52     if ( type != UNPACK_CPL )
53     {
54         dest[j++] = exp_acc;
55     }
56
57     /* Loop through the groups and fill the dest array appropriately */
58     switch ( expstr )
59     {
60     case EXP_D15:       /* 1 */
61         for ( i = 0; i < ngrps; i++ )
62         {
63             if ( exps[i] > 124 )
64             {
65                 fprintf( stderr, "ac3dec debug: invalid exponent\n" );
66                 return 1;
67             }
68             exp_acc += (exps_1[exps[i]] /*- 2*/);
69             dest[j++] = exp_acc;
70             exp_acc += (exps_2[exps[i]] /*- 2*/);
71             dest[j++] = exp_acc;
72             exp_acc += (exps_3[exps[i]] /*- 2*/);
73             dest[j++] = exp_acc;
74         }
75         break;
76
77     case EXP_D25:       /* 2 */
78         for ( i = 0; i < ngrps; i++ )
79         {
80             if ( exps[i] > 124 )
81             {
82                 fprintf( stderr, "ac3dec debug: invalid exponent\n" );
83                 return 1;
84             }
85             exp_acc += (exps_1[exps[i]] /*- 2*/);
86             dest[j++] = exp_acc;
87             dest[j++] = exp_acc;
88             exp_acc += (exps_2[exps[i]] /*- 2*/);
89             dest[j++] = exp_acc;
90             dest[j++] = exp_acc;
91             exp_acc += (exps_3[exps[i]] /*- 2*/);
92             dest[j++] = exp_acc;
93             dest[j++] = exp_acc;
94         }
95         break;
96
97     case EXP_D45:       /* 3 */
98         for ( i = 0; i < ngrps; i++ )
99         {
100             if ( exps[i] > 124 )
101             {
102                 fprintf( stderr, "ac3dec debug: invalid exponent\n" );
103                 return 1;
104             }
105             exp_acc += (exps_1[exps[i]] /*- 2*/);
106             dest[j++] = exp_acc;
107             dest[j++] = exp_acc;
108             dest[j++] = exp_acc;
109             dest[j++] = exp_acc;
110             exp_acc += (exps_2[exps[i]] /*- 2*/);
111             dest[j++] = exp_acc;
112             dest[j++] = exp_acc;
113             dest[j++] = exp_acc;
114             dest[j++] = exp_acc;
115             exp_acc += (exps_3[exps[i]] /*- 2*/);
116             dest[j++] = exp_acc;
117             dest[j++] = exp_acc;
118             dest[j++] = exp_acc;
119             dest[j++] = exp_acc;
120         }
121         break;
122     }
123
124     return 0;
125 }
126
127 int exponent_unpack( ac3dec_t * p_ac3dec )
128 {
129     u16 i;
130
131     for ( i = 0; i < p_ac3dec->bsi.nfchans; i++ )
132     {
133         if (exp_unpack_ch( p_ac3dec, UNPACK_FBW, p_ac3dec->audblk.chexpstr[i],
134                            p_ac3dec->audblk.nchgrps[i],
135                            p_ac3dec->audblk.exps[i][0],
136                            &p_ac3dec->audblk.exps[i][1],
137                            p_ac3dec->audblk.fbw_exp[i] ))
138             return 1;
139     }
140
141     if ( p_ac3dec->audblk.cplinu )
142     {
143         if (exp_unpack_ch( p_ac3dec, UNPACK_CPL, p_ac3dec->audblk.cplexpstr,
144                            p_ac3dec->audblk.ncplgrps,
145                            p_ac3dec->audblk.cplabsexp << 1,
146                            p_ac3dec->audblk.cplexps,
147                            &p_ac3dec->audblk.cpl_exp[p_ac3dec->audblk.cplstrtmant] ))
148             return 1;
149     }
150
151     if ( p_ac3dec->bsi.lfeon )
152     {
153         if (exp_unpack_ch( p_ac3dec, UNPACK_LFE, p_ac3dec->audblk.lfeexpstr,
154                            2, p_ac3dec->audblk.lfeexps[0],
155                            &p_ac3dec->audblk.lfeexps[1],
156                            p_ac3dec->audblk.lfe_exp ))
157             return 1;
158     }
159
160     return 0;
161 }