summaryrefslogtreecommitdiff
path: root/libavutil/tx_template.c
Commit message (Collapse)AuthorAge
* lavu/tx: add an RDFT implementationLynne2022-01-26
| | | | | | | | | | | | | | | | | | RDFTs are full of conventions that vary between implementations. What I've gone for here is what's most common between both fftw, avcodec's rdft and what we use, the equivalent of which is DFT_R2C for forward and IDFT_C2R for inverse. The other 2 conventions (IDFT_R2C and DFT_C2R) were not used at all in our code, and their names are also not appropriate. If there's a use for either, we can easily add a flag which would just flip the sign on one exptab. For some unknown reason, possibly to allow reusing FFT's exp tables, av_rdft's C2R output is 0.5x lower than what it should be to ensure a proper back-and-forth conversion. This code outputs its real samples at the correct level, which matches FFTW's level, and allows the user to change the level and insert arbitrary multiplies for free by setting the scale option.
* lavu/tx: rewrite internal code as a tree-based codelet constructorLynne2022-01-26
| | | | | | | | | | This commit rewrites the internal transform code into a constructor that stitches transforms (codelets). This allows for transforms to reuse arbitrary parts of other transforms, and allows transforms to be stacked onto one another (such as a full iMDCT using a half-iMDCT which in turn uses an FFT). It also permits for each step to be individually replaced by assembly or a custom implementation (such as an ASIC).
* checkasm: add av_tx FFT SIMD testing codeLynne2021-04-24
| | | | | | This sadly required making changes to the code itself, due to the same context needing to be reused for both versions. The lookup table had to be duplicated for both versions.
* lavu/tx: add full-sized iMDCT transform flagLynne2021-04-24
|
* lavu/tx: add a 9-point FFT and (i)MDCTLynne2021-04-24
|
* lavu/tx: add a 7-point FFT and (i)MDCTLynne2021-04-24
|
* lavu/tx: refactor power-of-two FFTLynne2021-04-24
| | | | | | | | | This commit refactors the power-of-two FFT, making it faster and halving the size of all tables, making the code much smaller on all systems. This removes the big/small pass split, because on modern systems the "big" pass is always faster, and even on older machines there is no measurable speed difference.
* lavu/tx: do not invert permutes on MDCTsLynne2021-02-27
|
* lavu/tx: invert permutation lookupsLynne2021-02-27
| | | | | | | | | | | | | out[lut[i]] = in[i] lookups were 4.04 times(!) slower than out[i] = in[lut[i]] lookups for an out-of-place FFT of length 4096. The permutes remain unchanged for anything but out-of-place monolithic FFT, as those benefit quite a lot from the current order (it means there's only 1 lookup necessary to add to an offset, rather than a full gather). The code was based around non-power-of-two FFTs, so this wasn't benchmarked early on.
* lavu/tx: require output argument to match input for inplace transformsLynne2021-02-26
| | | | | This simplifies some assembly code by a lot, by either saving a branch or saving an entire duplicated function.
* lavu/tx: support in-place FFT transformsLynne2021-02-21
| | | | | | | | | | | | | | | | | | | | | | | | | | | | | This commit adds support for in-place FFT transforms. Since our internal transforms were all in-place anyway, this only changes the permutation on the input. Unfortunately, research papers were of no help here. All focused on dry hardware implementations, where permutes are free, or on software implementations where binary bloat is of no concern so storing dozen times the transforms for each permutation and version is not considered bad practice. Still, for a pure C implementation, it's only around 28% slower than the multi-megabyte FFTW3 in unaligned mode. Unlike a closed permutation like with PFA, split-radix FFT bit-reversals contain multiple NOPs, multiple simple swaps, and a few chained swaps, so regular single-loop single-state permute loops were not possible. Instead, we filter out parts of the input indices which are redundant. This allows for a single branch, and with some clever AVX512 asm, could possibly be SIMD'd without refactoring. The inplace_idx array is guaranteed to never be larger than the revtab array, and in practice only requires around log2(len) entries. The power-of-two MDCTs can be done in-place as well. And it's possible to eliminate a copy in the compound MDCTs too, however it'll be slower than doing them out of place, and we'd need to dirty the input array.
* avutil/tx: use ENOSYS instead of ENOTSUPJames Almer2021-01-13
| | | | | | | It's the standard error code used across the codebase to signal unimplemented or unsupported features. Signed-off-by: James Almer <jamrial@gmail.com>
* lavu: support arbitrary-point FFTs and all even (i)MDCT transformsLynne2021-01-13
| | | | | | | | | This patch adds support for arbitrary-point FFTs and all even MDCT transforms. Odd MDCTs are not supported yet as they're based on the DCT-II and DCT-III and they're very niche. With this we can now write tests.
* lavu/tx: add 2-point FFT transformLynne2020-03-23
| | | | | | By itself, this allows 6-point, 10-point and 30-point transforms. When the 9-point transform is added it allows for 18-point FFT, and also for a 36-point MDCT (used by MP3).
* lavu/tx: improve 3-point fixed precisionLynne2020-02-14
| | | | | There's just no reason not to when its so easy (albeit messy) and its also reducing the precision of all non-power-of-two transforms that use it.
* lavu/tx: slightly optimize fft15Lynne2020-02-13
| | | | Saves 2 additions.
* lavu/tx: undef the correct macroLynne2020-02-13
| | | | It was renamed and no warning was given for undeffing a nonexisting one.
* lavu/tx: implement 32 bit fixed point FFT and MDCTLynne2020-02-13
| | | | | | | | | | | | | | | | | | | | Required minimal changes to the code so made sense to implement. FFT and MDCT tested, the output of both was properly rounded. Fun fact: the non-power-of-two fixed-point FFT and MDCT are the fastest ever non-power-of-two fixed-point FFT and MDCT written. This can replace the power of two integer MDCTs in aac and ac3 if the MIPS optimizations are ported across. Unfortunately the ac3 encoder uses a 16-bit fixed point forward transform, unlike the encoder which uses a 32bit inverse transform, so some modifications might be required there. The 3-point FFT is somewhat less accurate than it otherwise could be, having minor rounding errors with bigger transforms. However, this could be improved later, and the way its currently written is the way one would write assembly for it. Similar rounding errors can also be found throughout the power of two FFTs as well, though those are more difficult to correct. Despite this, the integer transforms are more than accurate enough.
* lavu/tx: add support for double precision FFT and MDCTLynne2019-08-02
Simply moves and templates the actual transforms to support an additional data type. Unlike the float version, which is equal or better than libfftw3f, double precision output is bit identical with libfftw3.