15abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick/*
25abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * Copyright (C) 2010 Google Inc. All rights reserved.
35abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick *
45abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * Redistribution and use in source and binary forms, with or without
55abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * modification, are permitted provided that the following conditions are
65abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * met:
75abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick *
85abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick *     * Redistributions of source code must retain the above copyright
95abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * notice, this list of conditions and the following disclaimer.
105abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick *     * Redistributions in binary form must reproduce the above
115abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * copyright notice, this list of conditions and the following disclaimer
125abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * in the documentation and/or other materials provided with the
135abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * distribution.
145abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick *     * Neither the name of Google Inc. nor the names of its
155abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * contributors may be used to endorse or promote products derived from
165abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * this software without specific prior written permission.
175abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick *
185abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
195abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
205abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
215abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
225abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
235abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
245abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
255abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
265abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
275abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
285abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
295abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick */
305abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
315abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick#include "config.h"
325abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
335abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick#if ENABLE(WEB_AUDIO)
345abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
355abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick#include "AudioDSPKernelProcessor.h"
365abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
375abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick#include "AudioDSPKernel.h"
385abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
395abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merricknamespace WebCore {
405abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
415abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick// setNumberOfChannels() may later be called if the object is not yet in an "initialized" state.
425abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain MerrickAudioDSPKernelProcessor::AudioDSPKernelProcessor(double sampleRate, unsigned numberOfChannels)
435abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    : AudioProcessor(sampleRate)
445abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    , m_numberOfChannels(numberOfChannels)
455abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    , m_hasJustReset(true)
465abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick{
475abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick}
485abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
495abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrickvoid AudioDSPKernelProcessor::initialize()
505abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick{
515abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    if (isInitialized())
525abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        return;
535abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
545abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    ASSERT(!m_kernels.size());
555abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
565abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    // Create processing kernels, one per channel.
575abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    for (unsigned i = 0; i < numberOfChannels(); ++i)
585abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        m_kernels.append(createKernel());
595abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
605abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    m_initialized = true;
615abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick}
625abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
635abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrickvoid AudioDSPKernelProcessor::uninitialize()
645abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick{
655abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    if (!isInitialized())
665abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        return;
675abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
685abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    m_kernels.clear();
695abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
705abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    m_initialized = false;
715abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick}
725abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
735abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrickvoid AudioDSPKernelProcessor::process(AudioBus* source, AudioBus* destination, size_t framesToProcess)
745abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick{
755abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    ASSERT(source && destination);
765abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    if (!source || !destination)
775abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        return;
785abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
795abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    if (!isInitialized()) {
805abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        destination->zero();
815abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        return;
825abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    }
835abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
845abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    bool channelCountMatches = source->numberOfChannels() == destination->numberOfChannels() && source->numberOfChannels() == m_kernels.size();
855abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    ASSERT(channelCountMatches);
865abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    if (!channelCountMatches)
875abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        return;
885abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
895abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    for (unsigned i = 0; i < m_kernels.size(); ++i)
905abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        m_kernels[i]->process(source->channel(i)->data(), destination->channel(i)->data(), framesToProcess);
915abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick}
925abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
935abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick// Resets filter state
945abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrickvoid AudioDSPKernelProcessor::reset()
955abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick{
965abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    if (!isInitialized())
975abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        return;
985abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
995abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    // Forces snap to parameter values - first time.
1005abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    // Any processing depending on this value must set it to false at the appropriate time.
1015abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    m_hasJustReset = true;
1025abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
1035abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    for (unsigned i = 0; i < m_kernels.size(); ++i)
1045abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        m_kernels[i]->reset();
1055abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick}
1065abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
1075abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrickvoid AudioDSPKernelProcessor::setNumberOfChannels(unsigned numberOfChannels)
1085abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick{
1095abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    ASSERT(!isInitialized());
1105abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick    if (!isInitialized())
1115abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick        m_numberOfChannels = numberOfChannels;
1125abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick}
1135abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
1145abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick} // namespace WebCore
1155abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick
1165abb8606fa57c3ebfc8b3c3dbc3fa4a25d2ae306Iain Merrick#endif // ENABLE(WEB_AUDIO)
117