fluid_dsp_simple.c
上传用户:tjmskj2
上传日期:2020-08-17
资源大小:577k
文件大小:5k
源码类别:

midi

开发平台:

C/C++

  1. /* FluidSynth - A Software Synthesizer
  2.  *
  3.  * Copyright (C) 2003  Peter Hanappe and others.
  4.  *
  5.  * This library is free software; you can redistribute it and/or
  6.  * modify it under the terms of the GNU Library General Public License
  7.  * as published by the Free Software Foundation; either version 2 of
  8.  * the License, or (at your option) any later version.
  9.  *
  10.  * This library is distributed in the hope that it will be useful, but
  11.  * WITHOUT ANY WARRANTY; without even the implied warranty of
  12.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  13.  * Library General Public License for more details.
  14.  *
  15.  * You should have received a copy of the GNU Library General Public
  16.  * License along with this library; if not, write to the Free
  17.  * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA
  18.  * 02111-1307, USA
  19.  */
  20. /* Purpose:
  21.  * Low-level voice processing:
  22.  *
  23.  * - interpolates (obtains values between the samples of the original waveform data)
  24.  * - filters (applies a lowpass filter with variable cutoff frequency and quality factor)
  25.  * - mixes the processed sample to left and right output using the pan setting
  26.  * - sends the processed sample to chorus and reverb
  27.  *
  28.  *
  29.  * This file does -not- generate an object file.
  30.  * Instead, it is #included in several places in fluid_voice.c.
  31.  * The motivation for this is
  32.  * - Calling it as a subroutine may be time consuming, especially with optimization off
  33.  * - The previous implementation as a macro was clumsy to handle
  34.  *
  35.  *
  36.  * Fluid_voice.c sets a couple of variables before #including this:
  37.  * - dsp_data: Pointer to the original waveform data
  38.  * - dsp_left_buf: The generated signal goes here, left channel
  39.  * - dsp_right_buf: right channel
  40.  * - dsp_reverb_buf: Send to reverb unit
  41.  * - dsp_chorus_buf: Send to chorus unit
  42.  * - dsp_start: Start processing at this output buffer index
  43.  * - dsp_end: End processing just before this output buffer index
  44.  * - dsp_a1: Coefficient for the filter
  45.  * - dsp_a2: same
  46.  * - dsp_b0: same
  47.  * - dsp_b1: same
  48.  * - dsp_b2: same
  49.  * - dsp_filter_flag: Set, the filter is needed (many sound fonts don't use
  50.  *                    the filter at all. If it is left at its default setting
  51.  *                    of roughly 20 kHz, there is no need to apply filterling.)
  52.  * - dsp_interp_method: Which interpolation method to use.
  53.  * - voice holds the voice structure
  54.  *
  55.  * Some variables are set and modified:
  56.  * - dsp_phase: The position in the original waveform data.
  57.  *              This has an integer and a fractional part (between samples).
  58.  * - dsp_phase_incr: For each output sample, the position in the original
  59.  *              waveform advances by dsp_phase_incr. This also has an integer
  60.  *              part and a fractional part.
  61.  *              If a sample is played at root pitch (no pitch change),
  62.  *              dsp_phase_incr is integer=1 and fractional=0.
  63.  * - dsp_amp: The current amplitude envelope value.
  64.  * - dsp_amp_incr: The changing rate of the amplitude envelope.
  65.  *
  66.  * A couple of variables are used internally, their results are discarded:
  67.  * - dsp_i: Index through the output buffer
  68.  * - dsp_phase_fractional: The fractional part of dsp_phase
  69.  * - dsp_coeff: A table of four coefficients, depending on the fractional phase.
  70.  *              Used to interpolate between samples.
  71.  * - dsp_process_buffer: Holds the processed signal between stages
  72.  * - dsp_centernode: delay line for the IIR filter
  73.  * - dsp_hist1: same
  74.  * - dsp_hist2: same
  75.  *
  76.  */
  77. /* Nonoptimized DSP loop */
  78. #warning "This code is meant for experiments only.";
  79. /* wave table interpolation */
  80. for (dsp_i = dsp_start; dsp_i < dsp_end; dsp_i++) {
  81. dsp_coeff = &interp_coeff[fluid_phase_fract_to_tablerow(dsp_phase)];
  82. dsp_phase_index = fluid_phase_index(dsp_phase);
  83. dsp_sample = (dsp_amp *
  84.       (dsp_coeff->a0 * dsp_data[dsp_phase_index]
  85.        + dsp_coeff->a1 * dsp_data[dsp_phase_index+1]
  86.        + dsp_coeff->a2 * dsp_data[dsp_phase_index+2]
  87.        + dsp_coeff->a3 * dsp_data[dsp_phase_index+3]));
  88. /* increment phase and amplitude */
  89. fluid_phase_incr(dsp_phase, dsp_phase_incr);
  90. dsp_amp += dsp_amp_incr;
  91. /* filter */
  92. /* The filter is implemented in Direct-II form. */
  93. dsp_centernode = dsp_sample - dsp_a1 * dsp_hist1 - dsp_a2 * dsp_hist2;
  94. dsp_sample = dsp_b0 * dsp_centernode + dsp_b1 * dsp_hist1 + dsp_b2 * dsp_hist2;
  95. dsp_hist2 = dsp_hist1;
  96. dsp_hist1 = dsp_centernode;
  97. /* pan */
  98. dsp_left_buf[dsp_i] += voice->amp_left * dsp_sample;
  99. dsp_right_buf[dsp_i] += voice->amp_right * dsp_sample;
  100. /* reverb */
  101. if (dsp_reverb_buf){
  102. dsp_reverb_buf[dsp_i] += voice->amp_reverb * dsp_sample;
  103. }
  104. /* chorus */
  105. if (dsp_chorus_buf){
  106. dsp_chorus_buf[dsp_i] += voice->amp_chorus * dsp_sample;
  107. }
  108. }