Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
V
vlc
Project overview
Project overview
Details
Activity
Releases
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Issues
0
Issues
0
List
Boards
Labels
Milestones
Redmine
Redmine
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Operations
Operations
Metrics
Environments
Analytics
Analytics
CI / CD
Repository
Value Stream
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
videolan
vlc
Commits
a906b2f5
Commit
a906b2f5
authored
Feb 20, 2001
by
Renaud Dartus
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
* Move ac3 globals variables into structures
* Adding authors * Prepared to add asm imdct and downmix
parent
1c5f8330
Changes
15
Show whitespace changes
Inline
Side-by-side
Showing
15 changed files
with
648 additions
and
569 deletions
+648
-569
Makefile.in
Makefile.in
+2
-1
src/ac3_decoder/ac3_bit_allocate.c
src/ac3_decoder/ac3_bit_allocate.c
+87
-110
src/ac3_decoder/ac3_bit_stream.h
src/ac3_decoder/ac3_bit_stream.h
+2
-1
src/ac3_decoder/ac3_decoder.c
src/ac3_decoder/ac3_decoder.c
+14
-5
src/ac3_decoder/ac3_decoder.h
src/ac3_decoder/ac3_decoder.h
+63
-2
src/ac3_decoder/ac3_decoder_thread.c
src/ac3_decoder/ac3_decoder_thread.c
+3
-7
src/ac3_decoder/ac3_downmix.c
src/ac3_decoder/ac3_downmix.c
+54
-284
src/ac3_decoder/ac3_downmix.h
src/ac3_decoder/ac3_downmix.h
+37
-0
src/ac3_decoder/ac3_downmix_c.c
src/ac3_decoder/ac3_downmix_c.c
+150
-0
src/ac3_decoder/ac3_exponent.c
src/ac3_decoder/ac3_exponent.c
+3
-1
src/ac3_decoder/ac3_imdct.c
src/ac3_decoder/ac3_imdct.c
+106
-99
src/ac3_decoder/ac3_internal.h
src/ac3_decoder/ac3_internal.h
+3
-3
src/ac3_decoder/ac3_mantissa.c
src/ac3_decoder/ac3_mantissa.c
+43
-51
src/ac3_decoder/ac3_parse.c
src/ac3_decoder/ac3_parse.c
+78
-3
src/ac3_decoder/ac3_rematrix.c
src/ac3_decoder/ac3_rematrix.c
+3
-2
No files found.
Makefile.in
View file @
a906b2f5
...
...
@@ -218,7 +218,8 @@ AC3_DECODER = src/ac3_decoder/ac3_decoder_thread.o \
src/ac3_decoder/ac3_mantissa.o
\
src/ac3_decoder/ac3_rematrix.o
\
src/ac3_decoder/ac3_imdct.o
\
src/ac3_decoder/ac3_downmix.o
src/ac3_decoder/ac3_downmix.o
\
src/ac3_decoder/ac3_downmix_c.o
LPCM_DECODER
=
src/lpcm_decoder/lpcm_decoder_thread.o
\
src/lpcm_decoder/lpcm_decoder.o
...
...
src/ac3_decoder/ac3_bit_allocate.c
View file @
a906b2f5
...
...
@@ -3,7 +3,9 @@
*****************************************************************************
* Copyright (C) 2000 VideoLAN
*
* Authors:
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
* Renaud Dartus <reno@videolan.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -25,49 +27,40 @@
#include "ac3_decoder.h"
#include "ac3_internal.h"
/*
static inline s16 logadd (s16 a, s16 b);
static s16 calc_lowcomp (s16 a, s16 b0, s16 b1, s16 bin);
static inline u16 min (s16 a, s16 b);
static inline u16 max (s16 a, s16 b);
*/
static
void
ba_compute_psd
(
s16
start
,
s16
end
,
s16
exps
[],
s16
psd
[],
s16
bndpsd
[]);
static
void
ba_compute_psd
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
s16
exps
[]);
static
void
ba_compute_excitation
(
s16
start
,
s16
end
,
s16
fgain
,
s16
fastleak
,
s16
slowleak
,
s16
is_lfe
,
s16
bndpsd
[],
s16
excite
[]);
static
void
ba_compute_mask
(
s16
start
,
s16
end
,
u16
fscod
,
static
void
ba_compute_excitation
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
s16
fgain
,
s16
fastleak
,
s16
slowleak
,
s16
is_lfe
);
static
void
ba_compute_mask
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
u16
fscod
,
u16
deltbae
,
u16
deltnseg
,
u16
deltoffst
[],
u16
deltba
[],
u16
deltlen
[],
s16
excite
[],
s16
mask
[]);
static
void
ba_compute_bap
(
s16
start
,
s16
end
,
s16
snroffset
,
s16
psd
[],
s16
mask
[],
s16
bap
[]);
u16
deltba
[],
u16
deltlen
[]);
static
void
ba_compute_bap
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
s16
snroffset
,
s16
bap
[]);
/* Misc LUTs for bit allocation process */
static
s16
slowdec
[]
=
{
0x0f
,
0x11
,
0x13
,
0x15
};
static
s16
fastdec
[]
=
{
0x3f
,
0x53
,
0x67
,
0x7b
};
static
s16
slowgain
[]
=
{
0x540
,
0x4d8
,
0x478
,
0x410
};
static
s16
dbpbtab
[]
=
{
0x000
,
0x700
,
0x900
,
0xb00
};
static
const
s16
slowdec
[]
=
{
0x0f
,
0x11
,
0x13
,
0x15
};
static
const
s16
fastdec
[]
=
{
0x3f
,
0x53
,
0x67
,
0x7b
};
static
const
s16
slowgain
[]
=
{
0x540
,
0x4d8
,
0x478
,
0x410
};
static
const
s16
dbpbtab
[]
=
{
0x000
,
0x700
,
0x900
,
0xb00
};
static
u16
floortab
[]
=
{
0x2f0
,
0x2b0
,
0x270
,
0x230
,
0x1f0
,
0x170
,
0x0f0
,
0xf800
};
static
s16
fastgain
[]
=
{
0x080
,
0x100
,
0x180
,
0x200
,
0x280
,
0x300
,
0x380
,
0x400
};
static
const
u16
floortab
[]
=
{
0x2f0
,
0x2b0
,
0x270
,
0x230
,
0x1f0
,
0x170
,
0x0f0
,
0xf800
};
static
const
s16
fastgain
[]
=
{
0x080
,
0x100
,
0x180
,
0x200
,
0x280
,
0x300
,
0x380
,
0x400
};
static
s16
bndtab
[]
=
{
0
,
1
,
2
,
3
,
4
,
5
,
6
,
7
,
8
,
9
,
static
const
s16
bndtab
[]
=
{
0
,
1
,
2
,
3
,
4
,
5
,
6
,
7
,
8
,
9
,
10
,
11
,
12
,
13
,
14
,
15
,
16
,
17
,
18
,
19
,
20
,
21
,
22
,
23
,
24
,
25
,
26
,
27
,
28
,
31
,
34
,
37
,
40
,
43
,
46
,
49
,
55
,
61
,
67
,
73
,
79
,
85
,
97
,
109
,
121
,
133
,
157
,
181
,
205
,
229
};
static
s16
bndsz
[]
=
{
1
,
1
,
1
,
1
,
1
,
1
,
1
,
1
,
1
,
1
,
static
const
s16
bndsz
[]
=
{
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
,
1
,
1
,
1
,
3
,
3
,
3
,
3
,
3
,
3
,
3
,
6
,
6
,
6
,
6
,
6
,
6
,
12
,
12
,
12
,
12
,
24
,
24
,
24
,
24
,
24
};
static
s16
masktab
[]
=
{
0
,
1
,
2
,
3
,
4
,
5
,
6
,
7
,
8
,
9
,
10
,
11
,
12
,
13
,
14
,
15
,
static
const
s16
masktab
[]
=
{
0
,
1
,
2
,
3
,
4
,
5
,
6
,
7
,
8
,
9
,
10
,
11
,
12
,
13
,
14
,
15
,
16
,
17
,
18
,
19
,
20
,
21
,
22
,
23
,
24
,
25
,
26
,
27
,
28
,
28
,
28
,
29
,
29
,
29
,
30
,
30
,
30
,
31
,
31
,
31
,
32
,
32
,
32
,
33
,
33
,
33
,
34
,
34
,
34
,
35
,
35
,
35
,
35
,
35
,
35
,
36
,
36
,
36
,
36
,
36
,
36
,
37
,
37
,
37
,
...
...
@@ -85,7 +78,7 @@ static s16 masktab[] = { 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,
49
,
49
,
49
,
49
,
49
,
49
,
49
,
49
,
49
,
49
,
49
,
49
,
49
,
0
,
0
,
0
};
static
s16
latab
[]
=
{
0x0040
,
0x003f
,
0x003e
,
0x003d
,
0x003c
,
0x003b
,
0x003a
,
0x0039
,
static
const
s16
latab
[]
=
{
0x0040
,
0x003f
,
0x003e
,
0x003d
,
0x003c
,
0x003b
,
0x003a
,
0x0039
,
0x0038
,
0x0037
,
0x0036
,
0x0035
,
0x0034
,
0x0034
,
0x0033
,
0x0032
,
0x0031
,
0x0030
,
0x002f
,
0x002f
,
0x002e
,
0x002d
,
0x002c
,
0x002c
,
0x002b
,
0x002a
,
0x0029
,
0x0029
,
0x0028
,
0x0027
,
0x0026
,
0x0026
,
...
...
@@ -119,7 +112,7 @@ static s16 latab[] = { 0x0040, 0x003f, 0x003e, 0x003d, 0x003c, 0x003b, 0x003a, 0
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
,
0x0000
};
static
s16
hth
[][
50
]
=
{{
0x04d0
,
0x04d0
,
0x0440
,
0x0400
,
0x03e0
,
0x03c0
,
0x03b0
,
0x03b0
,
static
const
s16
hth
[][
50
]
=
{{
0x04d0
,
0x04d0
,
0x0440
,
0x0400
,
0x03e0
,
0x03c0
,
0x03b0
,
0x03b0
,
0x03a0
,
0x03a0
,
0x03a0
,
0x03a0
,
0x03a0
,
0x0390
,
0x0390
,
0x0390
,
0x0380
,
0x0380
,
0x0370
,
0x0370
,
0x0360
,
0x0360
,
0x0350
,
0x0350
,
0x0340
,
0x0340
,
0x0330
,
0x0320
,
0x0310
,
0x0300
,
0x02f0
,
0x02f0
,
...
...
@@ -144,21 +137,11 @@ static s16 hth[][50] = {{ 0x04d0, 0x04d0, 0x0440, 0x0400, 0x03e0, 0x03c0, 0x03b0
0x0450
,
0x04e0
}};
static
s16
baptab
[]
=
{
0
,
1
,
1
,
1
,
1
,
1
,
2
,
2
,
3
,
3
,
3
,
4
,
4
,
5
,
5
,
6
,
static
const
s16
baptab
[]
=
{
0
,
1
,
1
,
1
,
1
,
1
,
2
,
2
,
3
,
3
,
3
,
4
,
4
,
5
,
5
,
6
,
6
,
6
,
6
,
7
,
7
,
7
,
7
,
8
,
8
,
8
,
8
,
9
,
9
,
9
,
9
,
10
,
10
,
10
,
10
,
11
,
11
,
11
,
11
,
12
,
12
,
12
,
12
,
13
,
13
,
13
,
13
,
14
,
14
,
14
,
14
,
14
,
14
,
14
,
14
,
15
,
15
,
15
,
15
,
15
,
15
,
15
,
15
,
15
};
static
s16
sdecay
;
static
s16
fdecay
;
static
s16
sgain
;
static
s16
dbknee
;
static
s16
floor
;
static
s16
psd
[
256
];
static
s16
bndpsd
[
256
];
static
s16
excite
[
256
];
static
s16
mask
[
256
];
static
__inline__
u16
max
(
s16
a
,
s16
b
)
{
return
(
a
>
b
?
a
:
b
);
...
...
@@ -218,11 +201,11 @@ void bit_allocate (ac3dec_t * p_ac3dec)
return
;
/* Do some setup before we do the bit alloc */
sdecay
=
slowdec
[
p_ac3dec
->
audblk
.
sdcycod
];
fdecay
=
fastdec
[
p_ac3dec
->
audblk
.
fdcycod
];
sgain
=
slowgain
[
p_ac3dec
->
audblk
.
sgaincod
];
dbknee
=
dbpbtab
[
p_ac3dec
->
audblk
.
dbpbcod
];
floor
=
floortab
[
p_ac3dec
->
audblk
.
floorcod
];
p_ac3dec
->
bit_allocate
.
sdecay
=
slowdec
[
p_ac3dec
->
audblk
.
sdcycod
];
p_ac3dec
->
bit_allocate
.
fdecay
=
fastdec
[
p_ac3dec
->
audblk
.
fdcycod
];
p_ac3dec
->
bit_allocate
.
sgain
=
slowgain
[
p_ac3dec
->
audblk
.
sgaincod
];
p_ac3dec
->
bit_allocate
.
dbknee
=
dbpbtab
[
p_ac3dec
->
audblk
.
dbpbcod
];
p_ac3dec
->
bit_allocate
.
floor
=
floortab
[
p_ac3dec
->
audblk
.
floorcod
];
/* if all the SNR offset constants are zero then the whole block is zero */
if
(
!
p_ac3dec
->
audblk
.
csnroffst
&&
!
p_ac3dec
->
audblk
.
fsnroffst
[
0
]
&&
...
...
@@ -239,24 +222,22 @@ void bit_allocate (ac3dec_t * p_ac3dec)
start
=
0
;
end
=
p_ac3dec
->
audblk
.
endmant
[
i
]
;
fgain
=
fastgain
[
p_ac3dec
->
audblk
.
fgaincod
[
i
]];
snroffset
=
(((
p_ac3dec
->
audblk
.
csnroffst
-
15
)
<<
4
)
+
p_ac3dec
->
audblk
.
fsnroffst
[
i
])
<<
2
;
snroffset
=
(((
p_ac3dec
->
audblk
.
csnroffst
-
15
)
<<
4
)
+
p_ac3dec
->
audblk
.
fsnroffst
[
i
])
<<
2
;
fastleak
=
0
;
slowleak
=
0
;
ba_compute_psd
(
start
,
end
,
p_ac3dec
->
audblk
.
fbw_exp
[
i
],
psd
,
bndpsd
);
ba_compute_psd
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
p_ac3dec
->
audblk
.
fbw_exp
[
i
]
);
ba_compute_excitation
(
start
,
end
,
fgain
,
fastleak
,
slowleak
,
0
,
bndpsd
,
excite
);
ba_compute_excitation
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
fgain
,
fastleak
,
slowleak
,
0
);
ba_compute_mask
(
start
,
end
,
p_ac3dec
->
syncinfo
.
fscod
,
ba_compute_mask
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
p_ac3dec
->
syncinfo
.
fscod
,
p_ac3dec
->
audblk
.
deltbae
[
i
],
p_ac3dec
->
audblk
.
deltnseg
[
i
],
p_ac3dec
->
audblk
.
deltoffst
[
i
],
p_ac3dec
->
audblk
.
deltba
[
i
],
p_ac3dec
->
audblk
.
deltlen
[
i
]
,
excite
,
mask
);
p_ac3dec
->
audblk
.
deltlen
[
i
]);
ba_compute_bap
(
start
,
end
,
snroffset
,
psd
,
mask
,
p_ac3dec
->
audblk
.
fbw_bap
[
i
]);
ba_compute_bap
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
snroffset
,
p_ac3dec
->
audblk
.
fbw_bap
[
i
]);
}
if
(
p_ac3dec
->
audblk
.
cplinu
)
{
...
...
@@ -267,20 +248,18 @@ void bit_allocate (ac3dec_t * p_ac3dec)
fastleak
=
(
p_ac3dec
->
audblk
.
cplfleak
<<
8
)
+
768
;
slowleak
=
(
p_ac3dec
->
audblk
.
cplsleak
<<
8
)
+
768
;
ba_compute_psd
(
start
,
end
,
p_ac3dec
->
audblk
.
cpl_exp
,
psd
,
bndpsd
);
ba_compute_psd
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
p_ac3dec
->
audblk
.
cpl_exp
);
ba_compute_excitation
(
start
,
end
,
fgain
,
fastleak
,
slowleak
,
0
,
bndpsd
,
excite
);
ba_compute_excitation
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
fgain
,
fastleak
,
slowleak
,
0
);
ba_compute_mask
(
start
,
end
,
p_ac3dec
->
syncinfo
.
fscod
,
ba_compute_mask
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
p_ac3dec
->
syncinfo
.
fscod
,
p_ac3dec
->
audblk
.
cpldeltbae
,
p_ac3dec
->
audblk
.
cpldeltnseg
,
p_ac3dec
->
audblk
.
cpldeltoffst
,
p_ac3dec
->
audblk
.
cpldeltba
,
p_ac3dec
->
audblk
.
cpldeltlen
,
excite
,
mask
);
p_ac3dec
->
audblk
.
cpldeltlen
);
ba_compute_bap
(
start
,
end
,
snroffset
,
psd
,
mask
,
p_ac3dec
->
audblk
.
cpl_bap
);
ba_compute_bap
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
snroffset
,
p_ac3dec
->
audblk
.
cpl_bap
);
}
if
(
p_ac3dec
->
bsi
.
lfeon
)
{
...
...
@@ -291,29 +270,25 @@ void bit_allocate (ac3dec_t * p_ac3dec)
fastleak
=
0
;
slowleak
=
0
;
ba_compute_psd
(
start
,
end
,
p_ac3dec
->
audblk
.
lfe_exp
,
psd
,
bndpsd
);
ba_compute_psd
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
p_ac3dec
->
audblk
.
lfe_exp
);
ba_compute_excitation
(
start
,
end
,
fgain
,
fastleak
,
slowleak
,
1
,
bndpsd
,
excite
);
ba_compute_excitation
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
fgain
,
fastleak
,
slowleak
,
1
);
ba_compute_mask
(
start
,
end
,
p_ac3dec
->
syncinfo
.
fscod
,
2
,
0
,
0
,
0
,
0
,
excite
,
mask
);
ba_compute_mask
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
p_ac3dec
->
syncinfo
.
fscod
,
2
,
0
,
0
,
0
,
0
);
ba_compute_bap
(
start
,
end
,
snroffset
,
psd
,
mask
,
p_ac3dec
->
audblk
.
lfe_bap
);
ba_compute_bap
(
&
p_ac3dec
->
bit_allocate
,
start
,
end
,
snroffset
,
p_ac3dec
->
audblk
.
lfe_bap
);
}
}
static
void
ba_compute_psd
(
s16
start
,
s16
end
,
s16
exps
[],
s16
psd
[],
s16
bndpsd
[])
static
void
ba_compute_psd
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
s16
exps
[])
{
int
bin
,
i
,
j
,
k
;
s16
lastbin
=
0
;
/* Map the exponents into dBs */
for
(
bin
=
start
;
bin
<
end
;
bin
++
)
{
psd
[
bin
]
=
(
3072
-
(
exps
[
bin
]
<<
7
));
p
_bit
->
p
sd
[
bin
]
=
(
3072
-
(
exps
[
bin
]
<<
7
));
}
/* Integrate the psd function over each bit allocation band */
...
...
@@ -322,11 +297,11 @@ static void ba_compute_psd (s16 start, s16 end, s16 exps[], s16 psd[],
do
{
lastbin
=
min
(
bndtab
[
k
]
+
bndsz
[
k
],
end
);
bndpsd
[
k
]
=
psd
[
j
];
p_bit
->
bndpsd
[
k
]
=
p_bit
->
psd
[
j
];
j
++
;
for
(
i
=
j
;
i
<
lastbin
;
i
++
)
{
bndpsd
[
k
]
=
logadd
(
bndpsd
[
k
],
psd
[
j
]);
p_bit
->
bndpsd
[
k
]
=
logadd
(
p_bit
->
bndpsd
[
k
],
p_bit
->
psd
[
j
]);
j
++
;
}
...
...
@@ -334,9 +309,8 @@ static void ba_compute_psd (s16 start, s16 end, s16 exps[], s16 psd[],
}
while
(
end
>
lastbin
);
}
static
void
ba_compute_excitation
(
s16
start
,
s16
end
,
s16
fgain
,
s16
fastleak
,
s16
slowleak
,
s16
is_lfe
,
s16
bndpsd
[],
s16
excite
[])
static
void
ba_compute_excitation
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
s16
fgain
,
s16
fastleak
,
s16
slowleak
,
s16
is_lfe
)
{
int
bin
;
s16
bndstrt
;
...
...
@@ -349,22 +323,24 @@ static void ba_compute_excitation (s16 start, s16 end,s16 fgain, s16 fastleak,
bndend
=
masktab
[
end
-
1
]
+
1
;
if
(
bndstrt
==
0
)
{
/* For fbw and lfe channels */
lowcomp
=
calc_lowcomp
(
lowcomp
,
bndpsd
[
0
],
bndpsd
[
1
],
0
);
excite
[
0
]
=
bndpsd
[
0
]
-
fgain
-
lowcomp
;
lowcomp
=
calc_lowcomp
(
lowcomp
,
bndpsd
[
1
],
bndpsd
[
2
],
1
);
excite
[
1
]
=
bndpsd
[
1
]
-
fgain
-
lowcomp
;
lowcomp
=
calc_lowcomp
(
lowcomp
,
p_bit
->
bndpsd
[
0
],
p_bit
->
bndpsd
[
1
],
0
);
p_bit
->
excite
[
0
]
=
p_bit
->
bndpsd
[
0
]
-
fgain
-
lowcomp
;
lowcomp
=
calc_lowcomp
(
lowcomp
,
p_bit
->
bndpsd
[
1
],
p_bit
->
bndpsd
[
2
],
1
);
p_bit
->
excite
[
1
]
=
p_bit
->
bndpsd
[
1
]
-
fgain
-
lowcomp
;
begin
=
7
;
/* Note: Do not call calc_lowcomp() for the last band of the lfe channel, (bin = 6) */
for
(
bin
=
2
;
bin
<
7
;
bin
++
)
{
if
(
!
(
is_lfe
&&
(
bin
==
6
)))
lowcomp
=
calc_lowcomp
(
lowcomp
,
bndpsd
[
bin
],
bndpsd
[
bin
+
1
],
bin
);
fastleak
=
bndpsd
[
bin
]
-
fgain
;
slowleak
=
bndpsd
[
bin
]
-
sgain
;
excite
[
bin
]
=
fastleak
-
lowcomp
;
lowcomp
=
calc_lowcomp
(
lowcomp
,
p_bit
->
bndpsd
[
bin
],
p_bit
->
bndpsd
[
bin
+
1
],
bin
);
fastleak
=
p_bit
->
bndpsd
[
bin
]
-
fgain
;
slowleak
=
p_bit
->
bndpsd
[
bin
]
-
p_bit
->
sgain
;
p_bit
->
excite
[
bin
]
=
fastleak
-
lowcomp
;
if
(
!
(
is_lfe
&&
(
bin
==
6
)))
{
if
(
bndpsd
[
bin
]
<=
bndpsd
[
bin
+
1
])
{
if
(
p_bit
->
bndpsd
[
bin
]
<=
p_bit
->
bndpsd
[
bin
+
1
])
{
begin
=
bin
+
1
;
break
;
}
...
...
@@ -373,12 +349,13 @@ static void ba_compute_excitation (s16 start, s16 end,s16 fgain, s16 fastleak,
for
(
bin
=
begin
;
bin
<
min
(
bndend
,
22
);
bin
++
)
{
if
(
!
(
is_lfe
&&
(
bin
==
6
)))
lowcomp
=
calc_lowcomp
(
lowcomp
,
bndpsd
[
bin
],
bndpsd
[
bin
+
1
],
bin
);
fastleak
-=
fdecay
;
fastleak
=
max
(
fastleak
,
bndpsd
[
bin
]
-
fgain
);
slowleak
-=
sdecay
;
slowleak
=
max
(
slowleak
,
bndpsd
[
bin
]
-
sgain
);
excite
[
bin
]
=
max
(
fastleak
-
lowcomp
,
slowleak
);
lowcomp
=
calc_lowcomp
(
lowcomp
,
p_bit
->
bndpsd
[
bin
],
p_bit
->
bndpsd
[
bin
+
1
],
bin
);
fastleak
-=
p_bit
->
fdecay
;
fastleak
=
max
(
fastleak
,
p_bit
->
bndpsd
[
bin
]
-
fgain
);
slowleak
-=
p_bit
->
sdecay
;
slowleak
=
max
(
slowleak
,
p_bit
->
bndpsd
[
bin
]
-
p_bit
->
sgain
);
p_bit
->
excite
[
bin
]
=
max
(
fastleak
-
lowcomp
,
slowleak
);
}
begin
=
22
;
}
else
{
/* For coupling channel */
...
...
@@ -386,17 +363,17 @@ static void ba_compute_excitation (s16 start, s16 end,s16 fgain, s16 fastleak,
}
for
(
bin
=
begin
;
bin
<
bndend
;
bin
++
)
{
fastleak
-=
fdecay
;
fastleak
=
max
(
fastleak
,
bndpsd
[
bin
]
-
fgain
);
slowleak
-=
sdecay
;
slowleak
=
max
(
slowleak
,
bndpsd
[
bin
]
-
sgain
);
excite
[
bin
]
=
max
(
fastleak
,
slowleak
)
;
fastleak
-=
p_bit
->
fdecay
;
fastleak
=
max
(
fastleak
,
p_bit
->
bndpsd
[
bin
]
-
fgain
);
slowleak
-=
p_bit
->
sdecay
;
slowleak
=
max
(
slowleak
,
p_bit
->
bndpsd
[
bin
]
-
p_bit
->
sgain
);
p_bit
->
excite
[
bin
]
=
max
(
fastleak
,
slowleak
)
;
}
}
static
void
ba_compute_mask
(
s16
start
,
s16
end
,
u16
fscod
,
u16
deltbae
,
u16
delt
nseg
,
u16
deltoffst
[],
u16
deltba
[],
u16
delt
len
[],
s16
excite
[],
s16
mask
[])
static
void
ba_compute_mask
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
u16
fscod
,
u16
delt
bae
,
u16
deltnseg
,
u16
deltoffst
[],
u16
delt
ba
[],
u16
deltlen
[])
{
int
bin
,
k
;
s16
bndstrt
;
...
...
@@ -408,10 +385,10 @@ static void ba_compute_mask (s16 start, s16 end, u16 fscod, u16 deltbae,
/* Compute the masking curve */
for
(
bin
=
bndstrt
;
bin
<
bndend
;
bin
++
)
{
if
(
bndpsd
[
bin
]
<
dbknee
)
{
excite
[
bin
]
+=
((
dbknee
-
bndpsd
[
bin
])
>>
2
);
if
(
p_bit
->
bndpsd
[
bin
]
<
p_bit
->
dbknee
)
{
p_bit
->
excite
[
bin
]
+=
((
p_bit
->
dbknee
-
p_bit
->
bndpsd
[
bin
])
>>
2
);
}
mask
[
bin
]
=
max
(
excite
[
bin
],
hth
[
fscod
][
bin
]);
p_bit
->
mask
[
bin
]
=
max
(
p_bit
->
excite
[
bin
],
hth
[
fscod
][
bin
]);
}
/* Perform delta bit modulation if necessary */
...
...
@@ -427,15 +404,15 @@ static void ba_compute_mask (s16 start, s16 end, u16 fscod, u16 deltbae,
delta
=
(
deltba
[
seg
]
-
4
)
<<
7
;
}
for
(
k
=
0
;
k
<
deltlen
[
seg
];
k
++
)
{
mask
[
band
]
+=
delta
;
p_bit
->
mask
[
band
]
+=
delta
;
band
++
;
}
}
}
}
static
void
ba_compute_bap
(
s16
start
,
s16
end
,
s16
snroffset
,
s16
psd
[]
,
s16
mask
[],
s16
bap
[])
static
void
ba_compute_bap
(
bit_allocate_t
*
p_bit
,
s16
start
,
s16
end
,
s16
snroffset
,
s16
bap
[])
{
int
i
,
j
,
k
;
s16
lastbin
=
0
;
...
...
@@ -447,16 +424,16 @@ static void ba_compute_bap (s16 start, s16 end, s16 snroffset, s16 psd[],
do
{
lastbin
=
min
(
bndtab
[
j
]
+
bndsz
[
j
],
end
);
mask
[
j
]
-=
snroffset
;
mask
[
j
]
-=
floor
;
p_bit
->
mask
[
j
]
-=
snroffset
;
p_bit
->
mask
[
j
]
-=
p_bit
->
floor
;
if
(
mask
[
j
]
<
0
)
mask
[
j
]
=
0
;
if
(
p_bit
->
mask
[
j
]
<
0
)
p_bit
->
mask
[
j
]
=
0
;
mask
[
j
]
&=
0x1fe0
;
mask
[
j
]
+=
floor
;
p_bit
->
mask
[
j
]
&=
0x1fe0
;
p_bit
->
mask
[
j
]
+=
p_bit
->
floor
;
for
(
k
=
i
;
k
<
lastbin
;
k
++
)
{
address
=
(
p
sd
[
i
]
-
mask
[
j
])
>>
5
;
address
=
(
p
_bit
->
psd
[
i
]
-
p_bit
->
mask
[
j
])
>>
5
;
address
=
min
(
63
,
max
(
0
,
address
));
bap
[
i
]
=
baptab
[
address
];
i
++
;
...
...
src/ac3_decoder/ac3_bit_stream.h
View file @
a906b2f5
...
...
@@ -3,7 +3,8 @@
*****************************************************************************
* Copyright (C) 2000, 2001 VideoLAN
*
* Authors: Renaud Dartus <reno@videolan.org>
* Authors: Michel Lespinasse <walken@zoy.org>
* Renaud Dartus <reno@videolan.org>
*
*
* This program is free software; you can redistribute it and/or modify
...
...
src/ac3_decoder/ac3_decoder.c
View file @
a906b2f5
...
...
@@ -3,7 +3,9 @@
*****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN
*
* Authors:
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Michel Lespinasse <walken@zoy.org>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -19,16 +21,23 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA.
*****************************************************************************/
#include "defs.h"
#include "int_types.h"
#include "ac3_decoder.h"
#include "ac3_internal.h"
#include <stdio.h>
void
imdct_init
(
imdct_t
*
p_imdct
);
int
ac3_init
(
ac3dec_t
*
p_ac3dec
)
{
//p_ac3dec->bit_stream.buffer = 0;
//p_ac3dec->bit_stream.i_available = 0;
p_ac3dec
->
mantissa
.
lfsr_state
=
1
;
/* dither_gen initialization */
imdct_init
(
&
p_ac3dec
->
imdct
);
return
0
;
}
...
...
@@ -49,8 +58,8 @@ int ac3_decode_frame (ac3dec_t * p_ac3dec, s16 * buffer)
mantissa_unpack
(
p_ac3dec
);
if
(
p_ac3dec
->
bsi
.
acmod
==
0x2
)
rematrix
(
p_ac3dec
);
imdct
(
p_ac3dec
);
downmix
(
p_ac3dec
,
buffer
);
imdct
(
p_ac3dec
,
buffer
);
//
downmix (p_ac3dec, buffer);
buffer
+=
2
*
256
;
}
...
...
src/ac3_decoder/ac3_decoder.h
View file @
a906b2f5
...
...
@@ -3,8 +3,8 @@
*****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN
*
* Authors:
*
Michel Kaempf <maxx@via.ecp.fr
>
* Authors:
Michel Kaempf <maxx@via.ecp.fr>
*
Renaud Dartus <reno@videolan.org
>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -355,6 +355,63 @@ typedef struct ac3_bit_stream_s
unsigned
int
total_bits_read
;
/* temporary */
}
ac3_bit_stream_t
;
typedef
struct
bit_allocate_s
{
s16
psd
[
256
];
s16
bndpsd
[
256
];
s16
excite
[
256
];
s16
mask
[
256
];
s16
sdecay
;
s16
fdecay
;
s16
sgain
;
s16
dbknee
;
s16
floor
;
}
bit_allocate_t
;
/* These store the persistent state of the packed mantissas */
typedef
struct
mantissa_s
{
float
q_1
[
2
];
float
q_2
[
2
];
float
q_4
[
1
];
s32
q_1_pointer
;
s32
q_2_pointer
;
s32
q_4_pointer
;
u16
lfsr_state
;
}
mantissa_t
;
typedef
struct
complex_s
{
float
real
;
float
imag
;
}
complex_t
;
#define N 512
typedef
struct
imdct_s
{
complex_t
buf
[
N
/
4
];
/* Delay buffer for time domain interleaving */
float
delay
[
6
][
256
];
/* Twiddle factors for IMDCT */
float
xcos1
[
N
/
4
];
float
xsin1
[
N
/
4
];
float
xcos2
[
N
/
8
];
float
xsin2
[
N
/
8
];
/* Twiddle factor LUT */
complex_t
*
w
[
7
];
complex_t
w_1
[
1
];
complex_t
w_2
[
2
];
complex_t
w_4
[
4
];
complex_t
w_8
[
8
];
complex_t
w_16
[
16
];
complex_t
w_32
[
32
];
complex_t
w_64
[
64
];
}
imdct_t
;
struct
ac3dec_s
{
/*
...
...
@@ -373,6 +430,10 @@ struct ac3dec_s
stream_coeffs_t
coeffs
;
stream_samples_t
samples
;
bit_allocate_t
bit_allocate
;
mantissa_t
mantissa
;
imdct_t
imdct
;
};
/**** ac3 decoder inline functions ****/
...
...
src/ac3_decoder/ac3_decoder_thread.c
View file @
a906b2f5
...
...
@@ -2,9 +2,9 @@
* ac3_decoder_thread.c: ac3 decoder thread
*****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN
* $Id: ac3_decoder_thread.c,v 1.2
4 2001/02/11 01:15:10 sam
Exp $
* $Id: ac3_decoder_thread.c,v 1.2
5 2001/02/20 12:06:28 reno
Exp $
*
* Authors:
* Authors:
Michel Lespinasse <walken@zoy.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -164,9 +164,6 @@ static void RunThread (ac3dec_thread_t * p_ac3dec)
intf_DbgMsg
(
"ac3dec debug: running ac3 decoder thread (%p) (pid == %i)"
,
p_ac3dec
,
getpid
());
/* FIXME ! Qu'est-ce que c'est que ce bordel !?!?!?!? --Meuuh */
//msleep (INPUT_PTS_DELAY);
/* Initializing the ac3 decoder thread */
if
(
InitThread
(
p_ac3dec
))
/* XXX?? */
{
...
...
@@ -326,7 +323,6 @@ static void EndThread (ac3dec_thread_t * p_ac3dec)
void
ac3_byte_stream_next
(
ac3_byte_stream_t
*
p_byte_stream
)
{
ac3dec_thread_t
*
p_ac3dec
=
p_byte_stream
->
info
;
/* We are looking for the next TS packet that contains real data,
* and not just a PES header */
do
...
...
src/ac3_decoder/ac3_downmix.c
View file @
a906b2f5
...
...
@@ -3,7 +3,9 @@
*****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN
*
* Authors:
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
* Renaud Dartus <reno@videolan.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -25,302 +27,70 @@
#include "ac3_decoder.h"
#include "ac3_internal.h"
#define NORM 16384
typedef
struct
prefs_s
{
u16
use_dolby_surround
;
u16
dual_mono_channel_select
;
}
prefs_t
;
prefs_t
global_prefs
=
{
0
,
0
};
#include "ac3_downmix.h"
/* Pre-scaled downmix coefficients */
static
float
cmixlev_lut
[
4
]
=
{
0
.
2928
,
0
.
2468
,
0
.
2071
,
0
.
2468
};
static
float
smixlev_lut
[
4
]
=
{
0
.
2928
,
0
.
2071
,
0
.
0
,
0
.
2071
};
static
const
float
cmixlev_lut
[
4
]
=
{
0
.
2928
,
0
.
2468
,
0
.
2071
,
0
.
2468
};
static
const
float
smixlev_lut
[
4
]
=
{
0
.
2928
,
0
.
2071
,
0
.
0
,
0
.
2071
};
/* Downmix into _two_ channels...other downmix modes aren't implemented
* to reduce complexity. Realistically, there aren't many machines around
* with > 2 channel output anyways */
void
downmix
(
ac3dec_t
*
p_ac3dec
,
s16
*
out_buf
)
int
__inline__
downmix
(
ac3dec_t
*
p_ac3dec
,
s16
*
out_buf
)
{
int
j
;
float
right_tmp
;
float
left_tmp
;
float
clev
,
slev
;
float
*
centre
=
0
,
*
left
=
0
,
*
right
=
0
,
*
left_sur
=
0
,
*
right_sur
=
0
;
/*
if (p_ac3dec->bsi.acmod > 7)
intf_ErrMsg( "ac3dec: (downmix) invalid acmod number" );
*/
/* There are two main cases, with or without Dolby Surround */
if
(
global_prefs
.
use_dolby_surround
)
{
switch
(
p_ac3dec
->
bsi
.
acmod
)
{
case
7
:
/* 3/2 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
centre
=
p_ac3dec
->
samples
.
channel
[
1
];
right
=
p_ac3dec
->
samples
.
channel
[
2
];
left_sur
=
p_ac3dec
->
samples
.
channel
[
3
];
right_sur
=
p_ac3dec
->
samples
.
channel
[
4
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
2265
f
*
*
left_sur
++
+
0
.
2265
f
*
*
right_sur
++
;
left_tmp
=
-
1
*
right_tmp
;
right_tmp
+=
0
.
3204
f
*
*
right
++
+
0
.
2265
f
*
*
centre
;
left_tmp
+=
0
.
3204
f
*
*
left
++
+
0
.
2265
f
*
*
centre
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
case
6
:
/* 2/2 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
right
=
p_ac3dec
->
samples
.
channel
[
1
];
left_sur
=
p_ac3dec
->
samples
.
channel
[
2
];
right_sur
=
p_ac3dec
->
samples
.
channel
[
3
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
2265
f
*
*
left_sur
++
+
0
.
2265
f
*
*
right_sur
++
;
left_tmp
=
-
1
*
right_tmp
;
right_tmp
+=
0
.
3204
f
*
*
right
++
;
left_tmp
+=
0
.
3204
f
*
*
left
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
case
5
:
/* 3/1 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
centre
=
p_ac3dec
->
samples
.
channel
[
1
];
right
=
p_ac3dec
->
samples
.
channel
[
2
];
/* Mono surround */
right_sur
=
p_ac3dec
->
samples
.
channel
[
3
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
2265
f
*
*
right_sur
++
;
left_tmp
=
-
right_tmp
;
right_tmp
+=
0
.
3204
f
*
*
right
++
+
0
.
2265
f
*
*
centre
;
left_tmp
+=
0
.
3204
f
*
*
left
++
+
0
.
2265
f
*
*
centre
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
dm_par_t
dm_par
;
float
*
center
=
0
;
case
4
:
/* 2/1 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
right
=
p_ac3dec
->
samples
.
channel
[
1
];
/* Mono surround */
right_sur
=
p_ac3dec
->
samples
.
channel
[
2
];
dm_par
.
clev
=
0
.
0
;
dm_par
.
slev
=
0
.
0
;
dm_par
.
unit
=
1
.
0
;
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
2265
f
*
*
right_sur
++
;
left_tmp
=
-
right_tmp
;
right_tmp
+=
0
.
3204
f
*
*
right
++
;
left_tmp
+=
0
.
3204
f
*
*
left
++
;
if
(
p_ac3dec
->
bsi
.
acmod
&
0x1
)
/* have center */
dm_par
.
clev
=
cmixlev_lut
[
p_ac3dec
->
bsi
.
cmixlev
];
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
if
(
p_ac3dec
->
bsi
.
acmod
&
0x4
)
/* have surround channels */
dm_par
.
slev
=
smixlev_lut
[
p_ac3dec
->
bsi
.
surmixlev
];
case
3
:
/* 3/0 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
centre
=
p_ac3dec
->
samples
.
channel
[
1
];
right
=
p_ac3dec
->
samples
.
channel
[
2
];
dm_par
.
unit
/=
1
.
0
+
dm_par
.
clev
+
dm_par
.
slev
;
dm_par
.
clev
*=
dm_par
.
unit
;
dm_par
.
slev
*=
dm_par
.
unit
;
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
3204
f
*
*
right
++
+
0
.
2265
f
*
*
centre
;
left_tmp
=
0
.
3204
f
*
*
left
++
+
0
.
2265
f
*
*
centre
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
case
2
:
/* 2/0 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
right
=
p_ac3dec
->
samples
.
channel
[
1
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
*
(
out_buf
++
)
=
*
(
left
++
)
*
NORM
;
*
(
out_buf
++
)
=
*
(
right
++
)
*
NORM
;
}
break
;
case
1
:
/* 1/0 */
/* Mono program! */
right
=
p_ac3dec
->
samples
.
channel
[
0
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
7071
f
*
*
right
++
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
case
0
:
/* 1+1 */
/* Dual mono, output selected by user */
right
=
p_ac3dec
->
samples
.
channel
[
global_prefs
.
dual_mono_channel_select
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
7071
f
*
*
right
++
;
/*
if (p_ac3dec->bsi.acmod > 7)
intf_ErrMsg( "ac3dec: (downmix) invalid acmod number" );
*/
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
}
}
else
{
/* Non-Dolby surround downmixes */
switch
(
p_ac3dec
->
bsi
.
acmod
)
{
case
7
:
/* 3/2 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
centre
=
p_ac3dec
->
samples
.
channel
[
1
];
right
=
p_ac3dec
->
samples
.
channel
[
2
];
left_sur
=
p_ac3dec
->
samples
.
channel
[
3
];
right_sur
=
p_ac3dec
->
samples
.
channel
[
4
];
clev
=
cmixlev_lut
[
p_ac3dec
->
bsi
.
cmixlev
];
slev
=
smixlev_lut
[
p_ac3dec
->
bsi
.
surmixlev
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
4142
f
*
*
right
++
+
clev
*
*
centre
+
slev
*
*
right_sur
++
;
left_tmp
=
0
.
4142
f
*
*
left
++
+
clev
*
*
centre
++
+
slev
*
*
left_sur
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
case
7
:
// 3/2
downmix_3f_2r_to_2ch_c
(
p_ac3dec
->
samples
.
channel
[
0
],
&
dm_par
);
break
;
case
6
:
/* 2/2 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
right
=
p_ac3dec
->
samples
.
channel
[
1
];
left_sur
=
p_ac3dec
->
samples
.
channel
[
2
];
right_sur
=
p_ac3dec
->
samples
.
channel
[
3
];
slev
=
smixlev_lut
[
p_ac3dec
->
bsi
.
surmixlev
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
4142
f
*
*
right
++
+
slev
*
*
right_sur
++
;
left_tmp
=
0
.
4142
f
*
*
left
++
+
slev
*
*
left_sur
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
case
5
:
/* 3/1 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
centre
=
p_ac3dec
->
samples
.
channel
[
1
];
right
=
p_ac3dec
->
samples
.
channel
[
2
];
/* Mono surround */
right_sur
=
p_ac3dec
->
samples
.
channel
[
3
];
clev
=
cmixlev_lut
[
p_ac3dec
->
bsi
.
cmixlev
];
slev
=
smixlev_lut
[
p_ac3dec
->
bsi
.
surmixlev
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
4142
f
*
*
right
++
+
clev
*
*
centre
+
slev
*
*
right_sur
;
left_tmp
=
0
.
4142
f
*
*
left
++
+
clev
*
*
centre
++
+
slev
*
*
right_sur
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
case
6
:
// 2/2
downmix_2f_2r_to_2ch_c
(
p_ac3dec
->
samples
.
channel
[
0
],
&
dm_par
);
break
;
case
4
:
/* 2/1 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
right
=
p_ac3dec
->
samples
.
channel
[
1
];
/* Mono surround */
right_sur
=
p_ac3dec
->
samples
.
channel
[
2
];
slev
=
smixlev_lut
[
p_ac3dec
->
bsi
.
surmixlev
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
4142
f
*
*
right
++
+
slev
*
*
right_sur
;
left_tmp
=
0
.
4142
f
*
*
left
++
+
slev
*
*
right_sur
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
case
5
:
// 3/1
downmix_3f_1r_to_2ch_c
(
p_ac3dec
->
samples
.
channel
[
0
],
&
dm_par
);
break
;
case
3
:
/* 3/0 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
centre
=
p_ac3dec
->
samples
.
channel
[
1
];
right
=
p_ac3dec
->
samples
.
channel
[
2
];
clev
=
cmixlev_lut
[
p_ac3dec
->
bsi
.
cmixlev
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
4142
f
*
*
right
++
+
clev
*
*
centre
;
left_tmp
=
0
.
4142
f
*
*
left
++
+
clev
*
*
centre
++
;
*
(
out_buf
++
)
=
left_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
case
4
:
// 2/1
downmix_2f_1r_to_2ch_c
(
p_ac3dec
->
samples
.
channel
[
0
],
&
dm_par
);
break
;
case
2
:
/* 2/0 */
left
=
p_ac3dec
->
samples
.
channel
[
0
];
right
=
p_ac3dec
->
samples
.
channel
[
1
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
*
(
out_buf
++
)
=
*
(
left
++
)
*
NORM
;
*
(
out_buf
++
)
=
*
(
right
++
)
*
NORM
;
}
case
3
:
// 3/0
downmix_3f_0r_to_2ch_c
(
p_ac3dec
->
samples
.
channel
[
0
],
&
dm_par
);
break
;
case
1
:
/* 1/0 */
/* Mono program! */
right
=
p_ac3dec
->
samples
.
channel
[
0
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
7071
f
*
*
right
++
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
case
2
:
break
;
default:
// 1/0
if
(
p_ac3dec
->
bsi
.
acmod
==
1
)
center
=
p_ac3dec
->
samples
.
channel
[
0
];
else
if
(
p_ac3dec
->
bsi
.
acmod
==
0
)
center
=
p_ac3dec
->
samples
.
channel
[
0
];
/* FIXME */
case
0
:
/* 1+1 */
/* Dual mono, output selected by user */
right
=
p_ac3dec
->
samples
.
channel
[
global_prefs
.
dual_mono_channel_select
];
for
(
j
=
0
;
j
<
256
;
j
++
)
{
right_tmp
=
0
.
7071
f
*
*
right
++
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
*
(
out_buf
++
)
=
right_tmp
*
NORM
;
}
break
;
}
stream_sample_1ch_to_s16_c
(
out_buf
,
center
);
return
1
;
}
return
0
;
}
src/ac3_decoder/ac3_downmix.h
0 → 100644
View file @
a906b2f5
/*****************************************************************************
* ac3_downmix.h: ac3 downmix functions
*****************************************************************************
* Copyright (C) 2000, 2001 VideoLAN
*
* Authors: Renaud Dartus <reno@videolan.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA.
*****************************************************************************/
#define NORM 16384
typedef
struct
dm_par_s
{
float
unit
;
float
clev
;
float
slev
;
}
dm_par_t
;
void
downmix_3f_2r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
);
void
downmix_3f_1r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
);
void
downmix_2f_2r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
);
void
downmix_2f_1r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
);
void
downmix_3f_0r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
);
void
stream_sample_2ch_to_s16_c
(
s16
*
s16_samples
,
float
*
left
,
float
*
right
);
void
stream_sample_1ch_to_s16_c
(
s16
*
s16_samples
,
float
*
center
);
src/ac3_decoder/ac3_downmix_c.c
0 → 100644
View file @
a906b2f5
/*****************************************************************************
* ac3_downmix_c.c: ac3 downmix functions
*****************************************************************************
* Copyright (C) 1999, 2000, 2001 VideoLAN
*
* Authors: Renaud Dartus <reno@videolan.org>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA.
*****************************************************************************/
#include "defs.h"
#include "int_types.h"
#include "ac3_decoder.h"
#include "ac3_internal.h"
#include "ac3_bit_stream.h"
#include "ac3_downmix.h"
void
__inline__
downmix_3f_2r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
)
{
int
i
;
float
*
left
,
*
right
,
*
center
,
*
left_sur
,
*
right_sur
;
float
left_tmp
,
right_tmp
;
left
=
samples
;
center
=
samples
+
256
;
right
=
samples
+
256
*
2
;
left_sur
=
samples
+
256
*
3
;
right_sur
=
samples
+
256
*
4
;
for
(
i
=
0
;
i
<
256
;
i
++
)
{
left_tmp
=
dm_par
->
unit
*
*
left
+
dm_par
->
clev
*
*
center
+
dm_par
->
slev
*
*
left_sur
++
;
right_tmp
=
dm_par
->
unit
*
*
right
++
+
dm_par
->
clev
*
*
center
+
dm_par
->
slev
*
*
right_sur
++
;
*
left
++
=
left_tmp
;
*
center
++
=
right_tmp
;
}
}
void
__inline__
downmix_2f_2r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
)
{
int
i
;
float
*
left
,
*
right
,
*
left_sur
,
*
right_sur
;
float
left_tmp
,
right_tmp
;
left
=
&
samples
[
0
];
right
=
&
samples
[
256
];
left_sur
=
&
samples
[
512
];
right_sur
=
&
samples
[
768
];
for
(
i
=
0
;
i
<
256
;
i
++
)
{
left_tmp
=
dm_par
->
unit
*
*
left
+
dm_par
->
slev
*
*
left_sur
++
;
right_tmp
=
dm_par
->
unit
*
*
right
+
dm_par
->
slev
*
*
right_sur
++
;
*
left
++
=
left_tmp
;
*
right
++
=
right_tmp
;
}
}
void
__inline__
downmix_3f_1r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
)
{
int
i
;
float
*
left
,
*
right
,
*
center
,
*
right_sur
;
float
left_tmp
,
right_tmp
;
left
=
&
samples
[
0
];
right
=
&
samples
[
512
];
center
=
&
samples
[
256
];
right_sur
=
&
samples
[
768
];
for
(
i
=
0
;
i
<
256
;
i
++
)
{
left_tmp
=
dm_par
->
unit
*
*
left
+
dm_par
->
clev
*
*
center
-
dm_par
->
slev
*
*
right_sur
;
right_tmp
=
dm_par
->
unit
*
*
right
++
+
dm_par
->
clev
*
*
center
+
dm_par
->
slev
*
*
right_sur
++
;
*
left
++
=
left_tmp
;
*
center
++
=
right_tmp
;
}
}
void
__inline__
downmix_2f_1r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
)
{
int
i
;
float
*
left
,
*
right
,
*
right_sur
;
float
left_tmp
,
right_tmp
;
left
=
&
samples
[
0
];
right
=
&
samples
[
256
];
right_sur
=
&
samples
[
512
];
for
(
i
=
0
;
i
<
256
;
i
++
)
{
left_tmp
=
dm_par
->
unit
*
*
left
-
dm_par
->
slev
*
*
right_sur
;
right_tmp
=
dm_par
->
unit
*
*
right
+
dm_par
->
slev
*
*
right_sur
++
;
*
left
++
=
left_tmp
;
*
right
++
=
right_tmp
;
}
}
void
__inline__
downmix_3f_0r_to_2ch_c
(
float
*
samples
,
dm_par_t
*
dm_par
)
{
int
i
;
float
*
left
,
*
right
,
*
center
;
float
left_tmp
,
right_tmp
;
left
=
&
samples
[
0
];
center
=
&
samples
[
256
];
right
=
&
samples
[
512
];
for
(
i
=
0
;
i
<
256
;
i
++
)
{
left_tmp
=
dm_par
->
unit
*
*
left
+
dm_par
->
clev
*
*
center
;
right_tmp
=
dm_par
->
unit
*
*
right
++
+
dm_par
->
clev
*
*
center
;
*
left
++
=
left_tmp
;
*
center
++
=
right_tmp
;
}
}
void
__inline__
stream_sample_2ch_to_s16_c
(
s16
*
out_buf
,
float
*
left
,
float
*
right
)
{
int
i
;
for
(
i
=
0
;
i
<
256
;
i
++
)
{
*
out_buf
++
=
(
s16
)
(
*
left
++
*
NORM
);
*
out_buf
++
=
(
s16
)
(
*
right
++
*
NORM
);
}
}
void
__inline__
stream_sample_1ch_to_s16_c
(
s16
*
out_buf
,
float
*
center
)
{
int
i
;
float
tmp
;
for
(
i
=
0
;
i
<
256
;
i
++
)
{
*
out_buf
++
=
tmp
=
(
s16
)
(
0
.
7071
f
*
*
center
++
*
NORM
);
*
out_buf
++
=
tmp
*
NORM
;
}
}
src/ac3_decoder/ac3_exponent.c
View file @
a906b2f5
...
...
@@ -3,7 +3,9 @@
*****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN
*
* Authors:
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Michel Lespinasse <walken@zoy.org>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
src/ac3_decoder/ac3_imdct.c
View file @
a906b2f5
...
...
@@ -3,7 +3,9 @@
*****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN
*
* Authors:
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
* Renaud Dartus <reno@videolan.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -19,28 +21,23 @@
* along with this program; if not, write to the Free Software
* Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111, USA.
*****************************************************************************/
#include "defs.h"
#include <math.h>
#include <stdio.h>
#include "int_types.h"
#include "ac3_decoder.h"
#include "ac3_internal.h"
void
imdct_do_256
(
float
x
[],
float
y
[],
float
delay
[]);
void
imdct_do_512
(
float
x
[],
float
y
[],
float
delay
[]);
typedef
struct
complex_s
{
float
real
;
float
imag
;
}
complex_t
;
#define N 512
#include "ac3_downmix.h"
static
complex_t
buf
[
N
/
4
];
void
imdct_do_256
(
imdct_t
*
p_imdct
,
float
x
[],
float
y
[],
int
id
);
void
imdct_do_512
(
imdct_t
*
p_imdct
,
float
x
[],
float
y
[],
int
id
);
/* 128 point bit-reverse LUT */
static
u8
bit_reverse_512
[]
=
{
static
const
u8
bit_reverse_512
[]
=
{
0x00
,
0x40
,
0x20
,
0x60
,
0x10
,
0x50
,
0x30
,
0x70
,
0x08
,
0x48
,
0x28
,
0x68
,
0x18
,
0x58
,
0x38
,
0x78
,
0x04
,
0x44
,
0x24
,
0x64
,
0x14
,
0x54
,
0x34
,
0x74
,
...
...
@@ -58,7 +55,7 @@ static u8 bit_reverse_512[] = {
0x07
,
0x47
,
0x27
,
0x67
,
0x17
,
0x57
,
0x37
,
0x77
,
0x0f
,
0x4f
,
0x2f
,
0x6f
,
0x1f
,
0x5f
,
0x3f
,
0x7f
};
static
u8
bit_reverse_256
[]
=
{
static
const
u8
bit_reverse_256
[]
=
{
0x00
,
0x20
,
0x10
,
0x30
,
0x08
,
0x28
,
0x18
,
0x38
,
0x04
,
0x24
,
0x14
,
0x34
,
0x0c
,
0x2c
,
0x1c
,
0x3c
,
0x02
,
0x22
,
0x12
,
0x32
,
0x0a
,
0x2a
,
0x1a
,
0x3a
,
...
...
@@ -68,25 +65,6 @@ static u8 bit_reverse_256[] = {
0x03
,
0x23
,
0x13
,
0x33
,
0x0b
,
0x2b
,
0x1b
,
0x3b
,
0x07
,
0x27
,
0x17
,
0x37
,
0x0f
,
0x2f
,
0x1f
,
0x3f
};
/* Twiddle factor LUT */
static
complex_t
*
w
[
7
];
static
complex_t
w_1
[
1
];
static
complex_t
w_2
[
2
];
static
complex_t
w_4
[
4
];
static
complex_t
w_8
[
8
];
static
complex_t
w_16
[
16
];
static
complex_t
w_32
[
32
];
static
complex_t
w_64
[
64
];
/* Twiddle factors for IMDCT */
static
float
xcos1
[
N
/
4
];
static
float
xsin1
[
N
/
4
];
static
float
xcos2
[
N
/
8
];
static
float
xsin2
[
N
/
8
];
/* Delay buffer for time domain interleaving */
static
float
delay
[
6
][
256
];
/* Windowing function for Modified DCT - Thank you acroread */
static
float
window
[]
=
{
0
.
00014
,
0
.
00024
,
0
.
00037
,
0
.
00051
,
0
.
00067
,
0
.
000
86
,
0
.
00107
,
0
.
00130
,
...
...
@@ -141,8 +119,7 @@ static __inline__ complex_t cmplx_mult(complex_t a, complex_t b)
return
ret
;
}
static
void
imdct_init
(
void
)
__attribute__
((
__constructor__
));
static
void
imdct_init
(
void
)
void
imdct_init
(
imdct_t
*
p_imdct
)
{
int
i
,
k
;
complex_t
angle_step
;
...
...
@@ -150,24 +127,24 @@ static void imdct_init(void)
/* Twiddle factors to turn IFFT into IMDCT */
for
(
i
=
0
;
i
<
N
/
4
;
i
++
)
{
xcos1
[
i
]
=
-
cos
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
8
*
N
))
;
xsin1
[
i
]
=
-
sin
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
8
*
N
))
;
p_imdct
->
xcos1
[
i
]
=
-
cos
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
8
*
N
))
;
p_imdct
->
xsin1
[
i
]
=
-
sin
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
8
*
N
))
;
}
/* More twiddle factors to turn IFFT into IMDCT */
for
(
i
=
0
;
i
<
N
/
8
;
i
++
)
{
xcos2
[
i
]
=
-
cos
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
4
*
N
))
;
xsin2
[
i
]
=
-
sin
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
4
*
N
))
;
p_imdct
->
xcos2
[
i
]
=
-
cos
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
4
*
N
))
;
p_imdct
->
xsin2
[
i
]
=
-
sin
(
2
*
M_PI
*
(
8
*
i
+
1
)
/
(
4
*
N
))
;
}
/* Canonical twiddle factors for FFT */
w
[
0
]
=
w_1
;
w
[
1
]
=
w_2
;
w
[
2
]
=
w_4
;
w
[
3
]
=
w_8
;
w
[
4
]
=
w_16
;
w
[
5
]
=
w_32
;
w
[
6
]
=
w_64
;
p_imdct
->
w
[
0
]
=
p_imdct
->
w_1
;
p_imdct
->
w
[
1
]
=
p_imdct
->
w_2
;
p_imdct
->
w
[
2
]
=
p_imdct
->
w_4
;
p_imdct
->
w
[
3
]
=
p_imdct
->
w_8
;
p_imdct
->
w
[
4
]
=
p_imdct
->
w_16
;
p_imdct
->
w
[
5
]
=
p_imdct
->
w_32
;
p_imdct
->
w
[
6
]
=
p_imdct
->
w_64
;
for
(
i
=
0
;
i
<
7
;
i
++
)
{
angle_step
.
real
=
cos
(
-
2
.
0
f
*
M_PI
/
(
1
<<
(
i
+
1
)));
...
...
@@ -177,21 +154,53 @@ static void imdct_init(void)
current_angle
.
imag
=
0
.
0
f
;
for
(
k
=
0
;
k
<
1
<<
i
;
k
++
)
{
w
[
i
][
k
]
=
current_angle
;
p_imdct
->
w
[
i
][
k
]
=
current_angle
;
current_angle
=
cmplx_mult
(
current_angle
,
angle_step
);
}
}
}
void
imdct
(
ac3dec_t
*
p_ac3dec
)
void
imdct
(
ac3dec_t
*
p_ac3dec
,
s16
*
buffer
)
{
int
i
;
int
i
,
i_stream_done
;
int
doable
=
0
;
void
(
*
do_imdct
)(
imdct_t
*
p_imdct
,
float
x
[],
float
y
[],
int
id
);
/* Test if dm in frequency is doable */
if
(
!
(
doable
=
p_ac3dec
->
audblk
.
blksw
[
0
])
)
do_imdct
=
imdct_do_512
;
else
do_imdct
=
imdct_do_256
;
/* Downmix in the frequency domain if all the channes use the same imdct */
for
(
i
=
0
;
i
<
p_ac3dec
->
bsi
.
nfchans
;
i
++
)
{
if
(
doable
!=
p_ac3dec
->
audblk
.
blksw
[
i
]
)
{
do_imdct
=
NULL
;
break
;
}
}
if
(
do_imdct
)
{
i_stream_done
=
downmix
(
p_ac3dec
,
buffer
);
do_imdct
(
&
p_ac3dec
->
imdct
,
p_ac3dec
->
coeffs
.
fbw
[
0
],
p_ac3dec
->
samples
.
channel
[
0
],
0
);
do_imdct
(
&
p_ac3dec
->
imdct
,
p_ac3dec
->
coeffs
.
fbw
[
1
],
p_ac3dec
->
samples
.
channel
[
1
],
1
);
}
else
{
for
(
i
=
0
;
i
<
p_ac3dec
->
bsi
.
nfchans
;
i
++
)
{
if
(
p_ac3dec
->
audblk
.
blksw
[
i
])
imdct_do_256
(
p_ac3dec
->
coeffs
.
fbw
[
i
],
p_ac3dec
->
samples
.
channel
[
i
],
delay
[
i
]
);
imdct_do_256
(
&
p_ac3dec
->
imdct
,
p_ac3dec
->
coeffs
.
fbw
[
i
],
p_ac3dec
->
samples
.
channel
[
i
],
i
);
else
imdct_do_512
(
p_ac3dec
->
coeffs
.
fbw
[
i
],
p_ac3dec
->
samples
.
channel
[
i
],
delay
[
i
]);
imdct_do_512
(
&
p_ac3dec
->
imdct
,
p_ac3dec
->
coeffs
.
fbw
[
i
],
p_ac3dec
->
samples
.
channel
[
i
],
i
);
}
i_stream_done
=
downmix
(
p_ac3dec
,
buffer
);
}
if
(
!
i_stream_done
)
/* We have to stream sample */
{
stream_sample_2ch_to_s16_c
(
buffer
,
p_ac3dec
->
samples
.
channel
[
0
],
p_ac3dec
->
samples
.
channel
[
1
]);
}
/* XXX?? We don't bother with the IMDCT for the LFE as it's currently
...
...
@@ -200,8 +209,7 @@ void imdct (ac3dec_t * p_ac3dec)
// imdct_do_512(coeffs->lfe,samples->channel[5],delay[5]);
}
void
imdct_do_512
(
float
x
[],
float
y
[],
float
delay
[])
void
imdct_do_512
(
imdct_t
*
p_imdct
,
float
x
[],
float
y
[],
int
id
)
{
int
i
,
k
;
int
p
,
q
;
...
...
@@ -222,15 +230,15 @@ imdct_do_512(float x[],float y[],float delay[])
/* Pre IFFT complex multiply plus IFFT cmplx conjugate */
for
(
i
=
0
;
i
<
N
/
4
;
i
++
)
{
/* z[i] = (X[N/2-2*i-1] + j * X[2*i]) * (xcos1[i] + j * xsin1[i]) ; */
buf
[
i
].
real
=
(
x
[
N
/
2
-
2
*
i
-
1
]
*
xcos1
[
i
])
-
(
x
[
2
*
i
]
*
xsin1
[
i
]);
buf
[
i
].
imag
=
-
((
x
[
2
*
i
]
*
xcos1
[
i
])
+
(
x
[
N
/
2
-
2
*
i
-
1
]
*
xsin1
[
i
]));
p_imdct
->
buf
[
i
].
real
=
(
x
[
N
/
2
-
2
*
i
-
1
]
*
p_imdct
->
xcos1
[
i
])
-
(
x
[
2
*
i
]
*
p_imdct
->
xsin1
[
i
]);
p_imdct
->
buf
[
i
].
imag
=
-
((
x
[
2
*
i
]
*
p_imdct
->
xcos1
[
i
])
+
(
x
[
N
/
2
-
2
*
i
-
1
]
*
p_imdct
->
xsin1
[
i
]));
}
/* Bit reversed shuffling */
for
(
i
=
0
;
i
<
N
/
4
;
i
++
)
{
k
=
bit_reverse_512
[
i
];
if
(
k
<
i
)
swap_cmplx
(
&
buf
[
i
],
&
buf
[
k
]);
swap_cmplx
(
&
p_imdct
->
buf
[
i
],
&
p_imdct
->
buf
[
k
]);
}
/* FFT Merge */
...
...
@@ -242,14 +250,14 @@ imdct_do_512(float x[],float y[],float delay[])
for
(
i
=
0
;
i
<
128
;
i
+=
two_m_plus_one
)
{
p
=
k
+
i
;
q
=
p
+
two_m
;
tmp_a_r
=
buf
[
p
].
real
;
tmp_a_i
=
buf
[
p
].
imag
;
tmp_b_r
=
buf
[
q
].
real
*
w
[
m
][
k
].
real
-
buf
[
q
].
imag
*
w
[
m
][
k
].
imag
;
tmp_b_i
=
buf
[
q
].
imag
*
w
[
m
][
k
].
real
+
buf
[
q
].
real
*
w
[
m
][
k
].
imag
;
buf
[
p
].
real
=
tmp_a_r
+
tmp_b_r
;
buf
[
p
].
imag
=
tmp_a_i
+
tmp_b_i
;
buf
[
q
].
real
=
tmp_a_r
-
tmp_b_r
;
buf
[
q
].
imag
=
tmp_a_i
-
tmp_b_i
;
tmp_a_r
=
p_imdct
->
buf
[
p
].
real
;
tmp_a_i
=
p_imdct
->
buf
[
p
].
imag
;
tmp_b_r
=
p_imdct
->
buf
[
q
].
real
*
p_imdct
->
w
[
m
][
k
].
real
-
p_imdct
->
buf
[
q
].
imag
*
p_imdct
->
w
[
m
][
k
].
imag
;
tmp_b_i
=
p_imdct
->
buf
[
q
].
imag
*
p_imdct
->
w
[
m
][
k
].
real
+
p_imdct
->
buf
[
q
].
real
*
p_imdct
->
w
[
m
][
k
].
imag
;
p_imdct
->
buf
[
p
].
real
=
tmp_a_r
+
tmp_b_r
;
p_imdct
->
buf
[
p
].
imag
=
tmp_a_i
+
tmp_b_i
;
p_imdct
->
buf
[
q
].
real
=
tmp_a_r
-
tmp_b_r
;
p_imdct
->
buf
[
q
].
imag
=
tmp_a_i
-
tmp_b_i
;
}
}
}
...
...
@@ -257,42 +265,41 @@ imdct_do_512(float x[],float y[],float delay[])
/* Post IFFT complex multiply plus IFFT complex conjugate*/
for
(
i
=
0
;
i
<
N
/
4
;
i
++
)
{
/* y[n] = z[n] * (xcos1[n] + j * xsin1[n]) ; */
tmp_a_r
=
buf
[
i
].
real
;
tmp_a_i
=
-
buf
[
i
].
imag
;
buf
[
i
].
real
=
(
tmp_a_r
*
xcos1
[
i
])
-
(
tmp_a_i
*
xsin1
[
i
]);
buf
[
i
].
imag
=
(
tmp_a_r
*
xsin1
[
i
])
+
(
tmp_a_i
*
xcos1
[
i
]);
tmp_a_r
=
p_imdct
->
buf
[
i
].
real
;
tmp_a_i
=
-
p_imdct
->
buf
[
i
].
imag
;
p_imdct
->
buf
[
i
].
real
=
(
tmp_a_r
*
p_imdct
->
xcos1
[
i
])
-
(
tmp_a_i
*
p_imdct
->
xsin1
[
i
]);
p_imdct
->
buf
[
i
].
imag
=
(
tmp_a_r
*
p_imdct
->
xsin1
[
i
])
+
(
tmp_a_i
*
p_imdct
->
xcos1
[
i
]);
}
y_ptr
=
y
;
delay_ptr
=
delay
;
delay_ptr
=
p_imdct
->
delay
[
id
]
;
window_ptr
=
window
;
/* Window and convert to real valued signal */
for
(
i
=
0
;
i
<
N
/
8
;
i
++
)
{
*
y_ptr
++
=
2
.
0
f
*
(
-
buf
[
N
/
8
+
i
].
imag
*
*
window_ptr
++
+
*
delay_ptr
++
);
*
y_ptr
++
=
2
.
0
f
*
(
buf
[
N
/
8
-
i
-
1
].
real
*
*
window_ptr
++
+
*
delay_ptr
++
);
*
y_ptr
++
=
2
.
0
f
*
(
-
p_imdct
->
buf
[
N
/
8
+
i
].
imag
*
*
window_ptr
++
+
*
delay_ptr
++
);
*
y_ptr
++
=
2
.
0
f
*
(
p_imdct
->
buf
[
N
/
8
-
i
-
1
].
real
*
*
window_ptr
++
+
*
delay_ptr
++
);
}
for
(
i
=
0
;
i
<
N
/
8
;
i
++
)
{
*
y_ptr
++
=
2
.
0
f
*
(
-
buf
[
i
].
real
*
*
window_ptr
++
+
*
delay_ptr
++
);
*
y_ptr
++
=
2
.
0
f
*
(
buf
[
N
/
4
-
i
-
1
].
imag
*
*
window_ptr
++
+
*
delay_ptr
++
);
*
y_ptr
++
=
2
.
0
f
*
(
-
p_imdct
->
buf
[
i
].
real
*
*
window_ptr
++
+
*
delay_ptr
++
);
*
y_ptr
++
=
2
.
0
f
*
(
p_imdct
->
buf
[
N
/
4
-
i
-
1
].
imag
*
*
window_ptr
++
+
*
delay_ptr
++
);
}
/* The trailing edge of the window goes into the delay line */
delay_ptr
=
delay
;
delay_ptr
=
p_imdct
->
delay
[
id
]
;
for
(
i
=
0
;
i
<
N
/
8
;
i
++
)
{
*
delay_ptr
++
=
-
buf
[
N
/
8
+
i
].
real
*
*--
window_ptr
;
*
delay_ptr
++
=
buf
[
N
/
8
-
i
-
1
].
imag
*
*--
window_ptr
;
*
delay_ptr
++
=
-
p_imdct
->
buf
[
N
/
8
+
i
].
real
*
*--
window_ptr
;
*
delay_ptr
++
=
p_imdct
->
buf
[
N
/
8
-
i
-
1
].
imag
*
*--
window_ptr
;
}
for
(
i
=
0
;
i
<
N
/
8
;
i
++
)
{
*
delay_ptr
++
=
buf
[
i
].
imag
*
*--
window_ptr
;
*
delay_ptr
++
=
-
buf
[
N
/
4
-
i
-
1
].
real
*
*--
window_ptr
;
*
delay_ptr
++
=
p_imdct
->
buf
[
i
].
imag
*
*--
window_ptr
;
*
delay_ptr
++
=
-
p_imdct
->
buf
[
N
/
4
-
i
-
1
].
real
*
*--
window_ptr
;
}
}
void
imdct_do_256
(
float
x
[],
float
y
[],
float
delay
[])
void
imdct_do_256
(
imdct_t
*
p_imdct
,
float
x
[],
float
y
[],
int
id
)
{
int
i
,
k
;
int
p
,
q
;
...
...
@@ -307,8 +314,8 @@ imdct_do_256(float x[],float y[],float delay[])
complex_t
*
buf_1
,
*
buf_2
;
buf_1
=
&
buf
[
0
];
buf_2
=
&
buf
[
64
];
buf_1
=
&
p_imdct
->
buf
[
0
];
buf_2
=
&
p_imdct
->
buf
[
64
];
/* Pre IFFT complex multiply plus IFFT cmplx conjugate */
for
(
k
=
0
;
k
<
N
/
8
;
k
++
)
{
...
...
@@ -319,11 +326,11 @@ imdct_do_256(float x[],float y[],float delay[])
q
=
2
*
(
2
*
k
);
/* Z1[k] = (X1[N/4-2*k-1] + j * X1[2*k]) * (xcos2[k] + j * xsin2[k]); */
buf_1
[
k
].
real
=
x
[
p
]
*
xcos2
[
k
]
-
x
[
q
]
*
xsin2
[
k
];
buf_1
[
k
].
imag
=
-
(
x
[
q
]
*
xcos2
[
k
]
+
x
[
p
]
*
xsin2
[
k
]);
buf_1
[
k
].
real
=
x
[
p
]
*
p_imdct
->
xcos2
[
k
]
-
x
[
q
]
*
p_imdct
->
xsin2
[
k
];
buf_1
[
k
].
imag
=
-
(
x
[
q
]
*
p_imdct
->
xcos2
[
k
]
+
x
[
p
]
*
p_imdct
->
xsin2
[
k
]);
/* Z2[k] = (X2[N/4-2*k-1] + j * X2[2*k]) * (xcos2[k] + j * xsin2[k]); */
buf_2
[
k
].
real
=
x
[
p
+
1
]
*
xcos2
[
k
]
-
x
[
q
+
1
]
*
xsin2
[
k
];
buf_2
[
k
].
imag
=
-
(
x
[
q
+
1
]
*
xcos2
[
k
]
+
x
[
p
+
1
]
*
xsin2
[
k
]);
buf_2
[
k
].
real
=
x
[
p
+
1
]
*
p_imdct
->
xcos2
[
k
]
-
x
[
q
+
1
]
*
p_imdct
->
xsin2
[
k
];
buf_2
[
k
].
imag
=
-
(
x
[
q
+
1
]
*
p_imdct
->
xcos2
[
k
]
+
x
[
p
+
1
]
*
p_imdct
->
xsin2
[
k
]);
}
/* IFFT Bit reversed shuffling */
...
...
@@ -347,8 +354,8 @@ imdct_do_256(float x[],float y[],float delay[])
/* Do block 1 */
tmp_a_r
=
buf_1
[
p
].
real
;
tmp_a_i
=
buf_1
[
p
].
imag
;
tmp_b_r
=
buf_1
[
q
].
real
*
w
[
m
][
k
].
real
-
buf_1
[
q
].
imag
*
w
[
m
][
k
].
imag
;
tmp_b_i
=
buf_1
[
q
].
imag
*
w
[
m
][
k
].
real
+
buf_1
[
q
].
real
*
w
[
m
][
k
].
imag
;
tmp_b_r
=
buf_1
[
q
].
real
*
p_imdct
->
w
[
m
][
k
].
real
-
buf_1
[
q
].
imag
*
p_imdct
->
w
[
m
][
k
].
imag
;
tmp_b_i
=
buf_1
[
q
].
imag
*
p_imdct
->
w
[
m
][
k
].
real
+
buf_1
[
q
].
real
*
p_imdct
->
w
[
m
][
k
].
imag
;
buf_1
[
p
].
real
=
tmp_a_r
+
tmp_b_r
;
buf_1
[
p
].
imag
=
tmp_a_i
+
tmp_b_i
;
buf_1
[
q
].
real
=
tmp_a_r
-
tmp_b_r
;
...
...
@@ -357,8 +364,8 @@ imdct_do_256(float x[],float y[],float delay[])
/* Do block 2 */
tmp_a_r
=
buf_2
[
p
].
real
;
tmp_a_i
=
buf_2
[
p
].
imag
;
tmp_b_r
=
buf_2
[
q
].
real
*
w
[
m
][
k
].
real
-
buf_2
[
q
].
imag
*
w
[
m
][
k
].
imag
;
tmp_b_i
=
buf_2
[
q
].
imag
*
w
[
m
][
k
].
real
+
buf_2
[
q
].
real
*
w
[
m
][
k
].
imag
;
tmp_b_r
=
buf_2
[
q
].
real
*
p_imdct
->
w
[
m
][
k
].
real
-
buf_2
[
q
].
imag
*
p_imdct
->
w
[
m
][
k
].
imag
;
tmp_b_i
=
buf_2
[
q
].
imag
*
p_imdct
->
w
[
m
][
k
].
real
+
buf_2
[
q
].
real
*
p_imdct
->
w
[
m
][
k
].
imag
;
buf_2
[
p
].
real
=
tmp_a_r
+
tmp_b_r
;
buf_2
[
p
].
imag
=
tmp_a_i
+
tmp_b_i
;
buf_2
[
q
].
real
=
tmp_a_r
-
tmp_b_r
;
...
...
@@ -372,13 +379,13 @@ imdct_do_256(float x[],float y[],float delay[])
/* y1[n] = z1[n] * (xcos2[n] + j * xs in2[n]) ; */
tmp_a_r
=
buf_1
[
i
].
real
;
tmp_a_i
=
-
buf_1
[
i
].
imag
;
buf_1
[
i
].
real
=
(
tmp_a_r
*
xcos2
[
i
])
-
(
tmp_a_i
*
xsin2
[
i
]);
buf_1
[
i
].
imag
=
(
tmp_a_r
*
xsin2
[
i
])
+
(
tmp_a_i
*
xcos2
[
i
]);
buf_1
[
i
].
real
=
(
tmp_a_r
*
p_imdct
->
xcos2
[
i
])
-
(
tmp_a_i
*
p_imdct
->
xsin2
[
i
]);
buf_1
[
i
].
imag
=
(
tmp_a_r
*
p_imdct
->
xsin2
[
i
])
+
(
tmp_a_i
*
p_imdct
->
xcos2
[
i
]);
/* y2[n] = z2[n] * (xcos2[n] + j * xsin2[n]) ; */
tmp_a_r
=
buf_2
[
i
].
real
;
tmp_a_i
=
-
buf_2
[
i
].
imag
;
buf_2
[
i
].
real
=
(
tmp_a_r
*
xcos2
[
i
])
-
(
tmp_a_i
*
xsin2
[
i
]);
buf_2
[
i
].
imag
=
(
tmp_a_r
*
xsin2
[
i
])
+
(
tmp_a_i
*
xcos2
[
i
]);
buf_2
[
i
].
real
=
(
tmp_a_r
*
p_imdct
->
xcos2
[
i
])
-
(
tmp_a_i
*
p_imdct
->
xsin2
[
i
]);
buf_2
[
i
].
imag
=
(
tmp_a_r
*
p_imdct
->
xsin2
[
i
])
+
(
tmp_a_i
*
p_imdct
->
xcos2
[
i
]);
}
/* Window and convert to real valued signal */
...
...
@@ -395,7 +402,7 @@ imdct_do_256(float x[],float y[],float delay[])
/* Overlap and add */
for
(
i
=
0
;
i
<
N
/
2
;
i
++
)
{
y
[
i
]
=
2
*
(
y
[
i
]
+
delay
[
i
]);
delay
[
i
]
=
y
[
N
/
2
+
i
];
y
[
i
]
=
2
*
(
y
[
i
]
+
p_imdct
->
delay
[
id
]
[
i
]);
p_imdct
->
delay
[
id
]
[
i
]
=
y
[
N
/
2
+
i
];
}
}
src/ac3_decoder/ac3_internal.h
View file @
a906b2f5
...
...
@@ -3,7 +3,7 @@
*****************************************************************************
* Copyright (C) 2000 VideoLAN
*
* Authors:
* Authors:
Michel Lespinasse <walken@zoy.org>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -36,13 +36,13 @@
void
bit_allocate
(
ac3dec_t
*
);
/* ac3_downmix.c */
void
downmix
(
ac3dec_t
*
,
s16
*
);
int
downmix
(
ac3dec_t
*
,
s16
*
);
/* ac3_exponent.c */
int
exponent_unpack
(
ac3dec_t
*
);
/* ac3_imdct.c */
void
imdct
(
ac3dec_t
*
p_ac3dec
);
void
imdct
(
ac3dec_t
*
p_ac3dec
,
s16
*
buffer
);
/* ac3_mantissa.c */
void
mantissa_unpack
(
ac3dec_t
*
);
...
...
src/ac3_decoder/ac3_mantissa.c
View file @
a906b2f5
...
...
@@ -4,6 +4,7 @@
* Copyright (C) 1999, 2000, 2001 VideoLAN
*
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
* Renaud Dartus <reno@videolan.org>
*
* This program is free software; you can redistribute it and/or modify
...
...
@@ -36,21 +37,21 @@
#define Q0 ((-2 << 15) / 3.0)
#define Q1 (0)
#define Q2 ((2 << 15) / 3.0)
static
float
q_1_0
[
32
]
=
static
const
float
q_1_0
[
32
]
=
{
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
0
,
0
,
0
,
0
,
0
};
static
float
q_1_1
[
32
]
=
static
const
float
q_1_1
[
32
]
=
{
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q2
,
Q2
,
Q2
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q2
,
Q2
,
Q2
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q2
,
Q2
,
Q2
,
0
,
0
,
0
,
0
,
0
};
static
float
q_1_2
[
32
]
=
static
const
float
q_1_2
[
32
]
=
{
Q0
,
Q1
,
Q2
,
Q0
,
Q1
,
Q2
,
Q0
,
Q1
,
Q2
,
Q0
,
Q1
,
Q2
,
Q0
,
Q1
,
Q2
,
Q0
,
Q1
,
Q2
,
...
...
@@ -66,7 +67,7 @@ static float q_1_2[ 32 ] =
#define Q2 (0)
#define Q3 ((2 << 15) / 5.0)
#define Q4 ((4 << 15) / 5.0)
static
float
q_2_0
[
128
]
=
static
const
float
q_2_0
[
128
]
=
{
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
...
...
@@ -75,7 +76,7 @@ static float q_2_0[ 128 ] =
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
0
,
0
,
0
};
static
float
q_2_1
[
128
]
=
static
const
float
q_2_1
[
128
]
=
{
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
Q3
,
Q3
,
Q3
,
Q3
,
Q3
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
Q3
,
Q3
,
Q3
,
Q3
,
Q3
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
...
...
@@ -84,7 +85,7 @@ static float q_2_1[ 128 ] =
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q2
,
Q2
,
Q2
,
Q2
,
Q2
,
Q3
,
Q3
,
Q3
,
Q3
,
Q3
,
Q4
,
Q4
,
Q4
,
Q4
,
Q4
,
0
,
0
,
0
};
static
float
q_2_2
[
128
]
=
static
const
float
q_2_2
[
128
]
=
{
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
...
...
@@ -110,7 +111,7 @@ static float q_2_2[ 128 ] =
#define Q8 ((6 << 15) / 11.0)
#define Q9 ((8 << 15) / 11.0)
#define QA ((10 << 15) / 11.0)
static
float
q_4_0
[
128
]
=
static
const
float
q_4_0
[
128
]
=
{
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q0
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
Q1
,
...
...
@@ -125,7 +126,7 @@ static float q_4_0[ 128 ] =
QA
,
QA
,
QA
,
QA
,
QA
,
QA
,
QA
,
QA
,
QA
,
QA
,
QA
,
0
,
0
,
0
,
0
,
0
,
0
,
0
};
static
float
q_4_1
[
128
]
=
static
const
float
q_4_1
[
128
]
=
{
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q5
,
Q6
,
Q7
,
Q8
,
Q9
,
QA
,
Q0
,
Q1
,
Q2
,
Q3
,
Q4
,
Q5
,
Q6
,
Q7
,
Q8
,
Q9
,
QA
,
...
...
@@ -154,14 +155,14 @@ static float q_4_1[ 128 ] =
/* Lookup tables of 0.16 two's complement quantization values */
static
float
q_3
[
8
]
=
static
const
float
q_3
[
8
]
=
{
(
-
6
<<
15
)
/
7
.
0
,
(
-
4
<<
15
)
/
7
.
0
,
(
-
2
<<
15
)
/
7
.
0
,
0
,
(
2
<<
15
)
/
7
.
0
,
(
4
<<
15
)
/
7
.
0
,
(
6
<<
15
)
/
7
.
0
,
0
};
static
float
q_5
[
16
]
=
static
const
float
q_5
[
16
]
=
{
(
-
14
<<
15
)
/
15
.
0
,
(
-
12
<<
15
)
/
15
.
0
,
(
-
10
<<
15
)
/
15
.
0
,
(
-
8
<<
15
)
/
15
.
0
,
(
-
6
<<
15
)
/
15
.
0
,
(
-
4
<<
15
)
/
15
.
0
,
...
...
@@ -171,22 +172,14 @@ static float q_5[16] =
0
};
/* These store the persistent state of the packed mantissas */
static
float
q_1
[
2
];
static
float
q_2
[
2
];
static
float
q_4
[
1
];
static
s32
q_1_pointer
;
static
s32
q_2_pointer
;
static
s32
q_4_pointer
;
/* Conversion from bap to number of bits in the mantissas
* zeros account for cases 0,1,2,4 which are special cased */
static
u16
qnttztab
[
16
]
=
static
const
u16
qnttztab
[
16
]
=
{
0
,
0
,
0
,
3
,
0
,
4
,
5
,
6
,
7
,
8
,
9
,
10
,
11
,
12
,
14
,
16
};
static
float
exp_lut
[
25
]
=
static
const
float
exp_lut
[
25
]
=
{
6.10351562500000000000000000e-05
,
3.05175781250000000000000000e-05
,
...
...
@@ -215,7 +208,7 @@ static float exp_lut[ 25 ] =
3.63797880709171295166015625e-12
,
};
const
u16
dither_lut
[
256
]
=
static
const
u16
dither_lut
[
256
]
=
{
0x0000
,
0xa011
,
0xe033
,
0x4022
,
0x6077
,
0xc066
,
0x8044
,
0x2055
,
0xc0ee
,
0x60ff
,
0x20dd
,
0x80cc
,
0xa099
,
0x0088
,
0x40aa
,
0xe0bb
,
...
...
@@ -251,14 +244,13 @@ const u16 dither_lut[256] =
0x8bf4
,
0x2be5
,
0x6bc7
,
0xcbd6
,
0xeb83
,
0x4b92
,
0x0bb0
,
0xaba1
};
u16
lfsr_state
=
1
;
static
__inline__
u16
dither_gen
(
void
)
static
__inline__
u16
dither_gen
(
mantissa_t
*
p_mantissa
)
{
s16
state
;
state
=
dither_lut
[
lfsr_state
>>
8
]
^
(
lfsr_state
<<
8
);
lfsr_state
=
(
u16
)
state
;
state
=
dither_lut
[
p_mantissa
->
lfsr_state
>>
8
]
^
(
p_mantissa
->
lfsr_state
<<
8
);
p_mantissa
->
lfsr_state
=
(
u16
)
state
;
return
(
(
state
*
(
s32
)
(
0
.
707106
*
256
.
0
))
>>
8
);
}
...
...
@@ -274,75 +266,75 @@ static __inline__ float float_get (ac3dec_t * p_ac3dec, u16 bap, u16 exp)
case
0
:
if
(
p_ac3dec
->
audblk
.
dithflag
[
exp
])
{
return
(
dither_gen
()
*
exp_lut
[
exp
]
);
return
(
dither_gen
(
&
p_ac3dec
->
mantissa
)
*
exp_lut
[
exp
]
);
}
return
(
0
);
case
1
:
if
(
q_1_pointer
>=
0
)
if
(
p_ac3dec
->
mantissa
.
q_1_pointer
>=
0
)
{
return
(
q_1
[
q_1_pointer
--
]
*
exp_lut
[
exp
]);
return
(
p_ac3dec
->
mantissa
.
q_1
[
p_ac3dec
->
mantissa
.
q_1_pointer
--
]
*
exp_lut
[
exp
]);
}
if
((
group_code
=
bitstream_get
(
&
(
p_ac3dec
->
bit_stream
),
5
))
>=
27
)
{
intf_
ErrMsg
(
"ac3dec error: invalid mantissa"
);
intf_
WarnMsg
(
1
,
"ac3dec error: invalid mantissa"
);
}
q_1
[
1
]
=
q_1_1
[
group_code
];
q_1
[
0
]
=
q_1_2
[
group_code
];
p_ac3dec
->
mantissa
.
q_1
[
1
]
=
q_1_1
[
group_code
];
p_ac3dec
->
mantissa
.
q_1
[
0
]
=
q_1_2
[
group_code
];
q_1_pointer
=
1
;
p_ac3dec
->
mantissa
.
q_1_pointer
=
1
;
return
(
q_1_0
[
group_code
]
*
exp_lut
[
exp
]);
case
2
:
if
(
q_2_pointer
>=
0
)
if
(
p_ac3dec
->
mantissa
.
q_2_pointer
>=
0
)
{
return
(
q_2
[
q_2_pointer
--
]
*
exp_lut
[
exp
]);
return
(
p_ac3dec
->
mantissa
.
q_2
[
p_ac3dec
->
mantissa
.
q_2_pointer
--
]
*
exp_lut
[
exp
]);
}
if
((
group_code
=
bitstream_get
(
&
(
p_ac3dec
->
bit_stream
),
7
))
>=
125
)
{
intf_
ErrMsg
(
"ac3dec error: invalid mantissa"
);
intf_
WarnMsg
(
1
,
"ac3dec error: invalid mantissa"
);
}
q_2
[
1
]
=
q_2_1
[
group_code
];
q_2
[
0
]
=
q_2_2
[
group_code
];
p_ac3dec
->
mantissa
.
q_2
[
1
]
=
q_2_1
[
group_code
];
p_ac3dec
->
mantissa
.
q_2
[
0
]
=
q_2_2
[
group_code
];
q_2_pointer
=
1
;
p_ac3dec
->
mantissa
.
q_2_pointer
=
1
;
return
(
q_2_0
[
group_code
]
*
exp_lut
[
exp
]);
case
3
:
if
((
group_code
=
bitstream_get
(
&
(
p_ac3dec
->
bit_stream
),
3
))
>=
7
)
{
intf_
ErrMsg
(
"ac3dec error: invalid mantissa"
);
intf_
WarnMsg
(
1
,
"ac3dec error: invalid mantissa"
);
}
return
(
q_3
[
group_code
]
*
exp_lut
[
exp
]);
case
4
:
if
(
q_4_pointer
>=
0
)
if
(
p_ac3dec
->
mantissa
.
q_4_pointer
>=
0
)
{
return
(
q_4
[
q_4_pointer
--
]
*
exp_lut
[
exp
]);
return
(
p_ac3dec
->
mantissa
.
q_4
[
p_ac3dec
->
mantissa
.
q_4_pointer
--
]
*
exp_lut
[
exp
]);
}
if
((
group_code
=
bitstream_get
(
&
(
p_ac3dec
->
bit_stream
),
7
))
>=
121
)
{
intf_
ErrMsg
(
"ac3dec error: invalid mantissa"
);
intf_
WarnMsg
(
1
,
"ac3dec error: invalid mantissa"
);
}
q_4
[
0
]
=
q_4_1
[
group_code
];
p_ac3dec
->
mantissa
.
q_4
[
0
]
=
q_4_1
[
group_code
];
q_4_pointer
=
0
;
p_ac3dec
->
mantissa
.
q_4_pointer
=
0
;
return
(
q_4_0
[
group_code
]
*
exp_lut
[
exp
]);
case
5
:
if
((
group_code
=
bitstream_get
(
&
(
p_ac3dec
->
bit_stream
),
4
))
>=
15
)
{
intf_
ErrMsg
(
"ac3dec error: invalid mantissa"
);
intf_
WarnMsg
(
1
,
"ac3dec error: invalid mantissa"
);
}
return
(
q_5
[
group_code
]
*
exp_lut
[
exp
]);
...
...
@@ -394,7 +386,7 @@ static __inline__ void uncouple_channel (ac3dec_t * p_ac3dec, u32 ch)
* so the channels are uncorrelated */
if
(
p_ac3dec
->
audblk
.
dithflag
[
ch
]
&&
!
p_ac3dec
->
audblk
.
cpl_bap
[
i
])
{
p_ac3dec
->
coeffs
.
fbw
[
ch
][
i
]
=
cpl_coord
*
dither_gen
()
*
p_ac3dec
->
coeffs
.
fbw
[
ch
][
i
]
=
cpl_coord
*
dither_gen
(
&
p_ac3dec
->
mantissa
)
*
exp_lut
[
p_ac3dec
->
audblk
.
cpl_exp
[
i
]];
}
else
{
p_ac3dec
->
coeffs
.
fbw
[
ch
][
i
]
=
cpl_coord
*
p_ac3dec
->
audblk
.
cplfbw
[
i
];
...
...
@@ -408,9 +400,9 @@ void mantissa_unpack (ac3dec_t * p_ac3dec)
{
int
i
,
j
;
q_1_pointer
=
-
1
;
q_2_pointer
=
-
1
;
q_4_pointer
=
-
1
;
p_ac3dec
->
mantissa
.
q_1_pointer
=
-
1
;
p_ac3dec
->
mantissa
.
q_2_pointer
=
-
1
;
p_ac3dec
->
mantissa
.
q_4_pointer
=
-
1
;
if
(
p_ac3dec
->
audblk
.
cplinu
)
{
...
...
src/ac3_decoder/ac3_parse.c
View file @
a906b2f5
...
...
@@ -4,6 +4,7 @@
* Copyright (C) 1999, 2000, 2001 VideoLAN
*
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
* Renaud Dartus <reno@videolan.org>
*
* This program is free software; you can redistribute it and/or modify
...
...
@@ -31,7 +32,7 @@
#include "ac3_bit_stream.h"
/* Misc LUT */
static
u16
nfchans
[]
=
{
2
,
1
,
2
,
3
,
3
,
4
,
4
,
5
};
static
const
u16
nfchans
[]
=
{
2
,
1
,
2
,
3
,
3
,
4
,
4
,
5
};
struct
frmsize_s
{
...
...
@@ -39,7 +40,7 @@ struct frmsize_s
u16
frm_size
[
3
];
};
static
struct
frmsize_s
frmsizecod_tbl
[]
=
static
const
struct
frmsize_s
frmsizecod_tbl
[]
=
{
{
32
,{
64
,
69
,
96
}
},
{
32
,{
64
,
70
,
96
}
},
...
...
@@ -80,7 +81,7 @@ static struct frmsize_s frmsizecod_tbl[] =
{
640
,{
1280
,
1393
,
1920
}
},
{
640
,{
1280
,
1394
,
1920
}
}};
static
int
fscod_tbl
[]
=
{
48000
,
44100
,
32000
};
static
const
int
fscod_tbl
[]
=
{
48000
,
44100
,
32000
};
/* Some internal functions */
void
parse_bsi_stats
(
ac3dec_t
*
p_ac3dec
);
...
...
@@ -264,6 +265,10 @@ int parse_bsi (ac3dec_t * p_ac3dec)
}
}
#ifdef STATS
parse_bsi_stats
(
p_ac3dec
);
#endif
return
0
;
}
...
...
@@ -692,6 +697,10 @@ int parse_audblk (ac3dec_t * p_ac3dec, int blknum)
}
}
#ifdef STATS
// parse_audblk_stats(p_ac3dec);
#endif
return
0
;
}
...
...
@@ -716,3 +725,69 @@ void parse_auxdata (ac3dec_t * p_ac3dec)
/* Get the crc */
bitstream_get
(
&
(
p_ac3dec
->
bit_stream
),
16
);
}
void
parse_bsi_stats
(
ac3dec_t
*
p_ac3dec
)
/*Some stats */
{
struct
mixlev_s
{
float
clev
;
char
*
desc
;
};
static
const
char
*
service_ids
[
8
]
=
{
"CM"
,
"ME"
,
"VI"
,
"HI"
,
"D"
,
"C"
,
"E"
,
"VO"
};
/*
static const struct mixlev_s cmixlev_tbl[4] =
{
{0.707, "(-3.0 dB)"}, {0.595, "(-4.5 dB)"},
{0.500, "(-6.0 dB)"}, {1.0, "Invalid"}
};
static const struct mixlev_s smixlev_tbl[4] =
{
{0.707, "(-3.0 dB)"}, {0.500, "(-6.0 dB)"},
{ 0.0, "off "}, { 1.0, "Invalid"}
};
*/
static
int
i
;
if
(
!
i
)
{
/* if ((p_ac3dec->bsi.acmod & 0x1) && (p_ac3dec->bsi.acmod != 0x1))
printf("CentreMixLevel %s ",cmixlev_tbl[p_ac3dec->bsi.cmixlev].desc);
if (p_ac3dec->bsi.acmod & 0x4)
printf("SurMixLevel %s",smixlev_tbl[p_ac3dec->bsi.cmixlev].desc);
*/
intf_Msg
(
"(ac3dec_parsebsi) %s %d.%d Mode"
,
service_ids
[
p_ac3dec
->
bsi
.
bsmod
],
p_ac3dec
->
bsi
.
nfchans
,
p_ac3dec
->
bsi
.
lfeon
);
}
i
++
;
if
(
i
>
100
)
i
=
0
;
}
void
parse_audblk_stats
(
ac3dec_t
*
p_ac3dec
)
{
char
*
exp_strat_tbl
[
4
]
=
{
"R "
,
"D15 "
,
"D25 "
,
"D45 "
};
u32
i
;
intf_ErrMsg
(
"(ac3dec_parseaudblk) "
);
intf_ErrMsg
(
"%s "
,
p_ac3dec
->
audblk
.
cplinu
?
"cpl on"
:
"cpl off"
);
intf_ErrMsg
(
"%s "
,
p_ac3dec
->
audblk
.
baie
?
"bai"
:
" "
);
intf_ErrMsg
(
"%s "
,
p_ac3dec
->
audblk
.
snroffste
?
"snroffst"
:
" "
);
intf_ErrMsg
(
"%s "
,
p_ac3dec
->
audblk
.
deltbaie
?
"deltba"
:
" "
);
intf_ErrMsg
(
"%s "
,
p_ac3dec
->
audblk
.
phsflginu
?
"phsflg"
:
" "
);
intf_ErrMsg
(
"(%s %s %s %s %s) "
,
exp_strat_tbl
[
p_ac3dec
->
audblk
.
chexpstr
[
0
]],
exp_strat_tbl
[
p_ac3dec
->
audblk
.
chexpstr
[
1
]],
exp_strat_tbl
[
p_ac3dec
->
audblk
.
chexpstr
[
2
]],
exp_strat_tbl
[
p_ac3dec
->
audblk
.
chexpstr
[
3
]],
exp_strat_tbl
[
p_ac3dec
->
audblk
.
chexpstr
[
4
]]);
intf_ErrMsg
(
"["
);
for
(
i
=
0
;
i
<
p_ac3dec
->
bsi
.
nfchans
;
i
++
)
intf_ErrMsg
(
"%1d"
,
p_ac3dec
->
audblk
.
blksw
[
i
]);
intf_ErrMsg
(
"]"
);
intf_ErrMsg
(
"
\n
"
);
}
src/ac3_decoder/ac3_rematrix.c
View file @
a906b2f5
...
...
@@ -3,7 +3,8 @@
*****************************************************************************
* Copyright (C) 1999, 2000 VideoLAN
*
* Authors:
* Authors: Michel Kaempf <maxx@via.ecp.fr>
* Aaron Holtzman <aholtzma@engr.uvic.ca>
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
...
...
@@ -30,7 +31,7 @@ struct rematrix_band_s {
u32
end
;
};
static
struct
rematrix_band_s
rematrix_band
[]
=
{
{
13
,
24
},
{
25
,
36
},
{
37
,
60
},
{
61
,
252
}};
static
const
struct
rematrix_band_s
rematrix_band
[]
=
{
{
13
,
24
},
{
25
,
36
},
{
37
,
60
},
{
61
,
252
}};
static
__inline__
u32
min
(
u32
a
,
u32
b
)
{
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment