1 /* 2 * Copyright (c) 2019 The WebRTC project authors. All Rights Reserved. 3 * 4 * Use of this source code is governed by a BSD-style license 5 * that can be found in the LICENSE file in the root of the source 6 * tree. An additional intellectual property rights grant can be found 7 * in the file PATENTS. All contributing project authors may 8 * be found in the AUTHORS file in the root of the source tree. 9 */ 10 11 #ifndef MODULES_AUDIO_PROCESSING_UTILITY_PFFFT_WRAPPER_H_ 12 #define MODULES_AUDIO_PROCESSING_UTILITY_PFFFT_WRAPPER_H_ 13 14 #include <memory> 15 16 #include "api/array_view.h" 17 18 // Forward declaration. 19 struct PFFFT_Setup; 20 21 namespace webrtc { 22 23 // Pretty-Fast Fast Fourier Transform (PFFFT) wrapper class. 24 // Not thread safe. 25 class Pffft { 26 public: 27 enum class FftType { kReal, kComplex }; 28 29 // 1D floating point buffer used as input/output data type for the FFT ops. 30 // It must be constructed using Pffft::CreateBuffer(). 31 class FloatBuffer { 32 public: 33 FloatBuffer(const FloatBuffer&) = delete; 34 FloatBuffer& operator=(const FloatBuffer&) = delete; 35 ~FloatBuffer(); 36 37 rtc::ArrayView<const float> GetConstView() const; 38 rtc::ArrayView<float> GetView(); 39 40 private: 41 friend class Pffft; 42 FloatBuffer(size_t fft_size, FftType fft_type); const_data()43 const float* const_data() const { return data_; } data()44 float* data() { return data_; } size()45 size_t size() const { return size_; } 46 47 const size_t size_; 48 float* const data_; 49 }; 50 51 // TODO(https://crbug.com/webrtc/9577): Consider adding a factory and making 52 // the ctor private. 53 // static std::unique_ptr<Pffft> Create(size_t fft_size, 54 // FftType fft_type); Ctor. |fft_size| must be a supported size (see 55 // Pffft::IsValidFftSize()). If not supported, the code will crash. 56 Pffft(size_t fft_size, FftType fft_type); 57 Pffft(const Pffft&) = delete; 58 Pffft& operator=(const Pffft&) = delete; 59 ~Pffft(); 60 61 // Returns true if the FFT size is supported. 62 static bool IsValidFftSize(size_t fft_size, FftType fft_type); 63 64 // Returns true if SIMD code optimizations are being used. 65 static bool IsSimdEnabled(); 66 67 // Creates a buffer of the right size. 68 std::unique_ptr<FloatBuffer> CreateBuffer() const; 69 70 // TODO(https://crbug.com/webrtc/9577): Overload with rtc::ArrayView args. 71 // Computes the forward fast Fourier transform. 72 void ForwardTransform(const FloatBuffer& in, FloatBuffer* out, bool ordered); 73 // Computes the backward fast Fourier transform. 74 void BackwardTransform(const FloatBuffer& in, FloatBuffer* out, bool ordered); 75 76 // Multiplies the frequency components of |fft_x| and |fft_y| and accumulates 77 // them into |out|. The arrays must have been obtained with 78 // ForwardTransform(..., /*ordered=*/false) - i.e., |fft_x| and |fft_y| must 79 // not be ordered. 80 void FrequencyDomainConvolve(const FloatBuffer& fft_x, 81 const FloatBuffer& fft_y, 82 FloatBuffer* out, 83 float scaling = 1.f); 84 85 private: 86 const size_t fft_size_; 87 const FftType fft_type_; 88 PFFFT_Setup* pffft_status_; 89 float* const scratch_buffer_; 90 }; 91 92 } // namespace webrtc 93 94 #endif // MODULES_AUDIO_PROCESSING_UTILITY_PFFFT_WRAPPER_H_ 95