Compare commits

..

134 Commits

Author SHA1 Message Date
Martin Storsjo
5fd7e6537d Merge remote-tracking branch 'aosp/master' 2016-10-28 10:26:20 +03:00
Treehugger Robot
ed91226cec Merge "Remove redundant register storage class specifiers" 2016-10-28 01:08:50 +00:00
Martin Storsjo
6ec082c6c3 Remove redundant register storage class specifiers
Clang warns about this being deprecated, when building without specifying
-std=c++98.

This doesn't give any measurable encoding speed impact on ARM or AArch64,
on neither GCC nor Clang.

Change-Id: I63a0bbd1dccb97547522da188ee585d4d8127c29
2016-10-18 09:22:55 +03:00
Martin Storsjo
2b1e8db04d Don't force C++98 mode any longer
The code builds fine in C++11 mode now.
2016-10-18 08:29:04 +03:00
Martin Storsjo
55554d0b2d Merge remote-tracking branch 'aosp/master' 2016-10-18 08:28:51 +03:00
Treehugger Robot
4556cb9cb8 Merge "Add casts to avoid errors due to narrowing" 2016-10-18 03:05:51 +00:00
Martin Storsjo
6d7d5013ea Add casts to avoid errors due to narrowing
This fixes building in C++11 mode, which normally errors out
on narrowing hex literals to signed long.

This is similar to what was done in git commit ef30836651
(change id I64d19a8a8059c5a96386b1eaac297fd2469515f8), completing
the fix for that category of issues.

Change-Id: I1907bc947d43bf44910fb2b34bf2b31c0e53aa53
2016-10-17 10:32:24 +03:00
Martin Storsjo
cb57d89522 Add new files to "make dist" 2016-09-24 13:36:43 +03:00
Martin Storsjo
72037da0ba Fix building with MSVC for ARM
cmnintrin.h only existed for Windows CE, and doesn't seem to actually
be necessary for building this.
2016-09-11 13:28:47 +03:00
Martin Storsjo
45915b67e4 Detect MSVC x64 2016-09-11 13:28:44 +03:00
opcodevoid
6ac0611b07 Windows MSVC Makefile 2016-09-11 13:28:30 +03:00
Martin Storsjo
5eb3c9be88 Merge remote-tracking branch 'aosp/master' 2016-09-10 14:38:15 +03:00
Lexyan
1d686c3a23 Add aarch64 assembly optimization (ARMv8a 64 bits)
The fixmuldiv functions don't need inline assembly to be fast
in this architecture; the compiler (both clang and GCC) figure
out to use the optimal instructions for this (which is 2 instruction
sequence), and when letting the compiler emit the instructions
instead of using inline assembly, the compiler is able to
interleave those instructions with other instructions,
improving scheduling, making it even faster than when using
inline assembly.

Overall, this gives about 50% speedup.
2016-09-10 14:33:39 +03:00
Jean-Michel Trivi
f935254cc9 Merge "Avoid a warning about extra parentheses" 2016-09-09 22:06:10 +00:00
Martin Storsjo
ebb66ffd4a Avoid a warning about extra parentheses
This fixes the following warning:

libSBRenc/src/sbr_encoder.cpp:1942:14: warning: equality comparison
      with extraneous parentheses [-Wparentheses-equality]

Change-Id: I2c833d19348574473c752076a4efff6642c0d653
2016-08-30 09:57:04 +03:00
Martin Storsjo
a0bd8aa3b6 Bump the package version to 0.1.5 2016-08-25 22:20:09 +03:00
Martin Storsjo
932fc12396 Update Makefile.am with newly added and removed files 2016-08-25 22:14:25 +03:00
Martin Storsjo
1ce312b1dc Bump the library versions in the headers 2016-08-25 22:13:16 +03:00
Martin Storsjo
f9d0f65e65 Merge remote-tracking branch 'aosp/master' 2016-08-25 22:12:15 +03:00
Martin Storsjo
15b128dd82 Explicitly force building in C++98 mode
GCC 6 defaults to C++14 (or more precisely, gnu++14) instead of C++98
(or gnu++98).

The fdk-aac source doesn't support being built in this mode at the
moment, since it relies on narrowing conversion from unsigned 32 bit
integers to FIXP_DBL (which is a signed data type of the same size).

The same approach is used upstream in Android as well, since
d52f3747683.

This fixes buliding with GCC 6.
2016-05-18 10:13:31 +03:00
Martin Storsjo
8fe6faf261 Merge remote-tracking branch 'aosp/master' 2016-05-18 09:36:12 +03:00
Guillaume Smaha
f132ac5f3d Invert inline and void to be compatible with gcc 3.3.4 2016-05-18 08:07:32 +02:00
Guillaume Smaha
112fe2c68d Fix issue with gcc 3.4.3 which doesn't support always_inline without inline 2016-05-17 15:39:10 +02:00
Glenn Kasten
00fc1c66d5 Merge "Disable warnings that are not easily fixable" am: 8192b1a
am: 2a923c9

* commit '2a923c92869efb277ca7d67ab6c27617ec26c128':
  Disable warnings that are not easily fixable

Change-Id: I920b16bdaa1ce7a00c91e129b950f0d486a1fa37
2016-04-20 23:40:45 +00:00
Glenn Kasten
c3f7cf7f1b Merge "Add default case for undefined pointer initialization" am: 9d0179c
am: 27625f2

* commit '27625f27066421ce38250272f4bb751cf6f58c17':
  Add default case for undefined pointer initialization

Change-Id: I601dc2afdfa8db2008628e05068d277a617c022d
2016-04-20 23:40:45 +00:00
Glenn Kasten
e34e2b9d54 Merge "Left shift of negative int is undefined" am: 6ae5480
am: 2b2e97b

* commit '2b2e97b893b16b69c7728d16e8653b9c94944294':
  Left shift of negative int is undefined

Change-Id: Ie90b850b7adf787dfb47f8b7c43a22744c3a7fa0
2016-04-20 23:40:45 +00:00
Glenn Kasten
28099687b7 resolve merge conflicts of ad1e898 to nyc-dev-plus-aosp
Change-Id: If143807a233d47fb7fd269fd263a8a898109b060
2016-04-20 16:28:31 -07:00
Glenn Kasten
2a923c9286 Merge "Disable warnings that are not easily fixable"
am: 8192b1a

* commit '8192b1a98f60cc39253c658ba1ca70a70c2e0dfa':
  Disable warnings that are not easily fixable

Change-Id: I5dc1fabd29cfb7024f8362359a796efd1764032d
2016-04-20 19:00:07 +00:00
Glenn Kasten
27625f2706 Merge "Add default case for undefined pointer initialization"
am: 9d0179c

* commit '9d0179c8a85f2b50bafdf6715fc266bc92771756':
  Add default case for undefined pointer initialization

Change-Id: I311521adebb1949747f0cb34bee19a57d8199558
2016-04-20 19:00:06 +00:00
Glenn Kasten
2b2e97b893 Merge "Left shift of negative int is undefined"
am: 6ae5480

* commit '6ae54806ab88efd76e884447680fd30b340936fd':
  Left shift of negative int is undefined

Change-Id: If6a4abe686d3ab6b7f825058255b03aa46055484
2016-04-20 19:00:06 +00:00
Glenn Kasten
ad1e8985d9 Merge "Remove redundant parentheses around == comparison operator"
am: 34fb053

* commit '34fb05353bbabe1ba04362f26b3ae507fbb687d4':
  Remove redundant parentheses around == comparison operator

Change-Id: I7a37ef8293371cc0287a0e0b9f0115f82f294b31
2016-04-20 19:00:06 +00:00
Glenn Kasten
8192b1a98f Merge "Disable warnings that are not easily fixable" 2016-04-20 18:45:30 +00:00
Glenn Kasten
9d0179c8a8 Merge "Add default case for undefined pointer initialization" 2016-04-20 18:45:18 +00:00
Glenn Kasten
6ae54806ab Merge "Left shift of negative int is undefined" 2016-04-20 18:45:09 +00:00
Glenn Kasten
34fb05353b Merge "Remove redundant parentheses around == comparison operator" 2016-04-20 18:44:59 +00:00
Jean-Michel Trivi
be845a7fc2 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638 am: 78653b30e9 am: 0a20959871 am: 6318d60241 am: 7147e71a75 am: 1de50b286f am: d110691d01 am: 0cf3a7671a
am: 9d4702f2d9

* commit '9d4702f2d9ecec00c4e28de638b1f79afb5d696c':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I0a57275a4ebc04cc3acafc6a0325b7fefe8e5ef0
2016-04-19 01:34:40 +00:00
Jean-Michel Trivi
9d4702f2d9 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638 am: 78653b30e9 am: 0a20959871 am: 6318d60241 am: 7147e71a75 am: 1de50b286f am: d110691d01
am: 0cf3a7671a

* commit '0cf3a7671ad40c1036387d55462f1710a44eec31':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I7ca67acba7d69472865efa84a63a49c7768487c5
2016-04-19 01:32:26 +00:00
Jean-Michel Trivi
0cf3a7671a Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638 am: 78653b30e9 am: 0a20959871 am: 6318d60241 am: 7147e71a75 am: 1de50b286f
am: d110691d01

* commit 'd110691d01e15a555d84fcd98e4b275dd38b37ba':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I6c009e94d626cc1dd6ec1510fd2e07c1b3a4031a
2016-04-19 01:30:15 +00:00
Jean-Michel Trivi
d110691d01 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638 am: 78653b30e9 am: 0a20959871 am: 6318d60241 am: 7147e71a75
am: 1de50b286f

* commit '1de50b286fdadc07f94e0d8fae69a564796ab12a':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: Ib1dce026d6ddc9fdfa68cc5b4213a2685dc1ac17
2016-04-19 01:27:53 +00:00
Jean-Michel Trivi
1de50b286f Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638 am: 78653b30e9 am: 0a20959871 am: 6318d60241
am: 7147e71a75

* commit '7147e71a75a48009e6d2b835422767cf466813d8':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I7f677fae038640739834d4c44309680b78748acf
2016-04-19 01:25:09 +00:00
Jean-Michel Trivi
7147e71a75 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638 am: 78653b30e9 am: 0a20959871
am: 6318d60241

* commit '6318d6024194f89d809f4e22266105f27389f41b':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I1a836bd8b024948f18b2d2c0e912601722f887bc
2016-04-19 01:00:01 +00:00
Jean-Michel Trivi
6318d60241 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638 am: 78653b30e9
am: 0a20959871

* commit '0a209598713cccc4f10e9c0036df487bea5af312':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: If2339aad0e0e825302773f2f04f0dd43cc754ac6
2016-04-19 00:57:44 +00:00
Jean-Michel Trivi
0a20959871 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f am: 1a54e8f638
am: 78653b30e9

* commit '78653b30e9c1907d4c6eefa30ff954e0c4398447':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I53cabb3bab17e8754a03648ffac356e4a3a05e28
2016-04-19 00:55:30 +00:00
Jean-Michel Trivi
78653b30e9 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425 am: b762ff3e4f
am: 1a54e8f638

* commit '1a54e8f6385f9cbb8d950f0ff003bb71daa62caf':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I3c992ce7d3a60685f75a944d8d588fb9ff0d050c
2016-04-19 00:53:17 +00:00
Jean-Michel Trivi
1a54e8f638 Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d am: be3ff35425
am: b762ff3e4f

* commit 'b762ff3e4fdc29ce517824e19d187ba667e80623':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I29eaf51574e1834f223a9755a353abd90fcf912b
2016-04-19 00:50:57 +00:00
Jean-Michel Trivi
b762ff3e4f Fix aacDecoder_drcExtractAndMap() am: 97a1b8140d
am: be3ff35425

* commit 'be3ff35425f026fb3714f1bd45c40aee6737fe05':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I82060408eab9a8990c511af4c6be8a588d2a1b49
2016-04-19 00:48:42 +00:00
Jean-Michel Trivi
be3ff35425 Fix aacDecoder_drcExtractAndMap()
am: 97a1b8140d

* commit '97a1b8140d410ed3942006aa22b40ccb322f747b':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I1bf523e635139d71ef124462bd61e0da06191d35
2016-04-19 00:46:26 +00:00
Glenn Kasten
32db3a45df Disable warnings that are not easily fixable
Bug: 28026175
Change-Id: I6e9cfcd9efeb853caee01b54b241f24e64cf1e94
2016-04-18 16:11:27 -07:00
Glenn Kasten
1dd7649666 Add default case for undefined pointer initialization
Bug: 28026175
Change-Id: I1b149bf1573296df18abbe44f737bd87ab3913f9
2016-04-18 16:11:16 -07:00
Glenn Kasten
4bd4510b19 Left shift of negative int is undefined
Bug: 28026175
Change-Id: I9dc851b818262e95711033bdc03b7b7f30cff133
2016-04-18 16:11:01 -07:00
Glenn Kasten
76b428d4b4 Remove redundant parentheses around == comparison operator
Bug: 28026175
Change-Id: I8ff9d8d1dd73933dc181f2745292a0a3398a2479
2016-04-18 16:10:57 -07:00
Jean-Michel Trivi
97a1b8140d Fix aacDecoder_drcExtractAndMap()
Parse DVB DRC data only when numThreads is below
 MAX_DRC_THREADS. The post-increment is necessary as
 it is used in fill element DRC data section.
This solution parses as many DRC payloads as allowed by
 MAX_DRC_THREADS and skips all remaining DRC elements in the stream.

Bug 27792766
Bug 26751339

Change-Id: Ie1641888bac1757c4d1491119f977fc5d436eaea
2016-04-15 08:14:50 -07:00
Jean-Michel Trivi
3fbcee8020 AAC/SBR decoder improvements and bugfixes
am: 203e3f2

* commit '203e3f28fbebec7011342017fafc2a0bda0ce530':
  AAC/SBR decoder improvements and bugfixes

Change-Id: I2f7f5bb7f4c486347a1fdbd7c481cde33037441e
2016-04-09 00:36:07 +00:00
Jean-Michel Trivi
125815b0ed AAC/SBR encoder improvements
am: 46ba367

* commit '46ba3676b854acbc69a4c7845f578d4c2886377b':
  AAC/SBR encoder improvements

Change-Id: Id839c5ba8b79eddb7e239b7ec1b26fb5079b7d81
2016-04-09 00:36:07 +00:00
Jean-Michel Trivi
203e3f28fb AAC/SBR decoder improvements and bugfixes
* AAC-Decoder

   - Add support for AOT 20 (ER-AAC scalable) (base layer only)
   - Add support for AAC as used in Digital Radio Mondiale (DRM30/DRM+)
     Modified file(s):
        libAACdec/src/aacdecoder.cpp
        libAACdec/src/aacdecoder_lib.cpp
        libFDK/src/FDK_core.cpp
        libFDK/src/FDK_tools_rom.cpp
        libMpegTPDec/src/tpdec_asc.cpp
        libMpegTPDec/src/tpdec_lib.cpp
        libMpegTPDec/src/version
        libSBRdec/include/sbrdecoder.h
        libSBRdec/src/env_extr.h
        libSBRdec/src/sbrdecoder.cpp
     Added file(s):
        libMpegTPDec/src/tpdec_drm.cpp
        libMpegTPDec/src/tpdec_drm.h

   - Fix sanity check in HCR module that was performed at the wrong point in time.
     Modified file(s):
        libAACdec/src/aacdecoder_lib.cpp
        libAACdec/src/block.cpp

   - Extend core sampling rate support up to 96 kHz.
     Modified file(s):
        libAACdec/src/aac_rom.cpp
        libAACdec/src/aacdecoder.cpp
        libAACdec/src/aacdecoder_lib.cpp

   - Return correct audio output channel description according number of output
     channels.
     Modified file(s):
        libAACdec/src/aacdecoder_lib.cpp

   - Indroduce decoder intern output buffer. This change allows to use framework
     output buffer with the actual size of the deocder output channels.
     Modified file(s):
        libAACdec/include/aacdecoder_lib.h
        libAACdec/src/aacdecoder.h
        libAACdec/src/aacdecoder_lib.cpp

* SBR-Decoder

   - Increase robustness for erroneous input data.
   - Improve error concealment performance.
   - Fix handling of lowest sub-band for LD-SBR
     Modified file(s):
        libAACdec/src/aacdecoder.cpp
        libAACdec/src/aacdecoder_lib.cpp
        libSBRdec/src/env_calc.cpp
        libSBRdec/src/env_dec.cpp
        libSBRdec/src/env_extr.cpp
        libSBRdec/src/env_extr.h
        libSBRdec/src/sbr_dec.cpp
        libSBRdec/src/sbr_rom.cpp
        libSBRdec/src/sbr_rom.h
        libSBRdec/src/sbrdecoder.cpp

   - Add QMF delay compensation for ELD v2 streams decoded with the complex
     low delay filter-bank.
     Modified file(s):
        libSBRdec/src/sbr_dec.cpp
        libSBRdec/src/sbr_dec.h
        libSBRdec/src/sbrdecoder.cpp

   - Introduce a different handling of frames to be flushed
     dependent on whether there are delayed frames available or not.
     Modified file(s):
        libSBRdec/src/sbr_ram.h
        libSBRdec/src/sbrdecoder.cpp

   - Calculate the correct number of samples for dual-mono copy in case of no
     available PS data.
     Modified file(s):
        libSBRdec/src/sbrdecoder.cpp

* SYS-Library

   - Change include order of genericStds.h to prevent conflict with definitions
     which are also used in math.h.
     Modified file(s):
        libSYS/src/genericStds.cpp

Change-Id: I3ecffbad85f39b056213107955cfadbeb3f4b6e1
2016-04-08 19:10:30 +00:00
Jean-Michel Trivi
46ba3676b8 AAC/SBR encoder improvements
* AAC-Encoder

  - AAC-ELD core encoder audio quality tuning. Update tuning tables, configure
    bitreservoir size and adapt afterburner iteration value.
     Modified file(s):
        libAACenc/src/aacenc.h
        libAACenc/src/aacenc_lib.cpp
        libAACenc/src/adj_thr.cpp
        libAACenc/src/adj_thr.h
        libAACenc/src/adj_thr_data.h
        libAACenc/src/bandwidth.cpp
        libAACenc/src/pnsparam.cpp
        libAACenc/src/qc_main.cpp

   - Introduze dead zone quantizer for ELD to improve audio quality at certain
     configurations.
     Modified file(s):
        libAACenc/src/aacenc_lib.cpp
        libAACenc/src/adj_thr.cpp
        libAACenc/src/adj_thr.h
        libAACenc/src/qc_data.h
        libAACenc/src/qc_main.cpp
        libAACenc/src/quantize.cpp
        libAACenc/src/quantize.h
        libAACenc/src/sf_estim.cpp
        libAACenc/src/sf_estim.h

   - Revise TNS module to improve ELD audio quality.
   - Use new window function and separate prediction gain according TNS filters.
   - Add missing memory initilization to TNS configuration.
     Modified file(s):
        libAACenc/src/aacenc_lib.cpp
        libAACenc/src/aacenc_tns.cpp
        libAACenc/src/aacenc_tns.h
        libAACenc/src/psy_main.cpp
        libAACenc/src/tns_func.h

* SBR-Encoder

   - Revise frequency resolution calculation and handle differently depending
     on number of envelopes and split frames decision.
   - Add and adjust ELD SBR tuning tables.
     Modified file(s):
        libSBRenc/include/sbr_encoder.h
        libSBRenc/src/bit_sbr.h
        libSBRenc/src/env_est.cpp
        libSBRenc/src/fram_gen.cpp
        libSBRenc/src/fram_gen.h
        libSBRenc/src/mh_det.cpp
        libSBRenc/src/sbr_def.h
        libSBRenc/src/sbr_encoder.cpp
        libSBRenc/src/sbr_rom.cpp
        libSBRenc/src/tran_det.cpp

   - Replace ELD transient detector with fast implementation.
     Modified file(s):
        libSBRenc/src/env_est.cpp
        libSBRenc/src/env_est.h
        libSBRenc/src/fram_gen.cpp
        libSBRenc/src/sbr_def.h
        libSBRenc/src/sbr_encoder.cpp
        libSBRenc/src/tran_det.cpp
        libSBRenc/src/tran_det.h

* FDK-Library
   - Introduce generic compare function in tools library.
     Modified file(s):
        libFDK/include/fixpoint_math.h
        libFDK/src/FDK_core.cpp

* SBR-Encoder

  -  Revise ELD frame splitter to improve bit distribution.
     Modified file(s):
        libSBRenc/include/sbr_encoder.h
        libSBRenc/src/bit_sbr.h
        libSBRenc/src/env_est.cpp
        libSBRenc/src/fram_gen.cpp
        libSBRenc/src/fram_gen.h
        libSBRenc/src/sbr_encoder.cpp
        libSBRenc/src/tran_det.cpp
        libSBRenc/src/tran_det.h

   - Configure amplitude resolution according the tonality of the audio signal.
     Modified file(s):
        libSBRenc/include/sbr_encoder.h
        libSBRenc/src/bit_sbr.h
        libSBRenc/src/env_est.cpp
        libSBRenc/src/nf_est.cpp
        libSBRenc/src/nf_est.h
        libSBRenc/src/sbr_def.h
        libSBRenc/src/sbr_encoder.cpp
        libSBRenc/src/ton_corr.cpp
        libSBRenc/src/ton_corr.h
        libSBRenc/src/tran_det.cpp
        libSBRenc/src/tran_det.h

Change-Id: Ie0672b989a06ee63b50240616b8d1d4b790b6cb2
2016-04-08 10:52:42 -07:00
Jean-Michel Trivi
d75233c2da Fix aacDecoder_drcExtractAndMap()
am: 4834f01

* commit '4834f01bdf9b9f371fcbb0b9cf4f7297fdf1fd55':
  Fix aacDecoder_drcExtractAndMap()

Change-Id: I4f9994a4d4e858b6193b006d6971536c391e0478
2016-04-05 21:08:27 +00:00
Jean-Michel Trivi
4834f01bdf Fix aacDecoder_drcExtractAndMap()
Parse DVB DRC data only when numThreads is below
 MAX_DRC_THREADS. The post-increment is necessary as
 it is used in fill element DRC data section.
This solution parses as many DRC payloads as allowed by
 MAX_DRC_THREADS and skips all remaining DRC elements in the stream.

Bug 27792766
Bug 26751339

Change-Id: Ie1641888bac1757c4d1491119f977fc5d436eaea
2016-04-05 20:50:05 +00:00
Jean-Michel Trivi
65750eae65 SBR/AAC encoder updates, code clean up
am: e1c78ed

* commit 'e1c78ed73faa51f2c7fcb0c4a17a92be9cc747f5':
  SBR/AAC encoder updates, code clean up

Change-Id: I908adc47823de593c3e258c67f360da9321780f5
2016-04-05 17:43:33 +00:00
Jean-Michel Trivi
0713b4acff Remove compiler warnings, revised ARM QMF encoder
am: ef30836

* commit 'ef30836651bf059c3120c03dd11e08b6aafdae13':
  Remove compiler warnings, revised ARM QMF encoder

Change-Id: I07babb4dc36b6ad7aebeb62c303a8380e99d691e
2016-04-05 16:11:23 +00:00
Jean-Michel Trivi
e1c78ed73f SBR/AAC encoder updates, code clean up
* SBR-Encoder

   - Prevent noise level overflow in noise floor detection.
   - Saturate threshold calculation in transient detection.
     Modified file(s):
        libSBRenc/src/nf_est.cpp
        libSBRenc/src/sbr_encoder.cpp
        libSBRenc/src/tran_det.cpp

* AAC-Encoder

   - Expand input data range of GetInvInt() function. There was an encoder
     assert observed in non-default bitrate configuration.
     Modified file(s):
        libAACenc/src/aacenc_lib.cpp
        libAACenc/src/intensity.cpp
        libFDK/include/fixpoint_math.h
        libFDK/src/FDK_core.cpp
        libFDK/src/FDK_tools_rom.cpp

   - Make sure that the encoder is stable with regard to very low audio bandwidth
     confguration parameter value.
   - Fix lowdelay blending for low audio bandwidth.
     Modified file(s):
        libAACenc/src/aacenc.cpp
        libAACenc/src/aacenc_lib.cpp
        libAACenc/src/adj_thr.cpp
        libAACenc/src/psy_configuration.cpp
        libAACenc/src/psy_main.cpp

   - Disable pseudo surround flag in case metadata matrix mixdown index is
     present in program config element.
     Modified file(s):
        libAACenc/src/aacenc_lib.cpp

   - Enable variable bitrate mode in encoder api.
   - Add AACENC_PEAK_BITRATE parameter to encoder api.
   - Add AACENC_AUDIOMUXVER parameter to encoder api.
     Modified file(s):
        libAACenc/include/aacenc_lib.h
        libAACenc/src/aacenc.cpp
        libAACenc/src/aacenc.h
        libAACenc/src/aacenc_lib.cpp
        libAACenc/src/qc_main.cpp
        libMpegTPEnc/src/tpenc_latm.cpp
        libMpegTPEnc/src/version

* FDK-Sources

   - Code clean up. Remove unneeded pseudo audio object types and transport types.
     Modified file(s):
        libAACdec/src/aacdecoder.cpp
        libAACdec/src/aacdecoder_lib.cpp
        libAACenc/include/aacenc_lib.h
        libAACenc/src/aacenc.cpp
        libAACenc/src/aacenc_lib.cpp
        libFDK/src/FDK_tools_rom.cpp
        libMpegTPDec/src/tpdec_lib.cpp
        libMpegTPDec/src/version
        libMpegTPEnc/src/tpenc_latm.cpp
        libMpegTPEnc/src/version
        libSBRdec/src/sbrdecoder.cpp
        libSBRenc/src/sbr_encoder.cpp
        libSYS/include/FDK_audio.h
        libSYS/src/genericStds.cpp

Change-Id: I807a53cb7f48c9ee7563cb8da1d0c52221576ca6
2016-04-04 17:25:36 -07:00
Jean-Michel Trivi
ef30836651 Remove compiler warnings, revised ARM QMF encoder
Bug 8493170

Change-Id: I64d19a8a8059c5a96386b1eaac297fd2469515f8
2016-04-04 15:03:26 -07:00
Jean-Michel Trivi
f86e64f5c7 Fix stack corruption happening in aacDecoder_drcExtractAndMap() am: a06d1c2 am: 47739cd am: 118fc75
am: 7657556

* commit '7657556633262752ad2db9e3914a04128bd64e1b':
  Fix stack corruption happening in aacDecoder_drcExtractAndMap()
2016-03-22 02:57:52 +00:00
Jean-Michel Trivi
7657556633 Fix stack corruption happening in aacDecoder_drcExtractAndMap() am: a06d1c2 am: 47739cd
am: 118fc75

* commit '118fc75eee6cc763a3105d6e963b77d76d114a2e':
  Fix stack corruption happening in aacDecoder_drcExtractAndMap()
2016-03-22 02:49:48 +00:00
Jean-Michel Trivi
118fc75eee Fix stack corruption happening in aacDecoder_drcExtractAndMap() am: a06d1c2
am: 47739cd

* commit '47739cd9d8d7842436b90ef14207c935b0a799fe':
  Fix stack corruption happening in aacDecoder_drcExtractAndMap()
2016-03-22 02:44:32 +00:00
Jean-Michel Trivi
47739cd9d8 Fix stack corruption happening in aacDecoder_drcExtractAndMap()
am: a06d1c2

* commit 'a06d1c2b9af1621037b48557aac42b5ecbdb03b3':
  Fix stack corruption happening in aacDecoder_drcExtractAndMap()
2016-03-22 02:36:16 +00:00
Jean-Michel Trivi
a06d1c2b9a Fix stack corruption happening in aacDecoder_drcExtractAndMap()
In the aacDecoder_drcExtractAndMap() function, self->numThreads
  can be used after having exceeded its intended max value,
  MAX_DRC_THREADS, causing memory to be cleared after the
  threadBs[MAX_DRC_THREADS] array.
The crash is prevented by never using self->numThreads with
  a value equal to or greater than MAX_DRC_THREADS.
A proper fix will be required as there seems to be an issue as
  to which entry in the threadBs array is meant to be initialized
  and used.

Bug 26751339

Change-Id: I655cc40c35d4206ab72e83b2bdb751be2fe52b5a
2016-03-21 21:59:22 +00:00
Jean-Michel Trivi
e46ff0f7f9 Fix stack corruption happening in aacDecoder_drcExtractAndMap()
In the aacDecoder_drcExtractAndMap() function, self->numThreads
  can be used after having exceeded its intended max value,
  MAX_DRC_THREADS, causing memory to be cleared after the
  threadBs[MAX_DRC_THREADS] array.
The crash is prevented by never using self->numThreads with
  a value equal to or greater than MAX_DRC_THREADS.
A proper fix will be required as there seems to be an issue as
  to which entry in the threadBs array is meant to be initialized
  and used.

Bug 26751339

Change-Id: I655cc40c35d4206ab72e83b2bdb751be2fe52b5a
2016-03-21 21:58:57 +00:00
Martin Storsjo
50a98d1fd2 Merge remote-tracking branch 'aosp/master' 2016-03-09 08:49:40 +02:00
Martin Storsjo
0943e715f7 Remove android specific diagnostic logging 2016-01-26 22:42:09 +02:00
Timothy Gu
c8ad7a2ef9 Merge remote-tracking branch 'aosp/master' into update 2016-01-26 11:57:49 -08:00
Dan Willemsen
c203653dcb Remove __DATE__/__TIME__
am: 2d435aa433

* commit '2d435aa43323935bd8ed293f4f12cddfdee81eb3':
  Remove __DATE__/__TIME__
2015-11-03 19:44:47 +00:00
Dan Willemsen
2d435aa433 Remove __DATE__/__TIME__
Building __DATE__/__TIME__ into the binaries means that every build will
create different binaries, even if all the sources are identical. This
also means that any libraries including this one will need to be patched
during every OTA.

Nothing appears to use the build_date/build_time fields, so just replace
them with empty strings.

Bug: 24204119
Change-Id: I9543eb388a1e8ab9284df9035a62fc8942cdc082
(cherry picked from commit 6e8330732f61d1da1485fc07b61444f490d5e623)
2015-10-30 21:53:59 +00:00
Dan Willemsen
ca249e444b Merge "Remove __DATE__/__TIME__"
am: a73b059815

* commit 'a73b059815fc35ba689e5a8235b567b2353eabad':
  Remove __DATE__/__TIME__
2015-10-27 23:27:46 +00:00
Dan Willemsen
a73b059815 Merge "Remove __DATE__/__TIME__" 2015-10-27 23:16:31 +00:00
Dan Willemsen
6e8330732f Remove __DATE__/__TIME__
Building __DATE__/__TIME__ into the binaries means that every build will
create different binaries, even if all the sources are identical. This
also means that any libraries including this one will need to be patched
during every OTA.

Nothing appears to use the build_date/build_time fields, so just replace
them with empty strings.

Bug: 24204119
Change-Id: I9543eb388a1e8ab9284df9035a62fc8942cdc082
2015-10-23 09:48:27 -07:00
Vicente Olivert Riera
047376af8c libFDK/include/mips/cplx_mul.h: use C code instead of ASM
Replace the assembler code by the equivalent in C. This way it will work
for every MIPS ISA. Now the check for __mips_isa_rev < 6 is no longer
necessary, so remove it.

Signed-off-by: Vicente Olivert Riera <Vincent.Riera@imgtec.com>
2015-09-21 11:59:02 +01:00
Marco Nelissen
106fb85b42 am 9f42dfb7: am b3c5a4bb: Fix crash on invalid channel config
* commit '9f42dfb7990a107da23454669459bb5e28d90726':
  Fix crash on invalid channel config
2015-09-15 02:12:36 +00:00
Marco Nelissen
9f42dfb799 am b3c5a4bb: Fix crash on invalid channel config
* commit 'b3c5a4bb8442ab3158fa1f52b790fadc64546f46':
  Fix crash on invalid channel config
2015-09-15 01:10:04 +00:00
Marco Nelissen
b3c5a4bb84 Fix crash on invalid channel config
Bug: 23876444
Change-Id: I90ad197811ebabceb5b5d74d6d3f20716fbe2d45
2015-09-08 15:50:08 +00:00
Dan Willemsen
8e8d920708 am 9f1b9bb7: (-s ours) am 5e7b21bb: Merge "build: wildcard isn\'t guaranteed to be sorted"
* commit '9f1b9bb71019b9a773d847cec6f10c198cd6c459':
2015-08-27 05:10:06 +00:00
Jasper Lievisse Adriaanse
2585f10da2 Fix the preprocessor statements controlling the use of mips{32,64}r1 instructions.
Only enable code using mips32/mips64 instructions if the compiler is targetting
this ISA. (integer madd and msub instructions aren't available in the
``canonical'' mips ISAs)
2015-08-13 10:53:07 +02:00
Dan Willemsen
ba8b18e1e8 am 5e7b21bb: Merge "build: wildcard isn\'t guaranteed to be sorted"
* commit '5e7b21bb954dcf74533a1725be62cf6bffcb34ce':
  build: wildcard isn't guaranteed to be sorted
2015-08-12 00:39:30 +00:00
Dan Willemsen
9f1b9bb710 am 5e7b21bb: Merge "build: wildcard isn\'t guaranteed to be sorted"
* commit '5e7b21bb954dcf74533a1725be62cf6bffcb34ce':
  build: wildcard isn't guaranteed to be sorted
2015-08-12 00:39:04 +00:00
Dan Willemsen
5e7b21bb95 Merge "build: wildcard isn't guaranteed to be sorted" 2015-08-12 00:24:06 +00:00
Dan Willemsen
f170f89906 build: wildcard isn't guaranteed to be sorted
To prevent this from changing between builds, wrap in $(sort )

Change-Id: I0571d7d8787a40ca107c7c735d79692d27bed06e
2015-08-07 13:51:09 -07:00
Martin Storsjo
83ac4a9860 Merge remote-tracking branch 'aosp/master' 2015-03-11 16:49:43 +02:00
Martin Storsjo
2ded8da912 Update the changelog for the upcoming 0.1.4 release 2015-03-05 10:26:54 +02:00
Martin Storsjo
d7fca408b4 Merge remote-tracking branch 'aosp/master' 2015-03-03 10:52:42 +02:00
Bill Yi
267940f5bd am f2df045a: Merge commit \'10d211b84a5f0790b28fcc8b3db66884d5f9c729\' into HEAD
* commit 'f2df045ae92ee655481f73b19986084308ae684c':
2015-02-20 00:22:52 +00:00
Bill Yi
f2df045ae9 Merge commit '10d211b84a5f0790b28fcc8b3db66884d5f9c729' into HEAD 2015-02-19 14:30:49 -08:00
Chih-Hung Hsieh
bd8021bef1 am 2b6bf8dc: Merge "Do not include genericStds_linux.cpp."
* commit '2b6bf8dc0941f3a4531030b950cf24fd31248b0b':
  Do not include genericStds_linux.cpp.
2015-02-18 02:53:59 +00:00
Chih-Hung Hsieh
2b6bf8dc09 Merge "Do not include genericStds_linux.cpp." 2015-02-18 02:41:47 +00:00
Chih-Hung Hsieh
09f1d04467 Do not include genericStds_linux.cpp.
The __aeabi_memcpy functions are already defined in Android libc.
Redefining them to call memcpy will become recursive when clang/llvm
converts the memcpy call to __aeabi_memcpy.
With this change, we can enable clang/llvm by removing LOCAL_CLANG from Android.mk.

BUG: 12216385
Change-Id: I8b8b4ba7f3ff1e66f8110fc3b6356865a582c1d8
2015-02-12 11:20:14 -08:00
Marco Nelissen
10d211b84a am 1c6ab7db: Merge "Use gcc for the AAC decoder"
* commit '1c6ab7db30867f3eee0d550adb015b340fbbc668':
  Use gcc for the AAC decoder
2015-02-11 01:51:25 +00:00
Marco Nelissen
1c6ab7db30 Merge "Use gcc for the AAC decoder" 2015-02-11 01:22:20 +00:00
Marco Nelissen
355baa79bf Use gcc for the AAC decoder
clang generates crashing code for this.

Change-Id: I90355d6735403290e7c0d93ff4854520b7b80f4a
2015-02-10 15:39:28 -08:00
Chih-Hung Hsieh
28e448bb55 am 66091e46: Merge "Fix checks for {Front,Side,Back}ElementIsCpe"
* commit '66091e46d7aae1b45ed96f5f39274954a296db71':
  Fix checks for {Front,Side,Back}ElementIsCpe
2014-12-01 19:45:05 +00:00
Chih-Hung Hsieh
66091e46d7 Merge "Fix checks for {Front,Side,Back}ElementIsCpe" 2014-12-01 19:31:58 +00:00
Dan Albert
57f76311ba am 84851b23: Merge "Move back to C++98."
* commit '84851b23d6f65ce03da4fa8ef2348b4f46c0ed0f':
  Move back to C++98.
2014-12-01 19:27:01 +00:00
Chih-Hung Hsieh
bb1e78a118 Fix checks for {Front,Side,Back}ElementIsCpe
{Front,Side,Back}ElementIsCpe is an array (per-channel). The check for
pPce->{Front,Side,Back}ElementIsCpe without an index checks the address
of the array, and will always evaluate to true. The elTagSce++
statements are unreachable.

Change-Id: If530371788a44038c500d6f9f7ac67681f77cc71
2014-12-01 11:26:03 -08:00
Dan Albert
84851b23d6 Merge "Move back to C++98." 2014-12-01 19:15:30 +00:00
Dan Albert
d52f374768 Move back to C++98.
This code depends on narrowing hex literals to a signed long, which
trips -Wc++11-narrowing (the fix would be to explicitly cast each
value to signed).

Change-Id: I581a02ef0eeee5a2d95ce0ff2ec6f7ff26f3a074
2014-11-28 13:56:59 -08:00
Andrew Stone
97b382cd3f Ignore file compile that is generated by autogen 2014-11-24 16:13:15 -05:00
Martin Storsjo
06ee7ef4e7 Bump the package version number to 0.1.4 2014-11-07 09:33:28 +02:00
Martin Storsjo
a0bfb7ee7c Bump the shared library major number
The AAC_PCM_OUTPUT_CHANNELS option no longer exists under the
same name nor enum value any longer, and the AUDIO_CHANNEL_TYPE
enum has been changed in a way which may break users.
2014-11-07 09:33:28 +02:00
Martin Storsjo
63447a9993 Include the decoder API version in the public header 2014-11-07 09:33:28 +02:00
Martin Storsjo
69a488faf2 Include the new file limiter.cpp in the build 2014-11-07 09:33:28 +02:00
Martin Storsjo
6ccecbc4b0 Merge remote-tracking branch 'aosp/master' 2014-11-07 09:32:48 +02:00
Martin Storsjo
ce1863444a Include libFDK ppc headers in make dist 2014-11-04 23:48:42 +02:00
Chih-Hung Hsieh
1c7368d7c0 am d149516e: am 7e464956: Merge "Move Clang only flags into LOCAL_CLANG_CPPFLAGS."
* commit 'd149516e1a3a63549d2c654b1398544d5de46a3e':
2014-10-25 19:54:26 +00:00
Chih-Hung Hsieh
d149516e1a am 7e464956: Merge "Move Clang only flags into LOCAL_CLANG_CPPFLAGS."
* commit '7e46495606bd66973a10565f932acee7bddcc003':
  Move Clang only flags into LOCAL_CLANG_CPPFLAGS.
2014-09-23 16:54:56 +00:00
Chih-Hung Hsieh
ab33d4d394 am 7e464956: Merge "Move Clang only flags into LOCAL_CLANG_CPPFLAGS."
* commit '7e46495606bd66973a10565f932acee7bddcc003':
  Move Clang only flags into LOCAL_CLANG_CPPFLAGS.
2014-09-23 16:54:34 +00:00
Chih-Hung Hsieh
7e46495606 Merge "Move Clang only flags into LOCAL_CLANG_CPPFLAGS." 2014-09-23 16:29:42 +00:00
Chih-Hung Hsieh
3c4c8d631f Move Clang only flags into LOCAL_CLANG_CPPFLAGS.
Gcc does not recognize -Wno-pointer-bool-conversion.

Change-Id: Ib6ffa321fff1947b6a098244f7d67fdeb45c2b41
2014-09-22 22:59:03 -07:00
Glenn Kasten
57daefcbe1 am 4803bf75: Merge "Ignore Clang warning on checking address of arrays."
* commit '4803bf75f564e5c9304527a5b902711f78e9f621':
  Ignore Clang warning on checking address of arrays.
2014-09-09 17:53:16 +00:00
Glenn Kasten
4803bf75f5 Merge "Ignore Clang warning on checking address of arrays." 2014-09-09 17:36:03 +00:00
Chih-Hung Hsieh
9428e080cc Ignore Clang warning on checking address of arrays.
BUG: 17356808
Change-Id: I464ffcfb3fc4f44ac8115f9ae98a8c46189b41cd
2014-09-03 12:40:41 -07:00
Keun-young Park
8d8580c267 am 2decc778: Merge "[MIPSR6] Skip assembler code using MFHI/MFLO on mips32r6"
* commit '2decc77814e729df47464a504123f9b398ac7077':
  [MIPSR6] Skip assembler code using MFHI/MFLO on mips32r6
2014-08-14 18:42:23 +00:00
Keun-young Park
2decc77814 Merge "[MIPSR6] Skip assembler code using MFHI/MFLO on mips32r6" 2014-08-14 16:10:21 +00:00
Martin Storsjo
9a3234055a Extend the GetInvInt table to 80 elements
This is a bug fix patch from Fraunhofer, amending/replacing/extending
the previous commit which only extended the table to 55 elements.
(In my previous fix, 55 seemed to be enough for the issue at hand at
least. A few of the coefficients had slightly different rounding than
what Fraunhofer had used though).

This will show up in AOSP in the next code drop as well.
2014-08-01 10:36:54 +03:00
Duane Sand
5c51a5898e [MIPSR6] Skip assembler code using MFHI/MFLO on mips32r6
Change-Id: I3dacd96cf9d5cf9c3d34d612ebb0456d64bc23bc
2014-07-31 15:40:38 -07:00
Martin Storsjo
6522e87ad6 Extend GetInvInt to support values up to 54
For sample rates >= 64 kHz with short blocks, the largest sfb
width is 36, which after grouping can be multiplied with 3,
ending up as 108. GetInvInt needs to be able to support
the largest grouped sfb width, divided by two (3 * 36 / 2 = 54).

This fixes VBR encoding with sample rates >= 64 kHz.
2014-07-29 15:00:56 +03:00
Jean-Michel Trivi
6792cf6361 AAC-Decoder: SBR delay for gapless
Revise decoder output delay determination. The output delay consisted of
  concealment and limiter delay. SBR delay was not covered but must be
  considered for gapless playback delay compensation.

Bug 9428126

Change-Id: I67483712c284de9b5378694f9db7acbed2547dd7
2014-05-20 17:39:03 -07:00
Jean-Michel Trivi
8e087bf394 AAC-Decoder: DRC metadata in stream info
Provide relevant DRC metadata information via API needed for DRC
  presentation mode wrapper.

Bug 9428126

Change-Id: I827cd6bdfd2a8799c21935ae32af23739c90a9b6
2014-05-20 17:29:03 -07:00
Jean-Michel Trivi
af967fcc55 AAC Decoder: flush/seek improvements
Improve flushing and seeking.
Add field to the API stream info structure signaling the additional output
 delay for flushing and delay compensation.

Bug 9428126

Change-Id: I808412905563ea3de50a2e77a9b5dfee829cd2ed
2014-05-20 17:24:06 -07:00
Glenn Kasten
fb2e845179 am 35f30c5a: Merge "AArch64: Make LONG 4 bytes"
* commit '35f30c5ab8089f38681d2fdd416c00aebef5a7ff':
  AArch64: Make LONG 4 bytes
2014-04-09 15:57:48 +00:00
Glenn Kasten
35f30c5ab8 Merge "AArch64: Make LONG 4 bytes" 2014-04-09 15:49:10 +00:00
Jean-Michel Trivi
603f48ab99 AAC Decoder: introduce time domain limiter
Introduce time domain limiter. The module is per default enabled for all
  AAC-LC and HE-AAC v1/2 streams. For all ER-AAC-LD and ER-AAC-ELD streams
  the limiter is disabled per default. The feature can be en- or disabled
  via dynamic API parameter. Note that the limiter introduces an additional
  output delay which depends on the module parameters and the streams
  sampling rate.

Bug 9428126

Change-Id: I299a072340b33e2c324facbd347a72c8de3d380e
2014-03-31 23:41:44 +00:00
Glenn Kasten
629f60c0e7 am 3252951f: Merge "Temporary workaround for 64-bit build error"
* commit '3252951f61e011241ce6dd8fff775fe9b9aed97f':
  Temporary workaround for 64-bit build error
2014-03-19 21:13:03 +00:00
Glenn Kasten
3252951f61 Merge "Temporary workaround for 64-bit build error" 2014-03-19 20:58:18 +00:00
Glenn Kasten
8609bfea36 Temporary workaround for 64-bit build error
Replace #error by #warning so we can build 64-bit

Change-Id: Ib52fbfb0e5e945ff04ba51ae06b4e3393886d7b7
2014-03-12 11:19:32 -07:00
Marcus Oakland
f2f96fb86d AArch64: Make LONG 4 bytes
The libSYS/include/machine_type.h header file states LONG should be
"Data type representing 4 byte signed integer on all supported
platforms" but only provided for defining LONG as INT and ULONG as
UINT when __x86_64__ was defined. This has been changed to when
__LP64__ is defined, so that it also applies to AArch64. The change
to libFDK/include/common_fix.h is then needed to get the project to
compile.

Change-Id: Iea42d7eca97dcc9da772a05b207d134cb999a72a
Signed-off-by: Marcus Oakland <marcus.oakland@arm.com>
2014-03-11 12:01:00 +00:00
Jean-Michel Trivi
47c680c622 AAC Decoder: support 6.1/7.1 decoded as 5.1
- Add 6.1 and 7.1 channel support including downmixer. Per default the
     decoder creates a 5.1 channel output for all streams with more than six
     encoded channels.
     Modified file(s):
        libPCMutils/include/pcmutils_lib.h
        libPCMutils/src/pcmutils_lib.cpp
        libAACdec/include/aacdecoder_lib.h
        libAACdec/src/aac_rom.h
        libAACdec/src/aacdecoder.cpp
        libAACdec/src/aac_ram.cpp
        libAACdec/src/aacdec_drc.cpp
        libAACdec/src/aacdecoder_lib.cpp
        libAACdec/src/aac_rom.cpp
        libAACdec/src/aacdecoder.h
        libSBRdec/include/sbrdecoder.h
        libSBRdec/src/sbrdec_drc.h
        libSBRdec/src/sbrdecoder.cpp
        libSBRdec/src/sbr_ram.cpp
        libSBRdec/src/sbr_ram.h
        libMpegTPDec/include/tp_data.h
        libMpegTPDec/include/tpdec_lib.h
        libMpegTPDec/src/version
        libMpegTPDec/src/tpdec_asc.cpp
        libMpegTPEnc/include/tp_data.h
        libMpegTPEnc/src/version
        libSYS/include/FDK_audio.h
        libSYS/src/genericStds.cpp

   - Fix error concealment modules fade-out/in mechanism.
     Modified file(s):
        libAACdec/src/conceal.cpp

Bug 9428126

Change-Id: I3230bd2072314b730911cd7ec1740e290cb1d254
2013-12-30 09:40:08 -08:00
112 changed files with 7913 additions and 1833 deletions

1
.gitignore vendored
View File

@ -26,3 +26,4 @@ m4/lt~obsolete.m4
missing
stamp-h1
aac-enc
compile

View File

@ -1,31 +1,31 @@
LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS)
aacdec_sources := $(wildcard $(LOCAL_PATH)/libAACdec/src/*.cpp)
aacdec_sources := $(sort $(wildcard $(LOCAL_PATH)/libAACdec/src/*.cpp))
aacdec_sources := $(aacdec_sources:$(LOCAL_PATH)/libAACdec/src/%=%)
aacenc_sources := $(wildcard $(LOCAL_PATH)/libAACenc/src/*.cpp)
aacenc_sources := $(sort $(wildcard $(LOCAL_PATH)/libAACenc/src/*.cpp))
aacenc_sources := $(aacenc_sources:$(LOCAL_PATH)/libAACenc/src/%=%)
pcmutils_sources := $(wildcard $(LOCAL_PATH)/libPCMutils/src/*.cpp)
pcmutils_sources := $(sort $(wildcard $(LOCAL_PATH)/libPCMutils/src/*.cpp))
pcmutils_sources := $(pcmutils_sources:$(LOCAL_PATH)/libPCMutils/src/%=%)
fdk_sources := $(wildcard $(LOCAL_PATH)/libFDK/src/*.cpp)
fdk_sources := $(sort $(wildcard $(LOCAL_PATH)/libFDK/src/*.cpp))
fdk_sources := $(fdk_sources:$(LOCAL_PATH)/libFDK/src/%=%)
sys_sources := $(wildcard $(LOCAL_PATH)/libSYS/src/*.cpp)
sys_sources := $(sort $(wildcard $(LOCAL_PATH)/libSYS/src/*.cpp))
sys_sources := $(sys_sources:$(LOCAL_PATH)/libSYS/src/%=%)
mpegtpdec_sources := $(wildcard $(LOCAL_PATH)/libMpegTPDec/src/*.cpp)
mpegtpdec_sources := $(sort $(wildcard $(LOCAL_PATH)/libMpegTPDec/src/*.cpp))
mpegtpdec_sources := $(mpegtpdec_sources:$(LOCAL_PATH)/libMpegTPDec/src/%=%)
mpegtpenc_sources := $(wildcard $(LOCAL_PATH)/libMpegTPEnc/src/*.cpp)
mpegtpenc_sources := $(sort $(wildcard $(LOCAL_PATH)/libMpegTPEnc/src/*.cpp))
mpegtpenc_sources := $(mpegtpenc_sources:$(LOCAL_PATH)/libMpegTPEnc/src/%=%)
sbrdec_sources := $(wildcard $(LOCAL_PATH)/libSBRdec/src/*.cpp)
sbrdec_sources := $(sort $(wildcard $(LOCAL_PATH)/libSBRdec/src/*.cpp))
sbrdec_sources := $(sbrdec_sources:$(LOCAL_PATH)/libSBRdec/src/%=%)
sbrenc_sources := $(wildcard $(LOCAL_PATH)/libSBRenc/src/*.cpp)
sbrenc_sources := $(sort $(wildcard $(LOCAL_PATH)/libSBRenc/src/*.cpp))
sbrenc_sources := $(sbrenc_sources:$(LOCAL_PATH)/libSBRenc/src/%=%)
LOCAL_SRC_FILES := \
@ -39,8 +39,8 @@ LOCAL_SRC_FILES := \
$(sbrdec_sources:%=libSBRdec/src/%) \
$(sbrenc_sources:%=libSBRenc/src/%)
LOCAL_CFLAGS := -DANDROID
LOCAL_CFLAGS += -Wno-sequence-point -Wno-extra
LOCAL_CFLAGS += "-Wno-\#warnings" -Wno-constant-logical-operand -Wno-self-assign
LOCAL_C_INCLUDES := \
$(LOCAL_PATH)/libAACdec/include \
@ -53,6 +53,7 @@ LOCAL_C_INCLUDES := \
$(LOCAL_PATH)/libSBRdec/include \
$(LOCAL_PATH)/libSBRenc/include
LOCAL_MODULE:= libFraunhoferAAC
include $(BUILD_STATIC_LIBRARY)

View File

@ -1,3 +1,12 @@
0.1.4
- Updated upstream sources, with minor changes to the decoder API
breaking the ABI. (Calling code using AUDIO_CHANNEL_TYPE may need to
be updated. A new option AAC_PCM_LIMITER_ENABLE has been added, enabled
by default, which incurs extra decoding delay.)
- PowerPC optimizations, fixes for building on AIX
- Support for reading streamed wav files in the encoder example
- Fix VBR encoding of sample rates over 64 kHz
0.1.3
- Updated upstream sources, with a number of crash fixes and new features
(including support for encoding 7.1)

View File

@ -74,7 +74,6 @@ AACENC_SRC = \
libAACenc/src/pre_echo_control.cpp \
libAACenc/src/quantize.cpp \
libAACenc/src/tonality.cpp \
libAACenc/src/aacenc_hcr.cpp \
libAACenc/src/aacEnc_rom.cpp \
libAACenc/src/bandwidth.cpp \
libAACenc/src/channel_map.cpp \
@ -119,6 +118,7 @@ MPEGTPDEC_SRC = \
libMpegTPDec/src/tpdec_adif.cpp \
libMpegTPDec/src/tpdec_adts.cpp \
libMpegTPDec/src/tpdec_asc.cpp \
libMpegTPDec/src/tpdec_drm.cpp \
libMpegTPDec/src/tpdec_latm.cpp \
libMpegTPDec/src/tpdec_lib.cpp
@ -130,6 +130,7 @@ MPEGTPENC_SRC = \
libMpegTPEnc/src/tpenc_lib.cpp
PCMUTILS_SRC = \
libPCMutils/src/limiter.cpp \
libPCMutils/src/pcmutils_lib.cpp
SBRDEC_SRC = \
@ -185,9 +186,11 @@ libfdk_aac_la_SOURCES = \
EXTRA_DIST = \
$(top_srcdir)/autogen.sh \
$(top_srcdir)/MODULE_LICENSE_FRAUNHOFER \
$(top_srcdir)/NOTICE \
$(top_srcdir)/Android.mk \
$(top_srcdir)/fdk-aac.sym \
$(top_srcdir)/Makefile.vc \
$(top_srcdir)/documentation/*.pdf \
$(top_srcdir)/libAACdec/src/*.h \
$(top_srcdir)/libAACdec/src/arm/*.cpp \
@ -208,9 +211,12 @@ EXTRA_DIST = \
$(top_srcdir)/libMpegTPDec/src/*.h \
$(top_srcdir)/libMpegTPDec/src/version \
$(top_srcdir)/libFDK/include/*.h \
$(top_srcdir)/libFDK/include/aarch64/*.h \
$(top_srcdir)/libFDK/include/arm/*.h \
$(top_srcdir)/libFDK/include/mips/*.h \
$(top_srcdir)/libFDK/include/ppc/*.h \
$(top_srcdir)/libFDK/include/x86/*.h \
$(top_srcdir)/libFDK/src/arm/*.cpp \
$(top_srcdir)/libFDK/src/mips/*.cpp
$(top_srcdir)/libFDK/src/mips/*.cpp \
$(top_srcdir)/win32/*.h

250
Makefile.vc Normal file
View File

@ -0,0 +1,250 @@
#
# Options:
# prefix=\path\to\install
#
# Compiling: nmake -f Makefile.vc
# Installing: nmake -f Makefile.vc prefix=\path\to\x install
#
VERSION=0.1.5
# Linker and librarian commands
LD = link
AR = lib
!IFDEF HOME
# In case we are using a cross compiler shell.
MKDIR_FLAGS = -p
!ENDIF
AM_CPPFLAGS = \
-Iwin32 \
-IlibAACdec/include \
-IlibAACenc/include \
-IlibSBRdec/include \
-IlibSBRenc/include \
-IlibMpegTPDec/include \
-IlibMpegTPEnc/include \
-IlibSYS/include \
-IlibFDK/include \
-IlibPCMutils/include
AACDEC_SRC = \
libAACdec/src/aacdec_drc.cpp \
libAACdec/src/aacdec_hcr.cpp \
libAACdec/src/aacdecoder.cpp \
libAACdec/src/aacdec_pns.cpp \
libAACdec/src/aac_ram.cpp \
libAACdec/src/block.cpp \
libAACdec/src/channelinfo.cpp \
libAACdec/src/ldfiltbank.cpp \
libAACdec/src/rvlcbit.cpp \
libAACdec/src/rvlc.cpp \
libAACdec/src/aacdec_hcr_bit.cpp \
libAACdec/src/aacdec_hcrs.cpp \
libAACdec/src/aacdecoder_lib.cpp \
libAACdec/src/aacdec_tns.cpp \
libAACdec/src/aac_rom.cpp \
libAACdec/src/channel.cpp \
libAACdec/src/conceal.cpp \
libAACdec/src/pulsedata.cpp \
libAACdec/src/rvlcconceal.cpp \
libAACdec/src/stereo.cpp
AACENC_SRC = \
libAACenc/src/aacenc.cpp \
libAACenc/src/aacEnc_ram.cpp \
libAACenc/src/band_nrg.cpp \
libAACenc/src/block_switch.cpp \
libAACenc/src/grp_data.cpp \
libAACenc/src/metadata_main.cpp \
libAACenc/src/pre_echo_control.cpp \
libAACenc/src/quantize.cpp \
libAACenc/src/tonality.cpp \
libAACenc/src/aacEnc_rom.cpp \
libAACenc/src/bandwidth.cpp \
libAACenc/src/channel_map.cpp \
libAACenc/src/intensity.cpp \
libAACenc/src/ms_stereo.cpp \
libAACenc/src/psy_configuration.cpp \
libAACenc/src/sf_estim.cpp \
libAACenc/src/transform.cpp \
libAACenc/src/aacenc_lib.cpp \
libAACenc/src/aacenc_tns.cpp \
libAACenc/src/bit_cnt.cpp \
libAACenc/src/chaosmeasure.cpp \
libAACenc/src/line_pe.cpp \
libAACenc/src/noisedet.cpp \
libAACenc/src/psy_main.cpp \
libAACenc/src/spreading.cpp \
libAACenc/src/aacenc_pns.cpp \
libAACenc/src/adj_thr.cpp \
libAACenc/src/bitenc.cpp \
libAACenc/src/dyn_bits.cpp \
libAACenc/src/metadata_compressor.cpp \
libAACenc/src/pnsparam.cpp \
libAACenc/src/qc_main.cpp
FDK_SRC = \
libFDK/src/autocorr2nd.cpp \
libFDK/src/dct.cpp \
libFDK/src/FDK_bitbuffer.cpp \
libFDK/src/FDK_core.cpp \
libFDK/src/FDK_crc.cpp \
libFDK/src/FDK_hybrid.cpp \
libFDK/src/FDK_tools_rom.cpp \
libFDK/src/FDK_trigFcts.cpp \
libFDK/src/fft.cpp \
libFDK/src/fft_rad2.cpp \
libFDK/src/fixpoint_math.cpp \
libFDK/src/mdct.cpp \
libFDK/src/qmf.cpp \
libFDK/src/scale.cpp \
MPEGTPDEC_SRC = \
libMpegTPDec/src/tpdec_adif.cpp \
libMpegTPDec/src/tpdec_adts.cpp \
libMpegTPDec/src/tpdec_asc.cpp \
libMpegTPDec/src/tpdec_drm.cpp \
libMpegTPDec/src/tpdec_latm.cpp \
libMpegTPDec/src/tpdec_lib.cpp
MPEGTPENC_SRC = \
libMpegTPEnc/src/tpenc_adif.cpp \
libMpegTPEnc/src/tpenc_adts.cpp \
libMpegTPEnc/src/tpenc_asc.cpp \
libMpegTPEnc/src/tpenc_latm.cpp \
libMpegTPEnc/src/tpenc_lib.cpp
PCMUTILS_SRC = \
libPCMutils/src/limiter.cpp \
libPCMutils/src/pcmutils_lib.cpp
SBRDEC_SRC = \
libSBRdec/src/env_calc.cpp \
libSBRdec/src/env_dec.cpp \
libSBRdec/src/env_extr.cpp \
libSBRdec/src/huff_dec.cpp \
libSBRdec/src/lpp_tran.cpp \
libSBRdec/src/psbitdec.cpp \
libSBRdec/src/psdec.cpp \
libSBRdec/src/psdec_hybrid.cpp \
libSBRdec/src/sbr_crc.cpp \
libSBRdec/src/sbr_deb.cpp \
libSBRdec/src/sbr_dec.cpp \
libSBRdec/src/sbrdec_drc.cpp \
libSBRdec/src/sbrdec_freq_sca.cpp \
libSBRdec/src/sbrdecoder.cpp \
libSBRdec/src/sbr_ram.cpp \
libSBRdec/src/sbr_rom.cpp
SBRENC_SRC = \
libSBRenc/src/bit_sbr.cpp \
libSBRenc/src/env_bit.cpp \
libSBRenc/src/fram_gen.cpp \
libSBRenc/src/mh_det.cpp \
libSBRenc/src/ps_bitenc.cpp \
libSBRenc/src/ps_encode.cpp \
libSBRenc/src/resampler.cpp \
libSBRenc/src/sbr_encoder.cpp \
libSBRenc/src/sbr_ram.cpp \
libSBRenc/src/ton_corr.cpp \
libSBRenc/src/code_env.cpp \
libSBRenc/src/env_est.cpp \
libSBRenc/src/invf_est.cpp \
libSBRenc/src/nf_est.cpp \
libSBRenc/src/ps_main.cpp \
libSBRenc/src/sbrenc_freq_sca.cpp \
libSBRenc/src/sbr_misc.cpp \
libSBRenc/src/sbr_rom.cpp \
libSBRenc/src/tran_det.cpp
SYS_SRC = \
libSYS/src/cmdl_parser.cpp \
libSYS/src/conv_string.cpp \
libSYS/src/genericStds.cpp \
libSYS/src/wav_file.cpp
libfdk_aac_SOURCES = \
$(AACDEC_SRC) $(AACENC_SRC) \
$(MPEGTPDEC_SRC) $(MPEGTPENC_SRC) \
$(SBRDEC_SRC) $(SBRENC_SRC) \
$(PCMUTILS_SRC) $(FDK_SRC) $(SYS_SRC)
aac_enc_SOURCES = aac-enc.c wavreader.c
prefix = \usr\local
prefix_win = $(prefix:/=\) # In case we are using MSYS or MinGW.
CFLAGS = /nologo /W3 /Ox /MT /EHsc /Dinline=__inline $(TARGET_FLAGS) $(AM_CPPFLAGS) $(XCFLAGS)
CXXFLAGS = $(CFLAGS)
CPPFLAGS = $(CFLAGS)
LDFLAGS = -nologo $(XLDFLAGS)
ARFLAGS = -nologo
incdir = $(prefix_win)\include\fdk-aac
bindir = $(prefix_win)\bin
libdir = $(prefix_win)\lib
INST_DIRS = $(bindir) $(incdir) $(libdir)
LIB_DEF = fdk-aac.def
STATIC_LIB = fdk-aac.lib
SHARED_LIB = fdk-aac-1.dll
IMP_LIB = fdk-aac.dll.lib
AAC_ENC_OBJS = $(aac_enc_SOURCES:.c=.obj)
FDK_OBJS = $(libfdk_aac_SOURCES:.cpp=.obj)
PROGS = aac-enc.exe
all: $(LIB_DEF) $(STATIC_LIB) $(SHARED_LIB) $(IMP_LIB) $(PROGS)
clean:
del /f $(LIB_DEF) $(STATIC_LIB) $(SHARED_LIB) $(IMP_LIB) $(PROGS) libfdk-aac.pc 2>NUL
del /f *.obj *.exp 2>NUL
del /f libAACdec\src\*.obj 2>NUL
del /f libAACenc\src\*.obj 2>NUL
del /f libFDK\src\*.obj 2>NUL
del /f libMpegTPDec\src\*.obj 2>NUL
del /f libMpegTPEnc\src\*.obj 2>NUL
del /f libPCMutils\src\*.obj 2>NUL
del /f libSBRdec\src\*.obj 2>NUL
del /f libSBRenc\src\*.obj 2>NUL
del /f libSYS\src\*.obj 2>NUL
install: $(INST_DIRS)
copy libAACdec\include\aacdecoder_lib.h $(incdir)
copy libAACenc\include\aacenc_lib.h $(incdir)
copy libSYS\include\FDK_audio.h $(incdir)
copy libSYS\include\genericStds.h $(incdir)
copy libSYS\include\machine_type.h $(incdir)
copy $(STATIC_LIB) $(libdir)
copy $(IMP_LIB) $(libdir)
copy $(SHARED_LIB) $(bindir)
copy $(PROGS) $(bindir)
copy $(LIB_DEF) $(libdir)
$(INST_DIRS):
@mkdir $(MKDIR_FLAGS) $@
$(STATIC_LIB): $(FDK_OBJS)
$(AR) $(ARFLAGS) -out:$@ $(FDK_OBJS)
$(IMP_LIB): $(SHARED_LIB)
$(SHARED_LIB): $(FDK_OBJS)
$(LD) $(LDFLAGS) -OUT:$@ -DEF:$(LIB_DEF) -implib:$(IMP_LIB) -DLL $(FDK_OBJS)
$(PROGS): $(AAC_ENC_OBJS)
$(LD) $(LDFLAGS) -out:$@ $(AAC_ENC_OBJS) $(STATIC_LIB)
.cpp.obj:
$(CXX) $(CXXFLAGS) -c -Fo$@ $<
$(LIB_DEF):
@echo EXPORTS > $(LIB_DEF)
@type fdk-aac.sym >> $(LIB_DEF)

View File

@ -18,7 +18,13 @@
#include <stdio.h>
#include <stdint.h>
#if defined(_MSC_VER)
#include <getopt.h>
#else
#include <unistd.h>
#endif
#include <stdlib.h>
#include "libAACenc/include/aacenc_lib.h"
#include "wavreader.h"

View File

@ -1,7 +1,7 @@
dnl -*- Autoconf -*-
dnl Process this file with autoconf to produce a configure script.
AC_INIT([fdk-aac], [0.1.3], [http://sourceforge.net/projects/opencore-amr/])
AC_INIT([fdk-aac], [0.1.5], [http://sourceforge.net/projects/opencore-amr/])
AC_CONFIG_AUX_DIR(.)
AC_CONFIG_MACRO_DIR([m4])
AM_INIT_AUTOMAKE([tar-ustar foreign])
@ -26,7 +26,7 @@ AC_SEARCH_LIBS([sin], [m])
dnl soname version to use
dnl goes by current[:revision[:age]] with the soname ending up as
dnl current.age.revision
FDK_AAC_VERSION=0:4:0
FDK_AAC_VERSION=1:0:0
AS_IF([test x$enable_shared = xyes], [LIBS_PRIVATE=$LIBS], [LIBS_PUBLIC=$LIBS])
AC_SUBST(FDK_AAC_VERSION)

Binary file not shown.

Binary file not shown.

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -144,10 +144,9 @@ to allocate memory for the required structures, and the corresponding mpegFileRe
files and to de-allocate associated structures. mpegFileRead_Open() tries to detect the bitstream format and
in case of MPEG-4 file format or Raw Packets file format (a Fraunhofer IIS proprietary format) reads the Audio
Specific Config data (ASC). An unsuccessful attempt to recognize the bitstream format requires the user to
provide this information manually (see \ref CommandLineUsage). For any other bitstream formats that are
usually applicable in streaming applications, the decoder itself will try to synchronize and parse the given
bitstream fragment using the FDK transport library. Hence, for streaming applications (without file access)
this step is not necessary.
provide this information manually. For any other bitstream formats that are usually applicable in streaming
applications, the decoder itself will try to synchronize and parse the given bitstream fragment using the
FDK transport library. Hence, for streaming applications (without file access) this step is not necessary.
-# Call aacDecoder_Open() to open and retrieve a handle to a new AAC decoder instance.
\dontinclude main.cpp
@ -349,6 +348,10 @@ Where N equals to CStreamInfo::frameSize .
#include "genericStds.h"
#define AACDECODER_LIB_VL0 2
#define AACDECODER_LIB_VL1 5
#define AACDECODER_LIB_VL2 17
/**
* \brief AAC decoder error codes.
*/
@ -379,6 +382,7 @@ typedef enum {
not exist. */
AAC_DEC_NEED_TO_RESTART = 0x200B, /*!< The decoder needs to be restarted, since the requiered configuration change cannot be
performed. */
AAC_DEC_OUTPUT_BUFFER_TOO_SMALL = 0x200C, /*!< The provided output buffer is too small. */
aac_dec_init_error_end = 0x2FFF,
/* Decode errors. Output buffer is valid but concealed. */
@ -430,21 +434,68 @@ typedef enum {
typedef enum
{
AAC_PCM_OUTPUT_INTERLEAVED = 0x0000, /*!< PCM output mode (1: interleaved (default); 0: not interleaved). */
AAC_PCM_OUTPUT_CHANNELS = 0x0001, /*!< Number of PCM output channels (if different from encoded audio channels, downmixing or
upmixing is applied). \n
-1: Disable up-/downmixing. The decoder output contains the same number of channels as the
encoded bitstream. \n
1: The decoder performs a mono matrix mix-down if the encoded audio channels are greater
than one. Thus it ouputs always exact one channel. \n
2: The decoder performs a stereo matrix mix-down if the encoded audio channels are greater
than two. If the encoded audio channels are smaller than two the decoder duplicates the
output. Thus it ouputs always exact two channels. \n */
AAC_PCM_DUAL_CHANNEL_OUTPUT_MODE = 0x0002, /*!< Defines how the decoder processes two channel signals:
0: Leave both signals as they are (default).
1: Create a dual mono output signal from channel 1.
2: Create a dual mono output signal from channel 2.
AAC_PCM_DUAL_CHANNEL_OUTPUT_MODE = 0x0002, /*!< Defines how the decoder processes two channel signals: \n
0: Leave both signals as they are (default). \n
1: Create a dual mono output signal from channel 1. \n
2: Create a dual mono output signal from channel 2. \n
3: Create a dual mono output signal by mixing both channels (L' = R' = 0.5*Ch1 + 0.5*Ch2). */
AAC_PCM_OUTPUT_CHANNEL_MAPPING = 0x0003, /*!< Output buffer channel ordering. 0: MPEG PCE style order, 1: WAV file channel order (default). */
AAC_PCM_LIMITER_ENABLE = 0x0004, /*!< Enable signal level limiting. \n
-1: Auto-config. Enable limiter for all non-lowdelay configurations by default. \n
0: Disable limiter in general. \n
1: Enable limiter always.
It is recommended to call the decoder with a AACDEC_CLRHIST flag to reset all states when
the limiter switch is changed explicitly. */
AAC_PCM_LIMITER_ATTACK_TIME = 0x0005, /*!< Signal level limiting attack time in ms.
Default confguration is 15 ms. Adjustable range from 1 ms to 15 ms. */
AAC_PCM_LIMITER_RELEAS_TIME = 0x0006, /*!< Signal level limiting release time in ms.
Default configuration is 50 ms. Adjustable time must be larger than 0 ms. */
AAC_PCM_MIN_OUTPUT_CHANNELS = 0x0011, /*!< Minimum number of PCM output channels. If higher than the number of encoded audio channels,
a simple channel extension is applied. \n
-1, 0: Disable channel extenstion feature. The decoder output contains the same number of
channels as the encoded bitstream. \n
1: This value is currently needed only together with the mix-down feature. See
::AAC_PCM_MAX_OUTPUT_CHANNELS and note 2 below. \n
2: Encoded mono signals will be duplicated to achieve a 2/0/0.0 channel output
configuration. \n
6: The decoder trys to reorder encoded signals with less than six channels to achieve
a 3/0/2.1 channel output signal. Missing channels will be filled with a zero signal.
If reordering is not possible the empty channels will simply be appended. Only
available if instance is configured to support multichannel output. \n
8: The decoder trys to reorder encoded signals with less than eight channels to
achieve a 3/0/4.1 channel output signal. Missing channels will be filled with a
zero signal. If reordering is not possible the empty channels will simply be
appended. Only available if instance is configured to support multichannel output.\n
NOTE: \n
1. The channel signalling (CStreamInfo::pChannelType and CStreamInfo::pChannelIndices)
will not be modified. Added empty channels will be signalled with channel type
AUDIO_CHANNEL_TYPE::ACT_NONE. \n
2. If the parameter value is greater than that of ::AAC_PCM_MAX_OUTPUT_CHANNELS both will
be set to the same value. \n
3. This parameter does not affect MPEG Surround processing. */
AAC_PCM_MAX_OUTPUT_CHANNELS = 0x0012, /*!< Maximum number of PCM output channels. If lower than the number of encoded audio channels,
downmixing is applied accordingly. If dedicated metadata is available in the stream it
will be used to achieve better mixing results. \n
-1, 0: Disable downmixing feature. The decoder output contains the same number of channels
as the encoded bitstream. \n
1: All encoded audio configurations with more than one channel will be mixed down to
one mono output signal. \n
2: The decoder performs a stereo mix-down if the number encoded audio channels is
greater than two. \n
6: If the number of encoded audio channels is greater than six the decoder performs a
mix-down to meet the target output configuration of 3/0/2.1 channels. Only
available if instance is configured to support multichannel output. \n
8: This value is currently needed only together with the channel extension feature.
See ::AAC_PCM_MIN_OUTPUT_CHANNELS and note 2 below. Only available if instance is
configured to support multichannel output. \n
NOTE: \n
1. Down-mixing of any seven or eight channel configuration not defined in ISO/IEC 14496-3
PDAM 4 is not supported by this software version. \n
2. If the parameter value is greater than zero but smaller than ::AAC_PCM_MIN_OUTPUT_CHANNELS
both will be set to same value. \n
3. The operating mode of the MPEG Surround module will be set accordingly. \n
4. Setting this param with any value will disable the binaural processing of the MPEG
Surround module (::AAC_MPEGS_BINAURAL_ENABLE=0). */
AAC_CONCEAL_METHOD = 0x0100, /*!< Error concealment: Processing method. \n
0: Spectral muting. \n
@ -485,18 +536,18 @@ typedef enum
*/
typedef struct
{
/* These three members are the only really relevant ones for the user. */
/* These five members are the only really relevant ones for the user. */
INT sampleRate; /*!< The samplerate in Hz of the fully decoded PCM audio signal (after SBR processing). */
INT frameSize; /*!< The frame size of the decoded PCM audio signal. \n
1024 or 960 for AAC-LC \n
2048 or 1920 for HE-AAC (v2) \n
512 or 480 for AAC-LD and AAC-ELD */
INT numChannels; /*!< The number of output audio channels in the decoded and interleaved PCM audio signal. */
AUDIO_CHANNEL_TYPE *pChannelType; /*!< Audio channel type of each output audio channel. */
UCHAR *pChannelIndices; /*!< Audio channel index for each output audio channel.
AUDIO_CHANNEL_TYPE *pChannelType; /*!< Audio channel type of each output audio channel. */
UCHAR *pChannelIndices; /*!< Audio channel index for each output audio channel.
See ISO/IEC 13818-7:2005(E), 8.5.3.2 Explicit channel mapping using a program_config_element() */
/* Decoder internal members. */
INT aacSampleRate; /*!< sampling rate in Hz without SBR (from configuration info). */
INT aacSampleRate; /*!< Sampling rate in Hz without SBR (from configuration info). */
INT profile; /*!< MPEG-2 profile (from file header) (-1: not applicable (e. g. MPEG-4)). */
AUDIO_OBJECT_TYPE aot; /*!< Audio Object Type (from ASC): is set to the appropriate value for MPEG-2 bitstreams (e. g. 2 for AAC-LC). */
INT channelConfig; /*!< Channel configuration (0: PCE defined, 1: mono, 2: stereo, ... */
@ -509,7 +560,9 @@ typedef struct
AUDIO_OBJECT_TYPE extAot; /*!< Extension Audio Object Type (from ASC) */
INT extSamplingRate; /*!< Extension sampling rate in Hz (from ASC) */
UINT flags; /*!< Copy if internal flags. Only to be written by the decoder, and only to be read externally. */
UINT outputDelay; /*!< The number of samples the output is additionally delayed by the decoder. */
UINT flags; /*!< Copy of internal flags. Only to be written by the decoder, and only to be read externally. */
SCHAR epConfig; /*!< epConfig level (from ASC): only level 0 supported, -1 means no ER (e. g. AOT=2, MPEG-2 AAC, etc.) */
@ -522,10 +575,25 @@ typedef struct
UINT numTotalAccessUnits; /*!< This is the number of total access units that have passed through the decoder. */
UINT numBadAccessUnits; /*!< This is the number of total access units that were considered with errors from numTotalBytes. */
/* Metadata */
SCHAR drcProgRefLev; /*!< DRC program reference level. Defines the reference level below full-scale.
It is quantized in steps of 0.25dB. The valid values range from 0 (0 dBFS) to 127 (-31.75 dBFS).
It is used to reflect the average loudness of the audio in LKFS accoring to ITU-R BS 1770.
If no level has been found in the bitstream the value is -1. */
SCHAR drcPresMode; /*!< DRC presentation mode. According to ETSI TS 101 154, this field indicates whether
light (MPEG-4 Dynamic Range Control tool) or heavy compression (DVB heavy compression)
dynamic range control shall take priority on the outputs.
For details, see ETSI TS 101 154, table C.33. Possible values are: \n
-1: No corresponding metadata found in the bitstream \n
0: DRC presentation mode not indicated \n
1: DRC presentation mode 1 \n
2: DRC presentation mode 2 \n
3: Reserved */
} CStreamInfo;
typedef struct AAC_DECODER_INSTANCE *HANDLE_AACDECODER;
typedef struct AAC_DECODER_INSTANCE *HANDLE_AACDECODER; /*!< Pointer to a AAC decoder instance. */
#ifdef __cplusplus
extern "C"
@ -634,11 +702,15 @@ aacDecoder_Fill ( HANDLE_AACDECODER self,
const UINT bufferSize[],
UINT *bytesValid );
#define AACDEC_CONCEAL 1 /*!< Flag for aacDecoder_DecodeFrame(): do not consider new input data. Do concealment. */
#define AACDEC_FLUSH 2 /*!< Flag for aacDecoder_DecodeFrame(): Do not consider new input data. Flush filterbanks (output delayed audio). */
#define AACDEC_INTR 4 /*!< Flag for aacDecoder_DecodeFrame(): Signal an input bit stream data discontinuity. Resync any internals as necessary. */
#define AACDEC_CLRHIST 8 /*!< Flag for aacDecoder_DecodeFrame(): Clear all signal delay lines and history buffers.
Caution: This can cause discontinuities in the output signal. */
#define AACDEC_CONCEAL 1 /*!< Flag for aacDecoder_DecodeFrame(): Trigger the built-in error concealment module \
to generate a substitute signal for one lost frame. New input data will not be
considered. */
#define AACDEC_FLUSH 2 /*!< Flag for aacDecoder_DecodeFrame(): Flush all filterbanks to get all delayed audio \
without having new input data. Thus new input data will not be considered.*/
#define AACDEC_INTR 4 /*!< Flag for aacDecoder_DecodeFrame(): Signal an input bit stream data discontinuity. \
Resync any internals as necessary. */
#define AACDEC_CLRHIST 8 /*!< Flag for aacDecoder_DecodeFrame(): Clear all signal delay lines and history buffers.\
CAUTION: This can cause discontinuities in the output signal. */
/**
* \brief Decode one audio frame

View File

@ -108,15 +108,15 @@ C_ALLOC_MEM(AacDecoder, AAC_DECODER_INSTANCE, 1)
/*! The structure CAacDecoderStaticChannelInfo contains the static sideinfo which is needed
for the decoding of one aac channel. <br>
Dimension: #AacDecoderChannels */
C_ALLOC_MEM2(AacDecoderStaticChannelInfo, CAacDecoderStaticChannelInfo, 1, (6))
C_ALLOC_MEM2(AacDecoderStaticChannelInfo, CAacDecoderStaticChannelInfo, 1, (8))
/*! The structure CAacDecoderChannelInfo contains the dynamic sideinfo which is needed
for the decoding of one aac channel. <br>
Dimension: #AacDecoderChannels */
C_ALLOC_MEM2(AacDecoderChannelInfo, CAacDecoderChannelInfo, 1, (6))
C_AALLOC_MEM2(AacDecoderChannelInfo, CAacDecoderChannelInfo, 1, (8))
/*! Overlap buffer */
C_ALLOC_MEM2(OverlapBuffer, FIXP_DBL, OverlapBufferSize, (6))
C_ALLOC_MEM2(OverlapBuffer, FIXP_DBL, OverlapBufferSize, (8))
C_ALLOC_MEM(DrcInfo, CDrcInfo, 1)
@ -128,7 +128,7 @@ C_ALLOC_MEM(DrcInfo, CDrcInfo, 1)
Dynamic memory areas, might be reused in other algorithm sections,
e.g. the sbr decoder
*/
C_ALLOC_MEM_OVERLAY(WorkBufferCore2, FIXP_DBL, ((6)*1024), SECT_DATA_L2, WORKBUFFER2_TAG)
C_ALLOC_MEM_OVERLAY(WorkBufferCore2, FIXP_DBL, ((8)*1024), SECT_DATA_L2, WORKBUFFER2_TAG)
C_ALLOC_MEM_OVERLAY(WorkBufferCore1, CWorkBufferCore1, 1, SECT_DATA_L1, WORKBUFFER1_TAG)

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -167,6 +167,36 @@ const SCHAR ExponentTable [4][14] =
} ;
/* 41 scfbands */
static const SHORT sfb_96_1024[42] =
{
0, 4, 8, 12, 16, 20, 24, 28, 32, 36, 40, 44,
48, 52, 56, 64, 72, 80, 88, 96, 108, 120, 132, 144,
156, 172, 188, 212, 240, 276, 320, 384, 448, 512, 576, 640,
704, 768, 832, 896, 960, 1024
};
/* 12 scfbands */
static const SHORT sfb_96_128[13] =
{
0, 4, 8, 12, 16, 20, 24, 32, 40, 48, 64, 92,
128
};
/* 47 scfbands*/
static const SHORT sfb_64_1024[48] =
{
0, 4, 8, 12, 16, 20, 24, 28, 32, 36, 40, 44, 48, 52,
56, 64, 72, 80, 88, 100, 112, 124, 140, 156, 172, 192, 216, 240,
268, 304, 344, 384, 424, 464, 504, 544, 584, 624, 664, 704, 744, 784,
824, 864, 904, 944, 984,1024
};
/* 12 scfbands */
static const SHORT sfb_64_128[13] =
{
0, 4, 8, 12, 16, 20, 24,
32, 40, 48, 64, 92, 128
};
/* 49 scfbands */
static const SHORT sfb_48_1024[50] = {
@ -239,6 +269,35 @@ static const SHORT sfb_8_128[16] =
};
static const SHORT sfb_96_960[42] =
{
0, 4, 8, 12, 16, 20, 24, 28, 32, 36,
40, 44, 48, 52, 56, 64, 72, 80, 88, 96,
108, 120, 132, 144, 156, 172, 188, 212, 240, 276,
320, 384, 448, 512, 576, 640, 704, 768, 832, 896,
960
}; /* 40 scfbands */
static const SHORT sfb_96_120[13] =
{
0, 4, 8, 12, 16, 20, 24, 32, 40, 48,
64, 92, 120
}; /* 12 scfbands */
static const SHORT sfb_64_960[47] =
{
0, 4, 8, 12, 16, 20, 24, 28, 32, 36,
40, 44, 48, 52, 56, 64, 72, 80, 88, 100,
112, 124, 140, 156, 172, 192, 216, 240, 268, 304,
344, 384, 424, 464, 504, 544, 584, 624, 664, 704,
744, 784, 824, 864, 904, 944, 960
}; /* 46 scfbands */
static const SHORT sfb_64_120[13] =
{
0, 4, 8, 12, 16, 20, 24, 32, 40, 48,
64, 92, 120
}; /* 12 scfbands */
static const SHORT sfb_48_960[50] =
{
@ -358,9 +417,9 @@ static const SHORT sfb_24_480[31] =
const SFB_INFO sfbOffsetTables[5][16] =
{
{
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ sfb_96_1024, sfb_96_128, 41, 12 },
{ sfb_96_1024, sfb_96_128, 41, 12 },
{ sfb_64_1024, sfb_64_128, 47, 12 },
{ sfb_48_1024, sfb_48_128, 49, 14 },
{ sfb_48_1024, sfb_48_128, 49, 14 },
{ sfb_32_1024, sfb_48_128, 51, 14 },
@ -372,9 +431,9 @@ const SFB_INFO sfbOffsetTables[5][16] =
{ sfb_8_1024, sfb_8_128, 40, 15 },
{ sfb_8_1024, sfb_8_128, 40, 15 },
}, {
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ sfb_96_960, sfb_96_120, 40, 12 },
{ sfb_96_960, sfb_96_120, 40, 12 },
{ sfb_64_960, sfb_64_120, 46, 12 },
{ sfb_48_960, sfb_48_120, 49, 14 },
{ sfb_48_960, sfb_48_120, 49, 14 },
{ sfb_32_960, sfb_48_120, 49, 14 },
@ -388,9 +447,9 @@ const SFB_INFO sfbOffsetTables[5][16] =
}, {
{ NULL, NULL, 0, 0 },
}, {
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ sfb_48_512, NULL, 36, 0 },
{ sfb_48_512, NULL, 36, 0 },
{ sfb_48_512, NULL, 36, 0 },
{ sfb_48_512, NULL, 36, 0 },
{ sfb_48_512, NULL, 36, 0},
{ sfb_32_512, NULL, 37, 0 },
@ -402,9 +461,9 @@ const SFB_INFO sfbOffsetTables[5][16] =
{ sfb_24_512, NULL, 31, 0 },
{ sfb_24_512, NULL, 31, 0 },
}, {
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ NULL, NULL, 0, 0 },
{ sfb_48_480, NULL, 35, 0 },
{ sfb_48_480, NULL, 35, 0 },
{ sfb_48_480, NULL, 35, 0 },
{ sfb_48_480, NULL, 35, 0 },
{ sfb_48_480, NULL, 35, 0 },
{ sfb_32_480, NULL, 37, 0 },
@ -1777,42 +1836,62 @@ const FIXP_TCC FDKaacDec_tnsCoeff4 [16] =
};
/* MPEG like mapping (no change). */
const UCHAR channelMappingTablePassthrough[8][8] =
const UCHAR channelMappingTablePassthrough[15][8] =
{
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* fallback */
{ 0, 1,255,255,255,255,255,255}, /* mono / PS */
{ 0, 1,255,255,255,255,255,255}, /* stereo */
{ 0, 1, 2,255,255,255,255,255}, /* 3ch */
{ 0, 1, 2, 3,255,255,255,255}, /* 4ch */
{ 0, 1, 2, 3, 4,255,255,255}, /* 5ch */
{ 0, 1, 2, 3, 4, 5,255,255}, /* 5.1ch */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* 7ch */
{ 0, 1, 2, 3, 4, 5, 6, 7} /* 7.1ch */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* 7.1 front */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 0, 1, 2, 3, 4, 5, 6,255}, /* 6.1ch */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* 7.1 rear */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 0, 1, 2, 3, 4, 5, 6, 7} /* 7.1 top */
};
/* WAV file like mapping (from MPEG mapping). */
const UCHAR channelMappingTableWAV[8][8] =
const UCHAR channelMappingTableWAV[15][8] =
{
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* fallback */
{ 0, 1,255,255,255,255,255,255}, /* mono / PS */
{ 0, 1,255,255,255,255,255,255}, /* stereo */
{ 2, 0, 1,255,255,255,255,255}, /* 3ch */
{ 2, 0, 1, 3,255,255,255,255}, /* 4ch */
{ 2, 0, 1, 3, 4,255,255,255}, /* 5ch */
{ 2, 0, 1, 4, 5, 3,255,255}, /* 5.1ch */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* 7ch */
{ 2, 0, 1, 6, 7, 4, 5, 3} /* 7.1ch */
{ 2, 6, 7, 0, 1, 4, 5, 3}, /* 7.1 front */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 2, 0, 1, 4, 5, 6, 3,255}, /* 6.1ch */
{ 2, 0, 1, 6, 7, 4, 5, 3}, /* 7.1 rear */
{ 0, 1, 2, 3, 4, 5, 6, 7}, /* reserved */
{ 2, 0, 1, 4, 5, 3, 6, 7} /* 7.1 top */
};
/* Lookup tables for elements in ER bitstream */
const MP4_ELEMENT_ID elementsTab[8][7] =
const MP4_ELEMENT_ID elementsTab[15][7] =
{
{ID_SCE, ID_EXT, ID_END, ID_NONE, ID_NONE,ID_NONE,ID_NONE }, /* 1 channel */
{ID_CPE, ID_EXT, ID_END, ID_NONE, ID_NONE,ID_NONE,ID_NONE } /* 2 channels */
,
{ID_SCE, ID_CPE, ID_EXT, ID_END, ID_NONE,ID_NONE,ID_NONE }, /* 3 channels */
{ID_SCE, ID_CPE, ID_SCE, ID_EXT, ID_END, ID_NONE,ID_NONE }, /* 4 channels */
{ID_SCE, ID_CPE, ID_CPE, ID_EXT, ID_END, ID_NONE,ID_NONE }, /* 5 channels */
{ID_SCE, ID_CPE, ID_CPE, ID_LFE, ID_EXT, ID_END, ID_NONE }, /* 6 channels */
{ID_SCE, ID_CPE, ID_CPE, ID_CPE, ID_LFE, ID_EXT, ID_END} /* 8 channels */
/* 1 */ { ID_SCE, ID_EXT, ID_END, ID_NONE, ID_NONE, ID_NONE, ID_NONE }, /* 1 channel */
/* 2 */ { ID_CPE, ID_EXT, ID_END, ID_NONE, ID_NONE, ID_NONE, ID_NONE } /* 2 channels */
/* 3 */ ,{ ID_SCE, ID_CPE, ID_EXT, ID_END, ID_NONE, ID_NONE, ID_NONE }, /* 3 channels */
/* 4 */ { ID_SCE, ID_CPE, ID_SCE, ID_EXT, ID_END, ID_NONE, ID_NONE }, /* 4 channels */
/* 5 */ { ID_SCE, ID_CPE, ID_CPE, ID_EXT, ID_END, ID_NONE, ID_NONE }, /* 5 channels */
/* 6 */ { ID_SCE, ID_CPE, ID_CPE, ID_LFE, ID_EXT, ID_END, ID_NONE } /* 6 channels */
/* 7 */ ,{ ID_SCE, ID_CPE, ID_CPE, ID_CPE, ID_LFE, ID_EXT, ID_END }, /* 8 channels */
/* 8 */ { ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE }, /* reserved */
/* 9 */ { ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE }, /* reserved */
/* 10 */ { ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE }, /* reserved */
/* 11 */ { ID_SCE, ID_CPE, ID_CPE, ID_SCE, ID_LFE, ID_EXT, ID_END }, /* 7 channels */
/* 12 */ { ID_SCE, ID_CPE, ID_CPE, ID_CPE, ID_LFE, ID_EXT, ID_END }, /* 8 channels */
/* 13 */ { ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE, ID_NONE }, /* reserved */
/* 14 */ { ID_SCE, ID_CPE, ID_CPE, ID_LFE, ID_CPE, ID_EXT, ID_END } /* 8 channels */
};
/*! Random sign bit used for concealment

View File

@ -177,11 +177,12 @@ extern const USHORT randomSign[AAC_NF_NO_RANDOM_VAL/16];
extern const FIXP_DBL pow2_div24minus1[47];
extern const int offsetTab[2][16];
/* Channel mapping indices for time domain I/O. First dimension is channel count-1. */
extern const UCHAR channelMappingTablePassthrough[8][8];
extern const UCHAR channelMappingTableWAV[8][8];
/* Channel mapping indices for time domain I/O.
The first dimension is the channel configuration index. */
extern const UCHAR channelMappingTablePassthrough[15][8];
extern const UCHAR channelMappingTableWAV[15][8];
/* Lookup tables for elements in ER bitstream */
extern const MP4_ELEMENT_ID elementsTab[8][7];
extern const MP4_ELEMENT_ID elementsTab[15][7];
#endif /* #ifndef AAC_ROM_H */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -130,7 +130,6 @@ void aacDecoder_drcInit (
/* init control fields */
self->enable = 0;
self->numThreads = 0;
self->digitalNorm = 0;
/* init params */
pParams = &self->params;
@ -139,12 +138,15 @@ void aacDecoder_drcInit (
pParams->usrCut = FL2FXCONST_DBL(0.0f);
pParams->boost = FL2FXCONST_DBL(0.0f);
pParams->usrBoost = FL2FXCONST_DBL(0.0f);
pParams->targetRefLevel = AACDEC_DRC_DEFAULT_REF_LEVEL;
pParams->targetRefLevel = -1;
pParams->expiryFrame = AACDEC_DRC_DFLT_EXPIRY_FRAMES;
pParams->applyDigitalNorm = 0;
pParams->applyHeavyCompression = 0;
/* initial program ref level = target ref level */
self->progRefLevel = pParams->targetRefLevel;
self->progRefLevelPresent = 0;
self->presMode = -1;
}
@ -222,11 +224,12 @@ AAC_DECODER_ERROR aacDecoder_drcSetParam (
return AAC_DEC_INVALID_HANDLE;
}
if (value < 0) {
self->digitalNorm = 0;
self->params.applyDigitalNorm = 0;
self->params.targetRefLevel = -1;
}
else {
/* ref_level must be between 0 and MAX_REFERENCE_LEVEL, inclusive */
self->digitalNorm = 1;
self->params.applyDigitalNorm = 1;
if (self->params.targetRefLevel != (SCHAR)value) {
self->params.targetRefLevel = (SCHAR)value;
self->progRefLevel = (SCHAR)value; /* Always set the program reference level equal to the
@ -234,6 +237,16 @@ AAC_DECODER_ERROR aacDecoder_drcSetParam (
}
}
break;
case APPLY_NORMALIZATION:
if (value < 0 || value > 1) {
return AAC_DEC_SET_PARAM_FAIL;
}
if (self == NULL) {
return AAC_DEC_INVALID_HANDLE;
}
/* Store new parameter value */
self->params.applyDigitalNorm = (UCHAR)value;
break;
case APPLY_HEAVY_COMPRESSION:
if (value < 0 || value > 1) {
return AAC_DEC_SET_PARAM_FAIL;
@ -278,7 +291,7 @@ AAC_DECODER_ERROR aacDecoder_drcSetParam (
self->enable = ( (self->params.boost > (FIXP_DBL)0)
|| (self->params.cut > (FIXP_DBL)0)
|| (self->params.applyHeavyCompression != 0)
|| (self->digitalNorm == 1) );
|| (self->params.targetRefLevel >= 0) );
return ErrorStatus;
@ -539,7 +552,7 @@ static int aacDecoder_drcReadCompression (
UINT payloadPosition )
{
int bitCnt = 0;
int dmxLevelsPresent, compressionPresent;
int dmxLevelsPresent, extensionPresent, compressionPresent;
int coarseGrainTcPresent, fineGrainTcPresent;
/* Move to the beginning of the DRC payload field */
@ -561,8 +574,9 @@ static int aacDecoder_drcReadCompression (
return 0;
}
FDKreadBits(bs, 2); /* dolby_surround_mode */
FDKreadBits(bs, 2); /* presentation_mode */
if (FDKreadBits(bs, 2) != 0) { /* reserved, set to 0 */
pDrcBs->presMode = FDKreadBits(bs, 2); /* presentation_mode */
FDKreadBits(bs, 1); /* stereo_downmix_mode */
if (FDKreadBits(bs, 1) != 0) { /* reserved, set to 0 */
return 0;
}
@ -571,9 +585,7 @@ static int aacDecoder_drcReadCompression (
return 0;
}
dmxLevelsPresent = FDKreadBits(bs, 1); /* downmixing_levels_MPEG4_status */
if (FDKreadBits(bs, 1) != 0) { /* reserved, set to 0 */
return 0;
}
extensionPresent = FDKreadBits(bs, 1); /* ancillary_data_extension_status; */
compressionPresent = FDKreadBits(bs, 1); /* audio_coding_mode_and_compression status */
coarseGrainTcPresent = FDKreadBits(bs, 1); /* coarse_grain_timecode_status */
fineGrainTcPresent = FDKreadBits(bs, 1); /* fine_grain_timecode_status */
@ -631,6 +643,19 @@ static int aacDecoder_drcReadCompression (
bitCnt += 16;
}
/* Read extension just to get the right amount of bits. */
if (extensionPresent) {
int extBits = 8;
FDKreadBits(bs, 1); /* reserved, set to 0 */
if (FDKreadBits(bs, 1)) extBits += 8; /* ext_downmixing_levels_status */
if (FDKreadBits(bs, 1)) extBits += 16; /* ext_downmixing_global_gains_status */
if (FDKreadBits(bs, 1)) extBits += 8; /* ext_downmixing_lfe_level_status */
FDKpushFor(bs, extBits - 4); /* skip the extension payload remainder. */
bitCnt += extBits;
}
return (bitCnt);
}
@ -680,7 +705,7 @@ static int aacDecoder_drcExtractAndMap (
}
self->numPayloads = 0;
if (self->dvbAncDataAvailable)
if (self->dvbAncDataAvailable && self->numThreads < MAX_DRC_THREADS)
{ /* Append a DVB heavy compression payload thread if available. */
int bitsParsed;
@ -780,9 +805,15 @@ static int aacDecoder_drcExtractAndMap (
*/
if (pThreadBs->progRefLevel >= 0) {
self->progRefLevel = pThreadBs->progRefLevel;
self->progRefLevelPresent = 1;
self->prlExpiryCount = 0; /* Got a new value -> Reset counter */
}
if (drcPayloadType == DVB_DRC_ANC_DATA) {
/* Announce the presentation mode of this valid thread. */
self->presMode = pThreadBs->presMode;
}
/* SCE, CPE and LFE */
for (ch = 0; ch < validChannels; ch++) {
int mapedChannel = channelMapping[ch];
@ -802,6 +833,7 @@ static int aacDecoder_drcExtractAndMap (
if ( (pParams->expiryFrame > 0)
&& (self->prlExpiryCount++ > pParams->expiryFrame) )
{ /* The program reference level is too old, so set it back to the target level. */
self->progRefLevelPresent = 0;
self->progRefLevel = pParams->targetRefLevel;
self->prlExpiryCount = 0;
}
@ -815,6 +847,7 @@ void aacDecoder_drcApply (
void *pSbrDec,
CAacDecoderChannelInfo *pAacDecoderChannelInfo,
CDrcChannelData *pDrcChData,
FIXP_DBL *extGain,
int ch, /* needed only for SBR */
int aacFrameSize,
int bSbrPresent )
@ -826,8 +859,8 @@ void aacDecoder_drcApply (
FIXP_DBL max_mantissa;
INT max_exponent;
FIXP_DBL norm_mantissa = FL2FXCONST_DBL(0.0f);
INT norm_exponent = 0;
FIXP_DBL norm_mantissa = FL2FXCONST_DBL(0.5f);
INT norm_exponent = 1;
FIXP_DBL fact_mantissa[MAX_DRC_BANDS];
INT fact_exponent[MAX_DRC_BANDS];
@ -849,6 +882,15 @@ void aacDecoder_drcApply (
if (!self->enable) {
sbrDecoder_drcDisable( (HANDLE_SBRDECODER)pSbrDec, ch );
if (extGain != NULL) {
INT gainScale = (INT)*extGain;
/* The gain scaling must be passed to the function in the buffer pointed on by extGain. */
if (gainScale >= 0 && gainScale <= DFRACT_BITS) {
*extGain = scaleValue(norm_mantissa, norm_exponent-gainScale);
} else {
FDK_ASSERT(0);
}
}
return;
}
@ -864,7 +906,7 @@ void aacDecoder_drcApply (
reduced DAC SNR (if signal is attenuated) or clipping (if signal is
boosted) */
if (self->digitalNorm == 1)
if (pParams->targetRefLevel >= 0)
{
/* 0.5^((targetRefLevel - progRefLevel)/24) */
norm_mantissa = fLdPow(
@ -874,7 +916,18 @@ void aacDecoder_drcApply (
3,
&norm_exponent );
}
else {
/* Always export the normalization gain (if possible). */
if (extGain != NULL) {
INT gainScale = (INT)*extGain;
/* The gain scaling must be passed to the function in the buffer pointed on by extGain. */
if (gainScale >= 0 && gainScale <= DFRACT_BITS) {
*extGain = scaleValue(norm_mantissa, norm_exponent-gainScale);
} else {
FDK_ASSERT(0);
}
}
if (self->params.applyDigitalNorm == 0) {
/* Reset normalization gain since this module must not apply it */
norm_mantissa = FL2FXCONST_DBL(0.5f);
norm_exponent = 1;
}
@ -1112,3 +1165,24 @@ int aacDecoder_drcEpilog (
return err;
}
/*
* Export relevant metadata info from bitstream payload.
*/
void aacDecoder_drcGetInfo (
HANDLE_AAC_DRC self,
SCHAR *pPresMode,
SCHAR *pProgRefLevel )
{
if (self != NULL) {
if (pPresMode != NULL) {
*pPresMode = self->presMode;
}
if (pProgRefLevel != NULL) {
if (self->progRefLevelPresent) {
*pProgRefLevel = self->progRefLevel;
} else {
*pProgRefLevel = -1;
}
}
}
}

View File

@ -98,7 +98,6 @@ amm-info@iis.fraunhofer.de
#include "channel.h"
#include "FDK_bitstream.h"
#define AACDEC_DRC_DEFAULT_REF_LEVEL ( 108 ) /* -27 dB below full scale (typical for movies) */
#define AACDEC_DRC_DFLT_EXPIRY_FRAMES ( 50 ) /* Default DRC data expiry time in AAC frames */
/**
@ -111,6 +110,7 @@ typedef enum
TARGET_REF_LEVEL,
DRC_BS_DELAY,
DRC_DATA_EXPIRY_FRAME,
APPLY_NORMALIZATION,
APPLY_HEAVY_COMPRESSION
} AACDEC_DRC_PARAM;
@ -149,6 +149,8 @@ int aacDecoder_drcProlog (
* \param pSbrDec pointer to SBR decoder instance
* \param pAacDecoderChannelInfo AAC decoder channel instance to be processed
* \param pDrcDat DRC channel data
* \param extGain Pointer to a FIXP_DBL where a externally applyable gain will be stored into (independently on whether it will be apply internally or not).
* At function call the buffer must hold the scale (0 >= scale < DFRACT_BITS) to be applied on the gain value.
* \param ch channel index
* \param aacFrameSize AAC frame size
* \param bSbrPresent flag indicating that SBR is present, in which case DRC is handed over to the SBR instance pSbrDec
@ -158,6 +160,7 @@ void aacDecoder_drcApply (
void *pSbrDec,
CAacDecoderChannelInfo *pAacDecoderChannelInfo,
CDrcChannelData *pDrcDat,
FIXP_DBL *extGain,
int ch,
int aacFrameSize,
int bSbrPresent );
@ -170,5 +173,17 @@ int aacDecoder_drcEpilog (
UCHAR channelMapping[],
int validChannels );
/**
* \brief Get metadata information found in bitstream.
* \param self DRC module instance handle.
* \param pPresMode Pointer to field where the presentation mode will be written to.
* \param pProgRefLevel Pointer to field where the program reference level will be written to.
* \return Nothing.
*/
void aacDecoder_drcGetInfo (
HANDLE_AAC_DRC self,
SCHAR *pPresMode,
SCHAR *pProgRefLevel );
#endif /* AACDEC_DRC_H */

View File

@ -124,6 +124,7 @@ typedef struct
{
UINT excludedChnsMask;
SCHAR progRefLevel;
SCHAR presMode; /* Presentation mode: 0 (not indicated), 1, 2, and 3 (reserved). */
SCHAR pceInstanceTag;
CDrcChannelData channelData;
@ -140,6 +141,7 @@ typedef struct
UINT expiryFrame;
SCHAR targetRefLevel;
UCHAR bsDelayEnable;
UCHAR applyDigitalNorm;
UCHAR applyHeavyCompression;
} CDrcParams;
@ -155,9 +157,11 @@ typedef struct
USHORT numPayloads; /* The number of DRC data payload elements found within frame */
USHORT numThreads; /* The number of DRC data threads extracted from the found payload elements */
SCHAR progRefLevel; /* Program reference level for all channels */
UCHAR progRefLevelPresent; /* Program reference level found in bitstream */
UINT prlExpiryCount; /* Counter that can be used to monitor the life time of the program reference level. */
SCHAR presMode; /* Presentation mode as defined in ETSI TS 101 154 */
UCHAR dvbAncDataAvailable; /* Flag that indicates whether DVB ancillary data is present or not */
UINT dvbAncDataPosition; /* Used to store the DVB ancillary data payload position in the bitstream (only one per frame) */
UINT drcPayloadPosition[MAX_DRC_THREADS]; /* Used to store the DRC payload positions in the bitstream */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -157,23 +157,9 @@ amm-info@iis.fraunhofer.de
#include "conceal.h"
#include "FDK_crc.h"
#define CAN_DO_PS(aot) \
((aot) == AOT_AAC_LC \
|| (aot) == AOT_SBR \
|| (aot) == AOT_PS \
|| (aot) == AOT_ER_BSAC \
|| (aot) == AOT_DRM_AAC)
#define IS_USAC(aot) \
((aot) == AOT_USAC \
|| (aot) == AOT_RSVD50)
#define IS_LOWDELAY(aot) \
((aot) == AOT_ER_AAC_LD \
|| (aot) == AOT_ER_AAC_ELD)
void CAacDecoder_SyncQmfMode(HANDLE_AACDECODER self)
{
@ -338,17 +324,22 @@ AAC_DECODER_ERROR CAacDecoder_AncDataParse (
\return Error code
*/
static AAC_DECODER_ERROR CDataStreamElement_Read (
HANDLE_AACDECODER self,
HANDLE_FDK_BITSTREAM bs,
CAncData *ancData,
HANDLE_AAC_DRC hDrcInfo,
HANDLE_TRANSPORTDEC pTp,
UCHAR *elementInstanceTag,
UINT alignmentAnchor )
{
HANDLE_TRANSPORTDEC pTp;
CAncData *ancData;
AAC_DECODER_ERROR error = AAC_DEC_OK;
UINT dataStart;
UINT dataStart, dseBits;
int dataByteAlignFlag, count;
FDK_ASSERT(self != NULL);
ancData = &self->ancData;
pTp = self->hInput;
int crcReg = transportDec_CrcStartReg(pTp, 0);
/* Element Instance Tag */
@ -361,6 +352,7 @@ static AAC_DECODER_ERROR CDataStreamElement_Read (
if (count == 255) {
count += FDKreadBits(bs,8); /* EscCount */
}
dseBits = count*8;
if (dataByteAlignFlag) {
FDKbyteAlign(bs, alignmentAnchor);
@ -372,20 +364,30 @@ static AAC_DECODER_ERROR CDataStreamElement_Read (
transportDec_CrcEndReg(pTp, crcReg);
{
INT readBits, dataBits = count<<3;
/* Move to the beginning of the data junk */
FDKpushBack(bs, dataStart-FDKgetValidBits(bs));
/* Read Anc data if available */
readBits = aacDecoder_drcMarkPayload( hDrcInfo, bs, DVB_DRC_ANC_DATA );
if (readBits != dataBits) {
/* Move to the end again. */
FDKpushBiDirectional(bs, FDKgetValidBits(bs)-dataStart+dataBits);
}
aacDecoder_drcMarkPayload( self->hDrcInfo, bs, DVB_DRC_ANC_DATA );
}
{
PCMDMX_ERROR dmxErr = PCMDMX_OK;
/* Move to the beginning of the data junk */
FDKpushBack(bs, dataStart-FDKgetValidBits(bs));
/* Read DMX meta-data */
dmxErr = pcmDmx_Parse (
self->hPcmUtils,
bs,
dseBits,
0 /* not mpeg2 */ );
}
/* Move to the very end of the element. */
FDKpushBiDirectional(bs, FDKgetValidBits(bs)-dataStart+dseBits);
return error;
}
@ -536,8 +538,9 @@ AAC_DECODER_ERROR CAacDecoder_ExtPayloadParse (HANDLE_AACDECODER self,
previous_element,
elIndex,
self->flags & AC_INDEP );
/* Enable SBR for implicit SBR signalling. */
if (sbrError == SBRDEC_OK) {
/* Enable SBR for implicit SBR signalling but only if no severe error happend. */
if ( (sbrError == SBRDEC_OK)
|| (sbrError == SBRDEC_PARSE_ERROR) ) {
self->sbrEnabled = 1;
}
} else {
@ -552,7 +555,7 @@ AAC_DECODER_ERROR CAacDecoder_ExtPayloadParse (HANDLE_AACDECODER self,
FDKpushBiDirectional(hBs, *count);
*count = 0;
} else {
/* If this is not a fill element with a known length, we are screwed an no further parsing makes sense. */
/* If this is not a fill element with a known length, we are screwed and further parsing makes no sense. */
if (sbrError != SBRDEC_OK) {
self->frameOK = 0;
}
@ -701,6 +704,12 @@ void CStreamInfoInit(CStreamInfo *pStreamInfo)
pStreamInfo->numChannels = 0;
pStreamInfo->sampleRate = 0;
pStreamInfo->frameSize = 0;
pStreamInfo->outputDelay = 0;
/* DRC */
pStreamInfo->drcProgRefLev = -1; /* set program reference level to not indicated */
pStreamInfo->drcPresMode = -1; /* default: presentation mode not indicated */
}
/*!
@ -774,7 +783,7 @@ LINKSPEC_CPP void CAacDecoder_Close(HANDLE_AACDECODER self)
if (self == NULL)
return;
for (ch=0; ch<(6); ch++) {
for (ch=0; ch<(8); ch++) {
if (self->pAacDecoderStaticChannelInfo[ch] != NULL) {
if (self->pAacDecoderStaticChannelInfo[ch]->pOverlapBuffer != NULL) {
FreeOverlapBuffer (&self->pAacDecoderStaticChannelInfo[ch]->pOverlapBuffer);
@ -825,12 +834,18 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_Init(HANDLE_AACDECODER self, const CS
switch (asc->m_aot) {
case AOT_AAC_LC:
self->streamInfo.profile = 1;
break;
case AOT_ER_AAC_SCAL:
if (asc->m_sc.m_gaSpecificConfig.m_layer > 0) {
/* aac_scalable_extension_element() currently not supported. */
return AAC_DEC_UNSUPPORTED_FORMAT;
}
case AOT_SBR:
case AOT_PS:
case AOT_ER_AAC_LD:
case AOT_ER_AAC_ELD:
case AOT_DRM_AAC:
break;
default:
@ -851,18 +866,19 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_Init(HANDLE_AACDECODER self, const CS
/* valid number of channels -> copy program config element (PCE) from ASC */
FDKmemcpy(&self->pce, &asc->m_progrConfigElement, sizeof(CProgramConfig));
/* Built element table */
el = CProgramConfig_GetElementTable(&asc->m_progrConfigElement, self->elements, 7);
for (; el<7; el++) {
el = CProgramConfig_GetElementTable(&asc->m_progrConfigElement, self->elements, (8), &self->chMapIndex);
for (; el<(8); el++) {
self->elements[el] = ID_NONE;
}
} else {
return AAC_DEC_UNSUPPORTED_CHANNELCONFIG;
}
} else {
self->chMapIndex = 0;
if (transportDec_GetFormat(self->hInput) == TT_MP4_ADTS) {
/* set default max_channels for memory allocation because in implicit channel mapping mode
we don't know the actual number of channels until we processed at least one raw_data_block(). */
ascChannels = (6);
ascChannels = (8);
} else {
return AAC_DEC_UNSUPPORTED_CHANNELCONFIG;
}
@ -874,26 +890,34 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_Init(HANDLE_AACDECODER self, const CS
case 1: case 2: case 3: case 4: case 5: case 6:
ascChannels = asc->m_channelConfiguration;
break;
case 7:
case 11:
ascChannels = 7;
break;
case 7: case 12: case 14:
ascChannels = 8;
break;
default:
return AAC_DEC_UNSUPPORTED_CHANNELCONFIG;
}
if (ascChannels > (8)) {
return AAC_DEC_UNSUPPORTED_CHANNELCONFIG;
}
/* Initialize constant mappings for channel config 1-7 */
if (asc->m_channelConfiguration > 0) {
int el;
FDKmemcpy(self->elements, elementsTab[asc->m_channelConfiguration-1], sizeof(MP4_ELEMENT_ID)*FDKmin(7,7));
for (el=7; el<7; el++) {
FDKmemcpy(self->elements, elementsTab[asc->m_channelConfiguration-1], sizeof(MP4_ELEMENT_ID)*FDKmin(7,(8)));
for (el=7; el<(8); el++) {
self->elements[el] = ID_NONE;
}
for (ch=0; ch<ascChannels; ch++) {
self->chMapping[ch] = ch;
}
for (; ch<(6); ch++) {
for (; ch<(8); ch++) {
self->chMapping[ch] = 255;
}
self->chMapIndex = asc->m_channelConfiguration;
}
#ifdef TP_PCE_ENABLE
else {
@ -909,9 +933,6 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_Init(HANDLE_AACDECODER self, const CS
self->streamInfo.channelConfig = asc->m_channelConfiguration;
if (ascChannels > (6)) {
return AAC_DEC_UNSUPPORTED_CHANNELCONFIG;
}
if (self->streamInfo.aot != asc->m_aot) {
self->streamInfo.aot = asc->m_aot;
ascChanged = 1;
@ -944,11 +965,20 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_Init(HANDLE_AACDECODER self, const CS
if (asc->m_aot == AOT_ER_AAC_ELD) {
self->flags |= AC_ELD;
self->flags |= (asc->m_sbrPresentFlag) ? AC_SBR_PRESENT : 0; /* Need to set the SBR flag for backward-compatibility
reasons. Even if SBR is not supported. */
self->flags |= (asc->m_sc.m_eldSpecificConfig.m_sbrCrcFlag) ? AC_SBRCRC : 0;
self->flags |= (asc->m_sc.m_eldSpecificConfig.m_useLdQmfTimeAlign) ? AC_LD_MPS : 0;
}
self->flags |= (asc->m_aot == AOT_ER_AAC_LD) ? AC_LD : 0;
self->flags |= (asc->m_epConfig >= 0) ? AC_ER : 0;
if ( asc->m_aot == AOT_DRM_AAC ) {
self->flags |= AC_DRM|AC_SBRCRC|AC_SCALABLE;
}
if ( (asc->m_aot == AOT_AAC_SCAL)
|| (asc->m_aot == AOT_ER_AAC_SCAL) ) {
self->flags |= AC_SCALABLE;
}
if (asc->m_sbrPresentFlag) {
@ -1096,6 +1126,7 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
MP4_ELEMENT_ID type = ID_NONE; /* Current element type */
INT aacChannels=0; /* Channel counter for channels found in the bitstream */
int chOutMapIdx; /* Output channel mapping index (see comment below) */
INT auStartAnchor = (INT)FDKgetValidBits(bs); /* AU start bit buffer position for AU byte alignment */
@ -1119,12 +1150,12 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
if (self->streamInfo.channelConfig == 0) {
/* Init Channel/Element mapping table */
for (ch=0; ch<(6); ch++) {
for (ch=0; ch<(8); ch++) {
self->chMapping[ch] = 255;
}
if (!CProgramConfig_IsValid(pce)) {
int el;
for (el=0; el<7; el++) {
for (el=0; el<(8); el++) {
self->elements[el] = ID_NONE;
}
}
@ -1133,6 +1164,9 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
/* Check sampling frequency */
switch ( self->streamInfo.aacSampleRate ) {
case 96000:
case 88200:
case 64000:
case 16000:
case 12000:
case 11025:
@ -1161,11 +1195,8 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
CConcealment_InitChannelData(&self->pAacDecoderStaticChannelInfo[ch]->concealmentInfo,
&self->concealCommonData,
self->streamInfo.aacSamplesPerFrame );
/* Clear concealment buffers to get rid of the complete history */
FDKmemclear(self->pAacDecoderStaticChannelInfo[ch]->concealmentInfo.spectralCoefficient, 1024 * sizeof(FIXP_CNCL));
FDKmemclear(self->pAacDecoderStaticChannelInfo[ch]->concealmentInfo.specScale, 8 * sizeof(SHORT));
/* Clear overlap-add buffers to avoid clicks. */
FDKmemclear(self->pAacDecoderStaticChannelInfo[ch]->IMdct.overlap.freq, OverlapBufferSize*sizeof(FIXP_DBL));
FDKmemclear(self->pAacDecoderStaticChannelInfo[ch]->pOverlapBuffer, OverlapBufferSize*sizeof(FIXP_DBL));
}
}
@ -1378,10 +1409,8 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
{
UCHAR element_instance_tag;
CDataStreamElement_Read( bs,
&self->ancData,
self->hDrcInfo,
self->hInput,
CDataStreamElement_Read( self,
bs,
&element_instance_tag,
auStartAnchor );
@ -1401,29 +1430,6 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
//self->frameOK = 0;
}
}
{
UCHAR *pDvbAncData = NULL;
AAC_DECODER_ERROR ancErr;
int ancIndex;
int dvbAncDataSize = 0;
/* Ask how many anc data elements are in buffer */
ancIndex = self->ancData.nrElements - 1;
/* Get the last one (if available) */
ancErr = CAacDecoder_AncDataGet( &self->ancData,
ancIndex,
&pDvbAncData,
&dvbAncDataSize );
if (ancErr == AAC_DEC_OK) {
pcmDmx_ReadDvbAncData (
self->hPcmUtils,
pDvbAncData,
dvbAncDataSize,
0 /* not mpeg2 */ );
}
}
break;
#ifdef TP_PCE_ENABLE
@ -1442,9 +1448,9 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
}
else if ( result > 1 ) {
/* Built element table */
int elIdx = CProgramConfig_GetElementTable(pce, self->elements, 7);
int elIdx = CProgramConfig_GetElementTable(pce, self->elements, (8), &self->chMapIndex);
/* Reset the remaining tabs */
for ( ; elIdx<7; elIdx++) {
for ( ; elIdx<(8); elIdx++) {
self->elements[elIdx] = ID_NONE;
}
/* Make new number of channel persistant */
@ -1489,7 +1495,7 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
/* get the remaining bits of this frame */
bitCnt = transportDec_GetAuBitsRemaining(self->hInput, 0);
if ( (bitCnt > 0) && (self->flags & AC_SBR_PRESENT) && (self->flags & (AC_USAC|AC_RSVD50|AC_ELD)) )
if ( (bitCnt > 0) && (self->flags & AC_SBR_PRESENT) && (self->flags & (AC_USAC|AC_RSVD50|AC_ELD|AC_DRM)) )
{
SBR_ERROR err = SBRDEC_OK;
int elIdx, numChElements = el_cnt[ID_SCE] + el_cnt[ID_CPE];
@ -1510,14 +1516,30 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
break;
}
}
if (err == SBRDEC_OK) {
switch (err) {
case SBRDEC_PARSE_ERROR:
/* Can not go on parsing because we do not
know the length of the SBR extension data. */
FDKpushFor(bs, bitCnt);
bitCnt = 0;
break;
case SBRDEC_OK:
self->sbrEnabled = 1;
} else {
break;
default:
self->frameOK = 0;
break;
}
}
if (self->flags & AC_DRM)
{
if ((bitCnt = (INT)FDKgetValidBits(bs)) != 0) {
FDKpushBiDirectional(bs, bitCnt);
}
}
if ( ! (self->flags & (AC_USAC|AC_RSVD50|AC_DRM)) )
{
while ( bitCnt > 7 ) {
@ -1603,13 +1625,17 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
self->frameOK=0;
}
/* store or restore the number of channels */
/* store or restore the number of channels and the corresponding info */
if ( self->frameOK && !(flags &(AACDEC_CONCEAL|AACDEC_FLUSH)) ) {
self->concealChannels = aacChannels; /* store */
self->aacChannelsPrev = aacChannels; /* store */
FDKmemcpy(self->channelTypePrev, self->channelType, (8)*sizeof(AUDIO_CHANNEL_TYPE)); /* store */
FDKmemcpy(self->channelIndicesPrev, self->channelIndices, (8)*sizeof(UCHAR)); /* store */
self->sbrEnabledPrev = self->sbrEnabled;
} else {
if (self->aacChannels > 0) {
aacChannels = self->concealChannels; /* restore */
aacChannels = self->aacChannelsPrev; /* restore */
FDKmemcpy(self->channelType, self->channelTypePrev, (8)*sizeof(AUDIO_CHANNEL_TYPE)); /* restore */
FDKmemcpy(self->channelIndices, self->channelIndicesPrev, (8)*sizeof(UCHAR)); /* restore */
self->sbrEnabled = self->sbrEnabledPrev;
}
}
@ -1632,12 +1658,31 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
return ErrorStatus;
}
/* Setup the output channel mapping. The table below shows the four possibilities:
* # | chCfg | PCE | cChCfg | chOutMapIdx
* ---+-------+-----+--------+------------------
* 1 | > 0 | no | - | chCfg
* 2 | 0 | yes | > 0 | cChCfg
* 3 | 0 | yes | 0 | aacChannels || 0
* 4 | 0 | no | - | aacChannels || 0
* ---+-------+-----+--------+------------------
* Where chCfg is the channel configuration index from ASC and cChCfg is a corresponding chCfg
* derived from a given PCE. The variable aacChannels represents the number of channel found
* during bitstream decoding. Due to the structure of the mapping table it can only be used for
* mapping if its value is smaller than 7. Otherwise we use the fallback (0) which is a simple
* pass-through. The possibility #4 should appear only with MPEG-2 (ADTS) streams. This is
* mode is called "implicit channel mapping".
*/
chOutMapIdx = ((self->chMapIndex==0) && (aacChannels<7)) ? aacChannels : self->chMapIndex;
/*
Inverse transform
*/
{
int stride, offset, c;
/* Turn on/off DRC modules level normalization in digital domain depending on the limiter status. */
aacDecoder_drcSetParam( self->hDrcInfo, APPLY_NORMALIZATION, (self->limiterEnableCurr) ? 0 : 1 );
/* Extract DRC control data and map it to channels (without bitstream delay) */
aacDecoder_drcProlog (
self->hDrcInfo,
@ -1663,13 +1708,18 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
/* Setup offset and stride for time buffer traversal. */
if (interleaved) {
stride = aacChannels;
offset = self->channelOutputMapping[aacChannels-1][c];
offset = self->channelOutputMapping[chOutMapIdx][c];
} else {
stride = 1;
offset = self->channelOutputMapping[aacChannels-1][c] * self->streamInfo.aacSamplesPerFrame;
offset = self->channelOutputMapping[chOutMapIdx][c] * self->streamInfo.aacSamplesPerFrame;
}
if ( flags&AACDEC_FLUSH ) {
/* Clear pAacDecoderChannelInfo->pSpectralCoefficient because with AACDEC_FLUSH set it contains undefined data. */
FDKmemclear(pAacDecoderChannelInfo->pSpectralCoefficient, sizeof(FIXP_DBL)*self->streamInfo.aacSamplesPerFrame);
}
/*
Conceal defective spectral data
*/
@ -1688,12 +1738,15 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
/* Reset DRC control data for this channel */
aacDecoder_drcInitChannelData ( &self->pAacDecoderStaticChannelInfo[c]->drcData );
}
/* The DRC module demands to be called with the gain field holding the gain scale. */
self->extGain[0] = (FIXP_DBL)TDL_GAIN_SCALING;
/* DRC processing */
aacDecoder_drcApply (
self->hDrcInfo,
self->hSbrDecoder,
pAacDecoderChannelInfo,
&self->pAacDecoderStaticChannelInfo[c]->drcData,
self->extGain,
c,
self->streamInfo.aacSamplesPerFrame,
self->sbrEnabled
@ -1711,6 +1764,7 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
(self->frameOK && !(flags&AACDEC_CONCEAL)),
self->aacCommonData.workBufferCore1->mdctOutTemp
);
self->extGainDelay = self->streamInfo.aacSamplesPerFrame;
break;
case AACDEC_RENDER_ELDFB:
CBlock_FrequencyToTimeLowDelay(
@ -1720,6 +1774,7 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
self->streamInfo.aacSamplesPerFrame,
stride
);
self->extGainDelay = (self->streamInfo.aacSamplesPerFrame*2 - self->streamInfo.aacSamplesPerFrame/2 - 1)/2;
break;
default:
ErrorStatus = AAC_DEC_UNKNOWN;
@ -1743,11 +1798,20 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
);
}
/* Add additional concealment delay */
self->streamInfo.outputDelay += CConcealment_GetDelay(&self->concealCommonData) * self->streamInfo.aacSamplesPerFrame;
/* Map DRC data to StreamInfo structure */
aacDecoder_drcGetInfo (
self->hDrcInfo,
&self->streamInfo.drcPresMode,
&self->streamInfo.drcProgRefLev
);
/* Reorder channel type information tables. */
{
AUDIO_CHANNEL_TYPE types[(6)];
UCHAR idx[(6)];
AUDIO_CHANNEL_TYPE types[(8)];
UCHAR idx[(8)];
int c;
FDK_ASSERT(sizeof(self->channelType) == sizeof(types));
@ -1757,8 +1821,8 @@ LINKSPEC_CPP AAC_DECODER_ERROR CAacDecoder_DecodeFrame(
FDKmemcpy(idx, self->channelIndices, sizeof(idx));
for (c=0; c<aacChannels; c++) {
self->channelType[self->channelOutputMapping[aacChannels-1][c]] = types[c];
self->channelIndices[self->channelOutputMapping[aacChannels-1][c]] = idx[c];
self->channelType[self->channelOutputMapping[chOutMapIdx][c]] = types[c];
self->channelIndices[self->channelOutputMapping[chOutMapIdx][c]] = idx[c];
}
}

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -111,6 +111,7 @@ amm-info@iis.fraunhofer.de
#include "aacdec_drc.h"
#include "pcmutils_lib.h"
#include "limiter.h"
/* Capabilities flags */
@ -176,27 +177,31 @@ struct AAC_DECODER_INSTANCE {
UINT flags; /*!< Flags for internal decoder use. DO NOT USE self::streaminfo::flags ! */
MP4_ELEMENT_ID elements[7]; /*!< Table where the element Id's are listed */
UCHAR elTags[7]; /*!< Table where the elements id Tags are listed */
UCHAR chMapping[(6)]; /*!< Table of MPEG canonical order to bitstream channel order mapping. */
MP4_ELEMENT_ID elements[(8)]; /*!< Table where the element Id's are listed */
UCHAR elTags[(8)]; /*!< Table where the elements id Tags are listed */
UCHAR chMapping[(8)]; /*!< Table of MPEG canonical order to bitstream channel order mapping. */
AUDIO_CHANNEL_TYPE channelType[(6)]; /*!< Audio channel type of each output audio channel (from 0 upto numChannels). */
UCHAR channelIndices[(6)]; /*!< Audio channel index for each output audio channel (from 0 upto numChannels). */
AUDIO_CHANNEL_TYPE channelType[(8)]; /*!< Audio channel type of each output audio channel (from 0 upto numChannels). */
UCHAR channelIndices[(8)]; /*!< Audio channel index for each output audio channel (from 0 upto numChannels). */
/* See ISO/IEC 13818-7:2005(E), 8.5.3.2 Explicit channel mapping using a program_config_element() */
const UCHAR (*channelOutputMapping)[8]; /*!< Table for MPEG canonical order to output channel order mapping. */
UCHAR chMapIndex; /*!< Index to access one line of the channelOutputMapping table. This is required
because not all 8 channel configurations have the same output mapping. */
CProgramConfig pce;
CStreamInfo streamInfo; /*!< pointer to StreamInfo data (read from the bitstream) */
CAacDecoderChannelInfo *pAacDecoderChannelInfo[(6)]; /*!< Temporal channel memory */
CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo[(6)]; /*!< Persistent channel memory */
CAacDecoderChannelInfo *pAacDecoderChannelInfo[(8)]; /*!< Temporal channel memory */
CAacDecoderStaticChannelInfo *pAacDecoderStaticChannelInfo[(8)]; /*!< Persistent channel memory */
CAacDecoderCommonData aacCommonData; /*!< Temporal shared data for all channels hooked into pAacDecoderChannelInfo */
CConcealParams concealCommonData;
INT concealChannels;
INT aacChannelsPrev; /*!< The amount of AAC core channels of the last successful decode call. */
AUDIO_CHANNEL_TYPE channelTypePrev[(8)]; /*!< Array holding the channelType values of the last successful decode call. */
UCHAR channelIndicesPrev[(8)]; /*!< Array holding the channelIndices values of the last successful decode call. */
HANDLE_SBRDECODER hSbrDecoder; /*!< SBR decoder handle. */
@ -214,6 +219,14 @@ struct AAC_DECODER_INSTANCE {
CAncData ancData; /*!< structure to handle ancillary data */
HANDLE_PCM_DOWNMIX hPcmUtils; /*!< privat data for the PCM utils. */
TDLimiterPtr hLimiter; /*!< Handle of time domain limiter. */
UCHAR limiterEnableUser; /*!< The limiter configuration requested by the library user */
UCHAR limiterEnableCurr; /*!< The current limiter configuration. */
FIXP_DBL extGain[1]; /*!< Gain that must be applied to the output signal. */
UINT extGainDelay; /*!< Delay that must be accounted for extGain. */
INT_PCM pcmOutputBuffer[(8)*(2048)];
};

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -110,10 +110,15 @@ amm-info@iis.fraunhofer.de
/* Decoder library info */
#define AACDECODER_LIB_VL0 2
#define AACDECODER_LIB_VL1 5
#define AACDECODER_LIB_VL2 5
#define AACDECODER_LIB_VL2 17
#define AACDECODER_LIB_TITLE "AAC Decoder Lib"
#ifdef __ANDROID__
#define AACDECODER_LIB_BUILD_DATE ""
#define AACDECODER_LIB_BUILD_TIME ""
#else
#define AACDECODER_LIB_BUILD_DATE __DATE__
#define AACDECODER_LIB_BUILD_TIME __TIME__
#endif
static AAC_DECODER_ERROR
setConcealMethod ( const HANDLE_AACDECODER self,
@ -176,8 +181,9 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_ConfigRaw (
break;
}
/* if baselayer is OK we continue decoding */
if(layer >= 1){
if(layer >= 1){
self->nrOfLayers = layer;
err = AAC_DEC_OK;
}
break;
}
@ -397,12 +403,14 @@ aacDecoder_SetParam ( const HANDLE_AACDECODER self, /*!< Handle of the decode
CConcealParams *pConcealData = NULL;
HANDLE_AAC_DRC hDrcInfo = NULL;
HANDLE_PCM_DOWNMIX hPcmDmx = NULL;
TDLimiterPtr hPcmTdl = NULL;
/* check decoder handle */
if (self != NULL) {
pConcealData = &self->concealCommonData;
hDrcInfo = self->hDrcInfo;
hPcmDmx = self->hPcmUtils;
hPcmTdl = self->hLimiter;
} else {
errorStatus = AAC_DEC_INVALID_HANDLE;
}
@ -420,8 +428,8 @@ aacDecoder_SetParam ( const HANDLE_AACDECODER self, /*!< Handle of the decode
self->outputInterleaved = value;
break;
case AAC_PCM_OUTPUT_CHANNELS:
if (value < -1 || value > (6)) {
case AAC_PCM_MIN_OUTPUT_CHANNELS:
if (value < -1 || value > (8)) {
return AAC_DEC_SET_PARAM_FAIL;
}
{
@ -429,7 +437,30 @@ aacDecoder_SetParam ( const HANDLE_AACDECODER self, /*!< Handle of the decode
err = pcmDmx_SetParam (
hPcmDmx,
NUMBER_OF_OUTPUT_CHANNELS,
MIN_NUMBER_OF_OUTPUT_CHANNELS,
value );
switch (err) {
case PCMDMX_OK:
break;
case PCMDMX_INVALID_HANDLE:
return AAC_DEC_INVALID_HANDLE;
default:
return AAC_DEC_SET_PARAM_FAIL;
}
}
break;
case AAC_PCM_MAX_OUTPUT_CHANNELS:
if (value < -1 || value > (8)) {
return AAC_DEC_SET_PARAM_FAIL;
}
{
PCMDMX_ERROR err;
err = pcmDmx_SetParam (
hPcmDmx,
MAX_NUMBER_OF_OUTPUT_CHANNELS,
value );
switch (err) {
@ -449,7 +480,7 @@ aacDecoder_SetParam ( const HANDLE_AACDECODER self, /*!< Handle of the decode
err = pcmDmx_SetParam (
hPcmDmx,
DUAL_CHANNEL_DOWNMIX_MODE,
DMX_DUAL_CHANNEL_MODE,
value );
switch (err) {
@ -463,6 +494,47 @@ aacDecoder_SetParam ( const HANDLE_AACDECODER self, /*!< Handle of the decode
}
break;
case AAC_PCM_LIMITER_ENABLE:
if (value < -1 || value > 1) {
return AAC_DEC_SET_PARAM_FAIL;
}
if (self == NULL) {
return AAC_DEC_INVALID_HANDLE;
}
self->limiterEnableUser = value;
break;
case AAC_PCM_LIMITER_ATTACK_TIME:
if (value <= 0) { /* module function converts value to unsigned */
return AAC_DEC_SET_PARAM_FAIL;
}
switch (setLimiterAttack(hPcmTdl, value)) {
case TDLIMIT_OK:
break;
case TDLIMIT_INVALID_HANDLE:
return AAC_DEC_INVALID_HANDLE;
case TDLIMIT_INVALID_PARAMETER:
default:
return AAC_DEC_SET_PARAM_FAIL;
}
break;
case AAC_PCM_LIMITER_RELEAS_TIME:
if (value <= 0) { /* module function converts value to unsigned */
return AAC_DEC_SET_PARAM_FAIL;
}
switch (setLimiterRelease(hPcmTdl, value)) {
case TDLIMIT_OK:
break;
case TDLIMIT_INVALID_HANDLE:
return AAC_DEC_INVALID_HANDLE;
case TDLIMIT_INVALID_PARAMETER:
default:
return AAC_DEC_SET_PARAM_FAIL;
}
break;
case AAC_PCM_OUTPUT_CHANNEL_MAPPING:
switch (value) {
case 0:
@ -609,6 +681,14 @@ LINKSPEC_CPP HANDLE_AACDECODER aacDecoder_Open(TRANSPORT_TYPE transportFmt, UINT
goto bail;
}
aacDec->hLimiter = createLimiter(TDL_ATTACK_DEFAULT_MS, TDL_RELEASE_DEFAULT_MS, SAMPLE_MAX, (8), 96000);
if (NULL == aacDec->hLimiter) {
err = -1;
goto bail;
}
aacDec->limiterEnableUser = (UCHAR)-1;
aacDec->limiterEnableCurr = 0;
/* Assure that all modules have same delay */
@ -706,8 +786,8 @@ static INT aacDecoder_EstimateNumberOfLostFrames(HANDLE_AACDECODER self)
LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
HANDLE_AACDECODER self,
INT_PCM *pTimeData,
const INT timeDataSize,
INT_PCM *pTimeData_extern,
const INT timeDataSize_extern,
const UINT flags)
{
AAC_DECODER_ERROR ErrorStatus;
@ -717,12 +797,17 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
HANDLE_FDK_BITSTREAM hBs;
int fTpInterruption = 0; /* Transport originated interruption detection. */
int fTpConceal = 0; /* Transport originated concealment. */
INT_PCM *pTimeData = NULL;
INT timeDataSize = 0;
if (self == NULL) {
return AAC_DEC_INVALID_HANDLE;
}
pTimeData = self->pcmOutputBuffer;
timeDataSize = sizeof(self->pcmOutputBuffer)/sizeof(*self->pcmOutputBuffer);
if (flags & AACDEC_INTR) {
self->streamInfo.numLostAccessUnits = 0;
}
@ -768,6 +853,7 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
/* Signal bit stream interruption to other modules if required. */
if ( fTpInterruption || (flags & (AACDEC_INTR|AACDEC_CLRHIST)) )
{
sbrDecoder_SetParam(self->hSbrDecoder, SBR_CLEAR_HISTORY, (flags&AACDEC_CLRHIST));
aacDecoder_SignalInterruption(self);
if ( ! (flags & AACDEC_INTR) ) {
ErrorStatus = AAC_DEC_TRANSPORT_SYNC_ERROR;
@ -783,6 +869,19 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
self->streamInfo.numBadBytes = 0;
self->streamInfo.numTotalBytes = 0;
}
/* Reset the output delay field. The modules will add their figures one after another. */
self->streamInfo.outputDelay = 0;
if (self->limiterEnableUser==(UCHAR)-1) {
/* Enbale limiter for all non-lowdelay AOT's. */
self->limiterEnableCurr = ( self->flags & (AC_LD|AC_ELD) ) ? 0 : 1;
}
else {
/* Use limiter configuration as requested. */
self->limiterEnableCurr = self->limiterEnableUser;
}
/* reset limiter gain on a per frame basis */
self->extGain[0] = FL2FXCONST_DBL(1.0f/(float)(1<<TDL_GAIN_SCALING));
ErrorStatus = CAacDecoder_DecodeFrame(self,
@ -825,11 +924,16 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
if (self->sbrEnabled)
{
SBR_ERROR sbrError = SBRDEC_OK;
int chIdx, numCoreChannel = self->streamInfo.numChannels;
int chOutMapIdx = ((self->chMapIndex==0) && (numCoreChannel<7)) ? numCoreChannel : self->chMapIndex;
/* set params */
sbrDecoder_SetParam ( self->hSbrDecoder,
SBR_SYSTEM_BITSTREAM_DELAY,
self->sbrParams.bsDelay);
sbrDecoder_SetParam ( self->hSbrDecoder,
SBR_FLUSH_DATA,
(flags & AACDEC_FLUSH) );
if ( self->streamInfo.aot == AOT_ER_AAC_ELD ) {
/* Configure QMF */
@ -838,7 +942,16 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
(self->flags & AC_LD_MPS) ? 1 : 0 );
}
{
PCMDMX_ERROR dmxErr;
INT maxOutCh = 0;
dmxErr = pcmDmx_GetParam(self->hPcmUtils, MAX_NUMBER_OF_OUTPUT_CHANNELS, &maxOutCh);
if ( (dmxErr == PCMDMX_OK) && (maxOutCh == 1) ) {
/* Disable PS processing if we have to create a mono output signal. */
self->psPossible = 0;
}
}
/* apply SBR processing */
@ -846,43 +959,50 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
pTimeData,
&self->streamInfo.numChannels,
&self->streamInfo.sampleRate,
self->channelOutputMapping[self->streamInfo.numChannels-1],
self->channelOutputMapping[chOutMapIdx],
interleaved,
self->frameOK,
&self->psPossible);
if (sbrError == SBRDEC_OK) {
#define UPS_SCALE 2 /* Maximum upsampling factor is 4 (CELP+SBR) */
FIXP_DBL upsampleFactor = FL2FXCONST_DBL(1.0f/(1<<UPS_SCALE));
/* Update data in streaminfo structure. Assume that the SBR upsampling factor is either 1 or 2 */
self->flags |= AC_SBR_PRESENT;
if (self->streamInfo.aacSampleRate != self->streamInfo.sampleRate) {
if (self->streamInfo.frameSize == 768) {
self->streamInfo.frameSize = (self->streamInfo.aacSamplesPerFrame * 8) / 3;
upsampleFactor = FL2FXCONST_DBL(8.0f/(3<<UPS_SCALE));
} else {
self->streamInfo.frameSize = self->streamInfo.aacSamplesPerFrame << 1;
upsampleFactor = FL2FXCONST_DBL(2.0f/(1<<UPS_SCALE));
}
}
/* Apply upsampling factor to both the core frame length and the core delay */
self->streamInfo.frameSize = (INT)fMult((FIXP_DBL)self->streamInfo.aacSamplesPerFrame<<UPS_SCALE, upsampleFactor);
self->streamInfo.outputDelay = (UINT)(INT)fMult((FIXP_DBL)self->streamInfo.outputDelay<<UPS_SCALE, upsampleFactor);
self->streamInfo.outputDelay += sbrDecoder_GetDelay( self->hSbrDecoder );
if (self->psPossible) {
self->flags |= AC_PS_PRESENT;
self->channelType[0] = ACT_FRONT;
self->channelType[1] = ACT_FRONT;
self->channelIndices[0] = 0;
self->channelIndices[1] = 1;
} else {
self->flags &= ~AC_PS_PRESENT;
}
for (chIdx = numCoreChannel; chIdx < self->streamInfo.numChannels; chIdx+=1) {
self->channelType[chIdx] = ACT_FRONT;
self->channelIndices[chIdx] = chIdx;
}
}
}
{
INT pcmLimiterScale = 0;
PCMDMX_ERROR dmxErr = PCMDMX_OK;
if ( flags & (AACDEC_INTR | AACDEC_CLRHIST) ) {
/* delete data from the past (e.g. mixdown coeficients) */
pcmDmx_Reset( self->hPcmUtils, PCMDMX_RESET_BS_DATA );
}
/* do PCM post processing */
pcmDmx_ApplyFrame (
dmxErr = pcmDmx_ApplyFrame (
self->hPcmUtils,
pTimeData,
self->streamInfo.frameSize,
@ -890,9 +1010,40 @@ LINKSPEC_CPP AAC_DECODER_ERROR aacDecoder_DecodeFrame(
interleaved,
self->channelType,
self->channelIndices,
self->channelOutputMapping
self->channelOutputMapping,
(self->limiterEnableCurr) ? &pcmLimiterScale : NULL
);
if ( (ErrorStatus == AAC_DEC_OK)
&& (dmxErr == PCMDMX_INVALID_MODE) ) {
/* Announce the framework that the current combination of channel configuration and downmix
* settings are not know to produce a predictable behavior and thus maybe produce strange output. */
ErrorStatus = AAC_DEC_DECODE_FRAME_ERROR;
}
if ( flags & AACDEC_CLRHIST ) {
/* Delete the delayed signal. */
resetLimiter(self->hLimiter);
}
if (self->limiterEnableCurr)
{
/* Set actual signal parameters */
setLimiterNChannels(self->hLimiter, self->streamInfo.numChannels);
setLimiterSampleRate(self->hLimiter, self->streamInfo.sampleRate);
applyLimiter(
self->hLimiter,
pTimeData,
self->extGain,
&pcmLimiterScale,
1,
self->extGainDelay,
self->streamInfo.frameSize
);
/* Announce the additional limiter output delay */
self->streamInfo.outputDelay += getLimiterDelay(self->hLimiter);
}
}
/* Signal interruption to take effect in next frame. */
@ -908,6 +1059,19 @@ bail:
/* Update Statistics */
aacDecoder_UpdateBitStreamCounters(&self->streamInfo, hBs, nBits, ErrorStatus);
/* Check whether external output buffer is large enough. */
if (timeDataSize_extern < self->streamInfo.numChannels*self->streamInfo.frameSize) {
ErrorStatus = AAC_DEC_OUTPUT_BUFFER_TOO_SMALL;
}
/* Update external output buffer. */
if ( IS_OUTPUT_VALID(ErrorStatus) ) {
FDKmemcpy(pTimeData_extern, pTimeData, self->streamInfo.numChannels*self->streamInfo.frameSize*sizeof(*pTimeData));
}
else {
FDKmemclear(pTimeData_extern, timeDataSize_extern*sizeof(*pTimeData_extern));
}
return ErrorStatus;
}
@ -917,6 +1081,9 @@ LINKSPEC_CPP void aacDecoder_Close ( HANDLE_AACDECODER self )
return;
if (self->hLimiter != NULL) {
destroyLimiter(self->hLimiter);
}
if (self->hPcmUtils != NULL) {
pcmDmx_Close( &self->hPcmUtils );
@ -974,6 +1141,7 @@ LINKSPEC_CPP INT aacDecoder_GetLibInfo ( LIB_INFO *info )
/* Set flags */
info->flags = 0
| CAPF_AAC_LC
| CAPF_ER_AAC_SCAL
| CAPF_AAC_VCB11
| CAPF_AAC_HCR
| CAPF_AAC_RVLC
@ -984,6 +1152,7 @@ LINKSPEC_CPP INT aacDecoder_GetLibInfo ( LIB_INFO *info )
| CAPF_AAC_MPEG4
| CAPF_AAC_DRM_BSFORMAT
| CAPF_AAC_1024
| CAPF_AAC_960

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -324,13 +324,12 @@ AAC_DECODER_ERROR CBlock_ReadSectionData(HANDLE_FDK_BITSTREAM bs,
if (flags & AC_ER_HCR) {
/* HCR input (long) -- collecting sideinfo (for HCR-_long_ only) */
pNumLinesInSec[numLinesInSecIdx] = BandOffsets[top] - BandOffsets[band];
numLinesInSecIdx++;
if (numLinesInSecIdx >= MAX_SFB_HCR) {
return AAC_DEC_PARSE_ERROR;
}
if (
(sect_cb == BOOKSCL) )
pNumLinesInSec[numLinesInSecIdx] = BandOffsets[top] - BandOffsets[band];
numLinesInSecIdx++;
if (sect_cb == BOOKSCL)
{
return AAC_DEC_INVALID_CODE_BOOK;
} else {

View File

@ -762,7 +762,6 @@ int
CConcealment_UpdateState( hConcealmentInfo,
frameOk );
if ( !frameOk )
{
/* Create data for signal rendering according to the selected concealment method and decoder operating mode. */
@ -775,11 +774,13 @@ int
{
default:
case ConcealMethodMute:
/* Mute spectral data in case of errors */
FDKmemclear(pAacDecoderChannelInfo->pSpectralCoefficient, samplesPerFrame * sizeof(FIXP_DBL));
/* Set last window shape */
pAacDecoderChannelInfo->icsInfo.WindowShape = hConcealmentInfo->windowShape;
appliedProcessing = 1;
if (!frameOk) {
/* Mute spectral data in case of errors */
FDKmemclear(pAacDecoderChannelInfo->pSpectralCoefficient, samplesPerFrame * sizeof(FIXP_DBL));
/* Set last window shape */
pAacDecoderChannelInfo->icsInfo.WindowShape = hConcealmentInfo->windowShape;
appliedProcessing = 1;
}
break;
case ConcealMethodNoise:
@ -801,7 +802,7 @@ int
pSamplingRateInfo,
samplesPerFrame,
0, /* don't use tonal improvement */
0);
frameOk);
break;
}

View File

@ -459,7 +459,7 @@ void BidirectionalEstimation_UseScfOfPrevFrameAsReference (
break;
case NOISE_HCB:
if ( (pAacDecoderStaticChannelInfo->concealmentInfo.aRvlcPreviousCodebook[bnds]==NOISE_HCB) ) {
if ( pAacDecoderStaticChannelInfo->concealmentInfo.aRvlcPreviousCodebook[bnds]==NOISE_HCB ) {
commonMin = FDKmin(pAacDecoderChannelInfo->pComData->overlay.aac.aRvlcScfFwd[bnds],pAacDecoderChannelInfo->pComData->overlay.aac.aRvlcScfBwd[bnds]);
pAacDecoderChannelInfo->pDynData->aScaleFactor[bnds] = FDKmin(commonMin, pAacDecoderStaticChannelInfo->concealmentInfo.aRvlcPreviousScaleFactor[bnds]);
} else {
@ -669,7 +669,7 @@ void PredictiveInterpolation (
break;
case NOISE_HCB:
if ( (pAacDecoderStaticChannelInfo->concealmentInfo.aRvlcPreviousCodebook[bnds]==NOISE_HCB) ) {
if ( pAacDecoderStaticChannelInfo->concealmentInfo.aRvlcPreviousCodebook[bnds]==NOISE_HCB ) {
commonMin = FDKmin(pAacDecoderChannelInfo->pComData->overlay.aac.aRvlcScfFwd[bnds],pAacDecoderChannelInfo->pComData->overlay.aac.aRvlcScfBwd[bnds]);
pAacDecoderChannelInfo->pDynData->aScaleFactor[bnds] = FDKmin(commonMin, pAacDecoderStaticChannelInfo->concealmentInfo.aRvlcPreviousScaleFactor[bnds]);
}

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -707,7 +707,7 @@ the encoder deactivates PNS calculation internally.
#define AACENCODER_LIB_VL0 3
#define AACENCODER_LIB_VL1 4
#define AACENCODER_LIB_VL2 12
#define AACENCODER_LIB_VL2 22
/**
* AAC encoder error codes.
@ -900,11 +900,7 @@ typedef enum
This configuration can be used only with stereo input audio data.
- 23: MPEG-4 AAC Low-Delay.
- 39: MPEG-4 AAC Enhanced Low-Delay. Since there is no ::AUDIO_OBJECT_TYPE for ELD in
combination with SBR defined, enable SBR explicitely by ::AACENC_SBR_MODE parameter.
- 129: MPEG-2 AAC Low Complexity.
- 132: MPEG-2 AAC Low Complexity with Spectral Band Replication (HE-AAC).
- 156: MPEG-2 AAC Low Complexity with Spectral Band Replication and Parametric Stereo (HE-AAC v2).
This configuration can be used only with stereo input audio data. */
combination with SBR defined, enable SBR explicitely by ::AACENC_SBR_MODE parameter. */
AACENC_BITRATE = 0x0101, /*!< Total encoder bitrate. This parameter is mandatory and interacts with ::AACENC_BITRATEMODE.
- CBR: Bitrate in bits/second.
@ -961,6 +957,16 @@ typedef enum
- 1 to fs/2: Frequency bandwidth in Hertz. (Experts only, better do not
touch this value to avoid degraded audio quality) */
AACENC_PEAK_BITRATE = 0x0207, /*!< Peak bitrate configuration parameter to adjust maximum bits per audio frame. Bitrate is in bits/second.
The peak bitrate will internally be limited to the chosen bitrate ::AACENC_BITRATE as lower limit
and the number_of_effective_channels*6144 bit as upper limit.
Setting the peak bitrate equal to ::AACENC_BITRATE does not necessarily mean that the audio frames
will be of constant size. Since the peak bitate is in bits/second, the frame sizes can vary by
one byte in one or the other direction over various frames. However, it is not recommended to reduce
the peak pitrate to ::AACENC_BITRATE - it would disable the bitreservoir, which would affect the
audio quality by a large amount. */
AACENC_TRANSMUX = 0x0300, /*!< Transport type to be used. See ::TRANSPORT_TYPE in FDK_audio.h. Following
types can be configured in encoder library:
- 0: raw access units
@ -1026,6 +1032,11 @@ typedef enum
- ADTS: Maximum number of sub frames restricted to 4.
- LOAS/LATM: Maximum number of sub frames restricted to 2.*/
AACENC_AUDIOMUXVER = 0x0304, /*!< AudioMuxVersion to be used for LATM. (AudioMuxVersionA, currently not implemented):
- 0: Default, no transmission of tara Buffer fullness, no ASC length and including actual latm Buffer fullnes.
- 1: Transmission of tara Buffer fullness, ASC length and actual latm Buffer fullness.
- 2: Transmission of tara Buffer fullness, ASC length and maximum level of latm Buffer fullness. */
AACENC_PROTECTION = 0x0306, /*!< Configure protection in tranpsort layer:
- 0: No protection. (default)
- 1: CRC active for ADTS bitstream format. */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -93,7 +93,7 @@ amm-info@iis.fraunhofer.de
/*
Huffman Tables
*/
const INT FDKaacEnc_huff_ltab1_2[3][3][3][3]=
const ULONG FDKaacEnc_huff_ltab1_2[3][3][3][3]=
{
{
{ {0x000b0009,0x00090007,0x000b0009}, {0x000a0008,0x00070006,0x000a0008}, {0x000b0009,0x00090008,0x000b0009} },
@ -113,7 +113,7 @@ const INT FDKaacEnc_huff_ltab1_2[3][3][3][3]=
};
const INT FDKaacEnc_huff_ltab3_4[3][3][3][3]=
const ULONG FDKaacEnc_huff_ltab3_4[3][3][3][3]=
{
{
{ {0x00010004,0x00040005,0x00080008}, {0x00040005,0x00050004,0x00080008}, {0x00090009,0x00090008,0x000a000b} },
@ -132,7 +132,7 @@ const INT FDKaacEnc_huff_ltab3_4[3][3][3][3]=
}
};
const INT FDKaacEnc_huff_ltab5_6[9][9]=
const ULONG FDKaacEnc_huff_ltab5_6[9][9]=
{
{0x000d000b, 0x000c000a, 0x000b0009, 0x000b0009, 0x000a0009, 0x000b0009, 0x000b0009, 0x000c000a, 0x000d000b},
{0x000c000a, 0x000b0009, 0x000a0008, 0x00090007, 0x00080007, 0x00090007, 0x000a0008, 0x000b0009, 0x000c000a},
@ -145,7 +145,7 @@ const INT FDKaacEnc_huff_ltab5_6[9][9]=
{0x000d000b, 0x000c000a, 0x000c0009, 0x000b0009, 0x000a0009, 0x000a0009, 0x000b0009, 0x000c000a, 0x000d000b}
};
const INT FDKaacEnc_huff_ltab7_8[8][8]=
const ULONG FDKaacEnc_huff_ltab7_8[8][8]=
{
{0x00010005, 0x00030004, 0x00060005, 0x00070006, 0x00080007, 0x00090008, 0x000a0009, 0x000b000a},
{0x00030004, 0x00040003, 0x00060004, 0x00070005, 0x00080006, 0x00080007, 0x00090007, 0x00090008},
@ -157,7 +157,7 @@ const INT FDKaacEnc_huff_ltab7_8[8][8]=
{0x000b000a, 0x000a0008, 0x000a0008, 0x000a0008, 0x000b0009, 0x000b0009, 0x000c0009, 0x000c000a}
};
const INT FDKaacEnc_huff_ltab9_10[13][13]=
const ULONG FDKaacEnc_huff_ltab9_10[13][13]=
{
{0x00010006, 0x00030005, 0x00060006, 0x00080006, 0x00090007, 0x000a0008, 0x000a0009, 0x000b000a, 0x000b000a, 0x000c000a, 0x000c000b, 0x000d000b, 0x000d000c},
{0x00030005, 0x00040004, 0x00060004, 0x00070005, 0x00080006, 0x00080007, 0x00090007, 0x000a0008, 0x000a0008, 0x000a0009, 0x000b000a, 0x000c000a, 0x000c000b},
@ -392,7 +392,7 @@ const USHORT FDKaacEnc_huff_ctab11[21][17]=
{0x0046, 0x00ea, 0x0034, 0x00ea, 0x0011, 0x001b, 0x00a9, 0x0094, 0x00e2, 0x0031, 0x00d0, 0x00e5, 0x0007, 0x0070, 0x0069, 0x003e, 0x0021}
};
const INT FDKaacEnc_huff_ctabscf[121]=
const ULONG FDKaacEnc_huff_ctabscf[121]=
{
0x0003ffe8, 0x0003ffe6, 0x0003ffe7, 0x0003ffe5, 0x0007fff5, 0x0007fff1, 0x0007ffed, 0x0007fff6,
0x0007ffee, 0x0007ffef, 0x0007fff0, 0x0007fffc, 0x0007fffd, 0x0007ffff, 0x0007fffe, 0x0007fff7,
@ -624,7 +624,7 @@ const SFB_PARAM_LONG p_FDKaacEnc_64000_long_1024 = {
};
const SFB_PARAM_SHORT p_FDKaacEnc_64000_short_128 = {
12,
{ 4, 4, 4, 4, 4, 4, 8, 8, 8, 18, 30, 32 }
{ 4, 4, 4, 4, 4, 4, 8, 8, 8, 16, 28, 36 }
};
const SFB_PARAM_LONG p_FDKaacEnc_88200_long_1024 = {
41,
@ -634,7 +634,7 @@ const SFB_PARAM_LONG p_FDKaacEnc_88200_long_1024 = {
};
const SFB_PARAM_SHORT p_FDKaacEnc_88200_short_128 = {
12,
{ 4, 4, 4, 4, 4, 4, 8, 8, 8, 18, 30, 32 }
{ 4, 4, 4, 4, 4, 4, 8, 8, 8, 16, 28, 36 }
};
const SFB_PARAM_LONG p_FDKaacEnc_96000_long_1024 = {
41,
@ -644,7 +644,7 @@ const SFB_PARAM_LONG p_FDKaacEnc_96000_long_1024 = {
};
const SFB_PARAM_SHORT p_FDKaacEnc_96000_short_128 = {
12,
{ 4, 4, 4, 4, 4, 4, 8, 8, 8, 18, 30, 32 }
{ 4, 4, 4, 4, 4, 4, 8, 8, 8, 16, 28, 36 }
};
@ -657,11 +657,11 @@ const SFB_PARAM_SHORT p_FDKaacEnc_96000_short_128 = {
*/
const FIXP_DBL FDKaacEnc_tnsEncCoeff3[8]=
{
0x81f1d201, 0x91261481, 0xadb92301, 0xd438af00, 0x00000000, 0x37898080, 0x64130dff, 0x7cca6fff
(FIXP_DBL)0x81f1d201, (FIXP_DBL)0x91261481, (FIXP_DBL)0xadb92301, (FIXP_DBL)0xd438af00, (FIXP_DBL)0x00000000, (FIXP_DBL)0x37898080, (FIXP_DBL)0x64130dff, (FIXP_DBL)0x7cca6fff
};
const FIXP_DBL FDKaacEnc_tnsCoeff3Borders[8]={
0x80000001 /*-4*/, 0x87b826df /*-3*/, 0x9df24154 /*-2*/, 0xbfffffe5 /*-1*/,
0xe9c5e578 /* 0*/, 0x1c7b90f0 /* 1*/, 0x4fce83a9 /* 2*/, 0x7352f2c3 /* 3*/
(FIXP_DBL)0x80000001 /*-4*/, (FIXP_DBL)0x87b826df /*-3*/, (FIXP_DBL)0x9df24154 /*-2*/, (FIXP_DBL)0xbfffffe5 /*-1*/,
(FIXP_DBL)0xe9c5e578 /* 0*/, (FIXP_DBL)0x1c7b90f0 /* 1*/, (FIXP_DBL)0x4fce83a9 /* 2*/, (FIXP_DBL)0x7352f2c3 /* 3*/
};
/*
@ -669,15 +669,15 @@ const FIXP_DBL FDKaacEnc_tnsCoeff3Borders[8]={
*/
const FIXP_DBL FDKaacEnc_tnsEncCoeff4[16]=
{
0x808bc881, 0x84e2e581, 0x8d6b4a01, 0x99da9201, 0xa9c45701, 0xbc9dde81, 0xd1c2d500, 0xe87ae540,
0x00000000, 0x1a9cd9c0, 0x340ff240, 0x4b3c8bff, 0x5f1f5e7f, 0x6ed9eb7f, 0x79bc387f, 0x7f4c7e7f
(FIXP_DBL)0x808bc881, (FIXP_DBL)0x84e2e581, (FIXP_DBL)0x8d6b4a01, (FIXP_DBL)0x99da9201, (FIXP_DBL)0xa9c45701, (FIXP_DBL)0xbc9dde81, (FIXP_DBL)0xd1c2d500, (FIXP_DBL)0xe87ae540,
(FIXP_DBL)0x00000000, (FIXP_DBL)0x1a9cd9c0, (FIXP_DBL)0x340ff240, (FIXP_DBL)0x4b3c8bff, (FIXP_DBL)0x5f1f5e7f, (FIXP_DBL)0x6ed9eb7f, (FIXP_DBL)0x79bc387f, (FIXP_DBL)0x7f4c7e7f
};
const FIXP_DBL FDKaacEnc_tnsCoeff4Borders[16]=
{
0x80000001 /*-8*/, 0x822deff0 /*-7*/, 0x88a4bfe6 /*-6*/, 0x932c159d /*-5*/,
0xa16827c2 /*-4*/, 0xb2dcde27 /*-3*/, 0xc6f20b91 /*-2*/, 0xdcf89c64 /*-1*/,
0xf4308ce1 /* 0*/, 0x0d613054 /* 1*/, 0x278dde80 /* 2*/, 0x4000001b /* 3*/,
0x55a6127b /* 4*/, 0x678dde8f /* 5*/, 0x74ef0ed7 /* 6*/, 0x7d33f0da /* 7*/
(FIXP_DBL)0x80000001 /*-8*/, (FIXP_DBL)0x822deff0 /*-7*/, (FIXP_DBL)0x88a4bfe6 /*-6*/, (FIXP_DBL)0x932c159d /*-5*/,
(FIXP_DBL)0xa16827c2 /*-4*/, (FIXP_DBL)0xb2dcde27 /*-3*/, (FIXP_DBL)0xc6f20b91 /*-2*/, (FIXP_DBL)0xdcf89c64 /*-1*/,
(FIXP_DBL)0xf4308ce1 /* 0*/, (FIXP_DBL)0x0d613054 /* 1*/, (FIXP_DBL)0x278dde80 /* 2*/, (FIXP_DBL)0x4000001b /* 3*/,
(FIXP_DBL)0x55a6127b /* 4*/, (FIXP_DBL)0x678dde8f /* 5*/, (FIXP_DBL)0x74ef0ed7 /* 6*/, (FIXP_DBL)0x7d33f0da /* 7*/
};
const FIXP_DBL FDKaacEnc_mTab_4_3Elc[512]={
FL2FXCONST_DBL(0.3968502629920499),FL2FXCONST_DBL(0.3978840634868335),FL2FXCONST_DBL(0.3989185359354711),FL2FXCONST_DBL(0.3999536794661432),

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -105,11 +105,11 @@ amm-info@iis.fraunhofer.de
/*
Huffman Tables
*/
extern const INT FDKaacEnc_huff_ltab1_2[3][3][3][3];
extern const INT FDKaacEnc_huff_ltab3_4[3][3][3][3];
extern const INT FDKaacEnc_huff_ltab5_6[9][9];
extern const INT FDKaacEnc_huff_ltab7_8[8][8];
extern const INT FDKaacEnc_huff_ltab9_10[13][13];
extern const ULONG FDKaacEnc_huff_ltab1_2[3][3][3][3];
extern const ULONG FDKaacEnc_huff_ltab3_4[3][3][3][3];
extern const ULONG FDKaacEnc_huff_ltab5_6[9][9];
extern const ULONG FDKaacEnc_huff_ltab7_8[8][8];
extern const ULONG FDKaacEnc_huff_ltab9_10[13][13];
extern const UCHAR FDKaacEnc_huff_ltab11[17][17];
extern const UCHAR FDKaacEnc_huff_ltabscf[121];
extern const USHORT FDKaacEnc_huff_ctab1[3][3][3][3];
@ -123,7 +123,7 @@ extern const USHORT FDKaacEnc_huff_ctab8[8][8];
extern const USHORT FDKaacEnc_huff_ctab9[13][13];
extern const USHORT FDKaacEnc_huff_ctab10[13][13];
extern const USHORT FDKaacEnc_huff_ctab11[21][17];
extern const INT FDKaacEnc_huff_ctabscf[121];
extern const ULONG FDKaacEnc_huff_ctabscf[121];
/*
quantizer

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -107,6 +107,39 @@ amm-info@iis.fraunhofer.de
#define MIN_BUFSIZE_PER_EFF_CHAN 6144
INT FDKaacEnc_CalcBitsPerFrame(
const INT bitRate,
const INT frameLength,
const INT samplingRate
)
{
int shift = 0;
while ((frameLength & ~((1 << (shift + 1)) - 1)) == frameLength
&& (samplingRate & ~((1 << (shift + 1)) - 1)) == samplingRate)
{
shift++;
}
return (bitRate*(frameLength>>shift)) / (samplingRate>>shift);
}
INT FDKaacEnc_CalcBitrate(
const INT bitsPerFrame,
const INT frameLength,
const INT samplingRate
)
{
int shift = 0;
while ((frameLength & ~((1 << (shift + 1)) - 1)) == frameLength
&& (samplingRate & ~((1 << (shift + 1)) - 1)) == samplingRate)
{
shift++;
}
return (bitsPerFrame * (samplingRate>>shift)) / ( frameLength>>shift) ;
}
static AAC_ENCODER_ERROR FDKaacEnc_InitCheckAncillary(INT bitRate,
INT framelength,
INT ancillaryRate,
@ -220,21 +253,19 @@ INT FDKaacEnc_GetVBRBitrate(INT bitrateMode, CHANNEL_MODE channelMode)
/**
* \brief Convert encoder bitreservoir value for transport library.
*
* \param bitrateMode Bitratemode used in current encoder instance. Se ::AACENC_BITRATE_MODE
* \param bitresTotal Encoder bitreservoir level in bits.
* \param hAacEnc Encoder handle
*
* \return Corrected bitreservoir level used in transport library.
*/
static INT FDKaacEnc_EncBitresToTpBitres(
const AACENC_BITRATE_MODE bitrateMode,
const INT bitresTotal
const HANDLE_AAC_ENC hAacEnc
)
{
INT transporBitreservoir = 0;
switch (bitrateMode) {
switch (hAacEnc->bitrateMode) {
case AACENC_BR_MODE_CBR:
transporBitreservoir = bitresTotal; /* encoder bitreservoir level */
transporBitreservoir = hAacEnc->qcKernel->bitResTot; /* encoder bitreservoir level */
break;
case AACENC_BR_MODE_VBR_1:
case AACENC_BR_MODE_VBR_2:
@ -253,6 +284,10 @@ static INT FDKaacEnc_EncBitresToTpBitres(
FDK_ASSERT(0);
}
if (hAacEnc->config->audioMuxVersion==2) {
transporBitreservoir = MIN_BUFSIZE_PER_EFF_CHAN * hAacEnc->channelMapping.nChannelsEff;
}
return transporBitreservoir;
}
@ -289,6 +324,7 @@ void FDKaacEnc_AacInitDefaultConfig(AACENC_CONFIG *config)
config->minBitsPerFrame = -1; /* minum number of bits in each AU */
config->maxBitsPerFrame = -1; /* minum number of bits in each AU */
config->bitreservoir = -1; /* default, uninitialized value */
config->audioMuxVersion = -1; /* audio mux version not configured */
/* init tabs in fixpoint_math */
InitLdInt();
@ -435,7 +471,9 @@ AAC_ENCODER_ERROR FDKaacEnc_Initialize(HANDLE_AAC_ENC hAacEnc,
&averageBitsPerFrame,
config->bitrateMode,
config->nSubFrames
) != config->bitRate )
) != config->bitRate
&& !((config->bitrateMode>=1) && (config->bitrateMode<=5))
)
{
return AAC_ENC_UNSUPPORTED_BITRATE;
}
@ -562,7 +600,10 @@ AAC_ENCODER_ERROR FDKaacEnc_Initialize(HANDLE_AAC_ENC hAacEnc,
qcInit.averageBits = (averageBitsPerFrame+7)&~7;
qcInit.bitRes = MIN_BUFSIZE_PER_EFF_CHAN*cm->nChannelsEff;
qcInit.maxBits = MIN_BUFSIZE_PER_EFF_CHAN*cm->nChannelsEff;
qcInit.minBits = 0;
qcInit.maxBits = (config->maxBitsPerFrame!=-1) ? fixMin(qcInit.maxBits, config->maxBitsPerFrame) : qcInit.maxBits;
qcInit.maxBits = fixMax(qcInit.maxBits, (averageBitsPerFrame+7)&~7);
qcInit.minBits = (config->minBitsPerFrame!=-1) ? config->minBitsPerFrame : 0;
qcInit.minBits = fixMin(qcInit.minBits, averageBitsPerFrame&~7);
}
else
{
@ -573,9 +614,11 @@ AAC_ENCODER_ERROR FDKaacEnc_Initialize(HANDLE_AAC_ENC hAacEnc,
qcInit.maxBits = fixMin(MIN_BUFSIZE_PER_EFF_CHAN*cm->nChannelsEff, ((averageBitsPerFrame+7)&~7)+qcInit.bitRes);
qcInit.maxBits = (config->maxBitsPerFrame!=-1) ? fixMin(qcInit.maxBits, config->maxBitsPerFrame) : qcInit.maxBits;
qcInit.maxBits = fixMin(MIN_BUFSIZE_PER_EFF_CHAN*cm->nChannelsEff, fixMax(qcInit.maxBits, (averageBitsPerFrame+7+8)&~7));
qcInit.minBits = fixMax(0, ((averageBitsPerFrame-1)&~7)-qcInit.bitRes-transportEnc_GetStaticBits(hTpEnc, ((averageBitsPerFrame+7)&~7)+qcInit.bitRes));
qcInit.minBits = (config->minBitsPerFrame!=-1) ? fixMax(qcInit.minBits, config->minBitsPerFrame) : qcInit.minBits;
qcInit.minBits = fixMin(qcInit.minBits, (averageBitsPerFrame - transportEnc_GetStaticBits(hTpEnc, qcInit.maxBits))&~7);
}
qcInit.sampleRate = config->sampleRate;
@ -583,11 +626,9 @@ AAC_ENCODER_ERROR FDKaacEnc_Initialize(HANDLE_AAC_ENC hAacEnc,
qcInit.nSubFrames = config->nSubFrames;
qcInit.padding.paddingRest = config->sampleRate;
/* Calc meanPe */
bw_ratio = fDivNorm((FIXP_DBL)hAacEnc->bandwidth90dB, (FIXP_DBL)(config->sampleRate>>1), &qbw);
qbw = DFRACT_BITS-1-qbw;
/* qcInit.meanPe = 10.0f * FRAME_LEN_LONG * hAacEnc->bandwidth90dB/(config->sampleRate/2.0f); */
qcInit.meanPe = fMult(bw_ratio, (FIXP_DBL)((10*config->framelength)<<16)) >> (qbw-15);
/* Calc meanPe: qcInit.meanPe = 10.0f * FRAME_LEN_LONG * hAacEnc->bandwidth90dB/(config->sampleRate/2.0f); */
bw_ratio = fDivNorm((FIXP_DBL)(10*config->framelength*hAacEnc->bandwidth90dB), (FIXP_DBL)(config->sampleRate), &qbw);
qcInit.meanPe = FDKmax((INT)scaleValue(bw_ratio, qbw+1-(DFRACT_BITS-1)), 1);
/* Calc maxBitFac */
mbfac = fDivNorm((MIN_BUFSIZE_PER_EFF_CHAN-744)*cm->nChannelsEff, qcInit.averageBits/qcInit.nSubFrames, &qmbfac);
@ -649,23 +690,7 @@ AAC_ENCODER_ERROR FDKaacEnc_Initialize(HANDLE_AAC_ENC hAacEnc,
if (ErrorStatus != AAC_ENC_OK)
goto bail;
/* Map virtual aot's to intern aot used in bitstream writer. */
switch (hAacEnc->config->audioObjectType) {
case AOT_MP2_AAC_LC:
case AOT_DABPLUS_AAC_LC:
hAacEnc->aot = AOT_AAC_LC;
break;
case AOT_MP2_SBR:
case AOT_DABPLUS_SBR:
hAacEnc->aot = AOT_SBR;
break;
case AOT_MP2_PS:
case AOT_DABPLUS_PS:
hAacEnc->aot = AOT_PS;
break;
default:
hAacEnc->aot = hAacEnc->config->audioObjectType;
}
hAacEnc->aot = hAacEnc->config->audioObjectType;
/* common things */
@ -930,7 +955,7 @@ AAC_ENCODER_ERROR FDKaacEnc_EncodeFrame( HANDLE_AAC_ENC hAacEnc,
transportEnc_WriteAccessUnit(
hTpEnc,
totalBits,
FDKaacEnc_EncBitresToTpBitres(hAacEnc->bitrateMode, hAacEnc->qcKernel->bitResTot),
FDKaacEnc_EncBitresToTpBitres(hAacEnc),
cm->nChannelsEff);
/* write bitstream */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -98,6 +98,11 @@ amm-info@iis.fraunhofer.de
#include "sbr_encoder.h"
#define BITRES_MAX_LD 4000
#define BITRES_MIN_LD 500
#define BITRATE_MAX_LD 70000 /* Max assumed bitrate for bitres calculation */
#define BITRATE_MIN_LD 12000 /* Min assumed bitrate for bitres calculation */
#ifdef __cplusplus
extern "C" {
#endif
@ -205,6 +210,8 @@ struct AACENC_CONFIG {
INT maxBitsPerFrame; /* maximum number of bits in AU */
INT bitreservoir; /* size of bitreservoir */
INT audioMuxVersion; /* audio mux version in loas/latm transport format */
UINT sbrRatio; /* sbr sampling rate ratio: dual- or single-rate */
UCHAR useTns; /* flag: use temporal noise shaping */
@ -223,6 +230,36 @@ typedef struct {
typedef struct AAC_ENC *HANDLE_AAC_ENC;
/**
* \brief Calculate framesize in bits for given bit rate, frame length and sampling rate.
*
* \param bitRate Ttarget bitrate in bits per second.
* \param frameLength Number of audio samples in one frame.
* \param samplingRate Sampling rate in Hz.
*
* \return Framesize in bits per frame.
*/
INT FDKaacEnc_CalcBitsPerFrame(
const INT bitRate,
const INT frameLength,
const INT samplingRate
);
/**
* \brief Calculate bitrate in bits per second for given framesize, frame length and sampling rate.
*
* \param bitsPerFrame Framesize in bits per frame.
* \param frameLength Number of audio samples in one frame.
* \param samplingRate Sampling rate in Hz.
*
* \return Bitrate in bits per second.
*/
INT FDKaacEnc_CalcBitrate(
const INT bitsPerFrame,
const INT frameLength,
const INT samplingRate
);
/**
* \brief Limit given bit rate to a valid value
* \param hTpEnc transport encoder handle

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -98,10 +98,15 @@ amm-info@iis.fraunhofer.de
/* Encoder library info */
#define AACENCODER_LIB_VL0 3
#define AACENCODER_LIB_VL1 4
#define AACENCODER_LIB_VL2 12
#define AACENCODER_LIB_VL2 22
#define AACENCODER_LIB_TITLE "AAC Encoder"
#ifdef __ANDROID__
#define AACENCODER_LIB_BUILD_DATE ""
#define AACENCODER_LIB_BUILD_TIME ""
#else
#define AACENCODER_LIB_BUILD_DATE __DATE__
#define AACENCODER_LIB_BUILD_TIME __TIME__
#endif
#include "sbr_encoder.h"
@ -148,6 +153,7 @@ typedef struct {
UINT userAfterburner;
UINT userFramelength;
UINT userAncDataRate;
UINT userPeakBitrate;
UCHAR userTns; /*!< Use TNS coding. */
UCHAR userPns; /*!< Use PNS coding. */
@ -298,7 +304,7 @@ static AACENC_ERROR eldSbrConfigurator(
int i, cfgIdx = -1;
const ULONG channelBitrate = totalBitrate / FDKaacEnc_GetChannelModeConfiguration(channelMode)->nChannelsEff;
for (i=0; i<(sizeof(eldSbrAutoConfigTab)/sizeof(ELD_SBR_CONFIGURATOR)); i++) {
for (i=0; i<(int)(sizeof(eldSbrAutoConfigTab)/sizeof(ELD_SBR_CONFIGURATOR)); i++) {
if ( (samplingRate <= eldSbrAutoConfigTab[i].samplingRate)
&& (channelBitrate >= eldSbrAutoConfigTab[i].bitrateRange) )
{
@ -321,10 +327,7 @@ static inline INT isSbrActive(const HANDLE_AACENC_CONFIG hAacConfig)
{
INT sbrUsed = 0;
if ( (hAacConfig->audioObjectType==AOT_SBR) || (hAacConfig->audioObjectType==AOT_PS)
|| (hAacConfig->audioObjectType==AOT_MP2_SBR) || (hAacConfig->audioObjectType==AOT_MP2_PS)
|| (hAacConfig->audioObjectType==AOT_DABPLUS_SBR) || (hAacConfig->audioObjectType==AOT_DABPLUS_PS)
|| (hAacConfig->audioObjectType==AOT_DRM_SBR) || (hAacConfig->audioObjectType==AOT_DRM_MPEG_PS) )
if ( (hAacConfig->audioObjectType==AOT_SBR) || (hAacConfig->audioObjectType==AOT_PS) )
{
sbrUsed = 1;
}
@ -340,10 +343,7 @@ static inline INT isPsActive(const AUDIO_OBJECT_TYPE audioObjectType)
{
INT psUsed = 0;
if ( (audioObjectType==AOT_PS)
|| (audioObjectType==AOT_MP2_PS)
|| (audioObjectType==AOT_DABPLUS_PS)
|| (audioObjectType==AOT_DRM_MPEG_PS) )
if ( (audioObjectType==AOT_PS) )
{
psUsed = 1;
}
@ -368,8 +368,7 @@ static SBR_PS_SIGNALING getSbrSignalingMode(
sbrSignaling = SIG_IMPLICIT; /* default: implicit signaling */
}
if ((audioObjectType==AOT_AAC_LC) || (audioObjectType==AOT_SBR) || (audioObjectType==AOT_PS) ||
(audioObjectType==AOT_MP2_AAC_LC) || (audioObjectType==AOT_MP2_SBR) || (audioObjectType==AOT_MP2_PS) ) {
if ( (audioObjectType==AOT_AAC_LC) || (audioObjectType==AOT_SBR) || (audioObjectType==AOT_PS) ) {
switch (transportType) {
case TT_MP4_ADIF:
case TT_MP4_ADTS:
@ -425,22 +424,7 @@ static void FDKaacEnc_MapConfig(
cc->flags = 0;
/* Map virtual aot to transport aot. */
switch (hAacConfig->audioObjectType) {
case AOT_MP2_AAC_LC:
transport_AOT = AOT_AAC_LC;
break;
case AOT_MP2_SBR:
transport_AOT = AOT_SBR;
cc->flags |= CC_SBR;
break;
case AOT_MP2_PS:
transport_AOT = AOT_PS;
cc->flags |= CC_SBR;
break;
default:
transport_AOT = hAacConfig->audioObjectType;
}
transport_AOT = hAacConfig->audioObjectType;
if (hAacConfig->audioObjectType == AOT_ER_AAC_ELD) {
cc->flags |= (hAacConfig->syntaxFlags & AC_SBR_PRESENT) ? CC_SBR : 0;
@ -506,16 +490,7 @@ static void FDKaacEnc_MapConfig(
cc->samplingRate = hAacConfig->sampleRate;
/* Mpeg-4 signaling for transport library. */
switch ( hAacConfig->audioObjectType ) {
case AOT_MP2_AAC_LC:
case AOT_MP2_SBR:
case AOT_MP2_PS:
cc->flags &= ~CC_MPEG_ID; /* Required for ADTS. */
cc->extAOT = AOT_NULL_OBJECT;
break;
default:
cc->flags |= CC_MPEG_ID;
}
cc->flags |= CC_MPEG_ID;
/* ER-tools signaling. */
cc->flags |= (hAacConfig->syntaxFlags & AC_ER_VCB11) ? CC_VCB11 : 0;
@ -580,6 +555,7 @@ AAC_ENCODER_ERROR aacEncDefaultConfig(HANDLE_AACENC_CONFIG hAacConfig,
config->userChannelMode = hAacConfig->channelMode;
config->userBitrate = hAacConfig->bitRate;
config->userBitrateMode = hAacConfig->bitrateMode;
config->userPeakBitrate = (UINT)-1;
config->userBandwidth = hAacConfig->bandWidth;
config->userTns = hAacConfig->useTns;
config->userPns = hAacConfig->usePns;
@ -787,12 +763,15 @@ AACENC_ERROR FDKaacEnc_AdjustEncSettings(HANDLE_AACENCODER hAacEncoder,
hAacConfig->syntaxFlags = 0;
hAacConfig->epConfig = -1;
if (config->userTpType==TT_MP4_LATM_MCP1 || config->userTpType==TT_MP4_LATM_MCP0 || config->userTpType==TT_MP4_LOAS) {
hAacConfig->audioMuxVersion = config->userTpAmxv;
}
else {
hAacConfig->audioMuxVersion = -1;
}
/* Adapt internal AOT when necessary. */
switch ( hAacConfig->audioObjectType ) {
case AOT_MP2_AAC_LC:
case AOT_MP2_SBR:
case AOT_MP2_PS:
hAacConfig->usePns = 0;
case AOT_AAC_LC:
case AOT_SBR:
case AOT_PS:
@ -834,11 +813,16 @@ AACENC_ERROR FDKaacEnc_AdjustEncSettings(HANDLE_AACENCODER hAacEncoder,
switch ( hAacConfig->audioObjectType ) {
case AOT_ER_AAC_LD:
case AOT_ER_AAC_ELD:
if (config->userBitrateMode==8) {
hAacConfig->bitrateMode = 0;
}
if (config->userBitrateMode==0) {
hAacConfig->bitreservoir = 100*config->nChannels; /* default, reduced bitreservoir */
/* bitreservoir = (maxBitRes-minBitRes)/(maxBitRate-minBitrate)*(bitRate-minBitrate)+minBitRes; */
if ( isLowDelay(hAacConfig->audioObjectType) ) {
INT bitreservoir;
INT brPerChannel = hAacConfig->bitRate/hAacConfig->nChannels;
brPerChannel = fMin(BITRATE_MAX_LD, fMax(BITRATE_MIN_LD, brPerChannel));
FIXP_DBL slope = fDivNorm((brPerChannel-BITRATE_MIN_LD), BITRATE_MAX_LD-BITRATE_MIN_LD); /* calc slope for interpolation */
bitreservoir = fMultI(slope, (INT)(BITRES_MAX_LD-BITRES_MIN_LD)) + BITRES_MIN_LD; /* interpolate */
hAacConfig->bitreservoir = bitreservoir & ~7; /* align to bytes */
}
}
if (hAacConfig->bitrateMode!=0) {
return AACENC_INVALID_CONFIG;
@ -879,6 +863,18 @@ AACENC_ERROR FDKaacEnc_AdjustEncSettings(HANDLE_AACENCODER hAacEncoder,
}
}
if ((hAacConfig->bitrateMode >= 0) && (hAacConfig->bitrateMode <= 5)) {
if ((INT)config->userPeakBitrate != -1) {
hAacConfig->maxBitsPerFrame = (FDKaacEnc_CalcBitsPerFrame(fMax(hAacConfig->bitRate, (INT)config->userPeakBitrate), hAacConfig->framelength, hAacConfig->sampleRate) + 7)&~7;
}
else {
hAacConfig->maxBitsPerFrame = -1;
}
if (hAacConfig->audioMuxVersion==2) {
hAacConfig->minBitsPerFrame = fMin(32*8, FDKaacEnc_CalcBitsPerFrame(hAacConfig->bitRate, hAacConfig->framelength, hAacConfig->sampleRate))&~7;
}
}
/* Initialize SBR parameters */
if ( (hAacConfig->audioObjectType==AOT_ER_AAC_ELD)
&& (config->userSbrEnabled == (UCHAR)-1) && (config->userSbrRatio==0) )
@ -909,7 +905,7 @@ AACENC_ERROR FDKaacEnc_AdjustEncSettings(HANDLE_AACENCODER hAacEncoder,
}
else {
/* SBR ratio has been set by the user, so use it. */
hAacConfig->sbrRatio = config->userSbrRatio;
hAacConfig->sbrRatio = isSbrActive(hAacConfig) ? config->userSbrRatio : 0;
}
{
@ -1041,7 +1037,7 @@ static AACENC_ERROR aacEncInit(HANDLE_AACENCODER hAacEncoder,
}
/* Clear input buffer */
if ( (InitFlags == AACENC_INIT_ALL) ) {
if ( InitFlags == AACENC_INIT_ALL ) {
FDKmemclear(hAacEncoder->inputBuffer, sizeof(INT_PCM)*hAacEncoder->nMaxAacChannels*INPUTBUFFER_SIZE);
}
@ -1134,7 +1130,7 @@ static AACENC_ERROR aacEncInit(HANDLE_AACENCODER hAacEncoder,
hAacConfig);
/* create flags for transport encoder */
if (config->userTpAmxv == 1) {
if (config->userTpAmxv != 0) {
flags |= TP_FLAG_LATM_AMV;
}
/* Clear output buffer */
@ -1564,7 +1560,7 @@ AACENC_ERROR aacEncEncode(
&& ((hAacEncoder->extParam.userChannelMode==MODE_1_2_2)||(hAacEncoder->extParam.userChannelMode==MODE_1_2_2_1)) )
{
/* Set matrix mixdown coefficient. */
UINT pceValue = (UINT)( (1<<3) | ((matrix_mixdown_idx&0x3)<<1) | 1 );
UINT pceValue = (UINT)( (0<<3) | ((matrix_mixdown_idx&0x3)<<1) | 1 );
if (hAacEncoder->extParam.userPceAdditions != pceValue) {
hAacEncoder->extParam.userPceAdditions = pceValue;
hAacEncoder->InitFlags |= AACENC_INIT_TRANSPORT;
@ -1780,19 +1776,16 @@ AACENC_ERROR aacEncoder_SetParam(
/* check if AOT matches the allocated modules */
switch ( value ) {
case AOT_PS:
case AOT_MP2_PS:
if (!(hAacEncoder->encoder_modis & (ENC_MODE_FLAG_PS))) {
err = AACENC_INVALID_CONFIG;
goto bail;
}
case AOT_SBR:
case AOT_MP2_SBR:
if (!(hAacEncoder->encoder_modis & (ENC_MODE_FLAG_SBR))) {
err = AACENC_INVALID_CONFIG;
goto bail;
}
case AOT_AAC_LC:
case AOT_MP2_AAC_LC:
case AOT_ER_AAC_LD:
case AOT_ER_AAC_ELD:
if (!(hAacEncoder->encoder_modis & (ENC_MODE_FLAG_AAC))) {
@ -1818,11 +1811,7 @@ AACENC_ERROR aacEncoder_SetParam(
if (settings->userBitrateMode != value) {
switch ( value ) {
case 0:
case 1:
case 2:
case 3:
case 4:
case 5:
case 1: case 2: case 3: case 4: case 5:
case 8:
settings->userBitrateMode = value;
hAacEncoder->InitFlags |= AACENC_INIT_CONFIG | AACENC_INIT_TRANSPORT;
@ -1973,6 +1962,16 @@ AACENC_ERROR aacEncoder_SetParam(
hAacEncoder->InitFlags |= AACENC_INIT_TRANSPORT;
}
break;
case AACENC_AUDIOMUXVER:
if (settings->userTpAmxv != value) {
if ( !((value==0) || (value==1) || (value==2)) ) {
err = AACENC_INVALID_CONFIG;
break;
}
settings->userTpAmxv = value;
hAacEncoder->InitFlags |= AACENC_INIT_TRANSPORT;
}
break;
case AACENC_TPSUBFRAMES:
if (settings->userTpNsubFrames != value) {
if (! ( (value>=1) && (value<=4) ) ) {
@ -1998,7 +1997,7 @@ AACENC_ERROR aacEncoder_SetParam(
break;
case AACENC_METADATA_MODE:
if ((UINT)settings->userMetaDataMode != value) {
if ( !((value>=0) && (value<=2)) ) {
if ( !(((INT)value>=0) && ((INT)value<=2)) ) {
err = AACENC_INVALID_CONFIG;
break;
}
@ -2006,6 +2005,12 @@ AACENC_ERROR aacEncoder_SetParam(
hAacEncoder->InitFlags |= AACENC_INIT_CONFIG;
}
break;
case AACENC_PEAK_BITRATE:
if (settings->userPeakBitrate != value) {
settings->userPeakBitrate = value;
hAacEncoder->InitFlags |= AACENC_INIT_CONFIG | AACENC_INIT_TRANSPORT;
}
break;
default:
err = AACENC_UNSUPPORTED_PARAMETER;
break;
@ -2076,6 +2081,9 @@ UINT aacEncoder_GetParam(
case AACENC_HEADER_PERIOD:
value = (UINT)hAacEncoder->coderConfig.headerPeriod;
break;
case AACENC_AUDIOMUXVER:
value = (UINT)hAacEncoder->aacConfig.audioMuxVersion;
break;
case AACENC_TPSUBFRAMES:
value = (UINT)settings->userTpNsubFrames;
break;
@ -2088,6 +2096,12 @@ UINT aacEncoder_GetParam(
case AACENC_METADATA_MODE:
value = (hAacEncoder->metaDataAllowed==0) ? 0 : (UINT)settings->userMetaDataMode;
break;
case AACENC_PEAK_BITRATE:
value = (UINT)-1; /* peak bitrate parameter is meaningless */
if ( ((INT)hAacEncoder->extParam.userPeakBitrate!=-1) ) {
value = (UINT)(fMax((INT)hAacEncoder->extParam.userPeakBitrate, hAacEncoder->aacConfig.bitRate)); /* peak bitrate parameter is in use */
}
break;
default:
//err = MPS_INVALID_PARAMETER;
break;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -95,13 +95,7 @@ amm-info@iis.fraunhofer.de
#include "aacEnc_rom.h"
#include "aacenc_tns.h"
enum {
HIFILT = 0, /* index of higher filter */
LOFILT = 1 /* index of lower filter */
};
#define FILTER_DIRECTION 0
#define FILTER_DIRECTION 0 /* 0 = up, 1 = down */
static const FIXP_DBL acfWindowLong[12+3+1] = {
0x7fffffff,0x7fb80000,0x7ee00000,0x7d780000,0x7b800000,0x78f80000,0x75e00000,0x72380000,
@ -112,20 +106,6 @@ static const FIXP_DBL acfWindowShort[4+3+1] = {
0x7fffffff,0x7e000000,0x78000000,0x6e000000,0x60000000,0x4e000000,0x38000000,0x1e000000
};
typedef struct {
INT filterEnabled[MAX_NUM_OF_FILTERS];
INT threshOn[MAX_NUM_OF_FILTERS]; /* min. prediction gain for using tns TABUL*/
INT filterStartFreq[MAX_NUM_OF_FILTERS]; /* lowest freq for lpc TABUL*/
INT tnsLimitOrder[MAX_NUM_OF_FILTERS]; /* Limit for TNS order TABUL*/
INT tnsFilterDirection[MAX_NUM_OF_FILTERS]; /* Filtering direction, 0=up, 1=down TABUL */
INT acfSplit[MAX_NUM_OF_FILTERS];
FIXP_DBL tnsTimeResolution[MAX_NUM_OF_FILTERS]; /* TNS max. time resolution TABUL. Should be fract but MSVC won't compile then */
INT seperateFiltersAllowed;
} TNS_PARAMETER_TABULATED;
typedef struct{
INT bitRateFrom[2]; /* noneSbr=0, useSbr=1 */
INT bitRateTo[2]; /* noneSbr=0, useSbr=1 */
@ -373,6 +353,7 @@ AAC_ENCODER_ERROR FDKaacEnc_InitTnsConfiguration(INT bitRate,
INT channels,
INT blockType,
INT granuleLength,
INT isLowDelay,
INT ldSbrPresent,
TNS_CONFIG *tC,
PSY_CONFIGURATION *pC,
@ -385,6 +366,8 @@ AAC_ENCODER_ERROR FDKaacEnc_InitTnsConfiguration(INT bitRate,
if (channels <= 0)
return (AAC_ENCODER_ERROR)1;
tC->isLowDelay = isLowDelay;
/* initialize TNS filter flag, order, and coefficient resolution (in bits per coeff) */
tC->tnsActive = (active) ? TRUE : FALSE;
tC->maxOrder = (blockType == SHORT_WINDOW) ? 5 : 12; /* maximum: 7, 20 */
@ -450,27 +433,14 @@ AAC_ENCODER_ERROR FDKaacEnc_InitTnsConfiguration(INT bitRate,
const TNS_PARAMETER_TABULATED* pCfg = FDKaacEnc_GetTnsParam(bitRate, channels, ldSbrPresent);
if ( pCfg != NULL ) {
FDKmemcpy(&(tC->confTab), pCfg, sizeof(tC->confTab));
tC->lpcStartBand[HIFILT] = FDKaacEnc_FreqToBandWithRounding(pCfg->filterStartFreq[HIFILT], sampleRate, pC->sfbCnt, pC->sfbOffset);
tC->lpcStartLine[HIFILT] = pC->sfbOffset[tC->lpcStartBand[HIFILT]];
tC->lpcStartBand[LOFILT] = FDKaacEnc_FreqToBandWithRounding(pCfg->filterStartFreq[LOFILT], sampleRate, pC->sfbCnt, pC->sfbOffset);
tC->lpcStartLine[LOFILT] = pC->sfbOffset[tC->lpcStartBand[LOFILT]];
tC->confTab.threshOn[HIFILT] = pCfg->threshOn[HIFILT];
tC->confTab.threshOn[LOFILT] = pCfg->threshOn[LOFILT];
tC->confTab.tnsLimitOrder[HIFILT] = pCfg->tnsLimitOrder[HIFILT];
tC->confTab.tnsLimitOrder[LOFILT] = pCfg->tnsLimitOrder[LOFILT];
tC->confTab.tnsFilterDirection[HIFILT] = pCfg->tnsFilterDirection[HIFILT];
tC->confTab.tnsFilterDirection[LOFILT] = pCfg->tnsFilterDirection[LOFILT];
tC->confTab.acfSplit[HIFILT] = pCfg->acfSplit[HIFILT];
tC->confTab.acfSplit[LOFILT] = pCfg->acfSplit[LOFILT];
tC->confTab.filterEnabled[HIFILT] = pCfg->filterEnabled[HIFILT];
tC->confTab.filterEnabled[LOFILT] = pCfg->filterEnabled[LOFILT];
tC->confTab.seperateFiltersAllowed = pCfg->seperateFiltersAllowed;
FDKaacEnc_CalcGaussWindow(tC->acfWindow[HIFILT], tC->maxOrder+1, sampleRate, granuleLength, pCfg->tnsTimeResolution[HIFILT], TNS_TIMERES_SCALE);
FDKaacEnc_CalcGaussWindow(tC->acfWindow[LOFILT], tC->maxOrder+1, sampleRate, granuleLength, pCfg->tnsTimeResolution[LOFILT], TNS_TIMERES_SCALE);
}
@ -614,6 +584,7 @@ static inline FIXP_DBL FDKaacEnc_AutoCorrNormFac(
static void FDKaacEnc_MergedAutoCorrelation(
const FIXP_DBL *spectrum,
const INT isLowDelay,
const FIXP_DBL acfWindow[MAX_NUM_OF_FILTERS][TNS_MAX_ORDER+3+1],
const INT lpcStartLine[MAX_NUM_OF_FILTERS],
const INT lpcStopLine,
@ -633,6 +604,8 @@ static void FDKaacEnc_MergedAutoCorrelation(
FDKmemclear(&_rxx1[0], sizeof(FIXP_DBL)*(maxOrder+1));
FDKmemclear(&_rxx2[0], sizeof(FIXP_DBL)*(maxOrder+1));
idx0 = idx1 = idx2 = idx3 = idx4 = 0;
/* MDCT line indices separating the 1st, 2nd, 3rd, and 4th analysis quarters */
if ( (acfSplit[LOFILT]==-1) || (acfSplit[HIFILT]==-1) ) {
/* autocorrelation function for 1st, 2nd, 3rd, and 4th quarter of the spectrum */
@ -676,17 +649,27 @@ static void FDKaacEnc_MergedAutoCorrelation(
/* compute energy normalization factors, i. e. 1/energy (saves some divisions) */
if (rxx1_0 != FL2FXCONST_DBL(0.f))
{
INT sc_fac1 = -1;
FIXP_DBL fac1 = FDKaacEnc_AutoCorrNormFac(rxx1_0, ((-2*sc1)+nsc1), &sc_fac1);
_rxx1[0] = scaleValue(fMult(rxx1_0,fac1),sc_fac1);
INT sc_fac1 = -1;
FIXP_DBL fac1 = FDKaacEnc_AutoCorrNormFac(rxx1_0, ((-2*sc1)+nsc1), &sc_fac1);
_rxx1[0] = scaleValue(fMult(rxx1_0,fac1),sc_fac1);
if (isLowDelay)
{
for (lag = 1; lag <= maxOrder; lag++) {
/* compute energy-normalized and windowed autocorrelation values at this lag */
FIXP_DBL x1 = FDKaacEnc_CalcAutoCorrValue(pSpectrum, idx0, idx1, lag, nsc1);
_rxx1[lag] = fMult(scaleValue(fMult(x1,fac1),sc_fac1), acfWindow[LOFILT][lag]);
}
}
else
{
for (lag = 1; lag <= maxOrder; lag++) {
if ((3 * lag) <= maxOrder + 3) {
FIXP_DBL x1 = FDKaacEnc_CalcAutoCorrValue(pSpectrum, idx0, idx1, lag, nsc1);
_rxx1[lag] = fMult(scaleValue(fMult(x1,fac1),sc_fac1), acfWindow[LOFILT][3*lag]);
}
}
}
}
/* auto corr over upper 3/4 of spectrum */
@ -762,8 +745,12 @@ INT FDKaacEnc_TnsDetect(
: &tnsData->dataRaw.Long.subBlockInfo;
tnsData->filtersMerged = FALSE;
tsbi->tnsActive = FALSE;
tsbi->predictionGain = 1000;
tsbi->tnsActive[HIFILT] = FALSE;
tsbi->predictionGain[HIFILT] = 1000;
tsbi->tnsActive[LOFILT] = FALSE;
tsbi->predictionGain[LOFILT] = 1000;
tnsInfo->numOfFilters[subBlockNumber] = 0;
tnsInfo->coefRes[subBlockNumber] = tC->coefRes;
for (i = 0; i < tC->maxOrder; i++) {
@ -779,6 +766,7 @@ INT FDKaacEnc_TnsDetect(
FDKaacEnc_MergedAutoCorrelation(
spectrum,
tC->isLowDelay,
tC->acfWindow,
tC->lpcStartLine,
tC->lpcStopLine,
@ -788,7 +776,7 @@ INT FDKaacEnc_TnsDetect(
rxx2);
/* compute higher TNS filter in lattice (ParCor) form with LeRoux-Gueguen algorithm */
tsbi->predictionGain = FDKaacEnc_AutoToParcor(rxx2, parcor_tmp, tC->confTab.tnsLimitOrder[HIFILT]);
tsbi->predictionGain[HIFILT] = FDKaacEnc_AutoToParcor(rxx2, parcor_tmp, tC->confTab.tnsLimitOrder[HIFILT]);
/* non-linear quantization of TNS lattice coefficients with given resolution */
FDKaacEnc_Parcor2Index(
@ -815,9 +803,9 @@ INT FDKaacEnc_TnsDetect(
tnsInfo->length[subBlockNumber][HIFILT] = sfbCnt - tC->lpcStartBand[HIFILT];
/* disable TNS if predictionGain is less than 3dB or sumSqrCoef is too small */
if ((tsbi->predictionGain > tC->confTab.threshOn[HIFILT]) || (sumSqrCoef > (tC->confTab.tnsLimitOrder[HIFILT]/2 + 2)))
if ((tsbi->predictionGain[HIFILT] > tC->confTab.threshOn[HIFILT]) || (sumSqrCoef > (tC->confTab.tnsLimitOrder[HIFILT]/2 + 2)))
{
tsbi->tnsActive = TRUE;
tsbi->tnsActive[HIFILT] = TRUE;
tnsInfo->numOfFilters[subBlockNumber]++;
/* compute second filter for lower quarter; only allowed for long windows! */
@ -857,6 +845,7 @@ INT FDKaacEnc_TnsDetect(
|| ( (sumSqrCoef > 9) && (sumSqrCoef < 22 * tC->confTab.tnsLimitOrder[LOFILT]) ) )
{
/* compare lower to upper filter; if they are very similar, merge them */
tsbi->tnsActive[LOFILT] = TRUE;
sumSqrCoef = 0;
for (i = 0; i < tC->confTab.tnsLimitOrder[LOFILT]; i++) {
sumSqrCoef += FDKabs(tnsInfo->coef[subBlockNumber][HIFILT][i] - tnsInfo->coef[subBlockNumber][LOFILT][i]);
@ -884,6 +873,8 @@ INT FDKaacEnc_TnsDetect(
tnsInfo->numOfFilters[subBlockNumber]++;
}
} /* filter lower part */
tsbi->predictionGain[LOFILT]=predGain;
} /* second filter allowed */
} /* if predictionGain > 1437 ... */
} /* maxOrder > 0 && tnsActive */
@ -944,7 +935,7 @@ void FDKaacEnc_TnsSync(
INT doSync = 1, absDiffSum = 0;
/* if TNS is active in at least one channel, check if ParCor coefficients of higher filter are similar */
if (pSbInfoDestW->tnsActive || pSbInfoSrcW->tnsActive) {
if (pSbInfoDestW->tnsActive[HIFILT] || pSbInfoSrcW->tnsActive[HIFILT]) {
for (i = 0; i < tC->maxOrder; i++) {
absDiff = FDKabs(tnsInfoDest->coef[w][HIFILT][i] - tnsInfoSrc->coef[w][HIFILT][i]);
absDiffSum += absDiff;
@ -957,12 +948,12 @@ void FDKaacEnc_TnsSync(
if (doSync) {
/* if no significant difference was detected, synchronize coefficient sets */
if (pSbInfoSrcW->tnsActive) {
if (pSbInfoSrcW->tnsActive[HIFILT]) {
/* no dest filter, or more dest than source filters: use one dest filter */
if ((!pSbInfoDestW->tnsActive) ||
((pSbInfoDestW->tnsActive) && (tnsInfoDest->numOfFilters[w] > tnsInfoSrc->numOfFilters[w])))
if ((!pSbInfoDestW->tnsActive[HIFILT]) ||
((pSbInfoDestW->tnsActive[HIFILT]) && (tnsInfoDest->numOfFilters[w] > tnsInfoSrc->numOfFilters[w])))
{
pSbInfoDestW->tnsActive = tnsInfoDest->numOfFilters[w] = 1;
pSbInfoDestW->tnsActive[HIFILT] = tnsInfoDest->numOfFilters[w] = 1;
}
tnsDataDest->filtersMerged = tnsDataSrc->filtersMerged;
tnsInfoDest->order [w][HIFILT] = tnsInfoSrc->order [w][HIFILT];
@ -975,7 +966,7 @@ void FDKaacEnc_TnsSync(
}
}
else
pSbInfoDestW->tnsActive = tnsInfoDest->numOfFilters[w] = 0;
pSbInfoDestW->tnsActive[HIFILT] = tnsInfoDest->numOfFilters[w] = 0;
}
}
@ -1012,8 +1003,8 @@ INT FDKaacEnc_TnsEncode(
{
INT i, startLine, stopLine;
if ( ( (blockType == SHORT_WINDOW) && (!tnsData->dataRaw.Short.subBlockInfo[subBlockNumber].tnsActive) )
|| ( (blockType != SHORT_WINDOW) && (!tnsData->dataRaw.Long.subBlockInfo.tnsActive) ) )
if ( ( (blockType == SHORT_WINDOW) && (!tnsData->dataRaw.Short.subBlockInfo[subBlockNumber].tnsActive[HIFILT]) )
|| ( (blockType != SHORT_WINDOW) && (!tnsData->dataRaw.Long.subBlockInfo.tnsActive[HIFILT]) ) )
{
return 1;
}
@ -1129,8 +1120,9 @@ static INT FDKaacEnc_AutoToParcor(
FIXP_DBL *RESTRICT workBuffer = parcorWorkBuffer;
const FIXP_DBL autoCorr_0 = input[0];
FDKmemclear(reflCoeff,numOfCoeff*sizeof(FIXP_DBL));
if((FIXP_DBL)input[0] == FL2FXCONST_DBL(0.0)) {
FDKmemclear(reflCoeff,numOfCoeff*sizeof(FIXP_DBL));
return(predictionGain);
}

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -117,21 +117,25 @@ amm-info@iis.fraunhofer.de
#define MAX_NUM_OF_FILTERS 2
#define HIFILT 0 /* index of higher filter */
#define LOFILT 1 /* index of lower filter */
typedef struct{ /*stuff that is tabulated dependent on bitrate etc. */
INT filterEnabled[MAX_NUM_OF_FILTERS];
INT threshOn[MAX_NUM_OF_FILTERS]; /* min. prediction gain for using tns TABUL*/
INT tnsLimitOrder[MAX_NUM_OF_FILTERS]; /* Limit for TNS order TABUL*/
INT tnsFilterDirection[MAX_NUM_OF_FILTERS]; /* Filtering direction, 0=up, 1=down TABUL */
INT acfSplit[MAX_NUM_OF_FILTERS];
INT seperateFiltersAllowed;
}TNS_CONFIG_TABULATED;
typedef struct{ /* stuff that is tabulated dependent on bitrate etc. */
INT filterEnabled[MAX_NUM_OF_FILTERS];
INT threshOn[MAX_NUM_OF_FILTERS]; /* min. prediction gain for using tns TABUL*/
INT filterStartFreq[MAX_NUM_OF_FILTERS]; /* lowest freq for lpc TABUL*/
INT tnsLimitOrder[MAX_NUM_OF_FILTERS]; /* Limit for TNS order TABUL*/
INT tnsFilterDirection[MAX_NUM_OF_FILTERS]; /* Filtering direction, 0=up, 1=down TABUL */
INT acfSplit[MAX_NUM_OF_FILTERS];
FIXP_DBL tnsTimeResolution[MAX_NUM_OF_FILTERS]; /* TNS max. time resolution TABUL. Should be fract but MSVC won't compile then */
INT seperateFiltersAllowed;
} TNS_PARAMETER_TABULATED;
typedef struct { /*assigned at InitTime*/
TNS_CONFIG_TABULATED confTab;
TNS_PARAMETER_TABULATED confTab;
INT isLowDelay;
INT tnsActive;
INT maxOrder; /* max. order of tns filter */
INT coefRes;
@ -148,8 +152,8 @@ typedef struct { /*assigned at InitTime*/
typedef struct {
INT tnsActive;
INT predictionGain;
INT tnsActive[MAX_NUM_OF_FILTERS];
INT predictionGain[MAX_NUM_OF_FILTERS];
} TNS_SUBBLOCK_INFO;
typedef struct{ /*changed at runTime*/

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -130,14 +130,14 @@ the crash recovery strategy will be activated once.
typedef struct {
INT bitrate;
LONG bits2PeFactor_mono;
LONG bits2PeFactor_mono_slope;
LONG bits2PeFactor_stereo;
LONG bits2PeFactor_stereo_slope;
LONG bits2PeFactor_mono_scfOpt;
LONG bits2PeFactor_mono_scfOpt_slope;
LONG bits2PeFactor_stereo_scfOpt;
LONG bits2PeFactor_stereo_scfOpt_slope;
ULONG bits2PeFactor_mono;
ULONG bits2PeFactor_mono_slope;
ULONG bits2PeFactor_stereo;
ULONG bits2PeFactor_stereo_slope;
ULONG bits2PeFactor_mono_scfOpt;
ULONG bits2PeFactor_mono_scfOpt_slope;
ULONG bits2PeFactor_stereo_scfOpt;
ULONG bits2PeFactor_stereo_scfOpt_slope;
} BIT_PE_SFAC;
@ -153,10 +153,10 @@ static const BIT_PE_SFAC S_Bits2PeTab16000[] = {
{ 24000, 0x23D70A3D, 0x029F16B1, 0x2199999A, 0x07DD4413, 0x23D70A3D, 0x029F16B1, 0x2199999A, 0x07DD4413},
{ 32000, 0x247AE148, 0x11B1D92B, 0x23851EB8, 0x01F75105, 0x247AE148, 0x110A137F, 0x23851EB8, 0x01F75105},
{ 48000, 0x2D1EB852, 0x6833C600, 0x247AE148, 0x014F8B59, 0x2CCCCCCD, 0x68DB8BAC, 0x247AE148, 0x01F75105},
{ 64000, 0x60000000, 0x00000000, 0x251EB852, 0x154C985F, 0x60000000, 0x00000000, 0x2570A3D7, 0x154C985F},
{ 96000, 0x60000000, 0x00000000, 0x39EB851F, 0x088509C0, 0x60000000, 0x00000000, 0x3A3D70A4, 0x088509C0},
{128000, 0x60000000, 0x00000000, 0x423D70A4, 0x18A43BB4, 0x60000000, 0x00000000, 0x428F5C29, 0x181E03F7},
{148000, 0x60000000, 0x00000000, 0x5147AE14, 0x00000000, 0x60000000, 0x00000000, 0x5147AE14, 0x00000000}
{ 64000, 0x25c28f40, 0x00000000, 0x251EB852, 0x01480000, 0x25c28f40, 0x00000000, 0x2570A3D7, 0x01480000},
{ 96000, 0x25c28f40, 0x00000000, 0x26000000, 0x01000000, 0x25c28f40, 0x00000000, 0x26000000, 0x01000000},
{128000, 0x25c28f40, 0x00000000, 0x270a3d80, 0x01000000, 0x25c28f40, 0x00000000, 0x270a3d80, 0x01000000},
{148000, 0x25c28f40, 0x00000000, 0x28000000, 0x00000000, 0x25c28f40, 0x00000000, 0x28000000, 0x00000000}
};
static const BIT_PE_SFAC S_Bits2PeTab22050[] = {
@ -166,8 +166,8 @@ static const BIT_PE_SFAC S_Bits2PeTab22050[] = {
{ 48000, 0x23d70a3d, 0x014f8b59, 0x2199999a, 0x03eea20a, 0x23d70a3d, 0x14f8b59, 0x2199999a, 0x03eea20a},
{ 64000, 0x247ae148, 0x08d8ec96, 0x23851eb8, 0x00fba882, 0x247ae148, 0x88509c0, 0x23851eb8, 0x00fba882},
{ 96000, 0x2d1eb852, 0x3419e300, 0x247ae148, 0x00a7c5ac, 0x2ccccccd, 0x346dc5d6, 0x247ae148, 0x00fba882},
{128000, 0x60000000, 0x00000000, 0x251eb852, 0x029f16b1, 0x60000000, 0x00000000, 0x2570a3d7, 0x009f16b1},
{148000, 0x60000000, 0x00000000, 0x26b851ec, 0x00000000, 0x60000000, 0x00000000, 0x270a3d71, 0x00000000}
{128000, 0x25c28f40, 0x00000000, 0x251eb852, 0x029f16b1, 0x60000000, 0x25c28f40, 0x2570a3d7, 0x009f16b1},
{148000, 0x25c28f40, 0x00000000, 0x26b851ec, 0x00000000, 0x60000000, 0x25c28f40, 0x270a3d71, 0x00000000}
};
static const BIT_PE_SFAC S_Bits2PeTab24000[] = {
@ -178,21 +178,21 @@ static const BIT_PE_SFAC S_Bits2PeTab24000[] = {
{ 64000, 0x24cccccd, 0x05e5f30e, 0x22e147ae, 0x01a36e2f, 0x24cccccd, 0x05e5f30e, 0x23333333, 0x014f8b59},
{ 96000, 0x2a8f5c29, 0x24b33db0, 0x247ae148, 0x00fba882, 0x2a8f5c29, 0x26fe718b, 0x247ae148, 0x00fba882},
{128000, 0x4e666666, 0x1cd5f99c, 0x2570a3d7, 0x010c6f7a, 0x50a3d70a, 0x192a7371, 0x2570a3d7, 0x010c6f7a},
{148000, 0x60000000, 0x00000000, 0x26147ae1, 0x00000000, 0x60000000, 0x00000000, 0x26147ae1, 0x00000000}
{148000, 0x25c28f40, 0x00000000, 0x26147ae1, 0x00000000, 0x25c28f40, 0x00000000, 0x26147ae1, 0x00000000}
};
static const BIT_PE_SFAC S_Bits2PeTab32000[] = {
{ 16000, 0x1199999a, 0x20c49ba6, 0x00000000, 0x4577d955, 0x00000000, 0x60fe4799, 0x00000000, 0x00000000},
{ 24000, 0x1999999a, 0x0fba8827, 0x10f5c28f, 0x1b866e44, 0x17ae147b, 0x0fba8827, 0x00000000, 0x4d551d69},
{ 16000, 0x247ae140, 0xFFFFAC1E, 0x270a3d80, 0xFFFE9B7C, 0x14ccccc0, 0x000110A1, 0x15c28f60, 0xFFFEEF5F},
{ 24000, 0x23333340, 0x0fba8827, 0x21999980, 0x1b866e44, 0x18f5c280, 0x0fba8827, 0x119999a0, 0x4d551d69},
{ 32000, 0x1d70a3d7, 0x07357e67, 0x17ae147b, 0x09d49518, 0x1b851eb8, 0x0a7c5ac4, 0x12e147ae, 0x110a137f},
{ 48000, 0x20f5c28f, 0x049667b6, 0x1c7ae148, 0x053e2d62, 0x20a3d70a, 0x053e2d62, 0x1b333333, 0x05e5f30e},
{ 64000, 0x23333333, 0x029f16b1, 0x1f0a3d71, 0x02f2f987, 0x23333333, 0x029f16b1, 0x1e147ae1, 0x03eea20a},
{ 96000, 0x25c28f5c, 0x2c3c9eed, 0x21eb851f, 0x01f75105, 0x25c28f5c, 0x0a7c5ac4, 0x21eb851f, 0x01a36e2f},
{128000, 0x50f5c28f, 0x18a43bb4, 0x23d70a3d, 0x010c6f7a, 0x30000000, 0x168b5cc0, 0x23851eb8, 0x0192a737},
{148000, 0x60000000, 0x00000000, 0x247ae148, 0x00dfb23b, 0x3dc28f5c, 0x300f4aaf, 0x247ae148, 0x01bf6476},
{160000, 0x60000000, 0xb15b5740, 0x24cccccd, 0x053e2d62, 0x4f5c28f6, 0xbefd0072, 0x251eb852, 0x04fb1184},
{200000, 0x00000000, 0x00000000, 0x2b333333, 0x0836be91, 0x00000000, 0x00000000, 0x2b333333, 0x0890390f},
{320000, 0x00000000, 0x00000000, 0x4947ae14, 0x00000000, 0x00000000, 0x00000000, 0x4a8f5c29, 0x00000000}
{148000, 0x25c28f40, 0x00000000, 0x247ae148, 0x00dfb23b, 0x3dc28f5c, 0x300f4aaf, 0x247ae148, 0x01bf6476},
{160000, 0x25c28f40, 0xb15b5740, 0x24cccccd, 0x053e2d62, 0x4f5c28f6, 0xbefd0072, 0x251eb852, 0x04fb1184},
{200000, 0x25c28f40, 0x00000000, 0x2b333333, 0x0836be91, 0x25c28f40, 0x00000000, 0x2b333333, 0x0890390f},
{320000, 0x25c28f40, 0x00000000, 0x4947ae14, 0x00000000, 0x25c28f40, 0x00000000, 0x4a8f5c29, 0x00000000}
};
static const BIT_PE_SFAC S_Bits2PeTab44100[] = {
@ -205,8 +205,8 @@ static const BIT_PE_SFAC S_Bits2PeTab44100[] = {
{128000, 0x2ae147ae, 0x1b435265, 0x223d70a4, 0x0192a737, 0x2a3d70a4, 0x1040bfe4, 0x21eb851f, 0x0192a737},
{148000, 0x3b851eb8, 0x2832069c, 0x23333333, 0x00dfb23b, 0x3428f5c3, 0x2054c288, 0x22e147ae, 0x00dfb23b},
{160000, 0x4a3d70a4, 0xc32ebe5a, 0x23851eb8, 0x01d5c316, 0x40000000, 0xcb923a2b, 0x23333333, 0x01d5c316},
{200000, 0x00000000, 0x00000000, 0x25c28f5c, 0x0713f078, 0x00000000, 0x00000000, 0x2570a3d7, 0x072a4f17},
{320000, 0x00000000, 0x00000000, 0x3fae147b, 0x00000000, 0x00000000, 0x00000000, 0x3fae147b, 0x00000000}
{200000, 0x25c28f40, 0x00000000, 0x25c28f5c, 0x0713f078, 0x25c28f40, 0x00000000, 0x2570a3d7, 0x072a4f17},
{320000, 0x25c28f40, 0x00000000, 0x3fae147b, 0x00000000, 0x25c28f40, 0x00000000, 0x3fae147b, 0x00000000}
};
static const BIT_PE_SFAC S_Bits2PeTab48000[] = {
@ -219,8 +219,8 @@ static const BIT_PE_SFAC S_Bits2PeTab48000[] = {
{128000, 0x28f5c28f, 0x14727dcc, 0x2147ae14, 0x0218def4, 0x2851eb85, 0x0e27e0f0, 0x20f5c28f, 0x0218def4},
{148000, 0x3570a3d7, 0x1cd5f99c, 0x228f5c29, 0x01bf6476, 0x30f5c28f, 0x18777e75, 0x223d70a4, 0x01bf6476},
{160000, 0x40000000, 0xcb923a2b, 0x23333333, 0x0192a737, 0x39eb851f, 0xd08d4bae, 0x22e147ae, 0x0192a737},
{200000, 0x00000000, 0x00000000, 0x251eb852, 0x06775a1b, 0x00000000, 0x00000000, 0x24cccccd, 0x06a4175a},
{320000, 0x00000000, 0x00000000, 0x3ccccccd, 0x00000000, 0x00000000, 0x00000000, 0x3d1eb852, 0x00000000}
{200000, 0x25c28f40, 0x00000000, 0x251eb852, 0x06775a1b, 0x25c28f40, 0x00000000, 0x24cccccd, 0x06a4175a},
{320000, 0x25c28f40, 0x00000000, 0x3ccccccd, 0x00000000, 0x25c28f40, 0x00000000, 0x3d1eb852, 0x00000000}
};
static const BITS2PE_CFG_TAB bits2PeConfigTab[] = {
@ -258,6 +258,7 @@ static void FDKaacEnc_InitBits2PeFactor(
const INT nChannels,
const INT sampleRate,
const INT advancedBitsToPe,
const INT dZoneQuantEnable,
const INT invQuant
)
{
@ -329,7 +330,32 @@ static void FDKaacEnc_InitBits2PeFactor(
} /* advancedBitsToPe */
/* return bits2pe factor */
if (dZoneQuantEnable)
{
if(bit2PE_m >= (FL2FXCONST_DBL(0.6f))>>bit2PE_e)
{
/* Additional headroom for addition */
bit2PE_m >>= 1;
bit2PE_e += 1;
}
/* the quantTendencyCompensator compensates a lower bit consumption due to increasing the tendency to quantize low spectral values to the lower quantizer border for bitrates below a certain bitrate threshold --> see also function calcSfbDistLD in quantize.c */
if ((bitRate/nChannels > 32000) && (bitRate/nChannels <= 40000)) {
bit2PE_m += (FL2FXCONST_DBL(0.4f))>>bit2PE_e;
}
else if (bitRate/nChannels > 20000) {
bit2PE_m += (FL2FXCONST_DBL(0.3f))>>bit2PE_e;
}
else if (bitRate/nChannels >= 16000) {
bit2PE_m += (FL2FXCONST_DBL(0.3f))>>bit2PE_e;
}
else {
bit2PE_m += (FL2FXCONST_DBL(0.0f))>>bit2PE_e;
}
}
/***** 3.) Return bits2pe factor *****/
*bits2PeFactor_m = bit2PE_m;
*bits2PeFactor_e = bit2PE_e;
}
@ -1649,6 +1675,7 @@ static void FDKaacEnc_adaptThresholdsToPe(CHANNEL_MAPPING* cm,
QC_OUT_ELEMENT* qcElement[(8)],
PSY_OUT_ELEMENT* psyOutElement[(8)],
const INT desiredPe,
const INT maxIter2ndGuess,
const INT processElements,
const INT elementOffset)
{
@ -1733,7 +1760,7 @@ static void FDKaacEnc_adaptThresholdsToPe(CHANNEL_MAPPING* cm,
/* Part III: Iterate until bit constraints are met */
/* -------------------------------------------------- */
iter = 0;
while ((fixp_abs(redPeGlobal - desiredPe) > fMultI(FL2FXCONST_DBL(0.05f),desiredPe)) && (iter < 1)) {
while ((fixp_abs(redPeGlobal - desiredPe) > fMultI(FL2FXCONST_DBL(0.05f),desiredPe)) && (iter < maxIter2ndGuess)) {
INT desiredPeNoAHGlobal;
INT redPeNoAHGlobal = 0;
@ -2138,7 +2165,7 @@ static FIXP_DBL FDKaacEnc_bitresCalcBitFac(const INT bitresBits,
bresParam->clipSpendLow, bresParam->clipSpendHigh,
bresParam->minBitSpend, bresParam->maxBitSpend, bitspend_slope);
pe_pers = fDivNorm(pex - adjThrChan->peMin, adjThrChan->peMax - adjThrChan->peMin);
pe_pers = (pex > adjThrChan->peMin) ? fDivNorm(pex - adjThrChan->peMin, adjThrChan->peMax - adjThrChan->peMin) : 0;
tmp_fix = fMult(((FIXP_DBL)bitSpend + (FIXP_DBL)bitSave), pe_pers);
bitresFac_fix = (UNITY>>1) - ((FIXP_DBL)bitSave>>1) + (tmp_fix>>1); qbres = (DFRACT_BITS-2);
@ -2225,7 +2252,8 @@ void FDKaacEnc_AdjThrInit(
INT nChannelsEff,
INT sampleRate,
INT advancedBitsToPe,
FIXP_DBL vbrQualFactor
FIXP_DBL vbrQualFactor,
const INT dZoneQuantEnable
)
{
INT i;
@ -2233,6 +2261,10 @@ void FDKaacEnc_AdjThrInit(
FIXP_DBL POINT8 = FL2FXCONST_DBL(0.8f);
FIXP_DBL POINT6 = FL2FXCONST_DBL(0.6f);
/* Max number of iterations in second guess is 3 for lowdelay aot and for configurations with
multiple audio elements in general, otherwise iteration value is always 1. */
hAdjThr->maxIter2ndGuess = (advancedBitsToPe!=0 || nElements>1) ? 3 : 1;
/* common for all elements: */
/* parameters for bitres control */
hAdjThr->bresParamLong.clipSaveLow = (FIXP_DBL)0x1999999a; /* FL2FXCONST_DBL(0.2f); */
@ -2313,10 +2345,11 @@ void FDKaacEnc_AdjThrInit(
FDKaacEnc_InitBits2PeFactor(
&atsElem->bits2PeFactor_m,
&atsElem->bits2PeFactor_e,
chBitrate, /* bitrate/channel*/
chBitrate*nChannelsEff, /* overall bitrate */
nChannelsEff, /* number of channels */
sampleRate,
advancedBitsToPe,
dZoneQuantEnable,
invQuant
);
@ -2545,6 +2578,7 @@ void FDKaacEnc_AdjustThresholds(ATS_ELEMENT* AdjThrStateElement[(8)],
QC_OUT* qcOut,
PSY_OUT_ELEMENT* psyOutElement[(8)],
INT CBRbitrateMode,
INT maxIter2ndGuess,
CHANNEL_MAPPING* cm)
{
int i;
@ -2570,6 +2604,7 @@ void FDKaacEnc_AdjustThresholds(ATS_ELEMENT* AdjThrStateElement[(8)],
qcElement,
psyOutElement,
qcElement[i]->grantedPeCorr,
maxIter2ndGuess,
1, /* Process only 1 element */
i); /* Process exactly THIS element */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -118,7 +118,8 @@ void FDKaacEnc_AdjThrInit(ADJ_THR_STATE *hAdjThr,
INT nChannelsEff,
INT sampleRate,
INT advancedBitsToPe,
FIXP_DBL vbrQualFactor);
FIXP_DBL vbrQualFactor,
const INT dZoneQuantEnable);
void FDKaacEnc_DistributeBits(ADJ_THR_STATE *adjThrState,
@ -140,6 +141,7 @@ void FDKaacEnc_AdjustThresholds(ATS_ELEMENT* AdjThrStateElement[(8)],
QC_OUT* qcOut,
PSY_OUT_ELEMENT* psyOutElement[(8)],
INT CBRbitrateMode,
INT maxIter2ndGuess,
CHANNEL_MAPPING* cm);
void FDKaacEnc_AdjThrClose(ADJ_THR_STATE** hAdjThr);

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -145,6 +145,7 @@ typedef struct {
typedef struct {
BRES_PARAM bresParamLong, bresParamShort;
ATS_ELEMENT* adjThrStateElem[(8)];
INT maxIter2ndGuess;
} ADJ_THR_STATE;
#endif

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -127,7 +127,7 @@ static const BANDWIDTH_TAB bandWidthTable_LD_24000[] = {
{ 8000, 2000, 2000},
{12000, 2000, 2300},
{16000, 2200, 2500},
{24000, 5650, 6400},
{24000, 5650, 7200},
{32000, 11600, 12000},
{40000, 12000, 16000},
{48000, 16000, 16000},
@ -138,10 +138,10 @@ static const BANDWIDTH_TAB bandWidthTable_LD_24000[] = {
static const BANDWIDTH_TAB bandWidthTable_LD_32000[] = {
{ 8000, 2000, 2000},
{12000, 2000, 2000},
{24000, 4250, 5200},
{24000, 4250, 7200},
{32000, 8400, 9000},
{40000, 9400, 11300},
{48000, 11900, 13700},
{48000, 11900, 14700},
{64000, 14800, 16000},
{76000, 16000, 16000},
{360001, 16000, 16000}

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -325,7 +325,6 @@ FDKaacEnc_prepareIntensityDecision(const FIXP_DBL *sfbEnergyLeft,
channelCorr[sfb + sfboffs] = FL2FXCONST_DBL(0.0f);
FDK_ASSERT(50 >= 49);
/* max width of scalefactorband is 96; width's are always even */
/* inv_n is scaled with factor 2 to compensate fMultDiv2() in subsequent loops */
inv_n = GetInvInt((sfbOffset[sfb + sfboffs + 1] - sfbOffset[sfb + sfboffs])>>1);

View File

@ -193,36 +193,36 @@ struct DRC_COMP {
* Profile tables.
*/
static const FIXP_DBL tabMaxBoostThr[] = {
(FIXP_DBL)(-43<<METADATA_FRACT_BITS),
(FIXP_DBL)(-53<<METADATA_FRACT_BITS),
(FIXP_DBL)(-55<<METADATA_FRACT_BITS),
(FIXP_DBL)(-65<<METADATA_FRACT_BITS),
(FIXP_DBL)(-50<<METADATA_FRACT_BITS),
(FIXP_DBL)(-40<<METADATA_FRACT_BITS)
(FIXP_DBL)(int)((unsigned)-43<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-53<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-55<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-65<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-50<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-40<<METADATA_FRACT_BITS)
};
static const FIXP_DBL tabBoostThr[] = {
(FIXP_DBL)(-31<<METADATA_FRACT_BITS),
(FIXP_DBL)(-41<<METADATA_FRACT_BITS),
(FIXP_DBL)(-31<<METADATA_FRACT_BITS),
(FIXP_DBL)(-41<<METADATA_FRACT_BITS),
(FIXP_DBL)(-31<<METADATA_FRACT_BITS),
(FIXP_DBL)(-31<<METADATA_FRACT_BITS)
(FIXP_DBL)(int)((unsigned)-31<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-41<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-31<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-41<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-31<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-31<<METADATA_FRACT_BITS)
};
static const FIXP_DBL tabEarlyCutThr[] = {
(FIXP_DBL)(-26<<METADATA_FRACT_BITS),
(FIXP_DBL)(-21<<METADATA_FRACT_BITS),
(FIXP_DBL)(-26<<METADATA_FRACT_BITS),
(FIXP_DBL)(-21<<METADATA_FRACT_BITS),
(FIXP_DBL)(-26<<METADATA_FRACT_BITS),
(FIXP_DBL)(-20<<METADATA_FRACT_BITS)
(FIXP_DBL)(int)((unsigned)-26<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-21<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-26<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-21<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-26<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-20<<METADATA_FRACT_BITS)
};
static const FIXP_DBL tabCutThr[] = {
(FIXP_DBL)(-16<<METADATA_FRACT_BITS),
(FIXP_DBL)(-11<<METADATA_FRACT_BITS),
(FIXP_DBL)(-16<<METADATA_FRACT_BITS),
(FIXP_DBL)(-21<<METADATA_FRACT_BITS),
(FIXP_DBL)(-16<<METADATA_FRACT_BITS),
(FIXP_DBL)(-10<<METADATA_FRACT_BITS)
(FIXP_DBL)(int)((unsigned)-16<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-11<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-16<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-21<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-16<<METADATA_FRACT_BITS),
(FIXP_DBL)(int)((unsigned)-10<<METADATA_FRACT_BITS)
};
static const FIXP_DBL tabMaxCutThr[] = {
(FIXP_DBL)(4<<METADATA_FRACT_BITS),
@ -576,7 +576,7 @@ INT FDK_DRC_Generator_Initialize(
drcComp->channels = channelMapping.nChannels;
/* Init states. */
drcComp->smoothLevel[0] = drcComp->smoothLevel[1] = (FIXP_DBL)(-135<<METADATA_FRACT_BITS);
drcComp->smoothLevel[0] = drcComp->smoothLevel[1] = (FIXP_DBL)(int)((unsigned)-135<<METADATA_FRACT_BITS);
FDKmemclear(drcComp->smoothGain, sizeof(drcComp->smoothGain));
FDKmemclear(drcComp->holdCnt, sizeof(drcComp->holdCnt));

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -107,6 +107,7 @@ typedef struct {
typedef struct {
ULONG brFrom;
ULONG brTo;
UCHAR S16000;
UCHAR S22050;
UCHAR S24000;
UCHAR S32000;
@ -115,25 +116,26 @@ typedef struct {
} AUTO_PNS_TAB;
static const AUTO_PNS_TAB levelTable_mono[]= {
{0, 11999, 1, 1, 1, 1, 1,},
{12000, 19999, 1, 1, 1, 1, 1,},
{20000, 28999, 2, 1, 1, 1, 1,},
{29000, 40999, 4, 4, 4, 2, 2,},
{41000, 55999, 9, 9, 7, 7, 7,},
{56000, 79999, 0, 0, 0, 9, 9,},
{80000, 99999, 0, 0, 0, 0, 0,},
{100000,999999, 0, 0, 0, 0, 0,},
{0, 11999, 0, 1, 1, 1, 1, 1,},
{12000, 19999, 0, 1, 1, 1, 1, 1,},
{20000, 28999, 0, 2, 1, 1, 1, 1,},
{29000, 40999, 0, 4, 4, 4, 2, 2,},
{41000, 55999, 0, 9, 9, 7, 7, 7,},
{56000, 61999, 0, 0, 0, 0, 9, 9,},
{62000, 75999, 0, 0, 0, 0, 0, 0,},
{76000, 92999, 0, 0, 0, 0, 0, 0,},
{93000, 999999, 0, 0, 0, 0, 0, 0,},
};
static const AUTO_PNS_TAB levelTable_stereo[]= {
{0, 11999, 1, 1, 1, 1, 1,},
{12000, 19999, 3, 1, 1, 1, 1,},
{20000, 28999, 3, 3, 3, 2, 2,},
{29000, 40999, 7, 6, 6, 5, 5,},
{41000, 55999, 9, 9, 7, 7, 7,},
{56000, 79999, 0, 0, 0, 0, 0,},
{80000, 99999, 0, 0, 0, 0, 0,},
{100000,999999, 0, 0, 0, 0, 0,},
{0, 11999, 0, 1, 1, 1, 1, 1,},
{12000, 19999, 0, 3, 1, 1, 1, 1,},
{20000, 28999, 0, 3, 3, 3, 2, 2,},
{29000, 40999, 0, 7, 6, 6, 5, 5,},
{41000, 55999, 0, 9, 9, 7, 7, 7,},
{56000, 79999, 0, 0, 0, 0, 0, 0,},
{80000, 99999, 0, 0, 0, 0, 0, 0,},
{100000,999999, 0, 0, 0, 0, 0, 0,},
};
@ -160,11 +162,11 @@ static const PNS_INFO_TAB pnsInfoTab[] = {
};
static const AUTO_PNS_TAB levelTable_lowComplexity[]= {
{0, 27999, 0, 0, 0, 0, 0,},
{28000, 31999, 2, 2, 2, 2, 2,},
{32000, 47999, 3, 3, 3, 3, 3,},
{48000, 48000, 4, 4, 4, 4, 4,},
{48001, 999999, 0, 0, 0, 0, 0,},
{0, 27999, 0, 0, 0, 0, 0, 0,},
{28000, 31999, 0, 2, 2, 2, 2, 2,},
{32000, 47999, 0, 3, 3, 3, 3, 3,},
{48000, 48000, 0, 4, 4, 4, 4, 4,},
{48001, 999999, 0, 0, 0, 0, 0, 0,},
};
/* conversion of old LC tuning tables to new (LD enc) structure (only entries which are actually used were converted) */
@ -211,6 +213,7 @@ int FDKaacEnc_lookUpPnsUse (int bitRate, int sampleRate, int numChan, const int
}
switch (sampleRate) {
case 16000: hUsePns = levelTable[i].S16000; break;
case 22050: hUsePns = levelTable[i].S22050; break;
case 24000: hUsePns = levelTable[i].S24000; break;
case 32000: hUsePns = levelTable[i].S32000; break;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -634,13 +634,14 @@ AAC_ENCODER_ERROR FDKaacEnc_InitPsyConfiguration(INT bitrate,
if (psyConf->sfbOffset[sfb] >= psyConf->lowpassLine)
break;
}
psyConf->sfbActive = sfb;
psyConf->sfbActive = FDKmax(sfb, 1);
for (sfb = 0; sfb < psyConf->sfbCnt; sfb++){
if (psyConf->sfbOffset[sfb] >= psyConf->lowpassLineLFE)
break;
}
psyConf->sfbActiveLFE = sfb;
psyConf->sfbActive = FDKmax(psyConf->sfbActive, psyConf->sfbActiveLFE);
/* calculate minSnr */
FDKaacEnc_initMinSnr(bitrate,

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -342,6 +342,7 @@ AAC_ENCODER_ERROR FDKaacEnc_psyMainInit(PSY_INTERNAL *hPsy,
tnsChannels,
LONG_WINDOW,
hPsy->granuleLength,
isLowDelay(audioObjectType),
(syntaxFlags&AC_SBR_PRESENT)?1:0,
&(hPsy->psyConf[0].tnsConf),
&hPsy->psyConf[0],
@ -362,6 +363,7 @@ AAC_ENCODER_ERROR FDKaacEnc_psyMainInit(PSY_INTERNAL *hPsy,
tnsChannels,
SHORT_WINDOW,
hPsy->granuleLength,
isLowDelay(audioObjectType),
(syntaxFlags&AC_SBR_PRESENT)?1:0,
&hPsy->psyConf[1].tnsConf,
&hPsy->psyConf[1],
@ -447,7 +449,7 @@ AAC_ENCODER_ERROR FDKaacEnc_psyMain(INT channels,
INT totalChannels
)
{
INT commonWindow = 1;
const INT commonWindow = 1;
INT maxSfbPerGroup[(2)];
INT mdctSpectrum_e;
INT ch; /* counts through channels */
@ -621,7 +623,7 @@ AAC_ENCODER_ERROR FDKaacEnc_psyMain(INT channels,
FDKmemclear(&psyData[ch]->mdctSpectrum[psyData[ch]->lowpassLine+wOffset],
(windowLength[ch]-psyData[ch]->lowpassLine)*sizeof(FIXP_DBL));
if (hPsyConfLong->filterbank != FB_LC) {
if ( (hPsyConfLong->filterbank != FB_LC) && (psyData[ch]->lowpassLine >= FADE_OUT_LEN) ) {
/* Do blending to reduce gibbs artifacts */
for (int i=0; i<FADE_OUT_LEN; i++) {
psyData[ch]->mdctSpectrum[psyData[ch]->lowpassLine+wOffset - FADE_OUT_LEN + i] = fMult(psyData[ch]->mdctSpectrum[psyData[ch]->lowpassLine+wOffset - FADE_OUT_LEN + i], fadeOutFactor[i]);
@ -763,7 +765,8 @@ AAC_ENCODER_ERROR FDKaacEnc_psyMain(INT channels,
/* Advance psychoacoustics: Tonality and TNS */
if (psyStatic[0]->isLFE) {
tnsData[0]->dataRaw.Long.subBlockInfo.tnsActive = 0;
tnsData[0]->dataRaw.Long.subBlockInfo.tnsActive[HIFILT] = 0;
tnsData[0]->dataRaw.Long.subBlockInfo.tnsActive[LOFILT] = 0;
}
else
{
@ -815,15 +818,19 @@ AAC_ENCODER_ERROR FDKaacEnc_psyMain(INT channels,
&hThisPsyConf[1]->tnsConf);
}
FDK_ASSERT(commonWindow=1); /* all checks for TNS do only work for common windows (which is always set)*/
FDK_ASSERT(1==commonWindow); /* all checks for TNS do only work for common windows (which is always set)*/
for(w = 0; w < nWindows[0]; w++)
{
if (isShortWindow[0])
tnsActive[w] = tnsData[0]->dataRaw.Short.subBlockInfo[w].tnsActive ||
((channels == 2) ? tnsData[1]->dataRaw.Short.subBlockInfo[w].tnsActive : 0);
tnsActive[w] = tnsData[0]->dataRaw.Short.subBlockInfo[w].tnsActive[HIFILT] ||
tnsData[0]->dataRaw.Short.subBlockInfo[w].tnsActive[LOFILT] ||
tnsData[channels-1]->dataRaw.Short.subBlockInfo[w].tnsActive[HIFILT] ||
tnsData[channels-1]->dataRaw.Short.subBlockInfo[w].tnsActive[LOFILT];
else
tnsActive[w] = tnsData[0]->dataRaw.Long.subBlockInfo.tnsActive ||
((channels == 2) ? tnsData[1]->dataRaw.Long.subBlockInfo.tnsActive : 0);
tnsActive[w] = tnsData[0]->dataRaw.Long.subBlockInfo.tnsActive[HIFILT] ||
tnsData[0]->dataRaw.Long.subBlockInfo.tnsActive[LOFILT] ||
tnsData[channels-1]->dataRaw.Long.subBlockInfo.tnsActive[HIFILT] ||
tnsData[channels-1]->dataRaw.Long.subBlockInfo.tnsActive[LOFILT];
}
for(ch = 0; ch < channels; ch++) {
@ -1150,8 +1157,8 @@ AAC_ENCODER_ERROR FDKaacEnc_psyMain(INT channels,
psyData[ch]->sfbMaxScaleSpec.Long,
sfbTonality[ch],
psyOutChannel[ch]->tnsInfo.order[0][0],
tnsData[ch]->dataRaw.Long.subBlockInfo.predictionGain,
tnsData[ch]->dataRaw.Long.subBlockInfo.tnsActive,
tnsData[ch]->dataRaw.Long.subBlockInfo.predictionGain[HIFILT],
tnsData[ch]->dataRaw.Long.subBlockInfo.tnsActive[HIFILT],
psyOutChannel[ch]->sfbEnergyLdData,
psyOutChannel[ch]->noiseNrg );
} /* !isLFE */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -269,6 +269,8 @@ typedef struct
BITCNTR_STATE *hBitCounter;
ADJ_THR_STATE *hAdjThr;
INT dZoneQuantEnable; /* enable dead zone quantizer */
} QC_STATE;
#endif /* _QC_DATA_H */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -107,14 +107,11 @@ typedef struct {
} TAB_VBR_QUAL_FACTOR;
static const TAB_VBR_QUAL_FACTOR tableVbrQualFactor[] = {
{QCDATA_BR_MODE_CBR, FL2FXCONST_DBL(0.00f)},
{QCDATA_BR_MODE_VBR_1, FL2FXCONST_DBL(0.160f)}, /* 32 kbps mono AAC-LC + SBR + PS */
{QCDATA_BR_MODE_VBR_2, FL2FXCONST_DBL(0.148f)}, /* 64 kbps stereo AAC-LC + SBR */
{QCDATA_BR_MODE_VBR_3, FL2FXCONST_DBL(0.135f)}, /* 80 - 96 kbps stereo AAC-LC */
{QCDATA_BR_MODE_VBR_4, FL2FXCONST_DBL(0.111f)}, /* 128 kbps stereo AAC-LC */
{QCDATA_BR_MODE_VBR_5, FL2FXCONST_DBL(0.070f)}, /* 192 kbps stereo AAC-LC */
{QCDATA_BR_MODE_SFR, FL2FXCONST_DBL(0.00f)},
{QCDATA_BR_MODE_FF, FL2FXCONST_DBL(0.00f)}
{QCDATA_BR_MODE_VBR_5, FL2FXCONST_DBL(0.070f)} /* 192 kbps stereo AAC-LC */
};
static INT isConstantBitrateMode(
@ -369,6 +366,7 @@ QCNew_bail:
AAC_ENCODER_ERROR FDKaacEnc_QCInit(QC_STATE *hQC,
struct QC_INIT *init)
{
int i;
hQC->maxBitsPerFrame = init->maxBits;
hQC->minBitsPerFrame = init->minBits;
hQC->nElements = init->channelMapping->nElements;
@ -382,7 +380,7 @@ AAC_ENCODER_ERROR FDKaacEnc_QCInit(QC_STATE *hQC,
if ( isConstantBitrateMode(hQC->bitrateMode) ) {
INT bitresPerChannel = (hQC->bitResTotMax / init->channelMapping->nChannelsEff);
/* 0: full bitreservoir, 1: reduced bitreservoir, 2: disabled bitreservoir */
hQC->bitDistributionMode = (bitresPerChannel>100) ? 0 : (bitresPerChannel>0) ? 1 : 2;
hQC->bitDistributionMode = (bitresPerChannel>BITRES_MIN_LD) ? 0 : (bitresPerChannel>0) ? 1 : 2;
}
else {
hQC->bitDistributionMode = 0; /* full bitreservoir */
@ -399,25 +397,22 @@ AAC_ENCODER_ERROR FDKaacEnc_QCInit(QC_STATE *hQC,
(init->averageBits/init->nSubFrames) - hQC->globHdrBits,
hQC->maxBitsPerFrame/init->channelMapping->nChannelsEff);
switch(hQC->bitrateMode){
case QCDATA_BR_MODE_CBR:
case QCDATA_BR_MODE_VBR_1:
case QCDATA_BR_MODE_VBR_2:
case QCDATA_BR_MODE_VBR_3:
case QCDATA_BR_MODE_VBR_4:
case QCDATA_BR_MODE_VBR_5:
case QCDATA_BR_MODE_SFR:
case QCDATA_BR_MODE_FF:
if((int)hQC->bitrateMode < (int)(sizeof(tableVbrQualFactor)/sizeof(TAB_VBR_QUAL_FACTOR))){
hQC->vbrQualFactor = (FIXP_DBL)tableVbrQualFactor[hQC->bitrateMode].vbrQualFactor;
} else {
hQC->vbrQualFactor = FL2FXCONST_DBL(0.f); /* default setting */
}
break;
case QCDATA_BR_MODE_INVALID:
default:
hQC->vbrQualFactor = FL2FXCONST_DBL(0.f);
hQC->vbrQualFactor = FL2FXCONST_DBL(0.f);
for (i=0; i<(int)(sizeof(tableVbrQualFactor)/sizeof(TAB_VBR_QUAL_FACTOR)); i++) {
if (hQC->bitrateMode==tableVbrQualFactor[i].bitrateMode) {
hQC->vbrQualFactor = (FIXP_DBL)tableVbrQualFactor[i].vbrQualFactor;
break;
}
}
if (init->channelMapping->nChannelsEff == 1 &&
(init->bitrate / init->channelMapping->nChannelsEff) < 32000 &&
init->advancedBitsToPe != 0
)
{
hQC->dZoneQuantEnable = 1;
} else {
hQC->dZoneQuantEnable = 0;
}
FDKaacEnc_AdjThrInit(
@ -429,7 +424,8 @@ AAC_ENCODER_ERROR FDKaacEnc_QCInit(QC_STATE *hQC,
init->channelMapping->nChannelsEff,
init->sampleRate, /* output sample rate */
init->advancedBitsToPe, /* if set, calc bits2PE factor depending on samplerate */
hQC->vbrQualFactor
hQC->vbrQualFactor,
hQC->dZoneQuantEnable
);
return AAC_ENC_OK;
@ -892,6 +888,7 @@ AAC_ENCODER_ERROR FDKaacEnc_QCMain(QC_STATE* RESTRICT hQC,
qcOut[c],
psyOut[c]->psyOutElement,
isConstantBitrateMode(hQC->bitrateMode),
hQC->hAdjThr->maxIter2ndGuess,
cm);
} /* -end- sub frame counter */
@ -919,6 +916,7 @@ AAC_ENCODER_ERROR FDKaacEnc_QCMain(QC_STATE* RESTRICT hQC,
FDKaacEnc_EstimateScaleFactors(psyOut[c]->psyOutElement[i]->psyOutChannel,
qcElement[c][i]->qcOutChannel,
hQC->invQuant,
hQC->dZoneQuantEnable,
cm->elInfo[i].nChannelsInEl);
@ -1013,7 +1011,8 @@ AAC_ENCODER_ERROR FDKaacEnc_QCMain(QC_STATE* RESTRICT hQC,
qcOutCh->mdctSpectrum,
qcOutCh->globalGain,
qcOutCh->scf,
qcOutCh->quantSpec) ;
qcOutCh->quantSpec,
hQC->dZoneQuantEnable);
/*-------------------------------------------- */
if (FDKaacEnc_calcMaxValueInSfb(psyOutCh->sfbCnt,
@ -1263,6 +1262,8 @@ AAC_ENCODER_ERROR FDKaacEnc_updateFillBits(CHANNEL_MAPPING* cm,
case QCDATA_BR_MODE_VBR_4:
case QCDATA_BR_MODE_VBR_5:
qcOut[0]->totFillBits = (qcOut[0]->grantedDynBits - qcOut[0]->usedDynBits)&7; /* precalculate alignment bits */
qcOut[0]->totalBits = qcOut[0]->staticBits + qcOut[0]->usedDynBits + qcOut[0]->totFillBits + qcOut[0]->elementExtBits + qcOut[0]->globalExtBits;
qcOut[0]->totFillBits += ( fixMax(0, qcKernel->minBitsPerFrame - qcOut[0]->totalBits) + 7) & ~7;
break;
case QCDATA_BR_MODE_CBR:
@ -1272,6 +1273,8 @@ AAC_ENCODER_ERROR FDKaacEnc_updateFillBits(CHANNEL_MAPPING* cm,
/* processing fill-bits */
INT deltaBitRes = qcOut[0]->grantedDynBits - qcOut[0]->usedDynBits ;
qcOut[0]->totFillBits = fixMax((deltaBitRes&7), (deltaBitRes - (fixMax(0,bitResSpace-7)&~7)));
qcOut[0]->totalBits = qcOut[0]->staticBits + qcOut[0]->usedDynBits + qcOut[0]->totFillBits + qcOut[0]->elementExtBits + qcOut[0]->globalExtBits;
qcOut[0]->totFillBits += ( fixMax(0, qcKernel->minBitsPerFrame - qcOut[0]->totalBits) + 7) & ~7;
break;
} /* switch (qcKernel->bitrateMode) */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -104,13 +104,19 @@ amm-info@iis.fraunhofer.de
static void FDKaacEnc_quantizeLines(INT gain,
INT noOfLines,
FIXP_DBL *mdctSpectrum,
SHORT *quaSpectrum)
SHORT *quaSpectrum,
INT dZoneQuantEnable)
{
int line;
FIXP_DBL k = FL2FXCONST_DBL(-0.0946f + 0.5f)>>16;
FIXP_DBL k = FL2FXCONST_DBL(0.0f);
FIXP_QTD quantizer = FDKaacEnc_quantTableQ[(-gain)&3];
INT quantizershift = ((-gain)>>2)+1;
const INT kShift=16;
if (dZoneQuantEnable)
k = FL2FXCONST_DBL(0.23f)>>kShift;
else
k = FL2FXCONST_DBL(-0.0946f + 0.5f)>>kShift;
for (line = 0; line < noOfLines; line++)
{
@ -263,7 +269,8 @@ void FDKaacEnc_QuantizeSpectrum(INT sfbCnt,
FIXP_DBL *mdctSpectrum,
INT globalGain,
INT *scalefactors,
SHORT *quantizedSpectrum)
SHORT *quantizedSpectrum,
INT dZoneQuantEnable)
{
INT sfbOffs,sfb;
@ -280,7 +287,8 @@ void FDKaacEnc_QuantizeSpectrum(INT sfbCnt,
FDKaacEnc_quantizeLines(globalGain - scalefactor, /* QSS */
sfbOffset[sfbOffs+sfb+1] - sfbOffset[sfbOffs+sfb],
mdctSpectrum + sfbOffset[sfbOffs+sfb],
quantizedSpectrum + sfbOffset[sfbOffs+sfb]);
quantizedSpectrum + sfbOffset[sfbOffs+sfb],
dZoneQuantEnable);
}
}
@ -296,7 +304,8 @@ void FDKaacEnc_QuantizeSpectrum(INT sfbCnt,
FIXP_DBL FDKaacEnc_calcSfbDist(FIXP_DBL *mdctSpectrum,
SHORT *quantSpectrum,
INT noOfLines,
INT gain
INT gain,
INT dZoneQuantEnable
)
{
INT i,scale;
@ -311,7 +320,8 @@ FIXP_DBL FDKaacEnc_calcSfbDist(FIXP_DBL *mdctSpectrum,
FDKaacEnc_quantizeLines(gain,
1,
&mdctSpectrum[i],
&quantSpectrum[i]);
&quantSpectrum[i],
dZoneQuantEnable);
if (fAbs(quantSpectrum[i])>MAX_QUANT) {
return FL2FXCONST_DBL(0.0f);

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -102,12 +102,14 @@ void FDKaacEnc_QuantizeSpectrum(INT sfbCnt,
INT sfbPerGroup,
INT *sfbOffset, FIXP_DBL *mdctSpectrum,
INT globalGain, INT *scalefactors,
SHORT *quantizedSpectrum);
SHORT *quantizedSpectrum,
INT dZoneQuantEnable);
FIXP_DBL FDKaacEnc_calcSfbDist(FIXP_DBL *mdctSpectrum,
SHORT *quantSpectrum,
INT noOfLines,
INT gain);
INT gain,
INT dZoneQuantEnable);
void FDKaacEnc_calcSfbQuantEnergyAndDist(FIXP_DBL *mdctSpectrum,
SHORT *quantSpectrum,

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -363,7 +363,8 @@ static INT FDKaacEnc_improveScf(FIXP_DBL *spec,
INT scf,
INT minScf,
FIXP_DBL *distLdData,
INT *minScfCalculated
INT *minScfCalculated,
INT dZoneQuantEnable
)
{
FIXP_DBL sfbDistLdData;
@ -375,7 +376,8 @@ static INT FDKaacEnc_improveScf(FIXP_DBL *spec,
sfbDistLdData = FDKaacEnc_calcSfbDist(spec,
quantSpec,
sfbWidth,
scf);
scf,
dZoneQuantEnable);
*minScfCalculated = scf;
/* nmr > 1.25 -> try to improve nmr */
if (sfbDistLdData > (threshLdData-distFactorLdData)) {
@ -390,7 +392,8 @@ static INT FDKaacEnc_improveScf(FIXP_DBL *spec,
sfbDistLdData = FDKaacEnc_calcSfbDist(spec,
quantSpecTmp,
sfbWidth,
scf);
scf,
dZoneQuantEnable);
if (sfbDistLdData < sfbDistBestLdData) {
scfBest = scf;
@ -408,7 +411,8 @@ static INT FDKaacEnc_improveScf(FIXP_DBL *spec,
sfbDistLdData = FDKaacEnc_calcSfbDist(spec,
quantSpecTmp,
sfbWidth,
scf);
scf,
dZoneQuantEnable);
if (sfbDistLdData < sfbDistBestLdData) {
scfBest = scf;
@ -429,7 +433,8 @@ static INT FDKaacEnc_improveScf(FIXP_DBL *spec,
sfbDistLdData = FDKaacEnc_calcSfbDist(spec,
quantSpecTmp,
sfbWidth,
scf);
scf,
dZoneQuantEnable);
if (sfbDistLdData < sfbDistAllowedLdData) {
*minScfCalculated = scfBest+1;
@ -454,6 +459,7 @@ static void FDKaacEnc_assimilateSingleScf(PSY_OUT_CHANNEL *psyOutChan,
QC_OUT_CHANNEL *qcOutChannel,
SHORT *quantSpec,
SHORT *quantSpecTmp,
INT dZoneQuantEnable,
INT *scf,
INT *minScf,
FIXP_DBL *sfbDist,
@ -570,7 +576,8 @@ static void FDKaacEnc_assimilateSingleScf(PSY_OUT_CHANNEL *psyOutChan,
sfbDistNew = FDKaacEnc_calcSfbDist(qcOutChannel->mdctSpectrum+sfbOffs,
quantSpecTmp+sfbOffs,
sfbWidth,
scfAct);
scfAct,
dZoneQuantEnable);
if (sfbDistNew < sfbDist[sfbAct]) {
/* success, replace scf by new one */
@ -629,6 +636,7 @@ static void FDKaacEnc_assimilateMultipleScf(PSY_OUT_CHANNEL *psyOutChan,
QC_OUT_CHANNEL *qcOutChannel,
SHORT *quantSpec,
SHORT *quantSpecTmp,
INT dZoneQuantEnable,
INT *scf,
INT *minScf,
FIXP_DBL *sfbDist,
@ -724,7 +732,8 @@ static void FDKaacEnc_assimilateMultipleScf(PSY_OUT_CHANNEL *psyOutChan,
sfbDistNew[sfb] = FDKaacEnc_calcSfbDist(qcOutChannel->mdctSpectrum+sfbOffs,
quantSpecTmp+sfbOffs,
sfbWidth,
scfAct);
scfAct,
dZoneQuantEnable);
if (sfbDistNew[sfb] >qcOutChannel->sfbThresholdLdData[sfb]) {
/* no improvement, skip further dist. calculations */
@ -768,6 +777,7 @@ static void FDKaacEnc_FDKaacEnc_assimilateMultipleScf2(PSY_OUT_CHANNEL *psyOutCh
QC_OUT_CHANNEL *qcOutChannel,
SHORT *quantSpec,
SHORT *quantSpecTmp,
INT dZoneQuantEnable,
INT *scf,
INT *minScf,
FIXP_DBL *sfbDist,
@ -883,7 +893,8 @@ static void FDKaacEnc_FDKaacEnc_assimilateMultipleScf2(PSY_OUT_CHANNEL *psyOutCh
sfbDistNew[sfb] = FDKaacEnc_calcSfbDist(qcOutChannel->mdctSpectrum+sfbOffs[sfb],
quantSpecTmp+sfbOffs[sfb],
sfbOffs[sfb+1]-sfbOffs[sfb],
scfNew);
scfNew,
dZoneQuantEnable);
if (sfbDistNew[sfb] > sfbDistMax[sfb]) {
/* no improvement, skip further dist. calculations */
@ -963,7 +974,8 @@ static void FDKaacEnc_FDKaacEnc_assimilateMultipleScf2(PSY_OUT_CHANNEL *psyOutCh
sfbDistNew[sfb] = FDKaacEnc_calcSfbDist(qcOutChannel->mdctSpectrum+sfbOffs[sfb],
quantSpecTmp+sfbOffs[sfb],
sfbOffs[sfb+1]-sfbOffs[sfb],
scfNew);
scfNew,
dZoneQuantEnable);
if (sfbDistNew[sfb] > qcOutChannel->sfbThresholdLdData[sfb]) {
/* no improvement, skip further dist. calculations */
@ -1058,7 +1070,8 @@ FDKaacEnc_FDKaacEnc_EstimateScaleFactorsChannel(QC_OUT_CHANNEL *qcOutChannel,
INT *RESTRICT globalGain,
FIXP_DBL *RESTRICT sfbFormFactorLdData
,const INT invQuant,
SHORT *RESTRICT quantSpec
SHORT *RESTRICT quantSpec,
const INT dZoneQuantEnable
)
{
INT i, j, sfb, sfbOffs;
@ -1160,7 +1173,8 @@ FDKaacEnc_FDKaacEnc_EstimateScaleFactorsChannel(QC_OUT_CHANNEL *qcOutChannel,
quantSpecTmp+psyOutChannel->sfbOffsets[sfbOffs+sfb],
psyOutChannel->sfbOffsets[sfbOffs+sfb+1]-psyOutChannel->sfbOffsets[sfbOffs+sfb],
threshLdData, scfInt, minSfMaxQuant[sfbOffs+sfb],
&sfbDistLdData[sfbOffs+sfb], &minScfCalculated[sfbOffs+sfb]
&sfbDistLdData[sfbOffs+sfb], &minScfCalculated[sfbOffs+sfb],
dZoneQuantEnable
);
}
scf[sfbOffs+sfb] = scfInt;
@ -1187,20 +1201,32 @@ FDKaacEnc_FDKaacEnc_EstimateScaleFactorsChannel(QC_OUT_CHANNEL *qcOutChannel,
sfbNRelevantLines);
FDKaacEnc_assimilateSingleScf(psyOutChannel, qcOutChannel, quantSpec, quantSpecTmp, scf,
FDKaacEnc_assimilateSingleScf(psyOutChannel, qcOutChannel, quantSpec, quantSpecTmp,
dZoneQuantEnable,
scf,
minSfMaxQuant, sfbDistLdData, sfbConstPePart,
sfbFormFactorLdData, sfbNRelevantLines, minScfCalculated, 1);
if(invQuant > 1) {
FDKaacEnc_assimilateMultipleScf(psyOutChannel, qcOutChannel, quantSpec, quantSpecTmp,
dZoneQuantEnable,
scf,
minSfMaxQuant, sfbDistLdData, sfbConstPePart,
sfbFormFactorLdData, sfbNRelevantLines);
FDKaacEnc_assimilateMultipleScf(psyOutChannel, qcOutChannel, quantSpec, quantSpecTmp, scf,
minSfMaxQuant, sfbDistLdData, sfbConstPePart,
sfbFormFactorLdData, sfbNRelevantLines);
FDKaacEnc_assimilateMultipleScf(psyOutChannel, qcOutChannel, quantSpec, quantSpecTmp,
dZoneQuantEnable,
scf,
minSfMaxQuant, sfbDistLdData, sfbConstPePart,
sfbFormFactorLdData, sfbNRelevantLines);
FDKaacEnc_FDKaacEnc_assimilateMultipleScf2(psyOutChannel, qcOutChannel, quantSpec, quantSpecTmp, scf,
minSfMaxQuant, sfbDistLdData, sfbConstPePart,
sfbFormFactorLdData, sfbNRelevantLines);
FDKaacEnc_FDKaacEnc_assimilateMultipleScf2(psyOutChannel, qcOutChannel, quantSpec, quantSpecTmp,
dZoneQuantEnable,
scf,
minSfMaxQuant, sfbDistLdData, sfbConstPePart,
sfbFormFactorLdData, sfbNRelevantLines);
}
}
@ -1223,7 +1249,8 @@ FDKaacEnc_FDKaacEnc_EstimateScaleFactorsChannel(QC_OUT_CHANNEL *qcOutChannel,
FDKaacEnc_calcSfbDist(qcOutChannel->mdctSpectrum+psyOutChannel->sfbOffsets[sfbOffs+sfb],
quantSpec+psyOutChannel->sfbOffsets[sfbOffs+sfb],
psyOutChannel->sfbOffsets[sfbOffs+sfb+1]-psyOutChannel->sfbOffsets[sfbOffs+sfb],
scf[sfbOffs+sfb]
scf[sfbOffs+sfb],
dZoneQuantEnable
);
}
}
@ -1281,6 +1308,7 @@ void
FDKaacEnc_EstimateScaleFactors(PSY_OUT_CHANNEL *psyOutChannel[],
QC_OUT_CHANNEL* qcOutChannel[],
const int invQuant,
const INT dZoneQuantEnable,
const int nChannels)
{
int ch;
@ -1293,7 +1321,8 @@ FDKaacEnc_EstimateScaleFactors(PSY_OUT_CHANNEL *psyOutChannel[],
&qcOutChannel[ch]->globalGain,
qcOutChannel[ch]->sfbFormFactorLdData
,invQuant,
qcOutChannel[ch]->quantSpec
qcOutChannel[ch]->quantSpec,
dZoneQuantEnable
);
}

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -110,6 +110,7 @@ void
FDKaacEnc_EstimateScaleFactors(PSY_OUT_CHANNEL *psyOutChannel[],
QC_OUT_CHANNEL* qcOutChannel[],
const int invQuant,
const INT dZoneQuantEnable,
const int nChannels);

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -100,6 +100,7 @@ AAC_ENCODER_ERROR FDKaacEnc_InitTnsConfiguration(INT bitrate,
INT channels,
INT blocktype,
INT granuleLength,
INT isLowDelay,
INT ldSbrPresent,
TNS_CONFIG *tnsConfig,
PSY_CONFIGURATION *psyConfig,

View File

@ -99,7 +99,7 @@ amm-info@iis.fraunhofer.de
/* Take action against VisualStudio 2005 crosscompile problems. */
/* Use single macro (the GCC built in macro) for architecture identification independent of the particular toolchain */
#if defined(__i386__) || defined(__i486__) || defined(__i586__) || defined(__i686__) || (defined(_MSC_VER) && defined(_M_IX86)) || defined (__x86_64__)
#if defined(__i386__) || defined(__i486__) || defined(__i586__) || defined(__i686__) || (defined(_MSC_VER) && defined(_M_IX86)) || defined (__x86_64__) || (defined(_MSC_VER) && defined(_M_X64))
#define __x86__
#endif
@ -154,7 +154,6 @@ amm-info@iis.fraunhofer.de
#endif
#ifdef _M_ARM
#include "cmnintrin.h"
#include "armintr.h"
#endif
@ -198,6 +197,14 @@ amm-info@iis.fraunhofer.de
#undef POW2COEFF_16BIT
#undef LDCOEFF_16BIT
#elif defined(__aarch64__) || defined(__AARCH64EL__)
#define ARCH_PREFER_MULT_32x32
#define ARCH_PREFER_MULT_32x16
#define SINETABLE_16BIT
#define POW2COEFF_16BIT
#define LDCOEFF_16BIT
#define WINDOWTABLE_16BIT
#elif defined(__x86__) /* cppp replaced: elif */
#define ARCH_PREFER_MULT_32x16
#define SINETABLE_16BIT
@ -215,7 +222,7 @@ amm-info@iis.fraunhofer.de
#else
#error >>>> Please set architecture characterization defines for your platform (FDK_HIGH_PERFORMANCE)! <<<<
#warning >>>> Please set architecture characterization defines for your platform (FDK_HIGH_PERFORMANCE)! <<<<
#endif /* Architecture switches */

View File

@ -81,13 +81,42 @@ www.iis.fraunhofer.de/amm
amm-info@iis.fraunhofer.de
----------------------------------------------------------------------------------------------------------- */
/*************************** MPEG AAC Audio Encoder *************************
/*************************** Fraunhofer IIS FDK Tools **********************
Initial author: R. Boehm
contents/description: huffman codeword reordering
based on source from aacErrRobTrans
Author(s):
Description: fixed point intrinsics
******************************************************************************/
#include "aacenc_hcr.h"
#if defined(__aarch64__) || defined(__AARCH64EL__)
#if defined(__GNUC__)
/* aarch64 gcc*/
#define FUNCTION_fixnormz_D
#define FUNCTION_fixnorm_D
inline INT fixnormz_D(LONG value)
{
INT result;
asm("clz %w0, %w1 ": "=r"(result) : "r"(value) );
return result;
}
inline INT fixnorm_D(LONG value)
{
INT result;
if (value == 0) {
return 0;
}
if (value < 0) {
value = ~value;
}
result = fixnormz_D(value);
return result - 1;
}
#endif /* aarch64 toolchain */
#endif /* __aarch64__ */

View File

@ -81,16 +81,33 @@ www.iis.fraunhofer.de/amm
amm-info@iis.fraunhofer.de
----------------------------------------------------------------------------------------------------------- */
/*************************** MPEG AAC Audio Encoder *************************
/*************************** Fraunhofer IIS FDK Tools **********************
Initial author: R. Boehm
contents/description: huffman codeword reordering
based on source from aacErrRobTrans
Author(s):
Description: fixed point intrinsics
******************************************************************************/
#ifndef _AACENC_HCR
#define _AACENC_HCR_H
#if defined(__aarch64__) || defined(__AARCH64EL__)
#if defined(__GNUC__) /* cppp replaced: elif */
/* ARM with GNU compiler */
#define FUNCTION_fixmuldiv2_DD
#define FUNCTION_fixmuldiv2BitExact_DD
#define fixmuldiv2BitExact_DD(a,b) fixmuldiv2_DD(a,b)
#define FUNCTION_fixmulBitExact_DD
#define fixmulBitExact_DD(a,b) fixmul_DD(a,b)
inline INT fixmuldiv2_DD (const INT a, const INT b)
{
INT result ;
result = ((long long)a * b)>>32;
return result ;
}
#endif /* defined(__GNUC__) */
#endif /* __aarch64__ */
#endif /* ifndef _AACENC_HCR */

View File

@ -97,6 +97,9 @@ amm-info@iis.fraunhofer.de
#if defined(__arm__)
#include "arm/clz_arm.h"
#elif defined(__aarch64__) || defined(__AARCH64EL__)
#include "aarch64/clz_aarch64.h"
#elif defined(__mips__) /* cppp replaced: elif */
#include "mips/clz_mips.h"

View File

@ -96,7 +96,7 @@ amm-info@iis.fraunhofer.de
#if defined(__CC_ARM) || defined(__arm__) || defined(_M_ARM) /* cppp replaced: elif */
#include "arm/cplx_mul.h"
#elif defined(__GNUC__) && defined(__mips__) /* cppp replaced: elif */
#elif defined(__GNUC__) && defined(__mips__) && __mips_isa_rev < 6
#include "mips/cplx_mul.h"
#endif /* #if defined all cores: bfin, arm, etc. */

View File

@ -121,7 +121,7 @@ void ifft(int length, FIXP_DBL *pInput, INT *scalefactor);
*/
LNK_SECTION_CODE_L1
static void FORCEINLINE fft_4(FIXP_DBL *x)
static FORCEINLINE void fft_4(FIXP_DBL *x)
{
FIXP_DBL a00, a10, a20, a30, tmp0, tmp1;
@ -149,7 +149,7 @@ static void FORCEINLINE fft_4(FIXP_DBL *x)
}
LNK_SECTION_CODE_L1
static void FORCEINLINE fft_8(FIXP_DBL *x)
static FORCEINLINE void fft_8(FIXP_DBL *x)
{
#define W_PiFOURTH STC(0x5a82799a)

View File

@ -98,6 +98,9 @@ amm-info@iis.fraunhofer.de
#if defined(__arm__)
#include "arm/fixmul_arm.h"
#elif defined(__aarch64__) || defined(__AARCH64EL__)
#include "aarch64/fixmul_aarch64.h"
#elif defined(__mips__) /* cppp replaced: elif */
#include "mips/fixmul_mips.h"

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -94,6 +94,35 @@ amm-info@iis.fraunhofer.de
#include "common_fix.h"
#if !defined(FUNCTION_fIsLessThan)
/**
* \brief Compares two fixpoint values incl. scaling.
* \param a_m mantissa of the first input value.
* \param a_e exponent of the first input value.
* \param b_m mantissa of the second input value.
* \param b_e exponent of the second input value.
* \return non-zero if (a_m*2^a_e) < (b_m*2^b_e), 0 otherwise
*/
FDK_INLINE INT fIsLessThan(FIXP_DBL a_m, INT a_e, FIXP_DBL b_m, INT b_e)
{
if (a_e > b_e) {
return (b_m >> fMin(a_e-b_e, DFRACT_BITS-1) > a_m);
} else {
return (a_m >> fMin(b_e-a_e, DFRACT_BITS-1) < b_m);
}
}
FDK_INLINE INT fIsLessThan(FIXP_SGL a_m, INT a_e, FIXP_SGL b_m, INT b_e)
{
if (a_e > b_e) {
return (b_m >> fMin(a_e-b_e, FRACT_BITS-1) > a_m);
} else {
return (a_m >> fMin(b_e-a_e, FRACT_BITS-1) < b_m);
}
}
#endif
#define LD_DATA_SCALING (64.0f)
#define LD_DATA_SHIFT 6 /* pow(2, LD_DATA_SHIFT) = LD_DATA_SCALING */
@ -438,11 +467,11 @@ inline FIXP_DBL fAddSaturate(const FIXP_DBL a, const FIXP_DBL b)
/*****************************************************************************
array for 1/n, n=1..50
array for 1/n, n=1..80
****************************************************************************/
extern const FIXP_DBL invCount[50];
extern const FIXP_DBL invCount[80];
LNK_SECTION_INITCODE
inline void InitInvInt(void) {}
@ -450,14 +479,14 @@ inline FIXP_DBL fAddSaturate(const FIXP_DBL a, const FIXP_DBL b)
/**
* \brief Calculate the value of 1/i where i is a integer value. It supports
* input values from 1 upto 50.
* input values from 1 upto 80.
* \param intValue Integer input value.
* \param FIXP_DBL representation of 1/intValue
*/
inline FIXP_DBL GetInvInt(int intValue)
{
FDK_ASSERT((intValue > 0) && (intValue < 50));
FDK_ASSERT(intValue<50);
FDK_ASSERT((intValue > 0) && (intValue < 80));
FDK_ASSERT(intValue<80);
return invCount[intValue];
}

View File

@ -107,24 +107,8 @@ inline void cplxMultDiv2( FIXP_DBL *c_Re,
FIXP_DBL b_Re,
FIXP_DBL b_Im)
{
INT result;
__asm__ ("mult %[a_Re], %[b_Re];\n"
"msub %[a_Im], %[b_Im];\n"
"mfhi %[result];\n"
: [result]"=r"(result)
: [a_Re]"d"(a_Re), [b_Re]"d"(b_Re), [a_Im]"d"(a_Im), [b_Im]"d"(b_Im)
: "lo");
*c_Re = result;
__asm__ ("mult %[a_Re], %[b_Im];\n"
"madd %[a_Im], %[b_Re];\n"
"mfhi %[result];\n"
: [result]"=r"(result)
: [a_Re]"r"(a_Re), [b_Im]"r"(b_Im), [a_Im]"r"(a_Im), [b_Re]"r"(b_Re)
: "lo");
*c_Im = result;
*c_Re = (((long long)a_Re * (long long)b_Re) - ((long long)a_Im * (long long)b_Im))>>32;
*c_Im = (((long long)a_Re * (long long)b_Im) + ((long long)a_Im * (long long)b_Re))>>32;
}
#endif
@ -136,25 +120,8 @@ inline void cplxMult( FIXP_DBL *c_Re,
FIXP_DBL b_Re,
FIXP_DBL b_Im)
{
INT result;
__asm__ ("mult %[a_Re], %[b_Re];\n"
"msub %[a_Im], %[b_Im];\n"
"mfhi %[result];\n"
//"extr_w %[result], 31;\n"
: [result]"=r"(result)
: [a_Re]"r"(a_Re), [b_Re]"r"(b_Re), [a_Im]"r"(a_Im), [b_Im]"r"(b_Im)
: "lo");
*c_Re = result<<1;
__asm__ ("mult %[a_Re], %[b_Im];\n"
"madd %[a_Im], %[b_Re];\n"
"mfhi %[result];\n"
//"extr_w %[result], 31;\n"
: [result]"=r"(result)
: [a_Re]"r"(a_Re), [b_Im]"r"(b_Im), [a_Im]"r"(a_Im), [b_Re]"r"(b_Re)
: "lo");
*c_Im = result<<1;
*c_Re = ((((long long)a_Re * (long long)b_Re) - ((long long)a_Im * (long long)b_Im))>>32)<<1;
*c_Im = ((((long long)a_Re * (long long)b_Im) + ((long long)a_Im * (long long)b_Re))>>32)<<1;
}
#endif

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -93,10 +93,15 @@ amm-info@iis.fraunhofer.de
/* FDK tools library info */
#define FDK_TOOLS_LIB_VL0 2
#define FDK_TOOLS_LIB_VL1 3
#define FDK_TOOLS_LIB_VL2 2
#define FDK_TOOLS_LIB_VL2 6
#define FDK_TOOLS_LIB_TITLE "FDK Tools"
#ifdef __ANDROID__
#define FDK_TOOLS_LIB_BUILD_DATE ""
#define FDK_TOOLS_LIB_BUILD_TIME ""
#else
#define FDK_TOOLS_LIB_BUILD_DATE __DATE__
#define FDK_TOOLS_LIB_BUILD_TIME __TIME__
#endif
int FDK_toolsGetLibInfo(LIB_INFO *info)
{

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -1260,9 +1260,9 @@ const FIXP_WTP * FDKgetWindowSlope(int length, int shape)
#define QTCFL(x) FL2FXCONST_SGL(x)
#define QTC(x) FX_DBL2FXCONST_SGL(x)
#else
#define QFC(x) (x)
#define QFC(x) ((FIXP_DBL)(x))
#define QTCFL(x) FL2FXCONST_DBL(x)
#define QTC(x) (x)
#define QTC(x) ((FIXP_DBL)(x))
#endif /* ARCH_PREFER_MULT_32x16 */
#ifndef LOW_POWER_SBR_ONLY
@ -1902,7 +1902,7 @@ const USHORT sqrt_tab[49]={
0xb504};
LNK_SECTION_CONSTDATA_L1
const FIXP_DBL invCount[50]= /* This could be 16-bit wide */
const FIXP_DBL invCount[80]= /* This could be 16-bit wide */
{
0x00000000, 0x7fffffff, 0x40000000, 0x2aaaaaab, 0x20000000,
0x1999999a, 0x15555555, 0x12492492, 0x10000000, 0x0e38e38e,
@ -1913,7 +1913,13 @@ const FIXP_DBL invCount[50]= /* This could be 16-bit wide */
0x04444444, 0x04210842, 0x04000000, 0x03e0f83e, 0x03c3c3c4,
0x03a83a84, 0x038e38e4, 0x03759f23, 0x035e50d8, 0x03483483,
0x03333333, 0x031f3832, 0x030c30c3, 0x02fa0be8, 0x02e8ba2f,
0x02d82d83, 0x02c8590b, 0x02b93105, 0x02aaaaab, 0x029cbc15
0x02d82d83, 0x02c8590b, 0x02b93105, 0x02aaaaab, 0x029cbc15,
0x028f5c29, 0x02828283, 0x02762762, 0x026a439f, 0x025ed098,
0x0253c825, 0x02492492, 0x023ee090, 0x0234f72c, 0x022b63cc,
0x02222222, 0x02192e2a, 0x02108421, 0x02082082, 0x02000000,
0x01f81f82, 0x01f07c1f, 0x01e9131b, 0x01e1e1e2, 0x01dae607,
0x01d41d42, 0x01cd8569, 0x01c71c72, 0x01c0e070, 0x01bacf91,
0x01b4e81b, 0x01af286c, 0x01a98ef6, 0x01a41a42, 0x019ec8e9
};
@ -2033,19 +2039,6 @@ static const element_list_t node_aac_cpe = {
{ &node_aac_cpe0, &node_aac_cpe1 }
};
#define el_mpegsres_sce &el_aac_sce[2]
static const element_list_t node_mpegsres_sce = {
el_mpegsres_sce,
{ NULL, NULL }
};
static const element_list_t node_mpegsres_cpe = {
el_aac_cpe1,
{ NULL, NULL }
};
/*
* AOT C- {17,23}
* epConfig = 0,1
@ -2243,7 +2236,7 @@ static const rbd_id_t el_aac_cpe1_epc1[] = {
ics_info,
ms,
ltp_data_present,
ltp_data,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
@ -2254,7 +2247,7 @@ static const rbd_id_t el_aac_cpe1_epc1[] = {
next_channel,
ltp_data_present,
ltp_data,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
@ -2297,7 +2290,178 @@ static const element_list_t node_aac_cpe_epc1 = {
{ &node_aac_cpe0_epc1, &node_aac_cpe1_epc1 }
};
/*
* AOT = 20
* epConfig = 0
*/
static const rbd_id_t el_scal_sce_epc0[] = {
ics_info, /* ESC 1 */
tns_data_present,
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
esc2_rvlc, /* ESC 2 */
tns_data, /* ESC 3 */
spectral_data, /* ESC 4 */
end_of_sequence
};
static const struct element_list node_scal_sce_epc0 = {
el_scal_sce_epc0,
{ NULL, NULL }
};
static const rbd_id_t el_scal_cpe_epc0[] = {
ics_info, /* ESC 0 */
ms,
tns_data_present, /* ESC 1 (ch 0) */
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
esc2_rvlc, /* ESC 2 (ch 0) */
tns_data, /* ESC 3 (ch 0) */
spectral_data, /* ESC 4 (ch 0) */
next_channel,
tns_data_present, /* ESC 1 (ch 1) */
ltp_data_present,
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
esc2_rvlc, /* ESC 2 (ch 1) */
tns_data, /* ESC 3 (ch 1) */
spectral_data, /* ESC 4 (ch 1) */
end_of_sequence
};
static const struct element_list node_scal_cpe_epc0 = {
el_scal_cpe_epc0,
{ NULL, NULL }
};
/*
* AOT = 20
* epConfig = 1
*/
static const rbd_id_t el_scal_sce_epc1[] = {
ics_info,
tns_data_present,
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
tns_data,
spectral_data,
end_of_sequence
};
static const struct element_list node_scal_sce_epc1 = {
el_scal_sce_epc1,
{ NULL, NULL }
};
static const rbd_id_t el_scal_cpe_epc1[] = {
ics_info,
ms,
tns_data_present,
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
next_channel,
tns_data_present,
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
next_channel,
tns_data,
next_channel,
tns_data,
next_channel,
spectral_data,
next_channel,
spectral_data,
end_of_sequence
};
static const struct element_list node_scal_cpe_epc1 = {
el_scal_cpe_epc1,
{ NULL, NULL }
};
/*
* Pseudo AOT for DRM/DRM+ (similar to AOT 20)
* Derived from epConfig = 1
*/
static const rbd_id_t el_drm_sce[] = {
drmcrc_start_reg,
ics_info,
tns_data_present,
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
tns_data,
drmcrc_end_reg,
spectral_data,
end_of_sequence
};
static const struct element_list node_drm_sce = {
el_drm_sce,
{ NULL, NULL }
};
static const rbd_id_t el_drm_cpe[] = {
drmcrc_start_reg,
ics_info,
ms,
tns_data_present,
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
next_channel,
tns_data_present,
ltp_data_present,
/* ltp_data, */
global_gain,
section_data,
scale_factor_data,
esc1_hcr,
next_channel,
tns_data,
next_channel,
tns_data,
drmcrc_end_reg,
next_channel,
spectral_data,
next_channel,
spectral_data,
end_of_sequence
};
static const struct element_list node_drm_cpe = {
el_drm_cpe,
{ NULL, NULL }
};
/*
* AOT = 39
@ -2412,6 +2576,19 @@ const element_list_t * getBitstreamElementList(AUDIO_OBJECT_TYPE aot, SCHAR epCo
return &node_aac_cpe_epc1;
}
break;
case AOT_ER_AAC_SCAL:
if (nChannels == 1) {
if (epConfig <= 0)
return &node_scal_sce_epc0;
else
return &node_scal_sce_epc1;
} else {
if (epConfig <= 0)
return &node_scal_cpe_epc0;
else
return &node_scal_cpe_epc1;
}
break;
case AOT_ER_AAC_ELD:
if (nChannels == 1) {
if (epConfig <= 0)
@ -2424,11 +2601,14 @@ const element_list_t * getBitstreamElementList(AUDIO_OBJECT_TYPE aot, SCHAR epCo
else
return &node_eld_cpe_epc1;
}
case AOT_MPEGS_RESIDUALS:
case AOT_DRM_AAC:
case AOT_DRM_SBR:
case AOT_DRM_MPEG_PS:
FDK_ASSERT(epConfig == 1);
if (nChannels == 1) {
return &node_mpegsres_sce;
return &node_drm_sce;
} else {
return &node_mpegsres_cpe;
return &node_drm_cpe;
}
break;
default:

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -482,42 +482,42 @@ static void qmfSynPrototypeFirSlot1_filter(FIXP_QMF *RESTRICT realSlot,
B = p_flt[4]; /* Bottom=[8] Top=[9] */
A = p_fltm[3]; /* Bottom=[316] Top=[317] */
sta0 = sta[0]; /* save state[0] */
*sta++ = SMLAWT( sta[1], imag, B ); /* index=9...........319 */
*sta++ = SMLAWB( sta[1], real, A ); /* index=316...........6 */
*sta++ = SMLAWB( sta[1], imag, B ); /* index=8,18, ...318 */
sta[0] = SMLAWT( sta[1], imag, B ); sta++; /* index=9...........319 */
sta[0] = SMLAWB( sta[1], real, A ); sta++; /* index=316...........6 */
sta[0] = SMLAWB( sta[1], imag, B ); sta++; /* index=8,18, ...318 */
B = p_flt[3]; /* Bottom=[6] Top=[7] */
*sta++ = SMLAWT( sta[1], real, A ); /* index=317...........7 */
sta[0] = SMLAWT( sta[1], real, A ); sta++; /* index=317...........7 */
A = p_fltm[4]; /* Bottom=[318] Top=[319] */
*sta++ = SMLAWT( sta[1], imag, B ); /* index=7...........317 */
*sta++ = SMLAWB( sta[1], real, A ); /* index=318...........8 */
*sta++ = SMLAWB( sta[1], imag, B ); /* index=6...........316 */
sta[0] = SMLAWT( sta[1], imag, B ); sta++; /* index=7...........317 */
sta[0] = SMLAWB( sta[1], real, A ); sta++; /* index=318...........8 */
sta[0] = SMLAWB( sta[1], imag, B ); sta++; /* index=6...........316 */
B = p_flt[2]; /* Bottom=[X] Top=[5] */
*sta++ = SMLAWT( sta[1], real, A ); /* index=9...........319 */
sta[0] = SMLAWT( sta[1], real, A ); sta++; /* index=9...........319 */
A = p_fltm[2]; /* Bottom=[X] Top=[315] */
*sta++ = SMULWT( imag, B ); /* index=5,15, ... 315 */
sta[0] = SMULWT( imag, B ); sta++; /* index=5,15, ... 315 */
result = SMLAWT( sta0, real, A ); /* index=315...........5 */
*pMyTimeOut++ = result;
pMyTimeOut[0] = result; pMyTimeOut++;
real = *--realSlot;
imag = *--imagSlot;
A = p_fltm[0]; /* Bottom=[310] Top=[311] */
B = p_flt[7]; /* Bottom=[14] Top=[15] */
result = SMLAWB( sta[0], real, A ); /* index=310...........0 */
*sta++ = SMLAWB( sta[1], imag, B ); /* index=14..........324 */
*pMyTimeOut++ = result;
sta[0] = SMLAWB( sta[1], imag, B ); sta++; /* index=14..........324 */
pMyTimeOut[0] = result; pMyTimeOut++;
B = p_flt[6]; /* Bottom=[12] Top=[13] */
*sta++ = SMLAWT( sta[1], real, A ); /* index=311...........1 */
sta[0] = SMLAWT( sta[1], real, A ); sta++; /* index=311...........1 */
A = p_fltm[1]; /* Bottom=[312] Top=[313] */
*sta++ = SMLAWT( sta[1], imag, B ); /* index=13..........323 */
*sta++ = SMLAWB( sta[1], real, A ); /* index=312...........2 */
*sta++ = SMLAWB( sta[1], imag, B ); /* index=12..........322 */
*sta++ = SMLAWT( sta[1], real, A ); /* index=313...........3 */
sta[0] = SMLAWT( sta[1], imag, B ); sta++; /* index=13..........323 */
sta[0] = SMLAWB( sta[1], real, A ); sta++; /* index=312...........2 */
sta[0] = SMLAWB( sta[1], imag, B ); sta++; /* index=12..........322 */
sta[0] = SMLAWT( sta[1], real, A ); sta++; /* index=313...........3 */
A = p_fltm[2]; /* Bottom=[314] Top=[315] */
B = p_flt[5]; /* Bottom=[10] Top=[11] */
*sta++ = SMLAWT( sta[1], imag, B ); /* index=11..........321 */
*sta++ = SMLAWB( sta[1], real, A ); /* index=314...........4 */
*sta++ = SMULWB( imag, B ); /* index=10..........320 */
sta[0] = SMLAWT( sta[1], imag, B ); sta++; /* index=11..........321 */
sta[0] = SMLAWB( sta[1], real, A ); sta++; /* index=314...........4 */
sta[0] = SMULWB( imag, B ); sta++; /* index=10..........320 */
p_flt += 5;
@ -566,21 +566,21 @@ INT qmfSynPrototypeFirSlot2(
A = p_fltm[0]; /* Bottom=[310] Top=[311] */
B = p_flt[7]; /* Bottom=[14] Top=[15] */
result = SMLAWB( sta[0], real, A ); /* index=310...........0 */
*sta++ = SMLAWB( sta[1], imag, B ); /* index=14..........324 */
sta[0] = SMLAWB( sta[1], imag, B ); sta++; /* index=14..........324 */
B = p_flt[6]; /* Bottom=[12] Top=[13] */
*sta++ = SMLAWT( sta[1], real, A ); /* index=311...........1 */
sta[0] = SMLAWT( sta[1], real, A ); sta++; /* index=311...........1 */
A = p_fltm[1]; /* Bottom=[312] Top=[313] */
*sta++ = SMLAWT( sta[1], imag, B ); /* index=13..........323 */
*sta++ = SMLAWB( sta[1], real, A ); /* index=312...........2 */
*sta++ = SMLAWB( sta[1], imag, B ); /* index=12..........322 */
*sta++ = SMLAWT( sta[1], real, A ); /* index=313...........3 */
sta[0] = SMLAWT( sta[1], imag, B ); sta++; /* index=13..........323 */
sta[0] = SMLAWB( sta[1], real, A ); sta++; /* index=312...........2 */
sta[0] = SMLAWB( sta[1], imag, B ); sta++; /* index=12..........322 */
sta[0] = SMLAWT( sta[1], real, A ); sta++; /* index=313...........3 */
A = p_fltm[2]; /* Bottom=[314] Top=[315] */
B = p_flt[5]; /* Bottom=[10] Top=[11] */
*sta++ = SMLAWT( sta[1], imag, B ); /* index=11..........321 */
*sta++ = SMLAWB( sta[1], real, A ); /* index=314...........4 */
*sta++ = SMULWB( imag, B ); /* index=10..........320 */
sta[0] = SMLAWT( sta[1], imag, B ); sta++; /* index=11..........321 */
sta[0] = SMLAWB( sta[1], real, A ); sta++; /* index=314...........4 */
sta[0] = SMULWB( imag, B ); sta++; /* index=10..........320 */
*pMyTimeOut++ = result;
pMyTimeOut[0] = result; pMyTimeOut++;
p_fltm -= 5;
p_flt += 5;
@ -610,8 +610,8 @@ INT qmfSynPrototypeFirSlot2(
{
FIXP_DBL result1, result2;
result1 = *pMyTimeOut++;
result2 = *pMyTimeOut++;
result1 = pMyTimeOut[0]; pMyTimeOut++;
result2 = pMyTimeOut[0]; pMyTimeOut++;
result1 = fMult(result1,gain);
timeOut -= stride;
@ -635,8 +635,8 @@ INT qmfSynPrototypeFirSlot2(
timeOut[0] = result2 << scale;
#endif
result1 = *pMyTimeOut++;
result2 = *pMyTimeOut++;
result1 = pMyTimeOut[0]; pMyTimeOut++;
result2 = pMyTimeOut[0]; pMyTimeOut++;
result1 = fMult(result1,gain);
timeOut -= stride;
@ -666,8 +666,8 @@ INT qmfSynPrototypeFirSlot2(
for (no_channels>>=2; no_channels--;)
{
FIXP_DBL result1, result2;
result1 = *pMyTimeOut++;
result2 = *pMyTimeOut++;
result1 = pMyTimeOut[0]; pMyTimeOut++;
result2 = pMyTimeOut[0]; pMyTimeOut++;
timeOut -= stride;
if (result1 < 0) result1 += add_neg;
if (result1 < max_neg) result1 = max_neg;
@ -688,8 +688,8 @@ INT qmfSynPrototypeFirSlot2(
timeOut[0] = result2 << scale;
#endif
result1 = *pMyTimeOut++;
result2 = *pMyTimeOut++;
result1 = pMyTimeOut[0]; pMyTimeOut++;
result2 = pMyTimeOut[0]; pMyTimeOut++;
timeOut -= stride;
if (result1 < 0) result1 += add_neg;
if (result1 < max_neg) result1 = max_neg;

View File

@ -324,12 +324,12 @@ void dct_IV(FIXP_DBL *pDat,
{
FIXP_DBL *RESTRICT pDat_0 = &pDat[0];
FIXP_DBL *RESTRICT pDat_1 = &pDat[L - 2];
register int i;
int i;
/* 29 cycles on ARM926 */
for (i = 0; i < M-1; i+=2,pDat_0+=2,pDat_1-=2)
{
register FIXP_DBL accu1,accu2,accu3,accu4;
FIXP_DBL accu1,accu2,accu3,accu4;
accu1 = pDat_1[1]; accu2 = pDat_0[0];
accu3 = pDat_0[1]; accu4 = pDat_1[0];
@ -342,7 +342,7 @@ void dct_IV(FIXP_DBL *pDat,
}
if (M&1)
{
register FIXP_DBL accu1,accu2;
FIXP_DBL accu1,accu2;
accu1 = pDat_1[1]; accu2 = pDat_0[0];
@ -363,7 +363,7 @@ void dct_IV(FIXP_DBL *pDat,
{
FIXP_DBL *RESTRICT pDat_0 = &pDat[0];
FIXP_DBL *RESTRICT pDat_1 = &pDat[L - 2];
register FIXP_DBL accu1,accu2,accu3,accu4;
FIXP_DBL accu1,accu2,accu3,accu4;
int idx, i;
/* Sin and Cos values are 0.0f and 1.0f */
@ -450,12 +450,12 @@ void dst_IV(FIXP_DBL *pDat,
FIXP_DBL *RESTRICT pDat_0 = &pDat[0];
FIXP_DBL *RESTRICT pDat_1 = &pDat[L - 2];
register int i;
int i;
/* 34 cycles on ARM926 */
for (i = 0; i < M-1; i+=2,pDat_0+=2,pDat_1-=2)
{
register FIXP_DBL accu1,accu2,accu3,accu4;
FIXP_DBL accu1,accu2,accu3,accu4;
accu1 = pDat_1[1]; accu2 = -pDat_0[0];
accu3 = pDat_0[1]; accu4 = -pDat_1[0];
@ -468,7 +468,7 @@ void dst_IV(FIXP_DBL *pDat,
}
if (M&1)
{
register FIXP_DBL accu1,accu2;
FIXP_DBL accu1,accu2;
accu1 = pDat_1[1]; accu2 = -pDat_0[0];
@ -488,7 +488,7 @@ void dst_IV(FIXP_DBL *pDat,
{
FIXP_DBL *RESTRICT pDat_0;
FIXP_DBL *RESTRICT pDat_1;
register FIXP_DBL accu1,accu2,accu3,accu4;
FIXP_DBL accu1,accu2,accu3,accu4;
int idx, i;
pDat_0 = &pDat[0];

View File

@ -322,31 +322,31 @@ LNK_SECTION_CODE_L1 FIXP_DBL CalcInvLdData(FIXP_DBL x)
LNK_SECTION_CONSTDATA_L1
static const FIXP_DBL ldIntCoeff[] = {
0x80000001, 0x00000000, 0x02000000, 0x032b8034, 0x04000000, 0x04a4d3c2, 0x052b8034, 0x059d5da0,
0x06000000, 0x06570069, 0x06a4d3c2, 0x06eb3a9f, 0x072b8034, 0x0766a009, 0x079d5da0, 0x07d053f7,
0x08000000, 0x082cc7ee, 0x08570069, 0x087ef05b, 0x08a4d3c2, 0x08c8ddd4, 0x08eb3a9f, 0x090c1050,
0x092b8034, 0x0949a785, 0x0966a009, 0x0982809d, 0x099d5da0, 0x09b74949, 0x09d053f7, 0x09e88c6b,
0x0a000000, 0x0a16bad3, 0x0a2cc7ee, 0x0a423162, 0x0a570069, 0x0a6b3d79, 0x0a7ef05b, 0x0a92203d,
0x0aa4d3c2, 0x0ab7110e, 0x0ac8ddd4, 0x0ada3f60, 0x0aeb3a9f, 0x0afbd42b, 0x0b0c1050, 0x0b1bf312,
0x0b2b8034, 0x0b3abb40, 0x0b49a785, 0x0b584822, 0x0b66a009, 0x0b74b1fd, 0x0b82809d, 0x0b900e61,
0x0b9d5da0, 0x0baa708f, 0x0bb74949, 0x0bc3e9ca, 0x0bd053f7, 0x0bdc899b, 0x0be88c6b, 0x0bf45e09,
0x0c000000, 0x0c0b73cb, 0x0c16bad3, 0x0c21d671, 0x0c2cc7ee, 0x0c379085, 0x0c423162, 0x0c4caba8,
0x0c570069, 0x0c6130af, 0x0c6b3d79, 0x0c7527b9, 0x0c7ef05b, 0x0c88983f, 0x0c92203d, 0x0c9b8926,
0x0ca4d3c2, 0x0cae00d2, 0x0cb7110e, 0x0cc0052b, 0x0cc8ddd4, 0x0cd19bb0, 0x0cda3f60, 0x0ce2c97d,
0x0ceb3a9f, 0x0cf39355, 0x0cfbd42b, 0x0d03fda9, 0x0d0c1050, 0x0d140ca0, 0x0d1bf312, 0x0d23c41d,
0x0d2b8034, 0x0d3327c7, 0x0d3abb40, 0x0d423b08, 0x0d49a785, 0x0d510118, 0x0d584822, 0x0d5f7cff,
0x0d66a009, 0x0d6db197, 0x0d74b1fd, 0x0d7ba190, 0x0d82809d, 0x0d894f75, 0x0d900e61, 0x0d96bdad,
0x0d9d5da0, 0x0da3ee7f, 0x0daa708f, 0x0db0e412, 0x0db74949, 0x0dbda072, 0x0dc3e9ca, 0x0dca258e,
0x0dd053f7, 0x0dd6753e, 0x0ddc899b, 0x0de29143, 0x0de88c6b, 0x0dee7b47, 0x0df45e09, 0x0dfa34e1,
0x0e000000, 0x0e05bf94, 0x0e0b73cb, 0x0e111cd2, 0x0e16bad3, 0x0e1c4dfb, 0x0e21d671, 0x0e275460,
0x0e2cc7ee, 0x0e323143, 0x0e379085, 0x0e3ce5d8, 0x0e423162, 0x0e477346, 0x0e4caba8, 0x0e51daa8,
0x0e570069, 0x0e5c1d0b, 0x0e6130af, 0x0e663b74, 0x0e6b3d79, 0x0e7036db, 0x0e7527b9, 0x0e7a1030,
0x0e7ef05b, 0x0e83c857, 0x0e88983f, 0x0e8d602e, 0x0e92203d, 0x0e96d888, 0x0e9b8926, 0x0ea03232,
0x0ea4d3c2, 0x0ea96df0, 0x0eae00d2, 0x0eb28c7f, 0x0eb7110e, 0x0ebb8e96, 0x0ec0052b, 0x0ec474e4,
0x0ec8ddd4, 0x0ecd4012, 0x0ed19bb0, 0x0ed5f0c4, 0x0eda3f60, 0x0ede8797, 0x0ee2c97d, 0x0ee70525,
0x0eeb3a9f, 0x0eef69ff, 0x0ef39355, 0x0ef7b6b4, 0x0efbd42b, 0x0effebcd, 0x0f03fda9, 0x0f0809cf,
0x0f0c1050, 0x0f10113b, 0x0f140ca0, 0x0f18028d, 0x0f1bf312, 0x0f1fde3d, 0x0f23c41d, 0x0f27a4c0,
0x0f2b8034
(FIXP_DBL)0x80000001, (FIXP_DBL)0x00000000, (FIXP_DBL)0x02000000, (FIXP_DBL)0x032b8034, (FIXP_DBL)0x04000000, (FIXP_DBL)0x04a4d3c2, (FIXP_DBL)0x052b8034, (FIXP_DBL)0x059d5da0,
(FIXP_DBL)0x06000000, (FIXP_DBL)0x06570069, (FIXP_DBL)0x06a4d3c2, (FIXP_DBL)0x06eb3a9f, (FIXP_DBL)0x072b8034, (FIXP_DBL)0x0766a009, (FIXP_DBL)0x079d5da0, (FIXP_DBL)0x07d053f7,
(FIXP_DBL)0x08000000, (FIXP_DBL)0x082cc7ee, (FIXP_DBL)0x08570069, (FIXP_DBL)0x087ef05b, (FIXP_DBL)0x08a4d3c2, (FIXP_DBL)0x08c8ddd4, (FIXP_DBL)0x08eb3a9f, (FIXP_DBL)0x090c1050,
(FIXP_DBL)0x092b8034, (FIXP_DBL)0x0949a785, (FIXP_DBL)0x0966a009, (FIXP_DBL)0x0982809d, (FIXP_DBL)0x099d5da0, (FIXP_DBL)0x09b74949, (FIXP_DBL)0x09d053f7, (FIXP_DBL)0x09e88c6b,
(FIXP_DBL)0x0a000000, (FIXP_DBL)0x0a16bad3, (FIXP_DBL)0x0a2cc7ee, (FIXP_DBL)0x0a423162, (FIXP_DBL)0x0a570069, (FIXP_DBL)0x0a6b3d79, (FIXP_DBL)0x0a7ef05b, (FIXP_DBL)0x0a92203d,
(FIXP_DBL)0x0aa4d3c2, (FIXP_DBL)0x0ab7110e, (FIXP_DBL)0x0ac8ddd4, (FIXP_DBL)0x0ada3f60, (FIXP_DBL)0x0aeb3a9f, (FIXP_DBL)0x0afbd42b, (FIXP_DBL)0x0b0c1050, (FIXP_DBL)0x0b1bf312,
(FIXP_DBL)0x0b2b8034, (FIXP_DBL)0x0b3abb40, (FIXP_DBL)0x0b49a785, (FIXP_DBL)0x0b584822, (FIXP_DBL)0x0b66a009, (FIXP_DBL)0x0b74b1fd, (FIXP_DBL)0x0b82809d, (FIXP_DBL)0x0b900e61,
(FIXP_DBL)0x0b9d5da0, (FIXP_DBL)0x0baa708f, (FIXP_DBL)0x0bb74949, (FIXP_DBL)0x0bc3e9ca, (FIXP_DBL)0x0bd053f7, (FIXP_DBL)0x0bdc899b, (FIXP_DBL)0x0be88c6b, (FIXP_DBL)0x0bf45e09,
(FIXP_DBL)0x0c000000, (FIXP_DBL)0x0c0b73cb, (FIXP_DBL)0x0c16bad3, (FIXP_DBL)0x0c21d671, (FIXP_DBL)0x0c2cc7ee, (FIXP_DBL)0x0c379085, (FIXP_DBL)0x0c423162, (FIXP_DBL)0x0c4caba8,
(FIXP_DBL)0x0c570069, (FIXP_DBL)0x0c6130af, (FIXP_DBL)0x0c6b3d79, (FIXP_DBL)0x0c7527b9, (FIXP_DBL)0x0c7ef05b, (FIXP_DBL)0x0c88983f, (FIXP_DBL)0x0c92203d, (FIXP_DBL)0x0c9b8926,
(FIXP_DBL)0x0ca4d3c2, (FIXP_DBL)0x0cae00d2, (FIXP_DBL)0x0cb7110e, (FIXP_DBL)0x0cc0052b, (FIXP_DBL)0x0cc8ddd4, (FIXP_DBL)0x0cd19bb0, (FIXP_DBL)0x0cda3f60, (FIXP_DBL)0x0ce2c97d,
(FIXP_DBL)0x0ceb3a9f, (FIXP_DBL)0x0cf39355, (FIXP_DBL)0x0cfbd42b, (FIXP_DBL)0x0d03fda9, (FIXP_DBL)0x0d0c1050, (FIXP_DBL)0x0d140ca0, (FIXP_DBL)0x0d1bf312, (FIXP_DBL)0x0d23c41d,
(FIXP_DBL)0x0d2b8034, (FIXP_DBL)0x0d3327c7, (FIXP_DBL)0x0d3abb40, (FIXP_DBL)0x0d423b08, (FIXP_DBL)0x0d49a785, (FIXP_DBL)0x0d510118, (FIXP_DBL)0x0d584822, (FIXP_DBL)0x0d5f7cff,
(FIXP_DBL)0x0d66a009, (FIXP_DBL)0x0d6db197, (FIXP_DBL)0x0d74b1fd, (FIXP_DBL)0x0d7ba190, (FIXP_DBL)0x0d82809d, (FIXP_DBL)0x0d894f75, (FIXP_DBL)0x0d900e61, (FIXP_DBL)0x0d96bdad,
(FIXP_DBL)0x0d9d5da0, (FIXP_DBL)0x0da3ee7f, (FIXP_DBL)0x0daa708f, (FIXP_DBL)0x0db0e412, (FIXP_DBL)0x0db74949, (FIXP_DBL)0x0dbda072, (FIXP_DBL)0x0dc3e9ca, (FIXP_DBL)0x0dca258e,
(FIXP_DBL)0x0dd053f7, (FIXP_DBL)0x0dd6753e, (FIXP_DBL)0x0ddc899b, (FIXP_DBL)0x0de29143, (FIXP_DBL)0x0de88c6b, (FIXP_DBL)0x0dee7b47, (FIXP_DBL)0x0df45e09, (FIXP_DBL)0x0dfa34e1,
(FIXP_DBL)0x0e000000, (FIXP_DBL)0x0e05bf94, (FIXP_DBL)0x0e0b73cb, (FIXP_DBL)0x0e111cd2, (FIXP_DBL)0x0e16bad3, (FIXP_DBL)0x0e1c4dfb, (FIXP_DBL)0x0e21d671, (FIXP_DBL)0x0e275460,
(FIXP_DBL)0x0e2cc7ee, (FIXP_DBL)0x0e323143, (FIXP_DBL)0x0e379085, (FIXP_DBL)0x0e3ce5d8, (FIXP_DBL)0x0e423162, (FIXP_DBL)0x0e477346, (FIXP_DBL)0x0e4caba8, (FIXP_DBL)0x0e51daa8,
(FIXP_DBL)0x0e570069, (FIXP_DBL)0x0e5c1d0b, (FIXP_DBL)0x0e6130af, (FIXP_DBL)0x0e663b74, (FIXP_DBL)0x0e6b3d79, (FIXP_DBL)0x0e7036db, (FIXP_DBL)0x0e7527b9, (FIXP_DBL)0x0e7a1030,
(FIXP_DBL)0x0e7ef05b, (FIXP_DBL)0x0e83c857, (FIXP_DBL)0x0e88983f, (FIXP_DBL)0x0e8d602e, (FIXP_DBL)0x0e92203d, (FIXP_DBL)0x0e96d888, (FIXP_DBL)0x0e9b8926, (FIXP_DBL)0x0ea03232,
(FIXP_DBL)0x0ea4d3c2, (FIXP_DBL)0x0ea96df0, (FIXP_DBL)0x0eae00d2, (FIXP_DBL)0x0eb28c7f, (FIXP_DBL)0x0eb7110e, (FIXP_DBL)0x0ebb8e96, (FIXP_DBL)0x0ec0052b, (FIXP_DBL)0x0ec474e4,
(FIXP_DBL)0x0ec8ddd4, (FIXP_DBL)0x0ecd4012, (FIXP_DBL)0x0ed19bb0, (FIXP_DBL)0x0ed5f0c4, (FIXP_DBL)0x0eda3f60, (FIXP_DBL)0x0ede8797, (FIXP_DBL)0x0ee2c97d, (FIXP_DBL)0x0ee70525,
(FIXP_DBL)0x0eeb3a9f, (FIXP_DBL)0x0eef69ff, (FIXP_DBL)0x0ef39355, (FIXP_DBL)0x0ef7b6b4, (FIXP_DBL)0x0efbd42b, (FIXP_DBL)0x0effebcd, (FIXP_DBL)0x0f03fda9, (FIXP_DBL)0x0f0809cf,
(FIXP_DBL)0x0f0c1050, (FIXP_DBL)0x0f10113b, (FIXP_DBL)0x0f140ca0, (FIXP_DBL)0x0f18028d, (FIXP_DBL)0x0f1bf312, (FIXP_DBL)0x0f1fde3d, (FIXP_DBL)0x0f23c41d, (FIXP_DBL)0x0f27a4c0,
(FIXP_DBL)0x0f2b8034
};

View File

@ -146,12 +146,15 @@ typedef struct
UCHAR FrontElementIsCpe[PC_FSB_CHANNELS_MAX];
UCHAR FrontElementTagSelect[PC_FSB_CHANNELS_MAX];
UCHAR FrontElementHeightInfo[PC_FSB_CHANNELS_MAX];
UCHAR SideElementIsCpe[PC_FSB_CHANNELS_MAX];
UCHAR SideElementTagSelect[PC_FSB_CHANNELS_MAX];
UCHAR SideElementHeightInfo[PC_FSB_CHANNELS_MAX];
UCHAR BackElementIsCpe[PC_FSB_CHANNELS_MAX];
UCHAR BackElementTagSelect[PC_FSB_CHANNELS_MAX];
UCHAR BackElementHeightInfo[PC_FSB_CHANNELS_MAX];
UCHAR LfeElementTagSelect[PC_LFE_CHANNELS_MAX];
@ -324,16 +327,23 @@ int getSamplingRateIndex( UINT samplingRate )
*/
static inline int getNumberOfTotalChannels(int channelConfig)
{
if (channelConfig > 0 && channelConfig < 8)
return (channelConfig == 7)?8:channelConfig;
else
switch (channelConfig) {
case 1: case 2: case 3:
case 4: case 5: case 6:
return channelConfig;
case 7: case 12: case 14:
return 8;
case 11:
return 7;
default:
return 0;
}
}
static inline
int getNumberOfEffectiveChannels(const int channelConfig)
{
const int n[] = {0,1,2,3,4,5,5,7};
{ /* index: 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15 */
const int n[] = {0,1,2,3,4,5,5,7,0,0, 0, 6, 7, 0, 7, 0};
return n[channelConfig];
}

View File

@ -151,6 +151,7 @@ typedef enum {
#define PC_ASSOCDATA_MAX 8
#define PC_CCEL_MAX 16 /* CC elements */
#define PC_COMMENTLENGTH 256
#define PC_NUM_HEIGHT_LAYER 3
/*!
@ -239,14 +240,20 @@ int CProgramConfig_LookupElement(
);
/**
* \brief Get table of elements in canonical order.
* \param pPce A valid program config structure.
* \param table An array where the element IDs are stored.
* \return Total element count including all SCE, CPE and LFE.
* \brief Get table of elements in canonical order from a
* give program config field.
* \param pPce A valid program config structure.
* \param table An array where the element IDs are stored.
* \param elListSize The length of the table array.
* \param pChMapIdx Pointer to a field receiving the corresponding
* implicit channel configuration index of the given
* PCE. If none can be found it receives the value 0.
* \return Total element count including all SCE, CPE and LFE.
*/
int CProgramConfig_GetElementTable( const CProgramConfig *pPce,
MP4_ELEMENT_ID table[],
const INT elListSize );
const INT elListSize,
UCHAR *pChMapIdx );
/**
* \brief Initialize a given AudioSpecificConfig structure.

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -90,6 +90,9 @@ amm-info@iis.fraunhofer.de
#include "tpdec_lib.h"
#include "tp_data.h"
#ifdef TP_PCE_ENABLE
#include "FDK_crc.h"
#endif
void CProgramConfig_Reset(CProgramConfig *pPce)
@ -111,13 +114,75 @@ int CProgramConfig_IsValid ( const CProgramConfig *pPce )
}
#ifdef TP_PCE_ENABLE
#define PCE_HEIGHT_EXT_SYNC ( 0xAC )
/*
* Read the extension for height info.
* return 0 if successfull or -1 if the CRC failed.
*/
static
int CProgramConfig_ReadHeightExt(
CProgramConfig *pPce,
HANDLE_FDK_BITSTREAM bs,
int * const bytesAvailable,
const UINT alignmentAnchor
)
{
int err = 0;
FDK_CRCINFO crcInfo; /* CRC state info */
INT crcReg;
FDKcrcInit(&crcInfo, 0x07, 0xFF, 8);
crcReg = FDKcrcStartReg(&crcInfo, bs, 0);
UINT startAnchor = FDKgetValidBits(bs);
FDK_ASSERT(pPce != NULL);
FDK_ASSERT(bs != NULL);
FDK_ASSERT(bytesAvailable != NULL);
if ( (startAnchor >= 24) && (*bytesAvailable >= 3)
&& (FDKreadBits(bs,8) == PCE_HEIGHT_EXT_SYNC) )
{
int i;
for (i=0; i < pPce->NumFrontChannelElements; i++)
{
pPce->FrontElementHeightInfo[i] = (UCHAR) FDKreadBits(bs,2);
}
for (i=0; i < pPce->NumSideChannelElements; i++)
{
pPce->SideElementHeightInfo[i] = (UCHAR) FDKreadBits(bs,2);
}
for (i=0; i < pPce->NumBackChannelElements; i++)
{
pPce->BackElementHeightInfo[i] = (UCHAR) FDKreadBits(bs,2);
}
FDKbyteAlign(bs, alignmentAnchor);
FDKcrcEndReg(&crcInfo, bs, crcReg);
if ((USHORT)FDKreadBits(bs,8) != FDKcrcGetCRC(&crcInfo)) {
/* CRC failed */
err = -1;
}
}
else {
/* No valid extension data found -> restore the initial bitbuffer state */
FDKpushBack(bs, startAnchor - FDKgetValidBits(bs));
}
/* Always report the bytes read. */
*bytesAvailable -= (startAnchor - FDKgetValidBits(bs)) >> 3;
return (err);
}
void CProgramConfig_Read(
CProgramConfig *pPce,
HANDLE_FDK_BITSTREAM bs,
UINT alignmentAnchor
)
{
int i;
int i, err = 0;
int commentBytes;
pPce->NumEffectiveChannels = 0;
pPce->NumChannels = 0;
@ -190,8 +255,12 @@ void CProgramConfig_Read(
FDKbyteAlign(bs, alignmentAnchor);
pPce->CommentFieldBytes = (UCHAR) FDKreadBits(bs,8);
commentBytes = pPce->CommentFieldBytes;
for (i=0; i < pPce->CommentFieldBytes; i++)
/* Search for height info extension and read it if available */
err = CProgramConfig_ReadHeightExt( pPce, bs, &commentBytes, alignmentAnchor );
for (i=0; i < commentBytes; i++)
{
UCHAR text;
@ -203,7 +272,7 @@ void CProgramConfig_Read(
}
}
pPce->isValid = 1;
pPce->isValid = (err) ? 0 : 1;
}
/*
@ -235,6 +304,10 @@ int CProgramConfig_Compare ( const CProgramConfig * const pPce1,
} else {
int el, numCh1 = 0, numCh2 = 0;
for (el = 0; el < pPce1->NumFrontChannelElements; el += 1) {
if (pPce1->FrontElementHeightInfo[el] != pPce2->FrontElementHeightInfo[el]) {
result = 2; /* different height info */
break;
}
numCh1 += pPce1->FrontElementIsCpe[el] ? 2 : 1;
numCh2 += pPce2->FrontElementIsCpe[el] ? 2 : 1;
}
@ -248,6 +321,10 @@ int CProgramConfig_Compare ( const CProgramConfig * const pPce1,
} else {
int el, numCh1 = 0, numCh2 = 0;
for (el = 0; el < pPce1->NumSideChannelElements; el += 1) {
if (pPce1->SideElementHeightInfo[el] != pPce2->SideElementHeightInfo[el]) {
result = 2; /* different height info */
break;
}
numCh1 += pPce1->SideElementIsCpe[el] ? 2 : 1;
numCh2 += pPce2->SideElementIsCpe[el] ? 2 : 1;
}
@ -261,6 +338,10 @@ int CProgramConfig_Compare ( const CProgramConfig * const pPce1,
} else {
int el, numCh1 = 0, numCh2 = 0;
for (el = 0; el < pPce1->NumBackChannelElements; el += 1) {
if (pPce1->BackElementHeightInfo[el] != pPce2->BackElementHeightInfo[el]) {
result = 2; /* different height info */
break;
}
numCh1 += pPce1->BackElementIsCpe[el] ? 2 : 1;
numCh2 += pPce2->BackElementIsCpe[el] ? 2 : 1;
}
@ -290,6 +371,44 @@ void CProgramConfig_GetDefault( CProgramConfig *pPce,
switch (channelConfig) {
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
case 32: /* 7.1 side channel configuration as defined in FDK_audio.h */
pPce->NumFrontChannelElements = 2;
pPce->FrontElementIsCpe[0] = 0;
pPce->FrontElementIsCpe[1] = 1;
pPce->NumSideChannelElements = 1;
pPce->SideElementIsCpe[0] = 1;
pPce->NumBackChannelElements = 1;
pPce->BackElementIsCpe[0] = 1;
pPce->NumLfeChannelElements = 1;
pPce->NumChannels = 8;
pPce->NumEffectiveChannels = 7;
pPce->isValid = 1;
break;
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
case 12: /* 3/0/4.1ch surround back */
pPce->BackElementIsCpe[1] = 1;
pPce->NumChannels += 1;
pPce->NumEffectiveChannels += 1;
case 11: /* 3/0/3.1ch */
pPce->NumFrontChannelElements += 2;
pPce->FrontElementIsCpe[0] = 0;
pPce->FrontElementIsCpe[1] = 1;
pPce->NumBackChannelElements += 2;
pPce->BackElementIsCpe[0] = 1;
pPce->BackElementIsCpe[1] += 0;
pPce->NumLfeChannelElements += 1;
pPce->NumChannels += 7;
pPce->NumEffectiveChannels += 6;
pPce->isValid = 1;
break;
/* - - - - - - - - - - - - - - - - - - - - - - - - - - - - */
case 14: /* 2/0/0-3/0/2-0.1ch front height */
pPce->FrontElementHeightInfo[2] = 1; /* Top speaker */
case 7: /* 5/0/2.1ch front */
pPce->NumFrontChannelElements += 1;
pPce->FrontElementIsCpe[2] = 1;
pPce->NumChannels += 2;
pPce->NumEffectiveChannels += 2;
case 6: /* 3/0/2.1ch */
pPce->NumLfeChannelElements += 1;
pPce->NumChannels += 1;
@ -330,13 +449,13 @@ void CProgramConfig_GetDefault( CProgramConfig *pPce,
int el, elTagSce = 0, elTagCpe = 0;
for (el = 0; el < pPce->NumFrontChannelElements; el += 1) {
pPce->FrontElementTagSelect[el] = (pPce->FrontElementIsCpe) ? elTagCpe++ : elTagSce++;
pPce->FrontElementTagSelect[el] = (pPce->FrontElementIsCpe[el]) ? elTagCpe++ : elTagSce++;
}
for (el = 0; el < pPce->NumSideChannelElements; el += 1) {
pPce->SideElementTagSelect[el] = (pPce->SideElementIsCpe) ? elTagCpe++ : elTagSce++;
pPce->SideElementTagSelect[el] = (pPce->SideElementIsCpe[el]) ? elTagCpe++ : elTagSce++;
}
for (el = 0; el < pPce->NumBackChannelElements; el += 1) {
pPce->BackElementTagSelect[el] = (pPce->BackElementIsCpe) ? elTagCpe++ : elTagSce++;
pPce->BackElementTagSelect[el] = (pPce->BackElementIsCpe[el]) ? elTagCpe++ : elTagSce++;
}
elTagSce = 0;
for (el = 0; el < pPce->NumLfeChannelElements; el += 1) {
@ -348,10 +467,11 @@ void CProgramConfig_GetDefault( CProgramConfig *pPce,
/**
* \brief get implicit audio channel type for given channelConfig and MPEG ordered channel index
* \param channelConfig MPEG channelConfiguration from 1 upto 7
* \param channelConfig MPEG channelConfiguration from 1 upto 14
* \param index MPEG channel order index
* \return audio channel type.
*/
static
void getImplicitAudioChannelTypeAndIndex(
AUDIO_CHANNEL_TYPE *chType,
UCHAR *chIndex,
@ -364,9 +484,9 @@ void getImplicitAudioChannelTypeAndIndex(
*chIndex = index;
} else {
switch (channelConfig) {
case MODE_1_2_1:
case MODE_1_2_2:
case MODE_1_2_2_1:
case 4: /* SCE, CPE, SCE */
case 5: /* SCE, CPE, CPE */
case 6: /* SCE, CPE, CPE, LFE */
switch (index) {
case 3:
case 4:
@ -379,12 +499,12 @@ void getImplicitAudioChannelTypeAndIndex(
break;
}
break;
case MODE_1_2_2_2_1:
case 7: /* SCE,CPE,CPE,CPE,LFE */
switch (index) {
case 3:
case 4:
*chType = ACT_SIDE;
*chIndex = index - 3;
*chType = ACT_FRONT;
*chIndex = index;
break;
case 5:
case 6:
@ -397,6 +517,42 @@ void getImplicitAudioChannelTypeAndIndex(
break;
}
break;
case 11: /* SCE,CPE,CPE,SCE,LFE */
if (index < 6) {
*chType = ACT_BACK;
*chIndex = index - 3;
} else {
*chType = ACT_LFE;
*chIndex = 0;
}
break;
case 12: /* SCE,CPE,CPE,CPE,LFE */
if (index < 7) {
*chType = ACT_BACK;
*chIndex = index - 3;
} else {
*chType = ACT_LFE;
*chIndex = 0;
}
break;
case 14: /* SCE,CPE,CPE,LFE,CPE */
switch (index) {
case 3:
case 4:
*chType = ACT_BACK;
*chIndex = index - 3;
break;
case 5:
*chType = ACT_LFE;
*chIndex = 0;
break;
case 6:
case 7:
*chType = ACT_FRONT_TOP;
*chIndex = index - 6; /* handle the top layer independently */
break;
}
break;
default:
*chType = ACT_NONE;
break;
@ -467,7 +623,24 @@ int CProgramConfig_LookupElement(
else {
/* Accept the additional channel(s), only if the tag is in the lists */
int isCpe = 0, i;
int cc = 0, fc = 0, sc = 0, bc = 0, lc = 0, ec = 0; /* Channel and element counters */
/* Element counter */
int ec[PC_NUM_HEIGHT_LAYER] = {0};
/* Channel counters */
int cc[PC_NUM_HEIGHT_LAYER] = {0};
int fc[PC_NUM_HEIGHT_LAYER] = {0};
int sc[PC_NUM_HEIGHT_LAYER] = {0};
int bc[PC_NUM_HEIGHT_LAYER] = {0};
int lc = 0;;
/* General MPEG (PCE) composition rules:
- Over all:
<normal height channels><top height channels><bottom height channels>
- Within each height layer:
<front channels><side channels><back channels>
- Exception:
The LFE channels have no height info and thus they are arranged at the very
end of the normal height layer channels.
*/
switch (elType)
{
@ -476,87 +649,206 @@ int CProgramConfig_LookupElement(
case ID_SCE:
/* search in front channels */
for (i = 0; i < pPce->NumFrontChannelElements; i++) {
int heightLayer = pPce->FrontElementHeightInfo[i];
if (isCpe == pPce->FrontElementIsCpe[i] && pPce->FrontElementTagSelect[i] == tag) {
chMapping[cc] = channelIdx;
chType[cc] = ACT_FRONT;
chIndex[cc] = fc;
if (isCpe) {
chMapping[cc+1] = channelIdx+1;
chType[cc+1] = ACT_FRONT;
chIndex[cc+1] = fc+1;
int h, elIdx = ec[heightLayer], chIdx = cc[heightLayer];
AUDIO_CHANNEL_TYPE aChType = (AUDIO_CHANNEL_TYPE)((heightLayer<<4) | ACT_FRONT);
for (h = heightLayer-1; h >= 0; h-=1) {
int el;
/* Count front channels/elements */
for (el = 0; el < pPce->NumFrontChannelElements; el+=1) {
if (pPce->FrontElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->FrontElementIsCpe[el]) ? 2 : 1;
}
}
/* Count side channels/elements */
for (el = 0; el < pPce->NumSideChannelElements; el+=1) {
if (pPce->SideElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->SideElementIsCpe[el]) ? 2 : 1;
}
}
/* Count back channels/elements */
for (el = 0; el < pPce->NumBackChannelElements; el+=1) {
if (pPce->BackElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->BackElementIsCpe[el]) ? 2 : 1;
}
}
if (h == 0) { /* normal height */
elIdx += pPce->NumLfeChannelElements;
chIdx += pPce->NumLfeChannelElements;
}
}
*elMapping = ec;
chMapping[chIdx] = channelIdx;
chType[chIdx] = aChType;
chIndex[chIdx] = fc[heightLayer];
if (isCpe) {
chMapping[chIdx+1] = channelIdx+1;
chType[chIdx+1] = aChType;
chIndex[chIdx+1] = fc[heightLayer]+1;
}
*elMapping = elIdx;
return 1;
}
ec++;
ec[heightLayer] += 1;
if (pPce->FrontElementIsCpe[i]) {
cc+=2; fc+=2;
cc[heightLayer] += 2;
fc[heightLayer] += 2;
} else {
cc++; fc++;
cc[heightLayer] += 1;
fc[heightLayer] += 1;
}
}
/* search in side channels */
for (i = 0; i < pPce->NumSideChannelElements; i++) {
int heightLayer = pPce->SideElementHeightInfo[i];
if (isCpe == pPce->SideElementIsCpe[i] && pPce->SideElementTagSelect[i] == tag) {
chMapping[cc] = channelIdx;
chType[cc] = ACT_SIDE;
chIndex[cc] = sc;
if (isCpe) {
chMapping[cc+1] = channelIdx+1;
chType[cc+1] = ACT_SIDE;
chIndex[cc+1] = sc+1;
int h, elIdx = ec[heightLayer], chIdx = cc[heightLayer];
AUDIO_CHANNEL_TYPE aChType = (AUDIO_CHANNEL_TYPE)((heightLayer<<4) | ACT_SIDE);
for (h = heightLayer-1; h >= 0; h-=1) {
int el;
/* Count front channels/elements */
for (el = 0; el < pPce->NumFrontChannelElements; el+=1) {
if (pPce->FrontElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->FrontElementIsCpe[el]) ? 2 : 1;
}
}
/* Count side channels/elements */
for (el = 0; el < pPce->NumSideChannelElements; el+=1) {
if (pPce->SideElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->SideElementIsCpe[el]) ? 2 : 1;
}
}
/* Count back channels/elements */
for (el = 0; el < pPce->NumBackChannelElements; el+=1) {
if (pPce->BackElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->BackElementIsCpe[el]) ? 2 : 1;
}
}
if (h == 0) { /* LFE channels belong to the normal height layer */
elIdx += pPce->NumLfeChannelElements;
chIdx += pPce->NumLfeChannelElements;
}
}
*elMapping = ec;
chMapping[chIdx] = channelIdx;
chType[chIdx] = aChType;
chIndex[chIdx] = sc[heightLayer];
if (isCpe) {
chMapping[chIdx+1] = channelIdx+1;
chType[chIdx+1] = aChType;
chIndex[chIdx+1] = sc[heightLayer]+1;
}
*elMapping = elIdx;
return 1;
}
ec++;
ec[heightLayer] += 1;
if (pPce->SideElementIsCpe[i]) {
cc+=2; sc+=2;
cc[heightLayer] += 2;
sc[heightLayer] += 2;
} else {
cc++; sc++;
cc[heightLayer] += 1;
sc[heightLayer] += 1;
}
}
/* search in back channels */
for (i = 0; i < pPce->NumBackChannelElements; i++) {
int heightLayer = pPce->BackElementHeightInfo[i];
if (isCpe == pPce->BackElementIsCpe[i] && pPce->BackElementTagSelect[i] == tag) {
chMapping[cc] = channelIdx;
chType[cc] = ACT_BACK;
chIndex[cc] = bc;
if (isCpe) {
chMapping[cc+1] = channelIdx+1;
chType[cc+1] = ACT_BACK;
chIndex[cc+1] = bc+1;
int h, elIdx = ec[heightLayer], chIdx = cc[heightLayer];
AUDIO_CHANNEL_TYPE aChType = (AUDIO_CHANNEL_TYPE)((heightLayer<<4) | ACT_BACK);
for (h = heightLayer-1; h >= 0; h-=1) {
int el;
/* Count front channels/elements */
for (el = 0; el < pPce->NumFrontChannelElements; el+=1) {
if (pPce->FrontElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->FrontElementIsCpe[el]) ? 2 : 1;
}
}
/* Count side channels/elements */
for (el = 0; el < pPce->NumSideChannelElements; el+=1) {
if (pPce->SideElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->SideElementIsCpe[el]) ? 2 : 1;
}
}
/* Count back channels/elements */
for (el = 0; el < pPce->NumBackChannelElements; el+=1) {
if (pPce->BackElementHeightInfo[el] == h) {
elIdx += 1;
chIdx += (pPce->BackElementIsCpe[el]) ? 2 : 1;
}
}
if (h == 0) { /* normal height */
elIdx += pPce->NumLfeChannelElements;
chIdx += pPce->NumLfeChannelElements;
}
}
*elMapping = ec;
chMapping[chIdx] = channelIdx;
chType[chIdx] = aChType;
chIndex[chIdx] = bc[heightLayer];
if (isCpe) {
chMapping[chIdx+1] = channelIdx+1;
chType[chIdx+1] = aChType;
chIndex[chIdx+1] = bc[heightLayer]+1;
}
*elMapping = elIdx;
return 1;
}
ec++;
ec[heightLayer] += 1;
if (pPce->BackElementIsCpe[i]) {
cc+=2; bc+=2;
cc[heightLayer] += 2;
bc[heightLayer] += 2;
} else {
cc++; bc++;
cc[heightLayer] += 1;
bc[heightLayer] += 1;
}
}
break;
case ID_LFE:
/* Initialize channel counter and element counter */
cc = pPce->NumEffectiveChannels;
ec = pPce->NumFrontChannelElements+ pPce->NumSideChannelElements + pPce->NumBackChannelElements;
{ /* Unfortunately we have to go through all normal height
layer elements to get the position of the LFE channels.
Start with counting the front channels/elements at normal height */
for (i = 0; i < pPce->NumFrontChannelElements; i+=1) {
int heightLayer = pPce->FrontElementHeightInfo[i];
ec[heightLayer] += 1;
cc[heightLayer] += (pPce->FrontElementIsCpe[i]) ? 2 : 1;
}
/* Count side channels/elements at normal height */
for (i = 0; i < pPce->NumSideChannelElements; i+=1) {
int heightLayer = pPce->SideElementHeightInfo[i];
ec[heightLayer] += 1;
cc[heightLayer] += (pPce->SideElementIsCpe[i]) ? 2 : 1;
}
/* Count back channels/elements at normal height */
for (i = 0; i < pPce->NumBackChannelElements; i+=1) {
int heightLayer = pPce->BackElementHeightInfo[i];
ec[heightLayer] += 1;
cc[heightLayer] += (pPce->BackElementIsCpe[i]) ? 2 : 1;
}
/* search in lfe channels */
for (i = 0; i < pPce->NumLfeChannelElements; i++) {
int elIdx = ec[0]; /* LFE channels belong to the normal height layer */
int chIdx = cc[0];
if ( pPce->LfeElementTagSelect[i] == tag ) {
chMapping[cc] = channelIdx;
*elMapping = ec;
chType[cc] = ACT_LFE;
chIndex[cc] = lc;
chMapping[chIdx] = channelIdx;
*elMapping = elIdx;
chType[chIdx] = ACT_LFE;
chIndex[chIdx] = lc;
return 1;
}
ec++;
cc++;
lc++;
ec[0] += 1;
cc[0] += 1;
lc += 1;
}
break;
} break;
/* Non audio elements */
case ID_CCE:
@ -590,13 +882,19 @@ int CProgramConfig_LookupElement(
int CProgramConfig_GetElementTable(
const CProgramConfig *pPce,
MP4_ELEMENT_ID elList[],
const INT elListSize
const INT elListSize,
UCHAR *pChMapIdx
)
{
int i, el = 0;
if ( elListSize
< pPce->NumFrontChannelElements + pPce->NumSideChannelElements + pPce->NumBackChannelElements + pPce->NumLfeChannelElements
FDK_ASSERT(elList != NULL);
FDK_ASSERT(pChMapIdx != NULL);
*pChMapIdx = 0;
if ( elListSize
< pPce->NumFrontChannelElements + pPce->NumSideChannelElements + pPce->NumBackChannelElements + pPce->NumLfeChannelElements
)
{
return 0;
@ -623,6 +921,47 @@ int CProgramConfig_GetElementTable(
}
/* Find an corresponding channel configuration if possible */
switch (pPce->NumChannels) {
case 1: case 2: case 3: case 4: case 5: case 6:
/* One and two channels have no alternatives. The other ones are mapped directly to the
corresponding channel config. Because of legacy reasons or for lack of alternative mappings. */
*pChMapIdx = pPce->NumChannels;
break;
case 7:
{
C_ALLOC_SCRATCH_START(tmpPce, CProgramConfig, 1);
/* Create a PCE for the config to test ... */
CProgramConfig_GetDefault(tmpPce, 11);
/* ... and compare it with the given one. */
*pChMapIdx = (!(CProgramConfig_Compare(pPce, tmpPce)&0xE)) ? 11 : 0;
/* If compare result is 0 or 1 we can be sure that it is channel config 11. */
C_ALLOC_SCRATCH_END(tmpPce, CProgramConfig, 1);
}
break;
case 8:
{ /* Try the four possible 7.1ch configurations. One after the other. */
UCHAR testCfg[4] = { 32, 14, 12, 7};
C_ALLOC_SCRATCH_START(tmpPce, CProgramConfig, 1);
for (i=0; i<4; i+=1) {
/* Create a PCE for the config to test ... */
CProgramConfig_GetDefault(tmpPce, testCfg[i]);
/* ... and compare it with the given one. */
if (!(CProgramConfig_Compare(pPce, tmpPce)&0xE)) {
/* If the compare result is 0 or 1 than the two channel configurations match. */
/* Explicit mapping of 7.1 side channel configuration to 7.1 rear channel mapping. */
*pChMapIdx = (testCfg[i]==32) ? 12 : testCfg[i];
}
}
C_ALLOC_SCRATCH_END(tmpPce, CProgramConfig, 1);
}
break;
default:
/* The PCE does not match any predefined channel configuration. */
*pChMapIdx = 0;
break;
}
return el;
}
#endif
@ -714,7 +1053,7 @@ TRANSPORTDEC_ERROR GaSpecificConfig_Parse( CSGaSpecificConfig *self,
#ifdef TP_ELD_ENABLE
static INT ld_sbr_header( const CSAudioSpecificConfig *asc,
HANDLE_FDK_BITSTREAM hBs,
HANDLE_FDK_BITSTREAM hBs,
CSTpCallBacks *cb )
{
const int channelConfiguration = asc->m_channelConfiguration;
@ -728,6 +1067,8 @@ static INT ld_sbr_header( const CSAudioSpecificConfig *asc,
}
switch ( channelConfiguration ) {
case 14:
case 12:
case 7:
error |= cb->cbSbr(cb->cbSbrData, hBs, asc->m_samplingFrequency, asc->m_extensionSamplingFrequency, asc->m_samplesPerFrame, AOT_ER_AAC_ELD, ID_CPE, i++);
case 6:
@ -737,6 +1078,8 @@ static INT ld_sbr_header( const CSAudioSpecificConfig *asc,
error |= cb->cbSbr(cb->cbSbrData, hBs, asc->m_samplingFrequency, asc->m_extensionSamplingFrequency, asc->m_samplesPerFrame, AOT_ER_AAC_ELD, ID_CPE, i++);
break;
case 11:
error |= cb->cbSbr(cb->cbSbrData, hBs, asc->m_samplingFrequency, asc->m_extensionSamplingFrequency, asc->m_samplesPerFrame, AOT_ER_AAC_ELD, ID_CPE, i++);
case 4:
error |= cb->cbSbr(cb->cbSbrData, hBs, asc->m_samplingFrequency, asc->m_extensionSamplingFrequency, asc->m_samplesPerFrame, AOT_ER_AAC_ELD, ID_CPE, i++);
error |= cb->cbSbr(cb->cbSbrData, hBs, asc->m_samplingFrequency, asc->m_extensionSamplingFrequency, asc->m_samplesPerFrame, AOT_ER_AAC_ELD, ID_SCE, i++);
@ -783,6 +1126,8 @@ TRANSPORTDEC_ERROR EldSpecificConfig_Parse(
if ( 0 != ld_sbr_header(asc, hBs, cb) ) {
return TRANSPORTDEC_PARSE_ERROR;
}
} else {
return TRANSPORTDEC_UNSUPPORTED_FORMAT;
}
}
esc->m_useLdQmfTimeAlign = 0;
@ -802,26 +1147,8 @@ TRANSPORTDEC_ERROR EldSpecificConfig_Parse(
}
switch (eldExtType) {
case ELDEXT_LDSAC:
esc->m_useLdQmfTimeAlign = 1;
if (cb->cbSsc != NULL) {
ErrorStatus = (TRANSPORTDEC_ERROR)cb->cbSsc(
cb->cbSscData,
hBs,
asc->m_aot,
asc->m_samplingFrequency,
1, /* muxMode */
len
);
} else {
ErrorStatus = TRANSPORTDEC_UNSUPPORTED_FORMAT;
}
if (ErrorStatus != TRANSPORTDEC_OK) {
goto bail;
}
break;
default:
for(cnt=0; cnt<len; cnt++) {
for(cnt=0; cnt<eldExtLen; cnt++) {
FDKreadBits(hBs, 8 );
}
break;
@ -1047,4 +1374,133 @@ TRANSPORTDEC_ERROR AudioSpecificConfig_Parse(
return (ErrorStatus);
}
TRANSPORTDEC_ERROR DrmRawSdcAudioConfig_Parse(
CSAudioSpecificConfig *self,
HANDLE_FDK_BITSTREAM bs
)
{
TRANSPORTDEC_ERROR ErrorStatus = TRANSPORTDEC_OK;
AudioSpecificConfig_Init(self);
if ((INT)FDKgetValidBits(bs) < 20) {
ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
goto bail;
}
else {
/* DRM - Audio information data entity - type 9
- Short Id 2 bits
- Stream Id 2 bits
- audio coding 2 bits
- SBR flag 1 bit
- audio mode 2 bits
- audio sampling rate 3 bits
- text flag 1 bit
- enhancement flag 1 bit
- coder field 5 bits
- rfa 1 bit */
int audioCoding, audioMode, cSamplingFreq, coderField, sfIdx, sbrFlag;
/* Read the SDC field */
FDKreadBits(bs,4); /* Short and Stream Id */
audioCoding = FDKreadBits(bs, 2);
sbrFlag = FDKreadBits(bs, 1);
audioMode = FDKreadBits(bs, 2);
cSamplingFreq = FDKreadBits(bs, 3); /* audio sampling rate */
FDKreadBits(bs, 2); /* Text and enhancement flag */
coderField = FDKreadBits(bs, 5);
FDKreadBits(bs, 1); /* rfa */
/* Evaluate configuration and fill the ASC */
switch (cSamplingFreq) {
case 0: /* 8 kHz */
sfIdx = 11;
break;
case 1: /* 12 kHz */
sfIdx = 9;
break;
case 2: /* 16 kHz */
sfIdx = 8;
break;
case 3: /* 24 kHz */
sfIdx = 6;
break;
case 5: /* 48 kHz */
sfIdx = 3;
break;
case 4: /* reserved */
case 6: /* reserved */
case 7: /* reserved */
default:
ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
goto bail;
}
self->m_samplingFrequencyIndex = sfIdx;
self->m_samplingFrequency = SamplingRateTable[sfIdx];
if ( sbrFlag ) {
UINT i;
int tmp = -1;
self->m_sbrPresentFlag = 1;
self->m_extensionAudioObjectType = AOT_SBR;
self->m_extensionSamplingFrequency = self->m_samplingFrequency << 1;
for (i=0; i<(sizeof(SamplingRateTable)/sizeof(SamplingRateTable[0])); i++){
if (SamplingRateTable[i] == self->m_extensionSamplingFrequency){
tmp = i;
break;
}
}
self->m_extensionSamplingFrequencyIndex = tmp;
}
switch (audioCoding) {
case 0: /* AAC */
self->m_aot = AOT_DRM_AAC ; /* Set pseudo AOT for Drm AAC */
switch (audioMode) {
case 1: /* parametric stereo */
self->m_psPresentFlag = 1;
case 0: /* mono */
self->m_channelConfiguration = 1;
break;
case 2: /* stereo */
self->m_channelConfiguration = 2;
break;
default:
ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
goto bail;
}
self->m_vcb11Flag = 1;
self->m_hcrFlag = 1;
self->m_samplesPerFrame = 960;
self->m_epConfig = 1;
break;
case 1: /* CELP */
self->m_aot = AOT_ER_CELP;
self->m_channelConfiguration = 1;
break;
case 2: /* HVXC */
self->m_aot = AOT_ER_HVXC;
self->m_channelConfiguration = 1;
break;
case 3: /* reserved */
default:
ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
self->m_aot = AOT_NONE;
break;
}
if (self->m_psPresentFlag && !self->m_sbrPresentFlag) {
ErrorStatus = TRANSPORTDEC_PARSE_ERROR;
goto bail;
}
}
bail:
return (ErrorStatus);
}

View File

@ -0,0 +1,146 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software that implements
the MPEG Advanced Audio Coding ("AAC") encoding and decoding scheme for digital audio.
This FDK AAC Codec software is intended to be used on a wide variety of Android devices.
AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient general perceptual
audio codecs. AAC-ELD is considered the best-performing full-bandwidth communications codec by
independent studies and is widely deployed. AAC has been standardized by ISO and IEC as part
of the MPEG specifications.
Patent licenses for necessary patent claims for the FDK AAC Codec (including those of Fraunhofer)
may be obtained through Via Licensing (www.vialicensing.com) or through the respective patent owners
individually for the purpose of encoding or decoding bit streams in products that are compliant with
the ISO/IEC MPEG audio standards. Please note that most manufacturers of Android devices already license
these patent claims through Via Licensing or directly from the patent owners, and therefore FDK AAC Codec
software may already be covered under those patent licenses when it is used for those licensed purposes only.
Commercially-licensed AAC software libraries, including floating-point versions with enhanced sound quality,
are also available from Fraunhofer. Users are encouraged to check the Fraunhofer website for additional
applications information and documentation.
2. COPYRIGHT LICENSE
Redistribution and use in source and binary forms, with or without modification, are permitted without
payment of copyright license fees provided that you satisfy the following conditions:
You must retain the complete text of this software license in redistributions of the FDK AAC Codec or
your modifications thereto in source code form.
You must retain the complete text of this software license in the documentation and/or other materials
provided with redistributions of the FDK AAC Codec or your modifications thereto in binary form.
You must make available free of charge copies of the complete source code of the FDK AAC Codec and your
modifications thereto to recipients of copies in binary form.
The name of Fraunhofer may not be used to endorse or promote products derived from this library without
prior written permission.
You may not charge copyright license fees for anyone to use, copy or distribute the FDK AAC Codec
software or your modifications thereto.
Your modified versions of the FDK AAC Codec must carry prominent notices stating that you changed the software
and the date of any change. For modified versions of the FDK AAC Codec, the term
"Fraunhofer FDK AAC Codec Library for Android" must be replaced by the term
"Third-Party Modified Version of the Fraunhofer FDK AAC Codec Library for Android."
3. NO PATENT LICENSE
NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without limitation the patents of Fraunhofer,
ARE GRANTED BY THIS SOFTWARE LICENSE. Fraunhofer provides no warranty of patent non-infringement with
respect to this software.
You may use this FDK AAC Codec software or modifications thereto only for purposes that are authorized
by appropriate patent licenses.
4. DISCLAIMER
This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright holders and contributors
"AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, including but not limited to the implied warranties
of merchantability and fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary, or consequential damages,
including but not limited to procurement of substitute goods or services; loss of use, data, or profits,
or business interruption, however caused and on any theory of liability, whether in contract, strict
liability, or tort (including negligence), arising in any way out of the use of this software, even if
advised of the possibility of such damage.
5. CONTACT INFORMATION
Fraunhofer Institute for Integrated Circuits IIS
Attention: Audio and Multimedia Departments - FDK AAC LL
Am Wolfsmantel 33
91058 Erlangen, Germany
www.iis.fraunhofer.de/amm
amm-info@iis.fraunhofer.de
----------------------------------------------------------------------------------------------------------- */
/***************************** MPEG-4 AAC Decoder **************************
Author(s): Christian Griebel
Description: DRM transport stuff
******************************************************************************/
#include "tpdec_drm.h"
#include "FDK_bitstream.h"
void drmRead_CrcInit(HANDLE_DRM pDrm) /*!< pointer to drm crc info stucture */
{
FDK_ASSERT(pDrm != NULL);
FDKcrcInit(&pDrm->crcInfo, 0x001d, 0xFFFF, 8);
}
int drmRead_CrcStartReg(
HANDLE_DRM pDrm, /*!< pointer to drm stucture */
HANDLE_FDK_BITSTREAM hBs, /*!< handle to current bit buffer structure */
int mBits /*!< number of bits in crc region */
)
{
FDK_ASSERT(pDrm != NULL);
FDKcrcReset(&pDrm->crcInfo);
pDrm->crcReadValue = FDKreadBits(hBs, 8);
return ( FDKcrcStartReg(&pDrm->crcInfo, hBs, mBits) );
}
void drmRead_CrcEndReg(
HANDLE_DRM pDrm, /*!< pointer to drm crc info stucture */
HANDLE_FDK_BITSTREAM hBs, /*!< handle to current bit buffer structure */
int reg /*!< crc region */
)
{
FDK_ASSERT(pDrm != NULL);
FDKcrcEndReg(&pDrm->crcInfo, hBs, reg);
}
TRANSPORTDEC_ERROR drmRead_CrcCheck( HANDLE_DRM pDrm )
{
TRANSPORTDEC_ERROR ErrorStatus = TRANSPORTDEC_OK;
USHORT crc;
crc = FDKcrcGetCRC(&pDrm->crcInfo) ^ 0xFF;
if (crc != pDrm->crcReadValue)
{
return (TRANSPORTDEC_CRC_ERROR);
}
return (ErrorStatus);
}

View File

@ -0,0 +1,194 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software that implements
the MPEG Advanced Audio Coding ("AAC") encoding and decoding scheme for digital audio.
This FDK AAC Codec software is intended to be used on a wide variety of Android devices.
AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient general perceptual
audio codecs. AAC-ELD is considered the best-performing full-bandwidth communications codec by
independent studies and is widely deployed. AAC has been standardized by ISO and IEC as part
of the MPEG specifications.
Patent licenses for necessary patent claims for the FDK AAC Codec (including those of Fraunhofer)
may be obtained through Via Licensing (www.vialicensing.com) or through the respective patent owners
individually for the purpose of encoding or decoding bit streams in products that are compliant with
the ISO/IEC MPEG audio standards. Please note that most manufacturers of Android devices already license
these patent claims through Via Licensing or directly from the patent owners, and therefore FDK AAC Codec
software may already be covered under those patent licenses when it is used for those licensed purposes only.
Commercially-licensed AAC software libraries, including floating-point versions with enhanced sound quality,
are also available from Fraunhofer. Users are encouraged to check the Fraunhofer website for additional
applications information and documentation.
2. COPYRIGHT LICENSE
Redistribution and use in source and binary forms, with or without modification, are permitted without
payment of copyright license fees provided that you satisfy the following conditions:
You must retain the complete text of this software license in redistributions of the FDK AAC Codec or
your modifications thereto in source code form.
You must retain the complete text of this software license in the documentation and/or other materials
provided with redistributions of the FDK AAC Codec or your modifications thereto in binary form.
You must make available free of charge copies of the complete source code of the FDK AAC Codec and your
modifications thereto to recipients of copies in binary form.
The name of Fraunhofer may not be used to endorse or promote products derived from this library without
prior written permission.
You may not charge copyright license fees for anyone to use, copy or distribute the FDK AAC Codec
software or your modifications thereto.
Your modified versions of the FDK AAC Codec must carry prominent notices stating that you changed the software
and the date of any change. For modified versions of the FDK AAC Codec, the term
"Fraunhofer FDK AAC Codec Library for Android" must be replaced by the term
"Third-Party Modified Version of the Fraunhofer FDK AAC Codec Library for Android."
3. NO PATENT LICENSE
NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without limitation the patents of Fraunhofer,
ARE GRANTED BY THIS SOFTWARE LICENSE. Fraunhofer provides no warranty of patent non-infringement with
respect to this software.
You may use this FDK AAC Codec software or modifications thereto only for purposes that are authorized
by appropriate patent licenses.
4. DISCLAIMER
This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright holders and contributors
"AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, including but not limited to the implied warranties
of merchantability and fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary, or consequential damages,
including but not limited to procurement of substitute goods or services; loss of use, data, or profits,
or business interruption, however caused and on any theory of liability, whether in contract, strict
liability, or tort (including negligence), arising in any way out of the use of this software, even if
advised of the possibility of such damage.
5. CONTACT INFORMATION
Fraunhofer Institute for Integrated Circuits IIS
Attention: Audio and Multimedia Departments - FDK AAC LL
Am Wolfsmantel 33
91058 Erlangen, Germany
www.iis.fraunhofer.de/amm
amm-info@iis.fraunhofer.de
----------------------------------------------------------------------------------------------------------- */
/***************************** MPEG-4 AAC Decoder **************************
Author(s): Josef Hoepfl
Description: DRM interface
******************************************************************************/
#ifndef TPDEC_DRM_H
#define TPDEC_DRM_H
#include "tpdec_lib.h"
#include "FDK_crc.h"
typedef struct {
FDK_CRCINFO crcInfo; /* CRC state info */
USHORT crcReadValue; /* CRC value read from bitstream data */
} STRUCT_DRM;
typedef STRUCT_DRM *HANDLE_DRM;
/*!
\brief Initialize DRM CRC
The function initialzes the crc buffer and the crc lookup table.
\return none
*/
void drmRead_CrcInit( HANDLE_DRM pDrm );
/**
* \brief Starts CRC region with a maximum number of bits
* If mBits is positive zero padding will be used for CRC calculation, if there
* are less than mBits bits available.
* If mBits is negative no zero padding is done.
* If mBits is zero the memory for the buffer is allocated dynamically, the
* number of bits is not limited.
*
* \param pDrm DRM data handle
* \param hBs bitstream handle, on which the CRC region referes to
* \param mBits max number of bits in crc region to be considered
*
* \return ID for the created region, -1 in case of an error
*/
int drmRead_CrcStartReg(
HANDLE_DRM pDrm,
HANDLE_FDK_BITSTREAM hBs,
int mBits
);
/**
* \brief Ends CRC region identified by reg
*
* \param pDrm DRM data handle
* \param hBs bitstream handle, on which the CRC region referes to
* \param reg CRC regions ID returned by drmRead_CrcStartReg()
*
* \return none
*/
void drmRead_CrcEndReg(
HANDLE_DRM pDrm,
HANDLE_FDK_BITSTREAM hBs,
int reg
);
/**
* \brief Check CRC
*
* Checks if the currently calculated CRC matches the CRC field read from the bitstream
* Deletes all CRC regions.
*
* \param pDrm DRM data handle
*
* \return Returns 0 if they are identical otherwise 1
*/
TRANSPORTDEC_ERROR drmRead_CrcCheck( HANDLE_DRM pDrm );
/**
* \brief Check if we have a valid DRM frame at the current bitbuffer position
*
* This function assumes enough bits in buffer for the current frame.
* It reads out the header bits to prepare the bitbuffer for the decode loop.
* In case the header bits show an invalid bitstream/frame, the whole frame is skipped.
*
* \param pDrm DRM data handle which is filled with parsed DRM header data
* \param bs handle of bitstream from whom the DRM header is read
*
* \return error status
*/
TRANSPORTDEC_ERROR drmRead_DecodeHeader(
HANDLE_DRM pDrm,
HANDLE_FDK_BITSTREAM bs
);
/**
* \brief Parse a Drm specific SDC audio config from a given bitstream handle.
*
* \param pAsc A pointer to an allocated CSAudioSpecificConfig struct.
* \param hBs Bitstream handle.
*
* \return Total element count including all SCE, CPE and LFE.
*/
TRANSPORTDEC_ERROR DrmRawSdcAudioConfig_Parse( CSAudioSpecificConfig *pAsc,
HANDLE_FDK_BITSTREAM hBs );
#endif /* TPDEC_DRM_H */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -102,6 +102,7 @@ amm-info@iis.fraunhofer.de
#include "tpdec_latm.h"
#include "tpdec_drm.h"
#define MODULE_NAME "transportDec"
@ -113,6 +114,7 @@ typedef union {
CLatmDemux latm;
STRUCT_DRM drm;
} transportdec_parser_t;
@ -182,6 +184,9 @@ HANDLE_TRANSPORTDEC transportDec_Open( const TRANSPORT_TYPE transportFmt, const
hInput->numberOfRawDataBlocks = 0;
break;
case TT_DRM:
drmRead_CrcInit(&hInput->parser.drm);
break;
case TT_MP4_LATM_MCP0:
case TT_MP4_LATM_MCP1:
@ -253,6 +258,18 @@ TRANSPORTDEC_ERROR transportDec_OutOfBandConfig(HANDLE_TRANSPORTDEC hTp, UCHAR *
}
}
break;
case TT_DRM:
fConfigFound = 1;
err = DrmRawSdcAudioConfig_Parse(&hTp->asc[layer], hBs);
if (err == TRANSPORTDEC_OK) {
int errC;
errC = hTp->callbacks.cbUpdateConfig(hTp->callbacks.cbUpdateConfigData, &hTp->asc[layer]);
if (errC != 0) {
err = TRANSPORTDEC_PARSE_ERROR;
}
}
break;
}
if (err == TRANSPORTDEC_OK && fConfigFound) {
@ -1083,6 +1100,7 @@ TRANSPORTDEC_ERROR transportDec_ReadAccessUnit( const HANDLE_TRANSPORTDEC hTp, c
break;
case TT_MP4_RAW:
case TT_DRM:
/* One Access Unit was filled into buffer.
So get the length out of the buffer. */
hTp->auLength[layer] = FDKgetValidBits(hBs);
@ -1100,7 +1118,6 @@ TRANSPORTDEC_ERROR transportDec_ReadAccessUnit( const HANDLE_TRANSPORTDEC hTp, c
}
break;
case TT_RSVD50:
case TT_MP4_ADTS:
case TT_MP4_LOAS:
err = transportDec_readStream(hTp, layer);
@ -1268,8 +1285,13 @@ TRANSPORTDEC_ERROR transportDec_GetLibInfo( LIB_INFO *info )
info += i;
info->module_id = FDK_TPDEC;
#ifdef __ANDROID__
info->build_date = "";
info->build_time = "";
#else
info->build_date = __DATE__;
info->build_time = __TIME__;
#endif
info->title = TP_LIB_TITLE;
info->version = LIB_VERSION(TP_LIB_VL0, TP_LIB_VL1, TP_LIB_VL2);
LIB_VERSION_STRING(info);
@ -1279,6 +1301,7 @@ TRANSPORTDEC_ERROR transportDec_GetLibInfo( LIB_INFO *info )
| CAPF_LATM
| CAPF_LOAS
| CAPF_RAWPACKETS
| CAPF_DRM
;
return TRANSPORTDEC_OK; /* FDKERR_NOERROR; */
@ -1290,6 +1313,8 @@ int transportDec_CrcStartReg(HANDLE_TRANSPORTDEC pTp, INT mBits)
switch (pTp->transportFmt) {
case TT_MP4_ADTS:
return adtsRead_CrcStartReg(&pTp->parser.adts, &pTp->bitStream[0], mBits);
case TT_DRM:
return drmRead_CrcStartReg(&pTp->parser.drm, &pTp->bitStream[0], mBits);
default:
return 0;
}
@ -1301,6 +1326,9 @@ void transportDec_CrcEndReg(HANDLE_TRANSPORTDEC pTp, INT reg)
case TT_MP4_ADTS:
adtsRead_CrcEndReg(&pTp->parser.adts, &pTp->bitStream[0], reg);
break;
case TT_DRM:
drmRead_CrcEndReg(&pTp->parser.drm, &pTp->bitStream[0], reg);
break;
default:
break;
}
@ -1317,6 +1345,9 @@ TRANSPORTDEC_ERROR transportDec_CrcCheck(HANDLE_TRANSPORTDEC pTp)
transportDec_AdjustEndOfAccessUnit(pTp);
}
return adtsRead_CrcCheck(&pTp->parser.adts);
case TT_DRM:
return drmRead_CrcCheck(&pTp->parser.drm);
break;
default:
return TRANSPORTDEC_OK;
}

View File

@ -2,7 +2,12 @@
/* library info */
#define TP_LIB_VL0 2
#define TP_LIB_VL1 3
#define TP_LIB_VL2 3
#define TP_LIB_VL2 7
#define TP_LIB_TITLE "MPEG Transport"
#ifdef __ANDROID__
#define TP_LIB_BUILD_DATE ""
#define TP_LIB_BUILD_TIME ""
#else
#define TP_LIB_BUILD_DATE __DATE__
#define TP_LIB_BUILD_TIME __TIME__
#endif

View File

@ -146,12 +146,15 @@ typedef struct
UCHAR FrontElementIsCpe[PC_FSB_CHANNELS_MAX];
UCHAR FrontElementTagSelect[PC_FSB_CHANNELS_MAX];
UCHAR FrontElementHeightInfo[PC_FSB_CHANNELS_MAX];
UCHAR SideElementIsCpe[PC_FSB_CHANNELS_MAX];
UCHAR SideElementTagSelect[PC_FSB_CHANNELS_MAX];
UCHAR SideElementHeightInfo[PC_FSB_CHANNELS_MAX];
UCHAR BackElementIsCpe[PC_FSB_CHANNELS_MAX];
UCHAR BackElementTagSelect[PC_FSB_CHANNELS_MAX];
UCHAR BackElementHeightInfo[PC_FSB_CHANNELS_MAX];
UCHAR LfeElementTagSelect[PC_LFE_CHANNELS_MAX];
@ -324,16 +327,23 @@ int getSamplingRateIndex( UINT samplingRate )
*/
static inline int getNumberOfTotalChannels(int channelConfig)
{
if (channelConfig > 0 && channelConfig < 8)
return (channelConfig == 7)?8:channelConfig;
else
switch (channelConfig) {
case 1: case 2: case 3:
case 4: case 5: case 6:
return channelConfig;
case 7: case 12: case 14:
return 8;
case 11:
return 7;
default:
return 0;
}
}
static inline
int getNumberOfEffectiveChannels(const int channelConfig)
{
const int n[] = {0,1,2,3,4,5,5,7};
{ /* index: 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15 */
const int n[] = {0,1,2,3,4,5,5,7,0,0, 0, 6, 7, 0, 7, 0};
return n[channelConfig];
}

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -296,6 +296,7 @@ CreateStreamMuxConfig(
USHORT coreFrameOffset=0;
hAss->taraBufferFullness = 0xFF;
hAss->audioMuxVersionA = 0; /* for future extensions */
hAss->streamMuxConfigBits = 0;
@ -339,13 +340,7 @@ CreateStreamMuxConfig(
hAss->streamMuxConfigBits+=1;
}
if( (useSameConfig == 0) || (transLayer==0) ) {
UINT bits;
if ( hAss->audioMuxVersion == 1 ) {
FDKpushFor(hBs, 2); /* align to ASC, even if we do not know the length of the "ascLen" field yet */
}
bits = FDKgetValidBits( hBs );
const UINT alignAnchor = FDKgetValidBits(hBs);
transportEnc_writeASC(
hBs,
@ -353,19 +348,24 @@ CreateStreamMuxConfig(
cb
);
bits = FDKgetValidBits( hBs ) - bits;
if ( hAss->audioMuxVersion == 1 ) {
FDKpushBack(hBs, bits+2);
hAss->streamMuxConfigBits += transportEnc_LatmWriteValue( hBs, bits );
UINT ascLen = transportEnc_LatmWriteValue(hBs, 0);
FDKbyteAlign(hBs, alignAnchor);
ascLen = FDKgetValidBits(hBs) - alignAnchor - ascLen;
FDKpushBack(hBs, FDKgetValidBits(hBs) - alignAnchor);
transportEnc_LatmWriteValue(hBs, ascLen);
transportEnc_writeASC(
hBs,
hAss->config[prog][layer],
cb
);
FDKbyteAlign(hBs, alignAnchor); /* asc length fillbits */
}
hAss->streamMuxConfigBits += bits; /* add asc length to smc summary */
hAss->streamMuxConfigBits += FDKgetValidBits(hBs) - alignAnchor; /* add asc length to smc summary */
}
transLayer++;
@ -384,7 +384,6 @@ CreateStreamMuxConfig(
case AOT_ER_AAC_LD :
case AOT_ER_AAC_ELD :
case AOT_USAC:
case AOT_RSVD50:
p_linfo->frameLengthType = 0;
FDKwriteBits( hBs, p_linfo->frameLengthType, 3 ); /* frameLengthType */

View File

@ -619,8 +619,13 @@ TRANSPORTENC_ERROR transportEnc_GetLibInfo( LIB_INFO *info )
info->module_id = FDK_TPENC;
info->version = LIB_VERSION(TP_LIB_VL0, TP_LIB_VL1, TP_LIB_VL2);
LIB_VERSION_STRING(info);
#ifdef __ANDROID__
info->build_date = "";
info->build_time = "";
#else
info->build_date = __DATE__;
info->build_time = __TIME__;
#endif
info->title = TP_LIB_TITLE;
/* Set flags */

View File

@ -2,7 +2,12 @@
/* library info */
#define TP_LIB_VL0 2
#define TP_LIB_VL1 3
#define TP_LIB_VL2 3
#define TP_LIB_VL2 6
#define TP_LIB_TITLE "MPEG Transport"
#ifdef __ANDROID__
#define TP_LIB_BUILD_DATE ""
#define TP_LIB_BUILD_TIME ""
#else
#define TP_LIB_BUILD_DATE __DATE__
#define TP_LIB_BUILD_TIME __TIME__
#endif

View File

@ -0,0 +1,233 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software that implements
the MPEG Advanced Audio Coding ("AAC") encoding and decoding scheme for digital audio.
This FDK AAC Codec software is intended to be used on a wide variety of Android devices.
AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient general perceptual
audio codecs. AAC-ELD is considered the best-performing full-bandwidth communications codec by
independent studies and is widely deployed. AAC has been standardized by ISO and IEC as part
of the MPEG specifications.
Patent licenses for necessary patent claims for the FDK AAC Codec (including those of Fraunhofer)
may be obtained through Via Licensing (www.vialicensing.com) or through the respective patent owners
individually for the purpose of encoding or decoding bit streams in products that are compliant with
the ISO/IEC MPEG audio standards. Please note that most manufacturers of Android devices already license
these patent claims through Via Licensing or directly from the patent owners, and therefore FDK AAC Codec
software may already be covered under those patent licenses when it is used for those licensed purposes only.
Commercially-licensed AAC software libraries, including floating-point versions with enhanced sound quality,
are also available from Fraunhofer. Users are encouraged to check the Fraunhofer website for additional
applications information and documentation.
2. COPYRIGHT LICENSE
Redistribution and use in source and binary forms, with or without modification, are permitted without
payment of copyright license fees provided that you satisfy the following conditions:
You must retain the complete text of this software license in redistributions of the FDK AAC Codec or
your modifications thereto in source code form.
You must retain the complete text of this software license in the documentation and/or other materials
provided with redistributions of the FDK AAC Codec or your modifications thereto in binary form.
You must make available free of charge copies of the complete source code of the FDK AAC Codec and your
modifications thereto to recipients of copies in binary form.
The name of Fraunhofer may not be used to endorse or promote products derived from this library without
prior written permission.
You may not charge copyright license fees for anyone to use, copy or distribute the FDK AAC Codec
software or your modifications thereto.
Your modified versions of the FDK AAC Codec must carry prominent notices stating that you changed the software
and the date of any change. For modified versions of the FDK AAC Codec, the term
"Fraunhofer FDK AAC Codec Library for Android" must be replaced by the term
"Third-Party Modified Version of the Fraunhofer FDK AAC Codec Library for Android."
3. NO PATENT LICENSE
NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without limitation the patents of Fraunhofer,
ARE GRANTED BY THIS SOFTWARE LICENSE. Fraunhofer provides no warranty of patent non-infringement with
respect to this software.
You may use this FDK AAC Codec software or modifications thereto only for purposes that are authorized
by appropriate patent licenses.
4. DISCLAIMER
This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright holders and contributors
"AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, including but not limited to the implied warranties
of merchantability and fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary, or consequential damages,
including but not limited to procurement of substitute goods or services; loss of use, data, or profits,
or business interruption, however caused and on any theory of liability, whether in contract, strict
liability, or tort (including negligence), arising in any way out of the use of this software, even if
advised of the possibility of such damage.
5. CONTACT INFORMATION
Fraunhofer Institute for Integrated Circuits IIS
Attention: Audio and Multimedia Departments - FDK AAC LL
Am Wolfsmantel 33
91058 Erlangen, Germany
www.iis.fraunhofer.de/amm
amm-info@iis.fraunhofer.de
----------------------------------------------------------------------------------------------------------- */
/************************ FDK PCM postprocessor module *********************
Author(s): Matthias Neusinger
Description: Hard limiter for clipping prevention
*******************************************************************************/
#ifndef _LIMITER_H_
#define _LIMITER_H_
#include "common_fix.h"
#define TDL_ATTACK_DEFAULT_MS (15) /* default attack time in ms */
#define TDL_RELEASE_DEFAULT_MS (50) /* default release time in ms */
#define TDL_GAIN_SCALING (15) /* scaling of gain value. */
#ifdef __cplusplus
extern "C" {
#endif
typedef enum {
TDLIMIT_OK = 0,
__error_codes_start = -100,
TDLIMIT_INVALID_HANDLE,
TDLIMIT_INVALID_PARAMETER,
__error_codes_end
} TDLIMITER_ERROR;
struct TDLimiter;
typedef struct TDLimiter* TDLimiterPtr;
/******************************************************************************
* createLimiter *
* maxAttackMs: maximum and initial attack/lookahead time in milliseconds *
* releaseMs: release time in milliseconds (90% time constant) *
* threshold: limiting threshold *
* maxChannels: maximum and initial number of channels *
* maxSampleRate: maximum and initial sampling rate in Hz *
* returns: limiter handle *
******************************************************************************/
TDLimiterPtr createLimiter(unsigned int maxAttackMs,
unsigned int releaseMs,
INT_PCM threshold,
unsigned int maxChannels,
unsigned int maxSampleRate);
/******************************************************************************
* resetLimiter *
* limiter: limiter handle *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR resetLimiter(TDLimiterPtr limiter);
/******************************************************************************
* destroyLimiter *
* limiter: limiter handle *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR destroyLimiter(TDLimiterPtr limiter);
/******************************************************************************
* applyLimiter *
* limiter: limiter handle *
* pGain : pointer to gains to be applied to the signal before limiting, *
* which are downscaled by TDL_GAIN_SCALING bit. *
* These gains are delayed by gain_delay, and smoothed. *
* Smoothing is done by a butterworth lowpass filter with a cutoff *
* frequency which is fixed with respect to the sampling rate. *
* It is a substitute for the smoothing due to windowing and *
* overlap/add, if a gain is applied in frequency domain. *
* gain_scale: pointer to scaling exponents to be applied to the signal before *
* limiting, without delay and without smoothing *
* gain_size: number of elements in pGain, currently restricted to 1 *
* gain_delay: delay [samples] with which the gains in pGain shall be applied *
* gain_delay <= nSamples *
* samples: input/output buffer containing interleaved samples *
* precision of output will be DFRACT_BITS-TDL_GAIN_SCALING bits *
* nSamples: number of samples per channel *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR applyLimiter(TDLimiterPtr limiter,
INT_PCM* samples,
FIXP_DBL* pGain,
const INT* gain_scale,
const UINT gain_size,
const UINT gain_delay,
const UINT nSamples);
/******************************************************************************
* getLimiterDelay *
* limiter: limiter handle *
* returns: exact delay caused by the limiter in samples *
******************************************************************************/
unsigned int getLimiterDelay(TDLimiterPtr limiter);
/******************************************************************************
* setLimiterNChannels *
* limiter: limiter handle *
* nChannels: number of channels ( <= maxChannels specified on create) *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR setLimiterNChannels(TDLimiterPtr limiter, unsigned int nChannels);
/******************************************************************************
* setLimiterSampleRate *
* limiter: limiter handle *
* sampleRate: sampling rate in Hz ( <= maxSampleRate specified on create) *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR setLimiterSampleRate(TDLimiterPtr limiter, unsigned int sampleRate);
/******************************************************************************
* setLimiterAttack *
* limiter: limiter handle *
* attackMs: attack time in ms ( <= maxAttackMs specified on create) *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR setLimiterAttack(TDLimiterPtr limiter, unsigned int attackMs);
/******************************************************************************
* setLimiterRelease *
* limiter: limiter handle *
* releaseMs: release time in ms *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR setLimiterRelease(TDLimiterPtr limiter, unsigned int releaseMs);
/******************************************************************************
* setLimiterThreshold *
* limiter: limiter handle *
* threshold: limiter threshold *
* returns: error code *
******************************************************************************/
TDLIMITER_ERROR setLimiterThreshold(TDLimiterPtr limiter, INT_PCM threshold);
#ifdef __cplusplus
}
#endif
#endif //#ifndef _LIMITER_H_

View File

@ -95,69 +95,88 @@ amm-info@iis.fraunhofer.de
#include "machine_type.h"
#include "common_fix.h"
#include "FDK_audio.h"
#include "FDK_bitstream.h"
/* ------------------------ *
* MODULE SETTINGS: *
* ------------------------ */
/* #define PCM_UPMIX_ENABLE */ /*!< Generally enable up mixing. */
#define PCM_DOWNMIX_ENABLE /*!< Generally enable down mixing. */
#define DVB_MIXDOWN_ENABLE /*!< Enable this to support DVB ancillary data for encoder
assisted downmixing of MPEG-4 AAC and
MPEG-1/2 layer 2 streams. PCM_DOWNMIX_ENABLE has to
be enabled, too! */
#define MPEG_PCE_MIXDOWN_ENABLE /*!< Enable this to support MPEG matrix mixdown with a
coefficient carried in the PCE. PCM_DOWNMIX_ENABLE
has to be enabled, too! */
/* #define ARIB_MIXDOWN_ENABLE */ /*!< Enable modifications to the MPEG PCE mixdown method
to fulfill ARIB standard. MPEG_PCE_MIXDOWN_ENABLE has
to be set. */
/* ------------------------ *
* ERROR CODES: *
* ------------------------ */
typedef enum
{
PCMDMX_OK = 0x0, /*!< No error happened. */
PCMDMX_OUT_OF_MEMORY = 0x2, /*!< Not enough memory to set up an instance of the module. */
PCMDMX_UNKNOWN = 0x5, /*!< Error condition is of unknown reason, or from a third
party module. */
PCMDMX_INVALID_HANDLE, /*!< The given instance handle is not valid. */
PCMDMX_INVALID_ARGUMENT, /*!< One of the parameters handed over is invalid. */
PCMDMX_INVALID_CH_CONFIG, /*!< The given channel configuration is not supported and
thus no processing was performed. */
PCMDMX_INVALID_MODE, /*!< The set configuration/mode is not applicable. */
PCMDMX_UNKNOWN_PARAM, /*!< The handed parameter is not known/supported. */
PCMDMX_UNABLE_TO_SET_PARAM, /*!< Unable to set the specific parameter. Most probably
the value ist out of range. */
PCMDMX_CORRUPT_ANC_DATA /*!< The read ancillary data was corrupt. */
PCMDMX_OK = 0x0, /*!< No error happened. */
pcm_dmx_fatal_error_start,
PCMDMX_OUT_OF_MEMORY = 0x2, /*!< Not enough memory to set up an instance of the module. */
PCMDMX_UNKNOWN = 0x5, /*!< Error condition is of unknown reason, or from a third
party module. */
pcm_dmx_fatal_error_end,
PCMDMX_INVALID_HANDLE, /*!< The given instance handle is not valid. */
PCMDMX_INVALID_ARGUMENT, /*!< One of the parameters handed over is invalid. */
PCMDMX_INVALID_CH_CONFIG, /*!< The given channel configuration is not supported and thus
no processing was performed. */
PCMDMX_INVALID_MODE, /*!< The set configuration/mode is not applicable. */
PCMDMX_UNKNOWN_PARAM, /*!< The handed parameter is not known/supported. */
PCMDMX_UNABLE_TO_SET_PARAM, /*!< Unable to set the specific parameter. Most probably the
value ist out of range. */
PCMDMX_CORRUPT_ANC_DATA /*!< The read ancillary data was corrupt. */
} PCMDMX_ERROR;
/** Macro to identify fatal errors. */
#define PCMDMX_IS_FATAL_ERROR(err) ( (((err)>=pcm_dmx_fatal_error_start) && ((err)<=pcm_dmx_fatal_error_end)) ? 1 : 0)
/* ------------------------ *
* RUNTIME PARAMS: *
* ------------------------ */
typedef enum
{
DMX_BS_DATA_EXPIRY_FRAME, /*!< The number of frames without new metadata that have to
go by before the bitstream data expires. The value 0
disables expiry. */
DMX_BS_DATA_DELAY, /*!< The number of delay frames of the output samples
compared to the bitstream data. */
NUMBER_OF_OUTPUT_CHANNELS , /*!< The number of output channels (equals the number of
channels processed by the audio output setup). */
DUAL_CHANNEL_DOWNMIX_MODE /*!< Downmix mode for two channel audio data. */
DMX_BS_DATA_EXPIRY_FRAME, /*!< The number of frames without new metadata that have to go
by before the bitstream data expires. The value 0 disables
expiry. */
DMX_BS_DATA_DELAY, /*!< The number of delay frames of the output samples compared
to the bitstream data. */
MIN_NUMBER_OF_OUTPUT_CHANNELS, /*!< The minimum number of output channels. For all input
configurations that have less than the given channels the
module will modify the output automatically to obtain the
given number of output channels. Mono signals will be
duplicated. If more than two output channels are desired
the module just adds empty channels. The parameter value
must be either -1, 0, 1, 2, 6 or 8. If the value is
greater than zero and exceeds the value of parameter
MAX_NUMBER_OF_OUTPUT_CHANNELS the latter will be set to
the same value. Both values -1 and 0 disable the feature. */
MAX_NUMBER_OF_OUTPUT_CHANNELS, /*!< The maximum number of output channels. For all input
configurations that have more than the given channels the
module will apply a mixdown automatically to obtain the
given number of output channels. The value must be either
-1, 0, 1, 2, 6 or 8. If it is greater than zero and lower
or equal than the value of MIN_NUMBER_OF_OUTPUT_CHANNELS
parameter the latter will be set to the same value.
The values -1 and 0 disable the feature. */
DMX_DUAL_CHANNEL_MODE, /*!< Downmix mode for two channel audio data. */
DMX_PSEUDO_SURROUND_MODE /*!< Defines how module handles pseudo surround compatible
signals. See PSEUDO_SURROUND_MODE type for details. */
} PCMDMX_PARAM;
/* Parameter value types */
typedef enum
{
NEVER_DO_PS_DMX = -1, /*!< Never create a pseudo surround compatible downmix. */
AUTO_PS_DMX = 0, /*!< Create a pseudo surround compatible downmix only if
signalled in bitstreams meta data. (Default) */
FORCE_PS_DMX = 1 /*!< Always create a pseudo surround compatible downmix.
CAUTION: This can lead to excessive signal cancellations
and signal level differences for non-compatible signals. */
} PSEUDO_SURROUND_MODE;
typedef enum
{
STEREO_MODE = 0x0, /*!< Leave stereo signals as they are. */
CH1_MODE = 0x1, /*!< Create a dual mono output signal from channel 1. */
CH2_MODE = 0x2, /*!< Create a dual mono output signal from channel 2. */
MIXED_MODE = 0x3 /*!< Create a dual mono output signal by mixing the two channels. */
STEREO_MODE = 0x0, /*!< Leave stereo signals as they are. */
CH1_MODE = 0x1, /*!< Create a dual mono output signal from channel 1. */
CH2_MODE = 0x2, /*!< Create a dual mono output signal from channel 2. */
MIXED_MODE = 0x3 /*!< Create a dual mono output signal by mixing the two
channels. */
} DUAL_CHANNEL_MODE;
@ -178,7 +197,7 @@ extern "C"
/** Open and initialize an instance of the PCM downmix module
* @param [out] Pointer to a buffer receiving the handle of the new instance.
* @returns Returns an error code.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_Open (
HANDLE_PCM_DOWNMIX *pSelf
@ -188,20 +207,46 @@ PCMDMX_ERROR pcmDmx_Open (
* @param [in] Handle of PCM downmix instance.
* @param [in] Parameter to be set.
* @param [in] Parameter value.
* @returns Returns an error code.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_SetParam (
HANDLE_PCM_DOWNMIX self,
PCMDMX_PARAM param,
UINT value
const PCMDMX_PARAM param,
const INT value
);
/** Read the ancillary data transported in DSEs of DVB streams with MPEG-4 content
/** Get one parameter value of one PCM downmix module instance.
* @param [in] Handle of PCM downmix module instance.
* @param [in] Parameter to be set.
* @param [out] Pointer to buffer receiving the parameter value.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_GetParam (
HANDLE_PCM_DOWNMIX self,
const PCMDMX_PARAM param,
INT * const pValue
);
/** Read downmix meta-data directly from a given bitstream.
* @param [in] Handle of PCM downmix instance.
* @param [in] Handle of FDK bitstream buffer.
* @param [in] Length of ancillary data in bits.
* @param [in] Flag indicating wheter the ancillary data is from a MPEG-1/2 or an MPEG-4 stream.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_Parse (
HANDLE_PCM_DOWNMIX self,
HANDLE_FDK_BITSTREAM hBitStream,
UINT ancDataBits,
int isMpeg2
);
/** Read downmix meta-data from a given data buffer.
* @param [in] Handle of PCM downmix instance.
* @param [in] Pointer to ancillary data buffer.
* @param [in] Size of ancillary data.
* @param [in] Size of ancillary data in bytes.
* @param [in] Flag indicating wheter the ancillary data is from a MPEG-1/2 or an MPEG-4 stream.
* @returns Returns an error code.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_ReadDvbAncData (
HANDLE_PCM_DOWNMIX self,
@ -211,12 +256,11 @@ PCMDMX_ERROR pcmDmx_ReadDvbAncData (
);
/** Set the matrix mixdown information extracted from the PCE of an AAC bitstream.
* Note: Call only if matrix_mixdown_idx_present is true.
* @param [in] Handle of PCM downmix instance.
* @param [in] Matrix mixdown index present flag extracted from PCE.
* @param [in] The 2 bit matrix mixdown index extracted from PCE.
* @param [in] The pseudo surround enable flag extracted from PCE.
* @returns Returns an error code.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_SetMatrixMixdownFromPce (
HANDLE_PCM_DOWNMIX self,
@ -235,34 +279,42 @@ PCMDMX_ERROR pcmDmx_Reset (
UINT flags
);
/** Apply down or up mixing.
/** Create a mixdown, bypass or extend the output signal depending on the modules settings and the
* respective given input configuration.
*
* \param [in] Handle of PCM downmix module instance.
* \param [inout] Pointer to time buffer with decoded PCM samples.
* \param [in] Pointer where the amount of output samples is returned into.
* \param [inout] Pointer where the amount of output channels is returned into.
* \param [in] Flag which indicates if output time data are writtern interleaved or as subsequent blocks.
* \param [inout] Array were the corresponding channel type for each output audio channel is stored into.
* \param [inout] Array were the corresponding channel type index for each output audio channel is stored into.
* \param [in] Array containing the output channel mapping to be used (From MPEG PCE ordering to whatever is required).
*
* @returns Returns an error code.
* \param [in] The I/O block size which is the number of samples per channel.
* \param [inout] Pointer to buffer that holds the number of input channels and where the
* amount of output channels is written to.
* \param [in] Flag which indicates if output time data is writtern interleaved or as
* subsequent blocks.
* \param [inout] Array were the corresponding channel type for each output audio channel is
* stored into.
* \param [inout] Array were the corresponding channel type index for each output audio channel
* is stored into.
* \param [in] Array containing the output channel mapping to be used (from MPEG PCE ordering
* to whatever is required).
* \param [out] Pointer on a field receiving the scale factor that has to be applied on all
* samples afterwards. If the handed pointer is NULL the final scaling is done
* internally.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_ApplyFrame (
HANDLE_PCM_DOWNMIX self,
INT_PCM *pPcmBuf,
UINT frameSize,
INT *nChannels,
int fInterleaved,
AUDIO_CHANNEL_TYPE channelType[],
UCHAR channelIndices[],
const UCHAR channelMapping[][8]
const UCHAR channelMapping[][8],
INT *pDmxOutScale
);
/** Close an instance of the PCM downmix module.
* @param [inout] Pointer to a buffer containing the handle of the instance.
* @returns Returns an error code.
* @returns Returns an error code.
**/
PCMDMX_ERROR pcmDmx_Close (
HANDLE_PCM_DOWNMIX *pSelf
@ -270,7 +322,7 @@ PCMDMX_ERROR pcmDmx_Close (
/** Get library info for this module.
* @param [out] Pointer to an allocated LIB_INFO structure.
* @returns Returns an error code.
* @returns Returns an error code.
*/
PCMDMX_ERROR pcmDmx_GetLibInfo( LIB_INFO *info );

498
libPCMutils/src/limiter.cpp Normal file
View File

@ -0,0 +1,498 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
The Fraunhofer FDK AAC Codec Library for Android ("FDK AAC Codec") is software that implements
the MPEG Advanced Audio Coding ("AAC") encoding and decoding scheme for digital audio.
This FDK AAC Codec software is intended to be used on a wide variety of Android devices.
AAC's HE-AAC and HE-AAC v2 versions are regarded as today's most efficient general perceptual
audio codecs. AAC-ELD is considered the best-performing full-bandwidth communications codec by
independent studies and is widely deployed. AAC has been standardized by ISO and IEC as part
of the MPEG specifications.
Patent licenses for necessary patent claims for the FDK AAC Codec (including those of Fraunhofer)
may be obtained through Via Licensing (www.vialicensing.com) or through the respective patent owners
individually for the purpose of encoding or decoding bit streams in products that are compliant with
the ISO/IEC MPEG audio standards. Please note that most manufacturers of Android devices already license
these patent claims through Via Licensing or directly from the patent owners, and therefore FDK AAC Codec
software may already be covered under those patent licenses when it is used for those licensed purposes only.
Commercially-licensed AAC software libraries, including floating-point versions with enhanced sound quality,
are also available from Fraunhofer. Users are encouraged to check the Fraunhofer website for additional
applications information and documentation.
2. COPYRIGHT LICENSE
Redistribution and use in source and binary forms, with or without modification, are permitted without
payment of copyright license fees provided that you satisfy the following conditions:
You must retain the complete text of this software license in redistributions of the FDK AAC Codec or
your modifications thereto in source code form.
You must retain the complete text of this software license in the documentation and/or other materials
provided with redistributions of the FDK AAC Codec or your modifications thereto in binary form.
You must make available free of charge copies of the complete source code of the FDK AAC Codec and your
modifications thereto to recipients of copies in binary form.
The name of Fraunhofer may not be used to endorse or promote products derived from this library without
prior written permission.
You may not charge copyright license fees for anyone to use, copy or distribute the FDK AAC Codec
software or your modifications thereto.
Your modified versions of the FDK AAC Codec must carry prominent notices stating that you changed the software
and the date of any change. For modified versions of the FDK AAC Codec, the term
"Fraunhofer FDK AAC Codec Library for Android" must be replaced by the term
"Third-Party Modified Version of the Fraunhofer FDK AAC Codec Library for Android."
3. NO PATENT LICENSE
NO EXPRESS OR IMPLIED LICENSES TO ANY PATENT CLAIMS, including without limitation the patents of Fraunhofer,
ARE GRANTED BY THIS SOFTWARE LICENSE. Fraunhofer provides no warranty of patent non-infringement with
respect to this software.
You may use this FDK AAC Codec software or modifications thereto only for purposes that are authorized
by appropriate patent licenses.
4. DISCLAIMER
This FDK AAC Codec software is provided by Fraunhofer on behalf of the copyright holders and contributors
"AS IS" and WITHOUT ANY EXPRESS OR IMPLIED WARRANTIES, including but not limited to the implied warranties
of merchantability and fitness for a particular purpose. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR
CONTRIBUTORS BE LIABLE for any direct, indirect, incidental, special, exemplary, or consequential damages,
including but not limited to procurement of substitute goods or services; loss of use, data, or profits,
or business interruption, however caused and on any theory of liability, whether in contract, strict
liability, or tort (including negligence), arising in any way out of the use of this software, even if
advised of the possibility of such damage.
5. CONTACT INFORMATION
Fraunhofer Institute for Integrated Circuits IIS
Attention: Audio and Multimedia Departments - FDK AAC LL
Am Wolfsmantel 33
91058 Erlangen, Germany
www.iis.fraunhofer.de/amm
amm-info@iis.fraunhofer.de
----------------------------------------------------------------------------------------------------------- */
/************************ FDK PCM postprocessor module *********************
Author(s): Matthias Neusinger
Description: Hard limiter for clipping prevention
*******************************************************************************/
#include "limiter.h"
struct TDLimiter {
unsigned int attack;
FIXP_DBL attackConst, releaseConst;
unsigned int attackMs, releaseMs, maxAttackMs;
FIXP_PCM threshold;
unsigned int channels, maxChannels;
unsigned int sampleRate, maxSampleRate;
FIXP_DBL cor, max;
FIXP_DBL* maxBuf;
FIXP_DBL* delayBuf;
unsigned int maxBufIdx, delayBufIdx;
FIXP_DBL smoothState0;
FIXP_DBL minGain;
FIXP_DBL additionalGainPrev;
FIXP_DBL additionalGainFilterState;
FIXP_DBL additionalGainFilterState1;
};
/* create limiter */
TDLimiterPtr createLimiter(
unsigned int maxAttackMs,
unsigned int releaseMs,
INT_PCM threshold,
unsigned int maxChannels,
unsigned int maxSampleRate
)
{
TDLimiterPtr limiter = NULL;
unsigned int attack, release;
FIXP_DBL attackConst, releaseConst, exponent;
INT e_ans;
/* calc attack and release time in samples */
attack = (unsigned int)(maxAttackMs * maxSampleRate / 1000);
release = (unsigned int)(releaseMs * maxSampleRate / 1000);
/* alloc limiter struct */
limiter = (TDLimiterPtr)FDKcalloc(1, sizeof(struct TDLimiter));
if (!limiter) return NULL;
/* alloc max and delay buffers */
limiter->maxBuf = (FIXP_DBL*)FDKcalloc(attack + 1, sizeof(FIXP_DBL));
limiter->delayBuf = (FIXP_DBL*)FDKcalloc(attack * maxChannels, sizeof(FIXP_DBL));
if (!limiter->maxBuf || !limiter->delayBuf) {
destroyLimiter(limiter);
return NULL;
}
/* attackConst = pow(0.1, 1.0 / (attack + 1)) */
exponent = invFixp(attack+1);
attackConst = fPow(FL2FXCONST_DBL(0.1f), 0, exponent, 0, &e_ans);
attackConst = scaleValue(attackConst, e_ans);
/* releaseConst = (float)pow(0.1, 1.0 / (release + 1)) */
exponent = invFixp(release + 1);
releaseConst = fPow(FL2FXCONST_DBL(0.1f), 0, exponent, 0, &e_ans);
releaseConst = scaleValue(releaseConst, e_ans);
/* init parameters */
limiter->attackMs = maxAttackMs;
limiter->maxAttackMs = maxAttackMs;
limiter->releaseMs = releaseMs;
limiter->attack = attack;
limiter->attackConst = attackConst;
limiter->releaseConst = releaseConst;
limiter->threshold = (FIXP_PCM)threshold;
limiter->channels = maxChannels;
limiter->maxChannels = maxChannels;
limiter->sampleRate = maxSampleRate;
limiter->maxSampleRate = maxSampleRate;
resetLimiter(limiter);
return limiter;
}
/* reset limiter */
TDLIMITER_ERROR resetLimiter(TDLimiterPtr limiter)
{
if (limiter != NULL) {
limiter->maxBufIdx = 0;
limiter->delayBufIdx = 0;
limiter->max = (FIXP_DBL)0;
limiter->cor = FL2FXCONST_DBL(1.0f/(1<<1));
limiter->smoothState0 = FL2FXCONST_DBL(1.0f/(1<<1));
limiter->minGain = FL2FXCONST_DBL(1.0f/(1<<1));
limiter->additionalGainPrev = FL2FXCONST_DBL(1.0f/(1<<TDL_GAIN_SCALING));
limiter->additionalGainFilterState = FL2FXCONST_DBL(1.0f/(1<<TDL_GAIN_SCALING));
limiter->additionalGainFilterState1 = FL2FXCONST_DBL(1.0f/(1<<TDL_GAIN_SCALING));
FDKmemset(limiter->maxBuf, 0, (limiter->attack + 1) * sizeof(FIXP_DBL) );
FDKmemset(limiter->delayBuf, 0, limiter->attack * limiter->channels * sizeof(FIXP_DBL) );
}
else {
return TDLIMIT_INVALID_HANDLE;
}
return TDLIMIT_OK;
}
/* destroy limiter */
TDLIMITER_ERROR destroyLimiter(TDLimiterPtr limiter)
{
if (limiter != NULL) {
FDKfree(limiter->maxBuf);
FDKfree(limiter->delayBuf);
FDKfree(limiter);
}
else {
return TDLIMIT_INVALID_HANDLE;
}
return TDLIMIT_OK;
}
/* apply limiter */
TDLIMITER_ERROR applyLimiter(TDLimiterPtr limiter,
INT_PCM* samples,
FIXP_DBL* pGain,
const INT* gain_scale,
const UINT gain_size,
const UINT gain_delay,
const UINT nSamples)
{
unsigned int i, j;
FIXP_PCM tmp1, tmp2;
FIXP_DBL tmp, old, gain, additionalGain, additionalGainUnfiltered;
FIXP_DBL minGain = FL2FXCONST_DBL(1.0f/(1<<1));
FDK_ASSERT(gain_size == 1);
FDK_ASSERT(gain_delay <= nSamples);
if ( limiter == NULL ) return TDLIMIT_INVALID_HANDLE;
{
unsigned int channels = limiter->channels;
unsigned int attack = limiter->attack;
FIXP_DBL attackConst = limiter->attackConst;
FIXP_DBL releaseConst = limiter->releaseConst;
FIXP_DBL threshold = FX_PCM2FX_DBL(limiter->threshold)>>TDL_GAIN_SCALING;
FIXP_DBL max = limiter->max;
FIXP_DBL* maxBuf = limiter->maxBuf;
unsigned int maxBufIdx = limiter->maxBufIdx;
FIXP_DBL cor = limiter->cor;
FIXP_DBL* delayBuf = limiter->delayBuf;
unsigned int delayBufIdx = limiter->delayBufIdx;
FIXP_DBL smoothState0 = limiter->smoothState0;
FIXP_DBL additionalGainSmoothState = limiter->additionalGainFilterState;
FIXP_DBL additionalGainSmoothState1 = limiter->additionalGainFilterState1;
for (i = 0; i < nSamples; i++) {
if (i < gain_delay) {
additionalGainUnfiltered = limiter->additionalGainPrev;
} else {
additionalGainUnfiltered = pGain[0];
}
/* Smooth additionalGain */
/* [b,a] = butter(1, 0.01) */
static const FIXP_SGL b[] = { FL2FXCONST_SGL(0.015466*2.0), FL2FXCONST_SGL( 0.015466*2.0) };
static const FIXP_SGL a[] = { FL2FXCONST_SGL(1.000000), FL2FXCONST_SGL(-0.96907) };
/* [b,a] = butter(1, 0.001) */
//static const FIXP_SGL b[] = { FL2FXCONST_SGL(0.0015683*2.0), FL2FXCONST_SGL( 0.0015683*2.0) };
//static const FIXP_SGL a[] = { FL2FXCONST_SGL(1.0000000), FL2FXCONST_SGL(-0.99686) };
additionalGain = - fMult(additionalGainSmoothState, a[1]) + fMultDiv2( additionalGainUnfiltered, b[0]) + fMultDiv2(additionalGainSmoothState1, b[1]);
additionalGainSmoothState1 = additionalGainUnfiltered;
additionalGainSmoothState = additionalGain;
/* Apply the additional scaling that has no delay and no smoothing */
if (gain_scale[0] > 0) {
additionalGain <<= gain_scale[0];
} else {
additionalGain >>= gain_scale[0];
}
/* get maximum absolute sample value of all channels, including the additional gain. */
tmp1 = (FIXP_PCM)0;
for (j = 0; j < channels; j++) {
tmp2 = (FIXP_PCM)samples[i * channels + j];
if (tmp2 == (FIXP_PCM)SAMPLE_MIN) /* protect fAbs from -1.0 value */
tmp2 = (FIXP_PCM)(SAMPLE_MIN+1);
tmp1 = fMax(tmp1, fAbs(tmp2));
}
tmp = SATURATE_LEFT_SHIFT(fMultDiv2(tmp1, additionalGain), 1, DFRACT_BITS);
/* set threshold as lower border to save calculations in running maximum algorithm */
tmp = fMax(tmp, threshold);
/* running maximum */
old = maxBuf[maxBufIdx];
maxBuf[maxBufIdx] = tmp;
if (tmp >= max) {
/* new sample is greater than old maximum, so it is the new maximum */
max = tmp;
}
else if (old < max) {
/* maximum does not change, as the sample, which has left the window was
not the maximum */
}
else {
/* the old maximum has left the window, we have to search the complete
buffer for the new max */
max = maxBuf[0];
for (j = 1; j <= attack; j++) {
if (maxBuf[j] > max) max = maxBuf[j];
}
}
maxBufIdx++;
if (maxBufIdx >= attack+1) maxBufIdx = 0;
/* calc gain */
/* gain is downscaled by one, so that gain = 1.0 can be represented */
if (max > threshold) {
gain = fDivNorm(threshold, max)>>1;
}
else {
gain = FL2FXCONST_DBL(1.0f/(1<<1));
}
/* gain smoothing, method: TDL_EXPONENTIAL */
/* first order IIR filter with attack correction to avoid overshoots */
/* correct the 'aiming' value of the exponential attack to avoid the remaining overshoot */
if (gain < smoothState0) {
cor = fMin(cor, fMultDiv2((gain - fMultDiv2(FL2FXCONST_SGL(0.1f*(1<<1)),smoothState0)), FL2FXCONST_SGL(1.11111111f/(1<<1)))<<2);
}
else {
cor = gain;
}
/* smoothing filter */
if (cor < smoothState0) {
smoothState0 = fMult(attackConst,(smoothState0 - cor)) + cor; /* attack */
smoothState0 = fMax(smoothState0, gain); /* avoid overshooting target */
}
else {
/* sign inversion twice to round towards +infinity,
so that gain can converge to 1.0 again,
for bit-identical output when limiter is not active */
smoothState0 = -fMult(releaseConst,-(smoothState0 - cor)) + cor; /* release */
}
gain = smoothState0;
/* lookahead delay, apply gain */
for (j = 0; j < channels; j++) {
tmp = delayBuf[delayBufIdx * channels + j];
delayBuf[delayBufIdx * channels + j] = fMult((FIXP_PCM)samples[i * channels + j], additionalGain);
/* Apply gain to delayed signal */
if (gain < FL2FXCONST_DBL(1.0f/(1<<1)))
tmp = fMult(tmp,gain<<1);
samples[i * channels + j] = FX_DBL2FX_PCM((FIXP_DBL)SATURATE_LEFT_SHIFT(tmp,TDL_GAIN_SCALING,DFRACT_BITS));
}
delayBufIdx++;
if (delayBufIdx >= attack) delayBufIdx = 0;
/* save minimum gain factor */
if (gain < minGain) minGain = gain;
}
limiter->max = max;
limiter->maxBufIdx = maxBufIdx;
limiter->cor = cor;
limiter->delayBufIdx = delayBufIdx;
limiter->smoothState0 = smoothState0;
limiter->additionalGainFilterState = additionalGainSmoothState;
limiter->additionalGainFilterState1 = additionalGainSmoothState1;
limiter->minGain = minGain;
limiter->additionalGainPrev = pGain[0];
return TDLIMIT_OK;
}
}
/* get delay in samples */
unsigned int getLimiterDelay(TDLimiterPtr limiter)
{
FDK_ASSERT(limiter != NULL);
return limiter->attack;
}
/* set number of channels */
TDLIMITER_ERROR setLimiterNChannels(TDLimiterPtr limiter, unsigned int nChannels)
{
if ( limiter == NULL ) return TDLIMIT_INVALID_HANDLE;
if (nChannels > limiter->maxChannels) return TDLIMIT_INVALID_PARAMETER;
limiter->channels = nChannels;
//resetLimiter(limiter);
return TDLIMIT_OK;
}
/* set sampling rate */
TDLIMITER_ERROR setLimiterSampleRate(TDLimiterPtr limiter, unsigned int sampleRate)
{
unsigned int attack, release;
FIXP_DBL attackConst, releaseConst, exponent;
INT e_ans;
if ( limiter == NULL ) return TDLIMIT_INVALID_HANDLE;
if (sampleRate > limiter->maxSampleRate) return TDLIMIT_INVALID_PARAMETER;
/* update attack and release time in samples */
attack = (unsigned int)(limiter->attackMs * sampleRate / 1000);
release = (unsigned int)(limiter->releaseMs * sampleRate / 1000);
/* attackConst = pow(0.1, 1.0 / (attack + 1)) */
exponent = invFixp(attack+1);
attackConst = fPow(FL2FXCONST_DBL(0.1f), 0, exponent, 0, &e_ans);
attackConst = scaleValue(attackConst, e_ans);
/* releaseConst = (float)pow(0.1, 1.0 / (release + 1)) */
exponent = invFixp(release + 1);
releaseConst = fPow(FL2FXCONST_DBL(0.1f), 0, exponent, 0, &e_ans);
releaseConst = scaleValue(releaseConst, e_ans);
limiter->attack = attack;
limiter->attackConst = attackConst;
limiter->releaseConst = releaseConst;
limiter->sampleRate = sampleRate;
/* reset */
//resetLimiter(limiter);
return TDLIMIT_OK;
}
/* set attack time */
TDLIMITER_ERROR setLimiterAttack(TDLimiterPtr limiter, unsigned int attackMs)
{
unsigned int attack;
FIXP_DBL attackConst, exponent;
INT e_ans;
if ( limiter == NULL ) return TDLIMIT_INVALID_HANDLE;
if (attackMs > limiter->maxAttackMs) return TDLIMIT_INVALID_PARAMETER;
/* calculate attack time in samples */
attack = (unsigned int)(attackMs * limiter->sampleRate / 1000);
/* attackConst = pow(0.1, 1.0 / (attack + 1)) */
exponent = invFixp(attack+1);
attackConst = fPow(FL2FXCONST_DBL(0.1f), 0, exponent, 0, &e_ans);
attackConst = scaleValue(attackConst, e_ans);
limiter->attack = attack;
limiter->attackConst = attackConst;
limiter->attackMs = attackMs;
return TDLIMIT_OK;
}
/* set release time */
TDLIMITER_ERROR setLimiterRelease(TDLimiterPtr limiter, unsigned int releaseMs)
{
unsigned int release;
FIXP_DBL releaseConst, exponent;
INT e_ans;
if ( limiter == NULL ) return TDLIMIT_INVALID_HANDLE;
/* calculate release time in samples */
release = (unsigned int)(releaseMs * limiter->sampleRate / 1000);
/* releaseConst = (float)pow(0.1, 1.0 / (release + 1)) */
exponent = invFixp(release + 1);
releaseConst = fPow(FL2FXCONST_DBL(0.1f), 0, exponent, 0, &e_ans);
releaseConst = scaleValue(releaseConst, e_ans);
limiter->releaseConst = releaseConst;
limiter->releaseMs = releaseMs;
return TDLIMIT_OK;
}
/* set limiter threshold */
TDLIMITER_ERROR setLimiterThreshold(TDLimiterPtr limiter, INT_PCM threshold)
{
if ( limiter == NULL ) return TDLIMIT_INVALID_HANDLE;
limiter->threshold = (FIXP_PCM)threshold;
return TDLIMIT_OK;
}

File diff suppressed because it is too large Load Diff

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -145,6 +145,8 @@ typedef enum
SBR_SYSTEM_BITSTREAM_DELAY, /*!< System: Switch to enable an additional SBR bitstream delay of one frame. */
SBR_QMF_MODE, /*!< Set QMF mode, either complex or low power. */
SBR_LD_QMF_TIME_ALIGN, /*!< Set QMF type, either LD-MPS or CLDFB. Relevant for ELD streams only. */
SBR_FLUSH_DATA, /*!< Set internal state to flush the decoder with the next process call. */
SBR_CLEAR_HISTORY, /*!< Clear all internal states (delay lines, QMF states, ...). */
SBR_BS_INTERRUPTION /*!< Signal bit stream interruption. Value is ignored. */
} SBRDEC_PARAM;
@ -260,6 +262,7 @@ void sbrDecoder_drcDisable ( HANDLE_SBRDECODER self,
* into *count if a payload length is given (byPayLen > 0). If no SBR payload length is
* given (bsPayLen < 0) then the bit stream position on return will be random after this
* function call in case of errors, and any further decoding will be completely pointless.
* This function accepts either normal ordered SBR data or reverse ordered DRM SBR data.
*
* \param self SBR decoder handle.
* \param hBs Bit stream handle as data source.
@ -308,7 +311,7 @@ SBR_ERROR sbrDecoder_Apply ( HANDLE_SBRDECODER self,
INT_PCM *timeData,
int *numChannels,
int *sampleRate,
const UCHAR channelMapping[(6)],
const UCHAR channelMapping[(8)],
const int interleaved,
const int coreDecodedOk,
UCHAR *psDecoded );
@ -329,6 +332,13 @@ SBR_ERROR sbrDecoder_Close ( HANDLE_SBRDECODER *self );
*/
INT sbrDecoder_GetLibInfo( LIB_INFO *info );
/**
* \brief Determine the modules output signal delay in samples.
* \param self SBR decoder handle.
* \return The number of samples signal delay added by the module.
*/
UINT sbrDecoder_GetDelay( const HANDLE_SBRDECODER self );
#ifdef __cplusplus
}

View File

@ -97,7 +97,10 @@ amm-info@iis.fraunhofer.de
#ifdef FUNCTION_LPPTRANSPOSER_func1
/* Note: This code requires only 43 cycles per iteration instead of 61 on ARM926EJ-S */
__attribute__ ((noinline)) static void lppTransposer_func1(
#ifdef __GNUC__
__attribute__ ((noinline))
#endif
static void lppTransposer_func1(
FIXP_DBL *lowBandReal,
FIXP_DBL *lowBandImag,
FIXP_DBL **qmfBufferReal,

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -151,13 +151,13 @@ typedef struct
}
ENV_CALC_NRGS;
/*static*/ void equalizeFiltBufferExp(FIXP_DBL *filtBuffer,
static void equalizeFiltBufferExp(FIXP_DBL *filtBuffer,
SCHAR *filtBuffer_e,
FIXP_DBL *NrgGain,
SCHAR *NrgGain_e,
int subbands);
/*static*/ void calcNrgPerSubband(FIXP_DBL **analysBufferReal,
static void calcNrgPerSubband(FIXP_DBL **analysBufferReal,
FIXP_DBL **analysBufferImag,
int lowSubband, int highSubband,
int start_pos, int next_pos,
@ -165,7 +165,7 @@ ENV_CALC_NRGS;
FIXP_DBL *nrgEst,
SCHAR *nrgEst_e );
/*static*/ void calcNrgPerSfb(FIXP_DBL **analysBufferReal,
static void calcNrgPerSfb(FIXP_DBL **analysBufferReal,
FIXP_DBL **analysBufferImag,
int nSfb,
UCHAR *freqBandTable,
@ -174,13 +174,13 @@ ENV_CALC_NRGS;
FIXP_DBL *nrg_est,
SCHAR *nrg_est_e );
/*static*/ void calcSubbandGain(FIXP_DBL nrgRef, SCHAR nrgRef_e, ENV_CALC_NRGS* nrgs, int c,
static void calcSubbandGain(FIXP_DBL nrgRef, SCHAR nrgRef_e, ENV_CALC_NRGS* nrgs, int c,
FIXP_DBL tmpNoise, SCHAR tmpNoise_e,
UCHAR sinePresentFlag,
UCHAR sineMapped,
int noNoiseFlag);
/*static*/ void calcAvgGain(ENV_CALC_NRGS* nrgs,
static void calcAvgGain(ENV_CALC_NRGS* nrgs,
int lowSubband,
int highSubband,
FIXP_DBL *sumRef_m,
@ -188,7 +188,7 @@ ENV_CALC_NRGS;
FIXP_DBL *ptrAvgGain_m,
SCHAR *ptrAvgGain_e);
/*static*/ void adjustTimeSlotLC(FIXP_DBL *ptrReal,
static void adjustTimeSlot_EldGrid(FIXP_DBL *ptrReal,
ENV_CALC_NRGS* nrgs,
UCHAR *ptrHarmIndex,
int lowSubbands,
@ -196,8 +196,17 @@ ENV_CALC_NRGS;
int scale_change,
int noNoiseFlag,
int *ptrPhaseIndex,
int fCldfb);
/*static*/ void adjustTimeSlotHQ(FIXP_DBL *ptrReal,
int scale_diff_low);
static void adjustTimeSlotLC(FIXP_DBL *ptrReal,
ENV_CALC_NRGS* nrgs,
UCHAR *ptrHarmIndex,
int lowSubbands,
int noSubbands,
int scale_change,
int noNoiseFlag,
int *ptrPhaseIndex);
static void adjustTimeSlotHQ(FIXP_DBL *ptrReal,
FIXP_DBL *ptrImag,
HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env,
ENV_CALC_NRGS* nrgs,
@ -224,7 +233,7 @@ ENV_CALC_NRGS;
Additionally, the flags in harmFlagsPrev are being updated by this function
for the next frame.
*/
/*static*/ void mapSineFlags(UCHAR *freqBandTable, /*!< Band borders (there's only 1 flag per band) */
static void mapSineFlags(UCHAR *freqBandTable, /*!< Band borders (there's only 1 flag per band) */
int nSfb, /*!< Number of bands in the table */
UCHAR *addHarmonics, /*!< vector with 1 flag per sfb */
int *harmFlagsPrev, /*!< Packed 'addHarmonics' */
@ -990,7 +999,6 @@ calculateSbrEnvelope (QMF_SCALE_FACTOR *sbrScaleFactor, /*!< Scaling
/* Prevent the smoothing filter from running on constant levels */
if (j-start_pos < smooth_length)
smooth_ratio = FDK_sbrDecoder_sbr_smoothFilter[j-start_pos];
else
smooth_ratio = FL2FXCONST_SGL(0.0f);
@ -1007,7 +1015,8 @@ calculateSbrEnvelope (QMF_SCALE_FACTOR *sbrScaleFactor, /*!< Scaling
}
else
{
adjustTimeSlotLC(&analysBufferReal[j][lowSubband],
if (flags & SBRDEC_ELD_GRID) {
adjustTimeSlot_EldGrid(&analysBufferReal[j][lowSubband],
pNrgs,
&h_sbr_cal_env->harmIndex,
lowSubband,
@ -1015,7 +1024,18 @@ calculateSbrEnvelope (QMF_SCALE_FACTOR *sbrScaleFactor, /*!< Scaling
scale_change,
noNoiseFlag,
&h_sbr_cal_env->phaseIndex,
(flags & SBRDEC_ELD_GRID));
EXP2SCALE(adj_e) - sbrScaleFactor->lb_scale);
} else
{
adjustTimeSlotLC(&analysBufferReal[j][lowSubband],
pNrgs,
&h_sbr_cal_env->harmIndex,
lowSubband,
noSubbands,
scale_change,
noNoiseFlag,
&h_sbr_cal_env->phaseIndex);
}
}
} // for
@ -1176,7 +1196,7 @@ resetSbrEnvelopeCalc (HANDLE_SBR_CALCULATE_ENVELOPE hCalEnv) /*!< pointer to env
can be performed.
This function is called once for each envelope before adjusting.
*/
/*static*/ void equalizeFiltBufferExp(FIXP_DBL *filtBuffer, /*!< bufferd gains */
static void equalizeFiltBufferExp(FIXP_DBL *filtBuffer, /*!< bufferd gains */
SCHAR *filtBuffer_e, /*!< exponents of bufferd gains */
FIXP_DBL *nrgGain, /*!< gains for current envelope */
SCHAR *nrgGain_e, /*!< exponents of gains for current envelope */
@ -1331,7 +1351,7 @@ FIXP_DBL maxSubbandSample( FIXP_DBL ** re, /*!< Real part of input and output
This function is used when interpolFreq is true.
*/
/*static*/ void calcNrgPerSubband(FIXP_DBL **analysBufferReal, /*!< Real part of subband samples */
static void calcNrgPerSubband(FIXP_DBL **analysBufferReal, /*!< Real part of subband samples */
FIXP_DBL **analysBufferImag, /*!< Imaginary part of subband samples */
int lowSubband, /*!< Begin of the SBR frequency range */
int highSubband, /*!< High end of the SBR frequency range */
@ -1452,7 +1472,7 @@ FIXP_DBL maxSubbandSample( FIXP_DBL ** re, /*!< Real part of input and output
This function is used when interpolFreq is false.
*/
/*static*/ void calcNrgPerSfb(FIXP_DBL **analysBufferReal, /*!< Real part of subband samples */
static void calcNrgPerSfb(FIXP_DBL **analysBufferReal, /*!< Real part of subband samples */
FIXP_DBL **analysBufferImag, /*!< Imaginary part of subband samples */
int nSfb, /*!< Number of scale factor bands */
UCHAR *freqBandTable, /*!< First Subband for each Sfb */
@ -1585,7 +1605,7 @@ FIXP_DBL maxSubbandSample( FIXP_DBL ** re, /*!< Real part of input and output
The resulting energy gain is given by mantissa and exponent.
*/
/*static*/ void calcSubbandGain(FIXP_DBL nrgRef, /*!< Reference Energy according to envelope data */
static void calcSubbandGain(FIXP_DBL nrgRef, /*!< Reference Energy according to envelope data */
SCHAR nrgRef_e, /*!< Reference Energy according to envelope data (exponent) */
ENV_CALC_NRGS* nrgs,
int i,
@ -1689,7 +1709,7 @@ FIXP_DBL maxSubbandSample( FIXP_DBL ** re, /*!< Real part of input and output
The result is used as a relative limit for all gains within the
current "limiter band" (a certain frequency range).
*/
/*static*/ void calcAvgGain(ENV_CALC_NRGS* nrgs,
static void calcAvgGain(ENV_CALC_NRGS* nrgs,
int lowSubband, /*!< Begin of the limiter band */
int highSubband, /*!< High end of the limiter band */
FIXP_DBL *ptrSumRef,
@ -1728,21 +1748,101 @@ FIXP_DBL maxSubbandSample( FIXP_DBL ** re, /*!< Real part of input and output
*ptrSumRef_e = sumRef_e;
}
static void adjustTimeSlot_EldGrid(
FIXP_DBL *ptrReal, /*!< Subband samples to be adjusted, real part */
ENV_CALC_NRGS* nrgs,
UCHAR *ptrHarmIndex, /*!< Harmonic index */
int lowSubband, /*!< Lowest QMF-channel in the currently used SBR range. */
int noSubbands, /*!< Number of QMF subbands */
int scale_change, /*!< Number of bits to shift adjusted samples */
int noNoiseFlag, /*!< Flag to suppress noise addition */
int *ptrPhaseIndex, /*!< Start index to random number array */
int scale_diff_low) /*!< */
{
int k;
FIXP_DBL signalReal, sbNoise;
int tone_count = 0;
FIXP_DBL *pGain = nrgs->nrgGain; /*!< Gains of current envelope */
FIXP_DBL *pNoiseLevel = nrgs->noiseLevel; /*!< Noise levels of current envelope */
FIXP_DBL *pSineLevel = nrgs->nrgSine; /*!< Sine levels */
int phaseIndex = *ptrPhaseIndex;
UCHAR harmIndex = *ptrHarmIndex;
static const INT harmonicPhase [2][4] = {
{ 1, 0, -1, 0},
{ 0, 1, 0, -1}
};
static const FIXP_DBL harmonicPhaseX [2][4] = {
{ FL2FXCONST_DBL(2.0*1.245183154539139e-001), FL2FXCONST_DBL(2.0*-1.123767859325028e-001), FL2FXCONST_DBL(2.0*-1.245183154539139e-001), FL2FXCONST_DBL(2.0* 1.123767859325028e-001) },
{ FL2FXCONST_DBL(2.0*1.245183154539139e-001), FL2FXCONST_DBL(2.0* 1.123767859325028e-001), FL2FXCONST_DBL(2.0*-1.245183154539139e-001), FL2FXCONST_DBL(2.0*-1.123767859325028e-001) }
};
for (k=0; k < noSubbands; k++) {
phaseIndex = (phaseIndex + 1) & (SBR_NF_NO_RANDOM_VAL - 1);
if( (pSineLevel[0] != FL2FXCONST_DBL(0.0f)) || (noNoiseFlag == 1) ){
sbNoise = FL2FXCONST_DBL(0.0f);
} else {
sbNoise = pNoiseLevel[0];
}
signalReal = fMultDiv2(*ptrReal,*pGain) << ((int)scale_change);
signalReal += (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[phaseIndex][0], sbNoise)<<4);
signalReal += pSineLevel[0] * harmonicPhase[0][harmIndex];
*ptrReal = signalReal;
if (k == 0) {
*(ptrReal-1) += scaleValue(fMultDiv2(harmonicPhaseX[lowSubband&1][harmIndex], pSineLevel[0]), -scale_diff_low) ;
if (k < noSubbands - 1) {
*(ptrReal) += fMultDiv2(pSineLevel[1], harmonicPhaseX[(lowSubband+1)&1][harmIndex]);
}
}
if (k > 0 && k < noSubbands - 1 && tone_count < 16) {
*(ptrReal) += fMultDiv2(pSineLevel[- 1], harmonicPhaseX [(lowSubband+k)&1] [harmIndex]);
*(ptrReal) += fMultDiv2(pSineLevel[+ 1], harmonicPhaseX [(lowSubband+k+1)&1][harmIndex]);
}
if (k == noSubbands - 1 && tone_count < 16) {
if (k > 0) {
*(ptrReal) += fMultDiv2(pSineLevel[- 1], harmonicPhaseX [(lowSubband+k)&1][harmIndex]);
}
if (k + lowSubband + 1< 63) {
*(ptrReal+1) += fMultDiv2(pSineLevel[0], harmonicPhaseX[(lowSubband+k+1)&1][harmIndex]);
}
}
if(pSineLevel[0] != FL2FXCONST_DBL(0.0f)){
tone_count++;
}
ptrReal++;
pNoiseLevel++;
pGain++;
pSineLevel++;
}
*ptrHarmIndex = (harmIndex + 1) & 3;
*ptrPhaseIndex = phaseIndex & (SBR_NF_NO_RANDOM_VAL - 1);
}
/*!
\brief Amplify one timeslot of the signal with the calculated gains
and add the noisefloor.
*/
/*static*/ void adjustTimeSlotLC(FIXP_DBL *ptrReal, /*!< Subband samples to be adjusted, real part */
static void adjustTimeSlotLC(FIXP_DBL *ptrReal, /*!< Subband samples to be adjusted, real part */
ENV_CALC_NRGS* nrgs,
UCHAR *ptrHarmIndex, /*!< Harmonic index */
int lowSubband, /*!< Lowest QMF-channel in the currently used SBR range. */
int noSubbands, /*!< Number of QMF subbands */
int scale_change, /*!< Number of bits to shift adjusted samples */
int noNoiseFlag, /*!< Flag to suppress noise addition */
int *ptrPhaseIndex, /*!< Start index to random number array */
int fCldfb) /*!< CLDFB 80 flag */
int *ptrPhaseIndex) /*!< Start index to random number array */
{
FIXP_DBL *pGain = nrgs->nrgGain; /*!< Gains of current envelope */
FIXP_DBL *pNoiseLevel = nrgs->noiseLevel; /*!< Noise levels of current envelope */
@ -1775,41 +1875,10 @@ FIXP_DBL maxSubbandSample( FIXP_DBL ** re, /*!< Real part of input and output
sineLevelNext = (noSubbands > 1) ? pSineLevel[0] : FL2FXCONST_DBL(0.0f);
if (sineLevel!=FL2FXCONST_DBL(0.0f)) tone_count++;
else if (!noNoiseFlag)
/* Add noisefloor to the amplified signal */
signalReal += (fMultDiv2(FDK_sbrDecoder_sbr_randomPhase[index][0], pNoiseLevel[0])<<4);
if (fCldfb) {
if (!(harmIndex&0x1)) {
/* harmIndex 0,2 */
signalReal += (harmIndex&0x2) ? -sineLevel : sineLevel;
*ptrReal++ = signalReal;
}
else {
/* harmIndex 1,3 in combination with freqInvFlag */
int shift = (int) (scale_change+1);
shift = (shift>=0) ? fixMin(DFRACT_BITS-1,shift) : fixMax(-(DFRACT_BITS-1),shift);
FIXP_DBL tmp1 = scaleValue( fMultDiv2(C1_CLDFB, sineLevel), -shift );
FIXP_DBL tmp2 = fMultDiv2(C1_CLDFB, sineLevelNext);
/* save switch and compare operations and reduce to XOR statement */
if ( ((harmIndex>>1)&0x1)^freqInvFlag) {
*(ptrReal-1) += tmp1;
signalReal -= tmp2;
} else {
*(ptrReal-1) -= tmp1;
signalReal += tmp2;
}
*ptrReal++ = signalReal;
freqInvFlag = !freqInvFlag;
}
} else
{
if (!(harmIndex&0x1)) {
/* harmIndex 0,2 */
@ -1933,8 +2002,9 @@ FIXP_DBL maxSubbandSample( FIXP_DBL ** re, /*!< Real part of input and output
*ptrHarmIndex = (harmIndex + 1) & 3;
*ptrPhaseIndex = index & (SBR_NF_NO_RANDOM_VAL - 1);
}
void adjustTimeSlotHQ(FIXP_DBL *RESTRICT ptrReal, /*!< Subband samples to be adjusted, real part */
FIXP_DBL *RESTRICT ptrImag, /*!< Subband samples to be adjusted, imag part */
static void adjustTimeSlotHQ(
FIXP_DBL *RESTRICT ptrReal, /*!< Subband samples to be adjusted, real part */
FIXP_DBL *RESTRICT ptrImag, /*!< Subband samples to be adjusted, imag part */
HANDLE_SBR_CALCULATE_ENVELOPE h_sbr_cal_env,
ENV_CALC_NRGS* nrgs,
int lowSubband, /*!< Lowest QMF-channel in the currently used SBR range. */
@ -1961,7 +2031,7 @@ void adjustTimeSlotHQ(FIXP_DBL *RESTRICT ptrReal, /*!< Subband samples
FIXP_SGL direct_ratio = /*FL2FXCONST_SGL(1.0f) */ (FIXP_SGL)MAXVAL_SGL - smooth_ratio;
int index = *ptrPhaseIndex;
UCHAR harmIndex = *ptrHarmIndex;
register int freqInvFlag = (lowSubband & 1);
int freqInvFlag = (lowSubband & 1);
FIXP_DBL sineLevel;
int shift;
@ -2137,7 +2207,6 @@ ResetLimiterBands ( UCHAR *limiterBandTable, /*!< Resulting band borders in QM
UCHAR workLimiterBandTable[MAX_FREQ_COEFFS / 2 + MAX_NUM_PATCHES + 1];
int patchBorders[MAX_NUM_PATCHES + 1];
int kx, k2;
FIXP_DBL temp;
int lowSubband = freqBandTable[0];
int highSubband = freqBandTable[noFreqBands];
@ -2169,13 +2238,32 @@ ResetLimiterBands ( UCHAR *limiterBandTable, /*!< Resulting band borders in QM
while (hiLimIndex <= tempNoLim) {
FIXP_DBL div_m, oct_m, temp;
INT div_e = 0, oct_e = 0, temp_e = 0;
k2 = workLimiterBandTable[hiLimIndex] + lowSubband;
kx = workLimiterBandTable[loLimIndex] + lowSubband;
temp = FX_SGL2FX_DBL(FDK_getNumOctavesDiv8(kx,k2)); /* Number of octaves */
temp = fMult(temp, FDK_sbrDecoder_sbr_limiterBandsPerOctaveDiv4[limiterBands]);
div_m = fDivNorm(k2, kx, &div_e);
/* calculate number of octaves */
oct_m = fLog2(div_m, div_e, &oct_e);
/* multiply with limiterbands per octave */
/* values 1, 1.2, 2, 3 -> scale factor of 2 */
temp = fMultNorm(oct_m, FDK_sbrDecoder_sbr_limiterBandsPerOctaveDiv4_DBL[limiterBands], &temp_e);
/* overall scale factor of temp ist addition of scalefactors from log2 calculation,
limiter bands scalefactor (2) and limiter bands multiplication */
temp_e += oct_e + 2;
/* div can be a maximum of 64 (k2 = 64 and kx = 1)
-> oct can be a maximum of 6
-> temp can be a maximum of 18 (as limiterBandsPerOctoave is a maximum factor of 3)
-> we need a scale factor of 5 for comparisson
*/
if (temp >> (5 - temp_e) < FL2FXCONST_DBL (0.49f) >> 5) {
if (temp < FL2FXCONST_DBL (0.49f)>>5) {
if (workLimiterBandTable[hiLimIndex] == workLimiterBandTable[loLimIndex]) {
workLimiterBandTable[hiLimIndex] = highSubband;
nBands--;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -369,7 +369,7 @@ leanSbrConcealment(HANDLE_SBR_HEADER_DATA hHeaderData, /*!< Static control d
FIXP_SGL step; /* speed of fade */
int i;
int currentStartPos = h_prev_data->stopPos - hHeaderData->numberTimeSlots;
int currentStartPos = FDKmax(0, h_prev_data->stopPos - hHeaderData->numberTimeSlots);
int currentStopPos = hHeaderData->numberTimeSlots;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -327,7 +327,7 @@ sbrGetHeaderData (HANDLE_SBR_HEADER_DATA hHeaderData,
}
/* Look for new settings. IEC 14496-3, 4.6.18.3.1 */
if(hHeaderData->syncState != SBR_ACTIVE ||
if(hHeaderData->syncState < SBR_HEADER ||
lastHeader.startFreq != pBsData->startFreq ||
lastHeader.stopFreq != pBsData->stopFreq ||
lastHeader.freqScale != pBsData->freqScale ||
@ -904,6 +904,9 @@ static const FRAME_INFO v_frame_info4_8 = { 0, 4, {0, 2, 4, 6, 8}, {1, 1, 1, 1},
break;
default:
FDK_ASSERT(0);
/* in case assertion checks are disabled, force a definite memory fault at first access */
pTable = NULL;
break;
}
/* look number of envelopes in table */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -125,6 +125,7 @@ amm-info@iis.fraunhofer.de
typedef enum
{
HEADER_NOT_PRESENT,
HEADER_ERROR,
HEADER_OK,
HEADER_RESET
}
@ -132,10 +133,10 @@ SBR_HEADER_STATUS;
typedef enum
{
SBR_NOT_INITIALIZED,
UPSAMPLING,
SBR_HEADER,
SBR_ACTIVE
SBR_NOT_INITIALIZED = 0,
UPSAMPLING = 1,
SBR_HEADER = 2,
SBR_ACTIVE = 3
}
SBR_SYNC_STATE;
@ -179,6 +180,10 @@ typedef FREQ_BAND_DATA *HANDLE_FREQ_BAND_DATA;
#define SBRDEC_LOW_POWER 16 /* Flag indicating that Low Power QMF mode shall be used. */
#define SBRDEC_PS_DECODED 32 /* Flag indicating that PS was decoded and rendered. */
#define SBRDEC_LD_MPS_QMF 512 /* Flag indicating that the LD-MPS QMF shall be used. */
#define SBRDEC_SYNTAX_DRM 2048 /* Flag indicating that DRM30/DRM+ reverse syntax is being used. */
#define SBRDEC_DOWNSAMPLE 8192 /* Flag indicating that the downsampling mode is used. */
#define SBRDEC_FLUSH 16384 /* Flag is used to flush all elements in use. */
#define SBRDEC_FORCE_RESET 32768 /* Flag is used to force a reset of all elements in use. */
#define SBRDEC_HDR_STAT_RESET 1
#define SBRDEC_HDR_STAT_UPDATE 2

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -225,7 +225,14 @@ static void changeQmfType( HANDLE_SBR_DEC hSbrDec, /*!< hand
}
if (resetAnaQmf) {
int qmfErr = qmfInitAnalysisFilterBank (
QMF_FILTER_BANK prvAnaQmf;
int qmfErr;
/* Store current configuration */
FDKmemcpy(&prvAnaQmf, &hSbrDec->AnalysiscQMF, sizeof(QMF_FILTER_BANK));
/* Reset analysis QMF */
qmfErr = qmfInitAnalysisFilterBank (
&hSbrDec->AnalysiscQMF,
hSbrDec->anaQmfStates,
hSbrDec->AnalysiscQMF.no_col,
@ -234,13 +241,22 @@ static void changeQmfType( HANDLE_SBR_DEC hSbrDec, /*!< hand
hSbrDec->AnalysiscQMF.no_channels,
anaQmfFlags | QMF_FLAG_KEEP_STATES
);
if (qmfErr != 0) {
FDK_ASSERT(0);
/* Restore old configuration of analysis QMF */
FDKmemcpy(&hSbrDec->AnalysiscQMF, &prvAnaQmf, sizeof(QMF_FILTER_BANK));
}
}
if (resetSynQmf) {
int qmfErr = qmfInitSynthesisFilterBank (
QMF_FILTER_BANK prvSynQmf;
int qmfErr;
/* Store current configuration */
FDKmemcpy(&prvSynQmf, &hSbrDec->SynthesisQMF, sizeof(QMF_FILTER_BANK));
/* Reset synthesis QMF */
qmfErr = qmfInitSynthesisFilterBank (
&hSbrDec->SynthesisQMF,
hSbrDec->pSynQmfStates,
hSbrDec->SynthesisQMF.no_col,
@ -251,7 +267,8 @@ static void changeQmfType( HANDLE_SBR_DEC hSbrDec, /*!< hand
);
if (qmfErr != 0) {
FDK_ASSERT(0);
/* Restore old configuration of synthesis QMF */
FDKmemcpy(&hSbrDec->SynthesisQMF, &prvSynQmf, sizeof(QMF_FILTER_BANK));
}
}
}
@ -321,7 +338,8 @@ sbr_dec ( HANDLE_SBR_DEC hSbrDec, /*!< handle to Decoder channel */
HANDLE_SBR_PREV_FRAME_DATA hPrevFrameData, /*!< Some control data of last frame */
const int applyProcessing, /*!< Flag for SBR operation */
HANDLE_PS_DEC h_ps_d,
const UINT flags
const UINT flags,
const int codecFrameSize
)
{
int i, slot, reserve;
@ -348,6 +366,33 @@ sbr_dec ( HANDLE_SBR_DEC hSbrDec, /*!< handle to Decoder channel */
if (flags & SBRDEC_ELD_GRID) {
/* Choose the right low delay filter bank */
changeQmfType( hSbrDec, (flags & SBRDEC_LD_MPS_QMF) ? 1 : 0 );
/* If the LD-MPS QMF is not available delay the signal by (96-48*ldSbrSamplingRate)
* samples according to ISO/IEC 14496-3:2009/FDAM 2:2010(E) chapter 4.5.2.13. */
if ( (flags & SBRDEC_LD_MPS_QMF)
&& (hSbrDec->AnalysiscQMF.flags & QMF_FLAG_CLDFB) )
{
INT_PCM *pDlyBuf = hSbrDec->coreDelayBuf; /* DLYBUF */
int smpl, delay = 96 >> (!(flags & SBRDEC_DOWNSAMPLE) ? 1 : 0);
/* Create TMPBUF */
C_AALLOC_SCRATCH_START(pcmTemp, INT_PCM, (96));
/* Copy delay samples from INBUF to TMPBUF */
for (smpl = 0; smpl < delay; smpl += 1) {
pcmTemp[smpl] = timeIn[(codecFrameSize-delay+smpl)*strideIn];
}
/* Move input signal remainder to the very end of INBUF */
for (smpl = (codecFrameSize-delay-1)*strideIn; smpl >= 0; smpl -= strideIn) {
timeIn[smpl+delay] = timeIn[smpl];
}
/* Copy delayed samples from last frame from DLYBUF to the very beginning of INBUF */
for (smpl = 0; smpl < delay; smpl += 1) {
timeIn[smpl*strideIn] = pDlyBuf[smpl];
}
/* Copy TMPBUF to DLYBUF */
FDKmemcpy(pDlyBuf, pcmTemp, delay*sizeof(INT_PCM));
/* Destory TMPBUF */
C_AALLOC_SCRATCH_END(pcmTemp, INT_PCM, (96));
}
}
/*
@ -761,7 +806,7 @@ createSbrDec (SBR_CHANNEL * hSbrChannel,
{
int qmfErr;
/* Adapted QMF analysis post-twiddles for down-sampled HQ SBR */
const UINT downSampledFlag = (downsampleFac==2) ? QMF_FLAG_DOWNSAMPLED : 0;
const UINT downSampledFlag = (flags & SBRDEC_DOWNSAMPLE) ? QMF_FLAG_DOWNSAMPLED : 0;
qmfErr = qmfInitAnalysisFilterBank (
&hs->AnalysiscQMF,
@ -836,6 +881,9 @@ createSbrDec (SBR_CHANNEL * hSbrChannel,
}
}
/* Clear input delay line */
FDKmemclear(hs->coreDelayBuf, (96)*sizeof(INT_PCM));
/* assign qmf time slots */
assignTimeSlots( &hSbrChannel->SbrDec, hHeaderData->numberTimeSlots * hHeaderData->timeStep, qmfFlags & QMF_FLAG_LP);

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -118,6 +118,9 @@ typedef struct
FIXP_DBL * WorkBuffer1;
FIXP_DBL * WorkBuffer2;
/* Delayed time input signal needed to align CLDFD with LD-MPS QMF. */
INT_PCM coreDelayBuf[(96)];
/* QMF filter states */
FIXP_QAS anaQmfStates[(320)];
FIXP_QSS * pSynQmfStates;
@ -182,7 +185,8 @@ sbr_dec (HANDLE_SBR_DEC hSbrDec, /*!< handle to Decoder channel */
HANDLE_SBR_PREV_FRAME_DATA hPrevFrameData, /*!< Some control data of last frame */
const int applyProcessing, /*!< Flag for SBR operation */
HANDLE_PS_DEC h_ps_d,
const UINT flags
const UINT flags,
const int codecFrameSize
);

View File

@ -107,19 +107,19 @@ amm-info@iis.fraunhofer.de
/*! SBR Decoder main structure */
C_ALLOC_MEM(Ram_SbrDecoder, struct SBR_DECODER_INSTANCE, 1)
/*! SBR Decoder element data <br>
Dimension: (4) */
C_ALLOC_MEM2(Ram_SbrDecElement, SBR_DECODER_ELEMENT, 1, (4))
Dimension: (8) */
C_ALLOC_MEM2(Ram_SbrDecElement, SBR_DECODER_ELEMENT, 1, (8))
/*! SBR Decoder individual channel data <br>
Dimension: (6) */
C_ALLOC_MEM2(Ram_SbrDecChannel, SBR_CHANNEL, 1, (6)+1)
Dimension: (8) */
C_ALLOC_MEM2(Ram_SbrDecChannel, SBR_CHANNEL, 1, (8)+1)
/*! Filter states for QMF-synthesis. <br>
Dimension: #(6) * (#QMF_FILTER_STATE_SYN_SIZE-#(64)) */
C_AALLOC_MEM2_L(Ram_sbr_QmfStatesSynthesis, FIXP_QSS, (640)-(64), (6)+1, SECT_DATA_L1)
Dimension: #(8) * (#QMF_FILTER_STATE_SYN_SIZE-#(64)) */
C_AALLOC_MEM2_L(Ram_sbr_QmfStatesSynthesis, FIXP_QSS, (640)-(64), (8)+1, SECT_DATA_L1)
/*! Delayed spectral data needed for the dynamic framing of SBR.
For mp3PRO, 1/3 of a frame is buffered (#(6) 6) */
C_AALLOC_MEM2(Ram_sbr_OverlapBuffer, FIXP_DBL, 2 * (6) * (64), (6)+1)
C_AALLOC_MEM2(Ram_sbr_OverlapBuffer, FIXP_DBL, 2 * (6) * (64), (8)+1)
/*! Static Data of PS */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -118,8 +118,8 @@ typedef struct
struct SBR_DECODER_INSTANCE
{
SBR_DECODER_ELEMENT *pSbrElement[(4)];
SBR_HEADER_DATA sbrHeader[(4)][(1)+1]; /* Sbr header for each individual channel of an element */
SBR_DECODER_ELEMENT *pSbrElement[(8)];
SBR_HEADER_DATA sbrHeader[(8)][(1)+1]; /* Sbr header for each individual channel of an element */
FIXP_DBL *workBuffer1;
FIXP_DBL *workBuffer2;
@ -135,6 +135,7 @@ struct SBR_DECODER_INSTANCE
USHORT codecFrameSize;
UCHAR synDownsampleFac;
UCHAR numDelayFrames; /* The current number of additional delay frames used for processing. */
UCHAR numFlushedFrames; /* The variable counts the number of frames which are flushed consecutively. */
UINT flags;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -189,6 +189,15 @@ const FIXP_SGL FDK_sbrDecoder_sbr_limiterBandsPerOctaveDiv4[4] =
FL2FXCONST_SGL(3.0f / 4.0f)
};
/*! Constants for calculating the number of limiter bands */
const FIXP_DBL FDK_sbrDecoder_sbr_limiterBandsPerOctaveDiv4_DBL[4] =
{
FL2FXCONST_DBL(1.0f / 4.0f),
FL2FXCONST_DBL(1.2f / 4.0f),
FL2FXCONST_DBL(2.0f / 4.0f),
FL2FXCONST_DBL(3.0f / 4.0f)
};
/*! Ratio of old gains and noise levels for the first 4 timeslots of an envelope */
const FIXP_SGL FDK_sbrDecoder_sbr_smoothFilter[4] = {
FL2FXCONST_SGL(0.66666666666666f),
@ -1176,7 +1185,7 @@ const FIXP_DBL Alphas[NO_ICC_LEVELS] = {
#define FL2FXCONST_PS FL2FXCONST_SGL
#else
#define FIXP_PS FIXP_DBL
#define FXP_CAST
#define FXP_CAST(x) ((FIXP_DBL)(x))
#define FL2FXCONST_PS FL2FXCONST_DBL
#endif

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -124,6 +124,7 @@ extern const FIXP_DBL FDK_sbrDecoder_sbr_whFactorsTable[NUM_WHFACTOR_TABLE_ENTRI
extern const FIXP_SGL FDK_sbrDecoder_sbr_limGains_m[4];
extern const UCHAR FDK_sbrDecoder_sbr_limGains_e[4];
extern const FIXP_SGL FDK_sbrDecoder_sbr_limiterBandsPerOctaveDiv4[4];
extern const FIXP_DBL FDK_sbrDecoder_sbr_limiterBandsPerOctaveDiv4_DBL[4];
extern const FIXP_SGL FDK_sbrDecoder_sbr_smoothFilter[4];
extern const FIXP_SGL FDK_sbrDecoder_sbr_randomPhase[SBR_NF_NO_RANDOM_VAL][2];
extern const FIXP_SGL harmonicPhaseX [2][4];

View File

@ -95,7 +95,7 @@ amm-info@iis.fraunhofer.de
#define SBRDEC_MAX_DRC_CHANNELS (6)
#define SBRDEC_MAX_DRC_CHANNELS (8)
#define SBRDEC_MAX_DRC_BANDS ( 16 )
typedef struct

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -128,6 +128,7 @@ amm-info@iis.fraunhofer.de
#include "lpp_tran.h"
#include "transcendent.h"
#include "FDK_crc.h"
#include "sbrdec_drc.h"
@ -137,10 +138,15 @@ amm-info@iis.fraunhofer.de
/* Decoder library info */
#define SBRDECODER_LIB_VL0 2
#define SBRDECODER_LIB_VL1 2
#define SBRDECODER_LIB_VL2 3
#define SBRDECODER_LIB_VL2 12
#define SBRDECODER_LIB_TITLE "SBR Decoder"
#ifdef __ANDROID__
#define SBRDECODER_LIB_BUILD_DATE ""
#define SBRDECODER_LIB_BUILD_TIME ""
#else
#define SBRDECODER_LIB_BUILD_DATE __DATE__
#define SBRDECODER_LIB_BUILD_TIME __TIME__
#endif
@ -189,6 +195,33 @@ static void copySbrHeader( HANDLE_SBR_HEADER_DATA hDst, const HANDLE_SBR_HEADER_
hDst->freqBandData.freqBandTable[1] = hDst->freqBandData.freqBandTableHi;
}
static int compareSbrHeader( const HANDLE_SBR_HEADER_DATA hHdr1, const HANDLE_SBR_HEADER_DATA hHdr2 )
{
int result = 0;
/* compare basic data */
result |= (hHdr1->syncState != hHdr2->syncState) ? 1 : 0;
result |= (hHdr1->status != hHdr2->status) ? 1 : 0;
result |= (hHdr1->frameErrorFlag != hHdr2->frameErrorFlag) ? 1 : 0;
result |= (hHdr1->numberTimeSlots != hHdr2->numberTimeSlots) ? 1 : 0;
result |= (hHdr1->numberOfAnalysisBands != hHdr2->numberOfAnalysisBands) ? 1 : 0;
result |= (hHdr1->timeStep != hHdr2->timeStep) ? 1 : 0;
result |= (hHdr1->sbrProcSmplRate != hHdr2->sbrProcSmplRate) ? 1 : 0;
/* compare bitstream data */
result |= FDKmemcmp( &hHdr1->bs_data, &hHdr2->bs_data, sizeof(SBR_HEADER_DATA_BS) );
result |= FDKmemcmp( &hHdr1->bs_info, &hHdr2->bs_info, sizeof(SBR_HEADER_DATA_BS_INFO) );
/* compare frequency band data */
result |= FDKmemcmp( &hHdr1->freqBandData, &hHdr2->freqBandData, (8+MAX_NUM_LIMITERS+1)*sizeof(UCHAR) );
result |= FDKmemcmp( hHdr1->freqBandData.freqBandTableLo, hHdr2->freqBandData.freqBandTableLo, (MAX_FREQ_COEFFS/2+1)*sizeof(UCHAR) );
result |= FDKmemcmp( hHdr1->freqBandData.freqBandTableHi, hHdr2->freqBandData.freqBandTableHi, (MAX_FREQ_COEFFS+1)*sizeof(UCHAR) );
result |= FDKmemcmp( hHdr1->freqBandData.freqBandTableNoise, hHdr2->freqBandData.freqBandTableNoise, (MAX_NOISE_COEFFS+1)*sizeof(UCHAR) );
result |= FDKmemcmp( hHdr1->freqBandData.v_k_master, hHdr2->freqBandData.v_k_master, (MAX_FREQ_COEFFS+1)*sizeof(UCHAR) );
return result;
}
/*!
\brief Reset SBR decoder.
@ -251,8 +284,10 @@ SBR_ERROR sbrDecoder_ResetElement (
if ( sampleRateIn == sampleRateOut ) {
synDownsampleFac = 2;
self->flags |= SBRDEC_DOWNSAMPLE;
} else {
synDownsampleFac = 1;
self->flags &= ~SBRDEC_DOWNSAMPLE;
}
self->synDownsampleFac = synDownsampleFac;
@ -311,7 +346,6 @@ SBR_ERROR sbrDecoder_ResetElement (
case AOT_PS:
case AOT_ER_AAC_SCAL:
case AOT_DRM_AAC:
case AOT_DRM_SURROUND:
if (CreatePsDec ( &self->hParametricStereoDec, samplesPerFrame )) {
sbrError = SBRDEC_CREATE_ERROR;
goto bail;
@ -385,6 +419,7 @@ int sbrDecoder_isCoreCodecValid(AUDIO_OBJECT_TYPE coreCodec)
case AOT_PS:
case AOT_ER_AAC_SCAL:
case AOT_ER_AAC_ELD:
case AOT_DRM_AAC:
return 1;
default:
return 0;
@ -428,7 +463,7 @@ SBR_ERROR sbrDecoder_InitElement (
int nSbrElementsStart = self->numSbrElements;
/* Check core codec AOT */
if (! sbrDecoder_isCoreCodecValid(coreCodec) || elementIndex >= (4)) {
if (! sbrDecoder_isCoreCodecValid(coreCodec) || elementIndex >= (8)) {
sbrError = SBRDEC_UNSUPPORTED_CONFIG;
goto bail;
}
@ -444,6 +479,7 @@ SBR_ERROR sbrDecoder_InitElement (
&& self->coreCodec == coreCodec
&& self->pSbrElement[elementIndex] != NULL
&& self->pSbrElement[elementIndex]->elementID == elementID
&& !(self->flags & SBRDEC_FORCE_RESET)
)
{
/* Nothing to do */
@ -456,6 +492,8 @@ SBR_ERROR sbrDecoder_InitElement (
self->flags = 0;
self->flags |= (coreCodec == AOT_ER_AAC_ELD) ? SBRDEC_ELD_GRID : 0;
self->flags |= (coreCodec == AOT_ER_AAC_SCAL) ? SBRDEC_SYNTAX_SCAL : 0;
self->flags |= (coreCodec == AOT_DRM_AAC) ? SBRDEC_SYNTAX_SCAL|SBRDEC_SYNTAX_DRM : 0;
/* Init SBR elements */
{
@ -495,7 +533,6 @@ SBR_ERROR sbrDecoder_InitElement (
case AOT_PS:
case AOT_ER_AAC_SCAL:
case AOT_DRM_AAC:
case AOT_DRM_SURROUND:
elChannels = 2;
break;
default:
@ -550,8 +587,9 @@ bail:
if (nSbrElementsStart < self->numSbrElements) {
/* Free the memory allocated for this element */
sbrDecoder_DestroyElement( self, elementIndex );
} else if (self->pSbrElement[elementIndex] != NULL) {
/* Set error flag to trigger concealment */
} else if ( (self->pSbrElement[elementIndex] != NULL)
&& (elementIndex < (8)))
{ /* Set error flag to trigger concealment */
self->pSbrElement[elementIndex]->frameErrorFlag[self->pSbrElement[elementIndex]->useFrameSlot] = 1;
}
}
@ -615,7 +653,7 @@ INT sbrDecoder_Header (
SBR_ERROR sbrError = SBRDEC_OK;
int headerIndex;
if ( self == NULL || elementIndex > (4) )
if ( self == NULL || elementIndex > (8) )
{
return SBRDEC_UNSUPPORTED_CONFIG;
}
@ -728,6 +766,24 @@ SBR_ERROR sbrDecoder_SetParam (HANDLE_SBRDECODER self,
}
}
break;
case SBR_FLUSH_DATA:
if (value != 0) {
if (self == NULL) {
errorStatus = SBRDEC_NOT_INITIALIZED;
} else {
self->flags |= SBRDEC_FLUSH;
}
}
break;
case SBR_CLEAR_HISTORY:
if (value != 0) {
if (self == NULL) {
errorStatus = SBRDEC_NOT_INITIALIZED;
} else {
self->flags |= SBRDEC_FORCE_RESET;
}
}
break;
case SBR_BS_INTERRUPTION:
{
int elementIndex;
@ -738,7 +794,8 @@ SBR_ERROR sbrDecoder_SetParam (HANDLE_SBRDECODER self,
}
/* Loop over SBR elements */
for (elementIndex = 0; elementIndex < self->numSbrElements; elementIndex++)
for (elementIndex = 0; elementIndex < self->numSbrElements; elementIndex++) {
if (self->pSbrElement[elementIndex] != NULL)
{
HANDLE_SBR_HEADER_DATA hSbrHeader;
int headerIndex = getHeaderSlot(self->pSbrElement[elementIndex]->useFrameSlot,
@ -750,7 +807,7 @@ SBR_ERROR sbrDecoder_SetParam (HANDLE_SBRDECODER self,
This switches off bitstream parsing until a new header arrives. */
hSbrHeader->syncState = UPSAMPLING;
hSbrHeader->status |= SBRDEC_HDR_STAT_UPDATE;
}
} }
}
break;
default:
@ -767,7 +824,7 @@ SBRDEC_DRC_CHANNEL * sbrDecoder_drcGetChannel( const HANDLE_SBRDECODER self, con
SBRDEC_DRC_CHANNEL *pSbrDrcChannelData = NULL;
int elementIndex, elChanIdx=0, numCh=0;
for (elementIndex = 0; (elementIndex < (4)) && (numCh <= channel); elementIndex++)
for (elementIndex = 0; (elementIndex < (8)) && (numCh <= channel); elementIndex++)
{
SBR_DECODER_ELEMENT *pSbrElement = self->pSbrElement[elementIndex];
int c, elChannels;
@ -829,7 +886,7 @@ SBR_ERROR sbrDecoder_drcFeedChannel ( HANDLE_SBRDECODER self,
if (self == NULL) {
return SBRDEC_NOT_INITIALIZED;
}
if (ch > (6) || pNextFact_mag == NULL) {
if (ch > (8) || pNextFact_mag == NULL) {
return SBRDEC_SET_PARAM_FAIL;
}
@ -874,7 +931,7 @@ void sbrDecoder_drcDisable ( HANDLE_SBRDECODER self,
SBRDEC_DRC_CHANNEL *pSbrDrcChannelData = NULL;
if ( (self == NULL)
|| (ch > (6))
|| (ch > (8))
|| (self->numSbrElements == 0)
|| (self->numSbrChannels == 0) ) {
return;
@ -902,24 +959,73 @@ SBR_ERROR sbrDecoder_Parse(
)
{
SBR_DECODER_ELEMENT *hSbrElement;
HANDLE_SBR_HEADER_DATA hSbrHeader;
HANDLE_SBR_HEADER_DATA hSbrHeader = NULL;
HANDLE_SBR_CHANNEL *pSbrChannel;
SBR_FRAME_DATA *hFrameDataLeft;
SBR_FRAME_DATA *hFrameDataRight;
SBR_ERROR errorStatus = SBRDEC_OK;
SBR_SYNC_STATE initialSyncState;
SBR_HEADER_STATUS headerStatus = HEADER_NOT_PRESENT;
INT startPos;
INT CRCLen = 0;
HANDLE_FDK_BITSTREAM hBsOriginal = hBs;
FDK_CRCINFO crcInfo; /* shall be used for all other CRCs in the future (TBD) */
INT crcReg = 0;
USHORT drmSbrCrc = 0;
int stereo;
int fDoDecodeSbrData = 1;
int lastSlot, lastHdrSlot = 0, thisHdrSlot;
/* Reverse bits of DRM SBR payload */
if ( (self->flags & SBRDEC_SYNTAX_DRM) && *count > 0 )
{
UCHAR *bsBufferDrm = (UCHAR*)self->workBuffer1;
HANDLE_FDK_BITSTREAM hBsBwd = (HANDLE_FDK_BITSTREAM) (bsBufferDrm + (512));
int dataBytes, dataBits;
dataBits = *count;
if (dataBits > ((512)*8)) {
/* do not flip more data than needed */
dataBits = (512)*8;
}
dataBytes = (dataBits+7)>>3;
int j;
if ((j = (int)FDKgetValidBits(hBs)) != 8) {
FDKpushBiDirectional(hBs, (j-8));
}
j = 0;
for ( ; dataBytes > 0; dataBytes--)
{
int i;
UCHAR tmpByte;
UCHAR buffer = 0x00;
tmpByte = (UCHAR) FDKreadBits(hBs, 8);
for (i = 0; i < 4; i++) {
int shift = 2 * i + 1;
buffer |= (tmpByte & (0x08>>i)) << shift;
buffer |= (tmpByte & (0x10<<i)) >> shift;
}
bsBufferDrm[j++] = buffer;
FDKpushBack(hBs, 16);
}
FDKinitBitStream(hBsBwd, bsBufferDrm, (512), dataBits, BS_READER);
/* Use reversed data */
hBs = hBsBwd;
bsPayLen = *count;
}
/* Remember start position of SBR element */
startPos = FDKgetValidBits(hBs);
@ -944,7 +1050,6 @@ SBR_ERROR sbrDecoder_Parse(
hFrameDataLeft = &self->pSbrElement[elementIndex]->pSbrChannel[0]->frameData[hSbrElement->useFrameSlot];
hFrameDataRight = &self->pSbrElement[elementIndex]->pSbrChannel[1]->frameData[hSbrElement->useFrameSlot];
initialSyncState = hSbrHeader->syncState;
/* reset PS flag; will be set after PS was found */
self->flags &= ~SBRDEC_PS_DECODED;
@ -980,12 +1085,19 @@ SBR_ERROR sbrDecoder_Parse(
*/
if (fDoDecodeSbrData)
{
if (crcFlag == 1) {
if (crcFlag) {
switch (self->coreCodec) {
case AOT_ER_AAC_ELD:
FDKpushFor (hBs, 10);
/* check sbrcrc later: we don't know the payload length now */
break;
case AOT_DRM_AAC:
drmSbrCrc = (USHORT)FDKreadBits(hBs, 8);
/* Setup CRC decoder */
FDKcrcInit(&crcInfo, 0x001d, 0xFFFF, 8);
/* Start CRC region */
crcReg = FDKcrcStartReg(&crcInfo, hBs, 0);
break;
default:
CRCLen = bsPayLen - 10; /* change: 0 => i */
if (CRCLen < 0) {
@ -1030,6 +1142,7 @@ SBR_ERROR sbrDecoder_Parse(
hSbrHeader->syncState = SBR_HEADER;
} else {
hSbrHeader->syncState = SBR_NOT_INITIALIZED;
headerStatus = HEADER_ERROR;
}
}
@ -1079,7 +1192,7 @@ SBR_ERROR sbrDecoder_Parse(
valBits = (INT)FDKgetValidBits(hBs);
}
if ( crcFlag == 1 ) {
if ( crcFlag ) {
switch (self->coreCodec) {
case AOT_ER_AAC_ELD:
{
@ -1091,6 +1204,14 @@ SBR_ERROR sbrDecoder_Parse(
FDKpushFor(hBs, crcLen);
}
break;
case AOT_DRM_AAC:
/* End CRC region */
FDKcrcEndReg(&crcInfo, hBs, crcReg);
/* Check CRC */
if ((FDKcrcGetCRC(&crcInfo)^0xFF) != drmSbrCrc) {
fDoDecodeSbrData = 0;
}
break;
default:
break;
}
@ -1119,6 +1240,10 @@ SBR_ERROR sbrDecoder_Parse(
}
}
}
} else {
/* The returned bit count will not be the actual payload size since we did not
parse the frame data. Return an error so that the caller can react respectively. */
errorStatus = SBRDEC_PARSE_ERROR;
}
if (!fDoDecodeSbrData) {
@ -1137,8 +1262,25 @@ SBR_ERROR sbrDecoder_Parse(
}
bail:
if (errorStatus == SBRDEC_OK) {
if (headerStatus == HEADER_NOT_PRESENT) {
if ( self->flags & SBRDEC_SYNTAX_DRM )
{
hBs = hBsOriginal;
}
if ( (errorStatus == SBRDEC_OK)
|| ( (errorStatus == SBRDEC_PARSE_ERROR)
&& (headerStatus != HEADER_ERROR) ) )
{
int useOldHdr = ( (headerStatus == HEADER_NOT_PRESENT)
|| (headerStatus == HEADER_ERROR) ) ? 1 : 0;
if (!useOldHdr && (thisHdrSlot != lastHdrSlot)) {
useOldHdr |= ( compareSbrHeader( hSbrHeader,
&self->sbrHeader[elementIndex][lastHdrSlot] ) == 0 ) ? 1 : 0;
}
if (useOldHdr != 0) {
/* Use the old header for this frame */
hSbrElement->useHeaderSlot[hSbrElement->useFrameSlot] = lastHdrSlot;
} else {
@ -1198,6 +1340,24 @@ sbrDecoder_DecodeElement (
int stereo = (hSbrElement->elementID == ID_CPE) ? 1 : 0;
int numElementChannels = hSbrElement->nChannels; /* Number of channels of the current SBR element */
if (self->flags & SBRDEC_FLUSH) {
if ( self->numFlushedFrames > self->numDelayFrames ) {
int hdrIdx;
/* No valid SBR payload available, hence switch to upsampling (in all headers) */
for (hdrIdx = 0; hdrIdx < ((1)+1); hdrIdx += 1) {
self->sbrHeader[elementIndex][hdrIdx].syncState = UPSAMPLING;
}
}
else {
/* Move frame pointer to the next slot which is up to be decoded/applied next */
hSbrElement->useFrameSlot = (hSbrElement->useFrameSlot+1) % (self->numDelayFrames+1);
/* Update header and frame data pointer because they have already been set */
hSbrHeader = &self->sbrHeader[elementIndex][hSbrElement->useHeaderSlot[hSbrElement->useFrameSlot]];
hFrameDataLeft = &hSbrElement->pSbrChannel[0]->frameData[hSbrElement->useFrameSlot];
hFrameDataRight = &hSbrElement->pSbrChannel[1]->frameData[hSbrElement->useFrameSlot];
}
}
/* Update the header error flag */
hSbrHeader->frameErrorFlag = hSbrElement->frameErrorFlag[hSbrElement->useFrameSlot];
@ -1315,7 +1475,8 @@ sbrDecoder_DecodeElement (
&pSbrChannel[0]->prevFrameData,
(hSbrHeader->syncState == SBR_ACTIVE),
h_ps_d,
self->flags
self->flags,
codecFrameSize
);
if (stereo) {
@ -1332,7 +1493,8 @@ sbrDecoder_DecodeElement (
&pSbrChannel[1]->prevFrameData,
(hSbrHeader->syncState == SBR_ACTIVE),
NULL,
self->flags
self->flags,
codecFrameSize
);
}
@ -1348,20 +1510,21 @@ sbrDecoder_DecodeElement (
if ( !(self->flags & SBRDEC_PS_DECODED) ) {
/* A decoder which is able to decode PS has to produce a stereo output even if no PS data is availble. */
/* So copy left channel to right channel. */
int copyFrameSize = codecFrameSize * 2 / self->synDownsampleFac;
if (interleaved) {
INT_PCM *ptr;
INT i;
FDK_ASSERT(strideOut == 2);
ptr = timeData;
for (i = codecFrameSize; i--; )
for (i = copyFrameSize>>1; i--; )
{
INT_PCM tmp; /* This temporal variable is required because some compilers can't do *ptr++ = *ptr++ correctly. */
tmp = *ptr++; *ptr++ = tmp;
tmp = *ptr++; *ptr++ = tmp;
}
} else {
FDKmemcpy( timeData+2*codecFrameSize, timeData, 2*codecFrameSize*sizeof(INT_PCM) );
FDKmemcpy( timeData+copyFrameSize, timeData, copyFrameSize*sizeof(INT_PCM) );
}
}
*numOutChannels = 2; /* Output minimum two channels when PS is enabled. */
@ -1375,7 +1538,7 @@ SBR_ERROR sbrDecoder_Apply ( HANDLE_SBRDECODER self,
INT_PCM *timeData,
int *numChannels,
int *sampleRate,
const UCHAR channelMapping[(6)],
const UCHAR channelMapping[(8)],
const int interleaved,
const int coreDecodedOk,
UCHAR *psDecoded )
@ -1425,14 +1588,23 @@ SBR_ERROR sbrDecoder_Apply ( HANDLE_SBRDECODER self,
self->flags &= ~SBRDEC_PS_DECODED;
}
if ( self->flags & SBRDEC_FLUSH ) {
/* flushing is signalized, hence increment the flush frame counter */
self->numFlushedFrames++;
}
else {
/* no flushing is signalized, hence reset the flush frame counter */
self->numFlushedFrames = 0;
}
/* Loop over SBR elements */
for (sbrElementNum = 0; sbrElementNum<self->numSbrElements; sbrElementNum++)
{
int numElementChan;
if (psPossible && self->pSbrElement[sbrElementNum]->pSbrChannel[1] == NULL) {
errorStatus = SBRDEC_UNSUPPORTED_CONFIG;
goto bail;
/* Disable PS and try decoding SBR mono. */
psPossible = 0;
}
numElementChan = (self->pSbrElement[sbrElementNum]->elementID == ID_CPE) ? 2 : 1;
@ -1472,6 +1644,10 @@ SBR_ERROR sbrDecoder_Apply ( HANDLE_SBRDECODER self,
/* Clear reset and flush flag because everything seems to be done successfully. */
self->flags &= ~SBRDEC_FORCE_RESET;
self->flags &= ~SBRDEC_FLUSH;
bail:
return errorStatus;
@ -1496,7 +1672,7 @@ SBR_ERROR sbrDecoder_Close ( HANDLE_SBRDECODER *pSelf )
FreeRam_SbrDecWorkBuffer2(&self->workBuffer2);
}
for (i = 0; i < (4); i++) {
for (i = 0; i < (8); i++) {
sbrDecoder_DestroyElement( self, i );
}
@ -1536,6 +1712,7 @@ INT sbrDecoder_GetLibInfo( LIB_INFO *info )
| CAPF_SBR_HQ
| CAPF_SBR_LP
| CAPF_SBR_PS_MPEG
| CAPF_SBR_DRM_BS
| CAPF_SBR_CONCEALMENT
| CAPF_SBR_DRC
;
@ -1544,3 +1721,37 @@ INT sbrDecoder_GetLibInfo( LIB_INFO *info )
return 0;
}
UINT sbrDecoder_GetDelay( const HANDLE_SBRDECODER self )
{
UINT outputDelay = 0;
if ( self != NULL) {
UINT flags = self->flags;
/* See chapter 1.6.7.2 of ISO/IEC 14496-3 for the GA-SBR figures below. */
/* Are we initialized? */
if ( (self->numSbrChannels > 0)
&& (self->numSbrElements > 0) )
{
/* Add QMF synthesis delay */
if ( (flags & SBRDEC_ELD_GRID)
&& IS_LOWDELAY(self->coreCodec) ) {
/* Low delay SBR: */
{
outputDelay += (flags & SBRDEC_DOWNSAMPLE) ? 32 : 64; /* QMF synthesis */
if (flags & SBRDEC_LD_MPS_QMF) {
outputDelay += 32;
}
}
}
else if (!IS_USAC(self->coreCodec)) {
/* By the method of elimination this is the GA (AAC-LC, HE-AAC, ...) branch: */
outputDelay += (flags & SBRDEC_DOWNSAMPLE) ? 481 : 962;
}
}
}
return (outputDelay);
}

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -135,6 +135,12 @@ enum
SBR_SYNTAX_DRM_CRC = 0x0008
};
typedef enum
{
FREQ_RES_LOW = 0,
FREQ_RES_HIGH
} FREQ_RES;
typedef struct
{
CODEC_TYPE coreCoder; /*!< LC or ELD */
@ -168,8 +174,9 @@ typedef struct sbrConfiguration
INT dynBwSupported; /*!< Flag: support for dynamic bandwidth in this combination. */
INT parametricCoding; /*!< Flag: usage of parametric coding tool. */
INT downSampleFactor; /*!< Sampling rate relation between the SBR and the core encoder. */
int freq_res_fixfix[3]; /*!< Frequency resolution of envelopes in frame class FIXFIX
0=1 Env; 1=2 Env; 2=4 Env; */
FREQ_RES freq_res_fixfix[2];/*!< Frequency resolution of envelopes in frame class FIXFIX, for non-split case and split case */
UCHAR fResTransIsLow; /*!< Frequency resolution of envelopes in transient frames: low (0) or variable (1) */
/*
core coder dependent tuning parameters
*/
@ -221,6 +228,8 @@ typedef struct sbrConfiguration
INT sbr_interpol_freq; /*!< Flag: use interpolation in freq. direction. */
INT sbr_smoothing_length; /*!< Flag: choose length 4 or 0 (=on, off). */
UCHAR init_amp_res_FF;
FIXP_DBL threshold_AmpRes_FF_m;
SCHAR threshold_AmpRes_FF_e;
} sbrConfiguration, *sbrConfigurationPtr ;
typedef struct SBR_CONFIG_DATA
@ -237,7 +246,7 @@ typedef struct SBR_CONFIG_DATA
INT noQmfBands; /**< Number of QMF frequency bands. */
INT noQmfSlots; /**< Number of QMF slots. */
UCHAR *freqBandTable[2]; /**< Frequency table for low and hires, only MAX_FREQ_COEFFS/2 +1 coeefs actually needed for lowres. */
UCHAR *freqBandTable[2]; /**< Frequency table for low and hires, only MAX_FREQ_COEFFS/2 +1 coeffs actually needed for lowres. */
UCHAR *v_k_master; /**< Master BandTable where freqBandTable is derived from. */
@ -249,6 +258,8 @@ typedef struct SBR_CONFIG_DATA
INT xposCtrlSwitch; /**< Flag indicates whether to switch xpos ctrl on the fly. */
INT switchTransposers; /**< Flag indicates whether to switch xpos on the fly . */
UCHAR initAmpResFF;
FIXP_DBL thresholdAmpResFF_m;
SCHAR thresholdAmpResFF_e;
} SBR_CONFIG_DATA, *HANDLE_SBR_CONFIG_DATA;
typedef struct {

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -283,9 +283,7 @@ void sbrEncoder_GetHeader(SBR_ENCODER *sbrEncoder,
INT element_index,
int fSendHeaders)
{
int bits;
bits = encodeSbrHeaderData (&sbrEncoder->sbrElement[element_index]->sbrHeaderData, hBs);
encodeSbrHeaderData (&sbrEncoder->sbrElement[element_index]->sbrHeaderData, hBs);
if (fSendHeaders == 0) {
/* Prevent header being embedded into the SBR payload. */

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -141,8 +141,8 @@ struct SBR_ENV_DATA
{
INT sbr_xpos_ctrl;
INT freq_res_fixfix;
FREQ_RES freq_res_fixfix[2];
UCHAR fResTransIsLow;
INVF_MODE sbr_invf_mode;
INVF_MODE sbr_invf_mode_vec[MAX_NUM_NOISE_VALUES];
@ -205,6 +205,8 @@ struct SBR_ENV_DATA
INT balance;
AMP_RES init_sbr_amp_res;
AMP_RES currentAmpResFF;
FIXP_DBL ton_HF[SBR_GLOBAL_TONALITY_VALUES]; /* tonality is scaled by 2^19/0.524288f (fract part of RELAXATION) */
FIXP_DBL global_tonality;
/* extended data */
INT extended_data;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -103,6 +103,114 @@ static const UCHAR panTable[2][10] = { { 0, 2, 4, 6, 8,12,16,20,24},
static const UCHAR maxIndex[2] = {9, 5};
/******************************************************************************
Functionname: FDKsbrEnc_GetTonality
******************************************************************************/
/***************************************************************************/
/*!
\brief Calculates complete energy per band from the energy values
of the QMF subsamples.
\brief quotaMatrix - calculated in FDKsbrEnc_CalculateTonalityQuotas()
\brief noEstPerFrame - number of estimations per frame
\brief startIndex - start index for the quota matrix
\brief Energies - energy matrix
\brief startBand - start band
\brief stopBand - number of QMF bands
\brief numberCols - number of QMF subsamples
\return mean tonality of the 5 bands with the highest energy
scaled by 2^(RELAXATION_SHIFT+2)*RELAXATION_FRACT
****************************************************************************/
static FIXP_DBL FDKsbrEnc_GetTonality(
const FIXP_DBL *const *quotaMatrix,
const INT noEstPerFrame,
const INT startIndex,
const FIXP_DBL *const *Energies,
const UCHAR startBand,
const INT stopBand,
const INT numberCols
)
{
UCHAR b, e, k;
INT no_enMaxBand[SBR_MAX_ENERGY_VALUES] = { -1, -1, -1, -1, -1 };
FIXP_DBL energyMax[SBR_MAX_ENERGY_VALUES] = { FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f) };
FIXP_DBL energyMaxMin = MAXVAL_DBL; /* min. energy in energyMax array */
UCHAR posEnergyMaxMin = 0; /* min. energy in energyMax array position */
FIXP_DBL tonalityBand[SBR_MAX_ENERGY_VALUES] = { FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f), FL2FXCONST_DBL(0.0f) };
FIXP_DBL globalTonality = FL2FXCONST_DBL(0.0f);
FIXP_DBL energyBand[QMF_CHANNELS];
INT maxNEnergyValues; /* max. number of max. energy values */
/*** Sum up energies for each band ***/
FDK_ASSERT(numberCols==15||numberCols==16);
/* numberCols is always 15 or 16 for ELD. In case of 16 bands, the
energyBands are initialized with the [15]th column.
The rest of the column energies are added in the next step. */
if (numberCols==15) {
for (b=startBand; b<stopBand; b++) {
energyBand[b]=FL2FXCONST_DBL(0.0f);
}
} else {
for (b=startBand; b<stopBand; b++) {
energyBand[b]=Energies[15][b]>>4;
}
}
for (k=0; k<15; k++) {
for (b=startBand; b<stopBand; b++) {
energyBand[b] += Energies[k][b]>>4;
}
}
/*** Determine 5 highest band-energies ***/
maxNEnergyValues = fMin(SBR_MAX_ENERGY_VALUES, stopBand-startBand);
/* Get min. value in energyMax array */
energyMaxMin = energyMax[0] = energyBand[startBand];
no_enMaxBand[0] = startBand;
posEnergyMaxMin = 0;
for (k=1; k<maxNEnergyValues; k++) {
energyMax[k] = energyBand[startBand+k];
no_enMaxBand[k] = startBand+k;
if (energyMaxMin > energyMax[k]) {
energyMaxMin = energyMax[k];
posEnergyMaxMin = k;
}
}
for (b=startBand+maxNEnergyValues; b<stopBand; b++) {
if (energyBand[b] > energyMaxMin) {
energyMax[posEnergyMaxMin] = energyBand[b];
no_enMaxBand[posEnergyMaxMin] = b;
/* Again, get min. value in energyMax array */
energyMaxMin = energyMax[0];
posEnergyMaxMin = 0;
for (k=1; k<maxNEnergyValues; k++) {
if (energyMaxMin > energyMax[k]) {
energyMaxMin = energyMax[k];
posEnergyMaxMin = k;
}
}
}
}
/*** End determine 5 highest band-energies ***/
/* Get tonality values for 5 highest energies */
for (e=0; e<maxNEnergyValues; e++) {
tonalityBand[e]=FL2FXCONST_DBL(0.0f);
for (k=0; k<noEstPerFrame; k++) {
tonalityBand[e] += quotaMatrix[startIndex + k][no_enMaxBand[e]] >> 1;
}
globalTonality += tonalityBand[e] >> 2; /* headroom of 2+1 (max. 5 additions) */
}
return globalTonality;
}
/***************************************************************************/
/*!
@ -919,10 +1027,42 @@ FDKsbrEnc_extractSbrEnvelope1 (
hEnvChan->qmfScale);
if(h_con->sbrSyntaxFlags & SBR_SYNTAX_LOW_DELAY) {
FIXP_DBL tonality = FDKsbrEnc_GetTonality (
hEnvChan->TonCorr.quotaMatrix,
hEnvChan->TonCorr.numberOfEstimatesPerFrame,
hEnvChan->TonCorr.startIndexMatrix,
sbrExtrEnv->YBuffer + sbrExtrEnv->YBufferWriteOffset,
h_con->freqBandTable[HI][0]+1,
h_con->noQmfBands,
sbrExtrEnv->no_cols
);
hEnvChan->encEnvData.ton_HF[1] = hEnvChan->encEnvData.ton_HF[0];
hEnvChan->encEnvData.ton_HF[0] = tonality;
/* tonality is scaled by 2^19/0.524288f (fract part of RELAXATION) */
hEnvChan->encEnvData.global_tonality = (hEnvChan->encEnvData.ton_HF[0]>>1) + (hEnvChan->encEnvData.ton_HF[1]>>1);
}
/*
Transient detection COEFF Transform OK
*/
if(h_con->sbrSyntaxFlags & SBR_SYNTAX_LOW_DELAY)
{
FDKsbrEnc_fastTransientDetect(
&hEnvChan->sbrFastTransientDetector,
sbrExtrEnv->YBuffer,
sbrExtrEnv->YBufferScale,
sbrExtrEnv->YBufferWriteOffset,
eData->transient_info
);
}
else
{
FDKsbrEnc_transientDetect(&hEnvChan->sbrTransientDetector,
sbrExtrEnv->YBuffer,
sbrExtrEnv->YBufferScale,
@ -931,6 +1071,7 @@ FDKsbrEnc_extractSbrEnvelope1 (
sbrExtrEnv->YBufferSzShift,
sbrExtrEnv->time_step,
hEnvChan->SbrEnvFrame.frameMiddleSlot);
}
@ -951,7 +1092,8 @@ FDKsbrEnc_extractSbrEnvelope1 (
sbrExtrEnv->YBufferSzShift,
h_con->nSfb[1],
sbrExtrEnv->time_step,
sbrExtrEnv->no_cols);
sbrExtrEnv->no_cols,
&hEnvChan->encEnvData.global_tonality);
}
@ -1128,12 +1270,26 @@ FDKsbrEnc_extractSbrEnvelope2 (
&& ( ed->nEnvelopes == 1 ) )
{
if (hEnvChan->encEnvData.ldGrid)
hEnvChan->encEnvData.currentAmpResFF = (AMP_RES)h_con->initAmpResFF;
else
if (h_con->sbrSyntaxFlags & SBR_SYNTAX_LOW_DELAY)
{
/* Note: global_tonaliy_float_value == ((float)hEnvChan->encEnvData.global_tonality/((INT64)(1)<<(31-(19+2)))/0.524288*(2.0/3.0)));
threshold_float_value == ((float)h_con->thresholdAmpResFF_m/((INT64)(1)<<(31-(h_con->thresholdAmpResFF_e)))/0.524288*(2.0/3.0))); */
/* decision of SBR_AMP_RES */
if (fIsLessThan( /* global_tonality > threshold ? */
h_con->thresholdAmpResFF_m, h_con->thresholdAmpResFF_e,
hEnvChan->encEnvData.global_tonality, RELAXATION_SHIFT+2 )
)
{
hEnvChan->encEnvData.currentAmpResFF = SBR_AMP_RES_1_5;
}
else {
hEnvChan->encEnvData.currentAmpResFF = SBR_AMP_RES_3_0;
}
} else {
hEnvChan->encEnvData.currentAmpResFF = SBR_AMP_RES_1_5;
}
if ( hEnvChan->encEnvData.currentAmpResFF != hEnvChan->encEnvData.init_sbr_amp_res) {
if ( hEnvChan->encEnvData.currentAmpResFF != hEnvChan->encEnvData.init_sbr_amp_res) {
FDKsbrEnc_InitSbrHuffmanTables(&hEnvChan->encEnvData,
&hEnvChan->sbrCodeEnvelope,
@ -1172,7 +1328,12 @@ FDKsbrEnc_extractSbrEnvelope2 (
}
/* Low energy in low band fix */
if ( hEnvChan->sbrTransientDetector.prevLowBandEnergy < hEnvChan->sbrTransientDetector.prevHighBandEnergy && hEnvChan->sbrTransientDetector.prevHighBandEnergy > FL2FX_DBL(0.03))
if ( hEnvChan->sbrTransientDetector.prevLowBandEnergy < hEnvChan->sbrTransientDetector.prevHighBandEnergy
&& hEnvChan->sbrTransientDetector.prevHighBandEnergy > FL2FX_DBL(0.03)
/* The fix needs the non-fast transient detector running.
It sets prevLowBandEnergy and prevHighBandEnergy. */
&& !(h_con->sbrSyntaxFlags & SBR_SYNTAX_LOW_DELAY)
)
{
int i;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -127,6 +127,7 @@ typedef SBR_EXTRACT_ENVELOPE *HANDLE_SBR_EXTRACT_ENVELOPE;
struct ENV_CHANNEL
{
FAST_TRAN_DETECTOR sbrFastTransientDetector;
SBR_TRANSIENT_DETECTOR sbrTransientDetector;
SBR_CODE_ENVELOPE sbrCodeEnvelope;
SBR_CODE_ENVELOPE sbrCodeNoiseFloor;

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -266,7 +266,7 @@ static void calcCtrlSignal (HANDLE_SBR_GRID hSbrGrid, FRAME_CLASS frameClass,
static void ctrlSignal2FrameInfo (HANDLE_SBR_GRID hSbrGrid,
HANDLE_SBR_FRAME_INFO hFrameInfo,
INT freq_res_fixfix);
FREQ_RES *freq_res_fixfix);
/* table for 8 time slot index */
@ -341,8 +341,9 @@ static const FREQ_RES freqRes_table_16[16] = {
static void generateFixFixOnly ( HANDLE_SBR_FRAME_INFO hSbrFrameInfo,
HANDLE_SBR_GRID hSbrGrid,
int tranPosInternal,
int numberTimeSlots
);
int numberTimeSlots,
UCHAR fResTransIsLow
);
/*!
@ -402,11 +403,10 @@ FDKsbrEnc_frameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
const int *v_tuningFreq = v_tuning + 3;
hSbrEnvFrame->v_tuningSegm = v_tuningSegm;
INT freq_res_fixfix = hSbrEnvFrame->freq_res_fixfix;
if (ldGrid) {
/* in case there was a transient at the very end of the previous frame, start with a transient envelope */
if(v_transient_info_pre[1] && (numberTimeSlots - v_transient_info_pre[0] < minFrameTranDistance)){
if ( !tranFlag && v_transient_info_pre[1] && (numberTimeSlots - v_transient_info_pre[0] < minFrameTranDistance) ){
tranFlag = 1;
tranPos = 0;
}
@ -529,7 +529,8 @@ FDKsbrEnc_frameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
generateFixFixOnly ( &(hSbrEnvFrame->SbrFrameInfo),
&(hSbrEnvFrame->SbrGrid),
tranPosInternal,
numberTimeSlots
numberTimeSlots,
hSbrEnvFrame->fResTransIsLow
);
return &(hSbrEnvFrame->SbrFrameInfo);
@ -677,7 +678,7 @@ FDKsbrEnc_frameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
---------------------------------------------------------------------------*/
ctrlSignal2FrameInfo (&hSbrEnvFrame->SbrGrid,
&hSbrEnvFrame->SbrFrameInfo,
freq_res_fixfix);
hSbrEnvFrame->freq_res_fixfix);
return &hSbrEnvFrame->SbrFrameInfo;
}
@ -692,7 +693,8 @@ FDKsbrEnc_frameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
static void generateFixFixOnly ( HANDLE_SBR_FRAME_INFO hSbrFrameInfo,
HANDLE_SBR_GRID hSbrGrid,
int tranPosInternal,
int numberTimeSlots
int numberTimeSlots,
UCHAR fResTransIsLow
)
{
int nEnv, i, k=0, tranIdx;
@ -727,8 +729,12 @@ static void generateFixFixOnly ( HANDLE_SBR_FRAME_INFO hSbrFrameInfo,
/* adjust segment-frequency-resolution according to the segment-length */
for (i=0; i<nEnv; i++){
k = hSbrFrameInfo->borders[i+1] - hSbrFrameInfo->borders[i];
hSbrFrameInfo->freqRes[i] = freqResTable[k];
hSbrGrid->v_f[i] = freqResTable[k];
if (!fResTransIsLow)
hSbrFrameInfo->freqRes[i] = freqResTable[k];
else
hSbrFrameInfo->freqRes[i] = FREQ_RES_LOW;
hSbrGrid->v_f[i] = hSbrFrameInfo->freqRes[i];
}
hSbrFrameInfo->nEnvelopes = nEnv;
@ -765,15 +771,16 @@ static void generateFixFixOnly ( HANDLE_SBR_FRAME_INFO hSbrFrameInfo,
*******************************************************************************/
void
FDKsbrEnc_initFrameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
INT allowSpread,
INT numEnvStatic,
INT staticFraming,
INT timeSlots,
INT freq_res_fixfix
,int ldGrid
)
FDKsbrEnc_initFrameInfoGenerator (
HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
INT allowSpread,
INT numEnvStatic,
INT staticFraming,
INT timeSlots,
const FREQ_RES* freq_res_fixfix
,UCHAR fResTransIsLow,
INT ldGrid
)
{ /* FH 00-06-26 */
FDKmemclear(hSbrEnvFrame,sizeof(SBR_ENVELOPE_FRAME ));
@ -786,7 +793,9 @@ FDKsbrEnc_initFrameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
hSbrEnvFrame->allowSpread = allowSpread;
hSbrEnvFrame->numEnvStatic = numEnvStatic;
hSbrEnvFrame->staticFraming = staticFraming;
hSbrEnvFrame->freq_res_fixfix = freq_res_fixfix;
hSbrEnvFrame->freq_res_fixfix[0] = freq_res_fixfix[0];
hSbrEnvFrame->freq_res_fixfix[1] = freq_res_fixfix[1];
hSbrEnvFrame->fResTransIsLow = fResTransIsLow;
hSbrEnvFrame->length_v_bord = 0;
hSbrEnvFrame->length_v_bordFollow = 0;
@ -804,6 +813,7 @@ FDKsbrEnc_initFrameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
hSbrEnvFrame->dmin = 2;
hSbrEnvFrame->dmax = 16;
hSbrEnvFrame->frameMiddleSlot = FRAME_MIDDLE_SLOT_512LD;
hSbrEnvFrame->SbrGrid.bufferFrameStart = 0;
} else
switch(timeSlots){
case NUMBER_TIME_SLOTS_1920:
@ -1862,19 +1872,28 @@ createDefFrameInfo(HANDLE_SBR_FRAME_INFO hSbrFrameInfo, INT nEnv, INT nTimeSlots
Functionname: ctrlSignal2FrameInfo
*******************************************************************************
Description: Calculates frame_info struct from control signal.
Description: Convert "clear-text" sbr_grid() to "frame info" used by the
envelope and noise floor estimators.
This is basically (except for "low level" calculations) the
bitstream decoder defined in the MPEG-4 standard, sub clause
4.6.18.3.3, Time / Frequency Grid. See inline comments for
explanation of the shorten and noise border algorithms.
Arguments: hSbrGrid - source
hSbrFrameInfo - destination
freq_res_fixfix - frequency resolution for FIXFIX frames
Return: void; hSbrFrameInfo contains the updated FRAME_INFO struct
*******************************************************************************/
static void
ctrlSignal2FrameInfo (HANDLE_SBR_GRID hSbrGrid,
HANDLE_SBR_FRAME_INFO hSbrFrameInfo,
INT freq_res_fixfix)
ctrlSignal2FrameInfo (
HANDLE_SBR_GRID hSbrGrid, /* input : the grid handle */
HANDLE_SBR_FRAME_INFO hSbrFrameInfo, /* output: the frame info handle */
FREQ_RES *freq_res_fixfix /* in/out: frequency resolution for FIXFIX frames */
)
{
INT frameSplit = 0;
INT nEnv = 0, border = 0, i, k, p /*?*/;
INT *v_r = hSbrGrid->bs_rel_bord;
INT *v_f = hSbrGrid->v_f;
@ -1887,17 +1906,10 @@ ctrlSignal2FrameInfo (HANDLE_SBR_GRID hSbrGrid,
case FIXFIX:
createDefFrameInfo(hSbrFrameInfo, hSbrGrid->bs_num_env, numberTimeSlots);
/* At this point all frequency resolutions are set to FREQ_RES_HIGH, so
* only if freq_res_fixfix is set to FREQ_RES_LOW, they all have to be
* changed.
* snd */
if (freq_res_fixfix == FREQ_RES_LOW) {
for (i = 0; i < hSbrFrameInfo->nEnvelopes; i++) {
hSbrFrameInfo->freqRes[i] = FREQ_RES_LOW;
}
frameSplit = (hSbrFrameInfo->nEnvelopes > 1);
for (i = 0; i < hSbrFrameInfo->nEnvelopes; i++) {
hSbrGrid->v_f[i] = hSbrFrameInfo->freqRes[i] = freq_res_fixfix[frameSplit];
}
/* ELD: store current frequency resolution */
hSbrGrid->v_f[0] = hSbrFrameInfo->freqRes[0];
break;
case FIXVAR:

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -89,6 +89,7 @@ amm-info@iis.fraunhofer.de
#define _FRAM_GEN_H
#include "sbr_def.h" /* for MAX_ENVELOPES and MAX_NOISE_ENVELOPES in struct FRAME_INFO and CODEC_TYPE */
#include "sbr_encoder.h" /* for FREQ_RES */
#define MAX_ENVELOPES_VARVAR MAX_ENVELOPES /*!< worst case number of envelopes in a VARVAR frame */
#define MAX_ENVELOPES_FIXVAR_VARFIX 4 /*!< worst case number of envelopes in VARFIX and FIXVAR frames */
@ -114,7 +115,7 @@ typedef enum {
#define NUMBER_TIME_SLOTS_1920 15
#define LD_PRETRAN_OFF 3
#define FRAME_MIDDLE_SLOT_512LD 0
#define FRAME_MIDDLE_SLOT_512LD 4
#define NUMBER_TIME_SLOTS_512LD 8
#define TRANSIENT_OFFSET_LD 0
@ -248,9 +249,10 @@ typedef struct
INT frameMiddleSlot; /*!< transient detector offset in SBR timeslots */
/* basic tuning parameters */
INT staticFraming; /*!< 1: run static framing in time, i.e. exclusive use of bs_frame_class = FIXFIX */
INT numEnvStatic; /*!< number of envelopes per frame for static framing */
INT freq_res_fixfix; /*!< envelope frequency resolution to use for bs_frame_class = FIXFIX */
INT staticFraming; /*!< 1: run static framing in time, i.e. exclusive use of bs_frame_class = FIXFIX */
INT numEnvStatic; /*!< number of envelopes per frame for static framing */
FREQ_RES freq_res_fixfix[2]; /*!< envelope frequency resolution to use for bs_frame_class = FIXFIX; single env and split */
UCHAR fResTransIsLow; /*!< frequency resolution for transient frames - always low (0) or according to table (1) */
/* expert tuning parameters */
const int *v_tuningSegm; /*!< segment lengths to use around transient */
@ -286,14 +288,16 @@ typedef SBR_ENVELOPE_FRAME *HANDLE_SBR_ENVELOPE_FRAME;
void
FDKsbrEnc_initFrameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
INT allowSpread,
INT numEnvStatic,
INT staticFraming,
INT timeSlots,
INT freq_res_fixfix
,int ldGrid
);
FDKsbrEnc_initFrameInfoGenerator (
HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,
INT allowSpread,
INT numEnvStatic,
INT staticFraming,
INT timeSlots,
const FREQ_RES* freq_res_fixfix
,UCHAR fResTransIsLow,
INT ldGrid
);
HANDLE_SBR_FRAME_INFO
FDKsbrEnc_frameInfoGenerator (HANDLE_SBR_ENVELOPE_FRAME hSbrEnvFrame,

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -663,10 +663,27 @@ static void transientCleanUp(FIXP_DBL **quotaBuffer,
}
/**************************************************************************/
/*****************************************************************************/
/*!
\brief Do detection for one tonality estimate.
\brief Detection for one tonality estimate.
This is the actual missing harmonics detection, using information from the
previous detection.
If a missing harmonic was detected (in a previous frame) due to too high
tonality differences, but there was not enough tonality difference in the
current frame, the detection algorithm still continues to trace the strongest
tone in the scalefactor band (assuming that this is the tone that is going to
be replaced in the decoder). This is done to avoid abrupt endings of sines
fading out (e.g. in the glockenspiel).
The function also tries to estimate where one sine is going to be replaced
with multiple sines (due to the patching). This is done by comparing the
tonality flatness measure of the original and the SBR signal.
The function also tries to estimate (for the scalefactor bands only
containing one qmf subband) when a strong tone in the original will be
replaced by a strong tone in the adjacent QMF subband.
\return none.
@ -694,10 +711,10 @@ static void detection(FIXP_DBL *quotaBuffer,
for(i=0;i<nSfb;i++){
thresTemp = (guideVectors.guideVectorDiff[i] != FL2FXCONST_DBL(0.0f))
? fixMax(fMult(mhThresh.decayGuideDiff,guideVectors.guideVectorDiff[i]), mhThresh.thresHoldDiffGuide)
? fMax(fMult(mhThresh.decayGuideDiff,guideVectors.guideVectorDiff[i]), mhThresh.thresHoldDiffGuide)
: mhThresh.thresHoldDiff;
thresTemp = fixMin(thresTemp, mhThresh.thresHoldDiff);
thresTemp = fMin(thresTemp, mhThresh.thresHoldDiff);
if(pDiffVecScfb[i] > thresTemp){
pHarmVec[i] = 1;
@ -813,8 +830,11 @@ static void detectionWithPrediction(FIXP_DBL **quotaBuffer,
if(newDetectionAllowed){
/* Since we don't want to use the transient region for detection (since the tonality values
tend to be a bit unreliable for this region) the guide-values are copied to the current
starting point. */
if(totNoEst > 1){
start = detectionStart;
start = detectionStart+1;
if (start != 0) {
FDKmemcpy(guideVectors[start].guideVectorDiff,guideVectors[0].guideVectorDiff,nSfb*sizeof(FIXP_DBL));

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -268,8 +268,9 @@ qmfBasedNoiseFloorDetection(FIXP_DBL *noiseLevel, /*!< Pointer to v
/*
* Add a noise floor offset to compensate for bias in the detector
*****************************************************************/
if(!missingHarmonicFlag)
*noiseLevel = fMult(*noiseLevel, noiseFloorOffset)<<(NOISE_FLOOR_OFFSET_SCALING);
if(!missingHarmonicFlag) {
*noiseLevel = fixMin(fMult(*noiseLevel, noiseFloorOffset), (FIXP_DBL)MAXVAL_DBL>>NOISE_FLOOR_OFFSET_SCALING) << NOISE_FLOOR_OFFSET_SCALING;
}
/*
* check to see that we don't exceed the maximum allowed level
@ -297,7 +298,7 @@ FDKsbrEnc_sbrNoiseFloorEstimateQmf(HANDLE_SBR_NOISE_FLOOR_ESTIMATE h_sbrNoiseFlo
SCHAR *indexVector, /*!< Index vector to obtain the patched data. */
INT missingHarmonicsFlag, /*!< Flag indicating if a strong tonal component will be missing. */
INT startIndex, /*!< Start index. */
int numberOfEstimatesPerFrame, /*!< The number of tonality estimates per frame. */
UINT numberOfEstimatesPerFrame, /*!< The number of tonality estimates per frame. */
int transientFrame, /*!< A flag indicating if a transient is present. */
INVF_MODE* pInvFiltLevels, /*!< Pointer to the vector holding the inverse filtering levels. */
UINT sbrSyntaxFlags

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -119,7 +119,7 @@ FDKsbrEnc_sbrNoiseFloorEstimateQmf(HANDLE_SBR_NOISE_FLOOR_ESTIMATE h_sbrNoiseFlo
SCHAR* indexVector, /*!< Index vector to obtain the patched data. */
INT missingHarmonicsFlag, /*!< Flag indicating if a strong tonal component will be missing. */
INT startIndex, /*!< Start index. */
int numberOfEstimatesPerFrame, /*!< The number of tonality estimates per frame. */
UINT numberOfEstimatesPerFrame, /*!< The number of tonality estimates per frame. */
INT transientFrame, /*!< A flag indicating if a transient is present. */
INVF_MODE* pInvFiltLevels, /*!< Pointer to the vector holding the inverse filtering levels. */
UINT sbrSyntaxFlags

View File

@ -2,7 +2,7 @@
/* -----------------------------------------------------------------------------------------------------------
Software License for The Fraunhofer FDK AAC Codec Library for Android
© Copyright 1995 - 2013 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
© Copyright 1995 - 2015 Fraunhofer-Gesellschaft zur Förderung der angewandten Forschung e.V.
All rights reserved.
1. INTRODUCTION
@ -261,21 +261,23 @@ static const UINT opdDeltaTime_Code[] =
0x00000001, 0x00000002, 0x00000001, 0x00000007, 0x00000006, 0000000000, 0x00000002, 0x00000003
};
static const INT psBands[] =
static INT getNoBands(const INT mode)
{
PS_BANDS_COARSE,
PS_BANDS_MID
};
INT noBands = 0;
static INT getNoBands(UINT mode)
{
if(mode>=6)
return 0;
switch (mode) {
case 0: case 3: /* coarse */
noBands = PS_BANDS_COARSE;
break;
case 1: case 4: /* mid */
noBands = PS_BANDS_MID;
break;
case 2: case 5: /* fine not supported */
default: /* coarse as default */
noBands = PS_BANDS_COARSE;
}
if(mode>=3)
mode = mode-3;
return psBands[mode];
return noBands;
}
static INT getIIDRes(INT iidMode)
@ -524,7 +526,7 @@ static INT encodeIpdOpd(HANDLE_PS_OUT psOut,
bitCnt += FDKsbrEnc_EncodeIpd( hBitBuf,
psOut->ipd[env],
ipdLast,
getNoBands((UINT)psOut->iidMode),
getNoBands(psOut->iidMode),
psOut->deltaIPD[env],
&error);
@ -532,7 +534,7 @@ static INT encodeIpdOpd(HANDLE_PS_OUT psOut,
bitCnt += FDKsbrEnc_EncodeOpd( hBitBuf,
psOut->opd[env],
opdLast,
getNoBands((UINT)psOut->iidMode),
getNoBands(psOut->iidMode),
psOut->deltaOPD[env],
&error );
}
@ -661,7 +663,7 @@ INT FDKsbrEnc_WritePSBitstream(const HANDLE_PS_OUT psOut,
bitCnt += FDKsbrEnc_EncodeIid( hBitBuf,
psOut->iid[env],
iidLast,
getNoBands((UINT)psOut->iidMode),
getNoBands(psOut->iidMode),
(PS_IID_RESOLUTION)getIIDRes(psOut->iidMode),
psOut->deltaIID[env],
&error );
@ -677,7 +679,7 @@ INT FDKsbrEnc_WritePSBitstream(const HANDLE_PS_OUT psOut,
bitCnt += FDKsbrEnc_EncodeIcc( hBitBuf,
psOut->icc[env],
iccLast,
getNoBands((UINT)psOut->iccMode),
getNoBands(psOut->iccMode),
psOut->deltaICC[env],
&error);

Some files were not shown because too many files have changed in this diff Show More