Exemple #1
0
void dsp_process_init(int cpu_hz, int hsb_hz, int pba_hz, int pbb_hz)
{
	// Initialize TPA6130
	tpa6130_init();

	// Initialize DAC that send audio to TPA6130
	tpa6130_dac_start(DAC_SAMPLING_RATE, DAC_NUM_CHANNELS,
			DAC_BITS_PER_SAMPLE, DAC_SWAP_CHANNELS,
			audio_callback, AUDIO_DAC_RELOAD_CB,
			FOSC0);

	tpa6130_set_volume(0x20);
	tpa6130_get_volume();

	signal_source_init(&signal1_generator, 433, 20000);
	signal_source_init(&signal2_generator, 2000, 10000);

	current_stereo_out_buf = stereo_out_buf1;
	signal_in_buf = signal_pre_filter_buf + FIR_NUM_COEF;
	filter_restore_default();

	/* Fill the initial buffer for the hamming window with ones. This buffer
	 * will then be multiplied by the hamming window.
	 */
	dsp16_gen_step(fft_window, BUFFER_LENGTH, DSP16_Q(1.), DSP16_Q(1.), 0);
	dsp16_win_hamm(fft_window, fft_window, BUFFER_LENGTH);

	/* Run the interrupt handler manually once to start the ABDAC */
	dac_reload_callback();
}
Exemple #2
0
/*! \brief Decreases the output volume of the amplifier by one step.
 *
 * Stops at the lowest possible volume.
 */
void tpa6130_dac_decrease_volume(void)
{
  int8_t volume = tpa6130_get_volume()& (~(MUTE_L | MUTE_R));;
  if( volume > TPA6130_VOL_MIN )
    --volume;
  tpa6130_set_volume( volume );
}
Exemple #3
0
/*! \brief Increases the output volume of the amplifier by one step.
 * Stops at the maximum volume and thus does not wrap to the
 * lowest volume.
 */
void tpa6130_dac_increase_volume(void)
{
  int8_t volume = tpa6130_get_volume()& (~(MUTE_L | MUTE_R));
  if( volume < TPA6130_VOL_MIN )
    volume = TPA6130_VOL_MIN;
  tpa6130_set_volume(volume+1);
}
Exemple #4
0
/*! \brief Returns the current volume of the DAC.
 *         The volume is in the range 0 - 255
 */
uint8_t tpa6130_dac_get_volume(void)
{
 // return volume is num display step for LCD
 //  volume scale is between 10 and 245
 // 0 is -100db
 // 245 is max volume
  uint16_t raw_volume;
  raw_volume = (tpa6130_get_volume() & (~(MUTE_L | MUTE_R)));
  return (uint8_t) ((raw_volume * 255) / TPA6130_VOL_MAX);
}
Exemple #5
0
static bool state_machine_idle(enum state_function *state)
{
  uint32_t frame_rate_ms;
  S8 volume;
  const S8 volume_inc = (TPA6130_VOL_MAX - TPA6130_VOL_MIN) / 20;

  switch (*state)
  {
  case STATE_FCT_IDLE:
    if (new_state_fct)
    {
      gui_set_selection(GUI_NO_SEL);
      gui_text_print(GUI_COMMENT_ID, TEXT_IDLE);
    }
    else
    {
      if (controller_wheel_right(1) || controller_wheel_left(1))
        switch_state(STATE_SOURCE1);
      return false;
    }
    break;
  // Frame rate
  case STATE_FCT_FUNCTION1:
    frame_rate_ms = gui_get_update_fs();
    if (controller_wheel_left(1) && frame_rate_ms < 1000)
    {
      if (!frame_rate_ms)
        frame_rate_ms = 40;
      else
        frame_rate_ms = 1000 / ((1000 / frame_rate_ms) - 1);
      new_state_fct = true;
    }
    else if (controller_wheel_right(1))
    {
      if (frame_rate_ms <= 40)
        frame_rate_ms = 0;
      else
        frame_rate_ms = 1000 / ((1000 / frame_rate_ms) + 1);
      new_state_fct = true;
    }
    if (new_state_fct)
    {
      gui_change_update_fs(frame_rate_ms);
      if (frame_rate_ms)
      {
        gui_text_printf(GUI_COMMENT_ID, TEXT_FUNC1 "\n%i Frame(s)/s\n\n\n\n" TEXT_WHEEL, (1000 / frame_rate_ms));
      }
      else
        gui_text_print(GUI_COMMENT_ID, TEXT_FUNC1 "\nMAX Frame(s)/s\n\n\n\n" TEXT_WHEEL);
    }
    break;
  // Volume
  case STATE_FCT_FUNCTION2:
    volume = tpa6130_get_volume();
    if (volume < TPA6130_VOL_MIN)
      volume = TPA6130_VOL_MIN;
    if (controller_wheel_right(1))
    {
      if (volume < TPA6130_VOL_MAX - volume_inc)
        volume += volume_inc;
      else
        volume = TPA6130_VOL_MAX;
      new_state_fct = true;
    }
    else if (controller_wheel_left(1))
    {
      if (volume > TPA6130_VOL_MIN + volume_inc)
        volume -= volume_inc;
      else
        volume = TPA6130_VOL_MIN;
      new_state_fct = true;
    }
    if (new_state_fct)
    {
      tpa6130_set_volume(volume);
      gui_text_printf(GUI_COMMENT_ID, TEXT_FUNC2 "\nVolume %i%%\n\n\n\n" TEXT_WHEEL, ((int) volume * 100) / (TPA6130_VOL_MAX - TPA6130_VOL_MIN));
    }
    break;
  /*
extern U8 tpa6130_get_volume(void);
extern void tpa6130_set_volume(U8 volume);
  */
  case STATE_FCT_FUNCTION3:
    if (new_state_fct)
      gui_text_print(GUI_COMMENT_ID, TEXT_FUNC_NOT_IMPLEMENTED);
    else if (controller_wheel_right(1) || controller_wheel_left(1)) {
      switch_state(STATE_SOURCE1);
      return false;
    }
    break;
  case STATE_FCT_ZOOM:
    break;
  }
  return true;
}
Exemple #6
0
/*! \brief Sets the DACs up with new settings.
 *
 * \note The DACs must have been started beforehand.
 */
void tpa6130_dac_setup(uint32_t sample_rate_hz,
                       uint8_t num_channels,
                       uint8_t bits_per_sample,
                       bool swap_channels,
                       void (*callback)(uint32_t arg),
                       uint32_t callback_opt,
                       uint32_t pba_hz)
{
  // save input parameters to local driver data
  tpa6130_output_param.num_channels = num_channels;
  tpa6130_output_param.callback     = callback;
  tpa6130_output_param.callback_opt = callback_opt;

  /* Probe for amplifier and initialize it */
  tpa6130_init();

#if defined(TPA6130_DAC_CLOCK_SET_CALLBACK)
  TPA6130_DAC_CLOCK_SET_CALLBACK(sample_rate_hz);
#else
  /* ABDAC configuration
   * The ABDAC needs the input frequency of its generic clock (bus_hz)
   * Here we use the configuration value from the conf_tpa6130.h file
   * (TPA6130_ABDAC_GCLK_INPUT_HZ).
   * The sample rate specifies the desired sample rate for the ABDAC.
   * The generic clock input must be greater than 256*sample_rate_hz
   * or the setup of the ABDAC will fail silently here.
   * TODO we could add asserts here to detect wrong settings during
   * compile time.
   */
  if(!abdac_set_dac_sample_rate(sample_rate_hz)) {
    // if it is not possible to set correctly the sample rate
    // Use default set function
    abdac_set_dac_hz(TPA6130_ABDAC, TPA6130_ABDAC_GCLK_INPUT_HZ,sample_rate_hz);
  }
#endif

  if(swap_channels)
  {
    abdac_swap_channels(TPA6130_ABDAC);
  }
  abdac_enable(TPA6130_ABDAC);

  /* PDCA setup */
  /*FIXME we use only word as transfer size for now.
   * half-word transfer size will only write to channel0
   * of the ABDAC, this can be used to implement mono */
  pdca_channel_options_t tpa6130_abdac_pdca_options =
  {
    .addr   = NULL,
    .size   = 0,
    .r_addr   = 0,
    .r_size   = 0,
    .pid    = TPA6130_ABDAC_PDCA_PID,
    .transfer_size  = PDCA_TRANSFER_SIZE_WORD
  };

  /* Initialize the PCDA for the ABDAC
   * The channel number can be set in the configuration file
   * with the define TPA6130_ABDAC_PDCA_CHANNEL.
   */
  pdca_init_channel(TPA6130_ABDAC_PDCA_CHANNEL,
    &tpa6130_abdac_pdca_options);
  /* Enable the PDCA channel. Since we did not provide any data
   * yet the channel is in idle mode */
  pdca_enable(TPA6130_ABDAC_PDCA_CHANNEL);

}

/*! \brief Outputs a sample buffer to the DACs.
 * The input requires a sample buffer that consists of words (32-bit)
 * which contain two (16-bit) samples, one for each channel.
 *
 * \note The DACs must have been started beforehand.
 */
bool tpa6130_dac_output(void *sample_buffer, size_t sample_length)
{
  //int global_interrupt_enabled;

  /*Wait until the PDCA loads the reload value to its transfer
   * counter register(TCRR=0). Then we are ready to set up a new
   * transfer */
  if(!(pdca_get_transfer_status(TPA6130_ABDAC_PDCA_CHANNEL) &
    PDCA_TRANSFER_COUNTER_RELOAD_IS_ZERO))
  {
    return false;
  }

  /* Nothing to do if we get no data. */
  if(sample_length)
  {

    /*TODO Do we really need to adjust the buffer for mono*/

    /* While reloading the PDC we do not need any active interrupt*/
    //if((global_interrupt_enabled = cpu_irq_is_enabled()))
    //  cpu_irq_disable();

    /*FIXME This assumes a stereo 16-bit sample size */
    // one sample here consists of 2x16-bit (16-bit stereo)
    pdca_reload_channel(TPA6130_ABDAC_PDCA_CHANNEL,
      sample_buffer, sample_length);

    //if(global_interrupt_enabled)
    //  cpu_irq_enable();

    /*TODO enable transfer complete interrupt
     * Is it possible to move this to setup or other places?*/
    if(tpa6130_output_param.callback_opt & AUDIO_DAC_OUT_OF_SAMPLE_CB)
      pdca_enable_interrupt_transfer_complete(TPA6130_ABDAC_PDCA_CHANNEL);
    if (tpa6130_output_param.callback_opt & AUDIO_DAC_RELOAD_CB)
      pdca_enable_interrupt_reload_counter_zero(TPA6130_ABDAC_PDCA_CHANNEL);
  }
  return true;
}

bool tpa6130_dac_is_volume_muted(void)
{
  return false;
}

void tpa6130_dac_mute(bool mute)
{
  // //1st Version Mute Audio for Play/Pause
/*  int volume=tpa6130_get_volume();
  if(mute==true) {
     //Mute volume
     volume= volume|MUTE_L|MUTE_R;
  }
  else {
     //Unmute volume
     volume= volume&(~(MUTE_L|MUTE_R));

  }
 tpa6130_write_data(TPA6130_VOLUME_AND_MUTE,volume);
*/
  //2n Version Stop PDCA >> No lost of audio when pause
/*  if(mute==true) {
    pdca_disable(TPA6130_ABDAC_PDCA_CHANNEL);
  }
  else {
    pdca_enable(TPA6130_ABDAC_PDCA_CHANNEL);
  }
*/

  // 3rd Version wait until the current buffers are empty and disable the interrupts
  int8_t volume = tpa6130_get_volume();
  if (mute)
  {
    uint32_t save_dac_reload_callback_opt;

    // Mute the audio stream
    volume = volume | MUTE_L | MUTE_R;
    tpa6130_write_data(TPA6130_VOLUME_AND_MUTE, volume);
    // Disable the reload channel of the interrupt
    save_dac_reload_callback_opt = tpa6130_output_param.callback_opt;
    tpa6130_output_param.callback_opt = 0;
    // Disable the reload interruption and wait until the transfer is complete
    pdca_disable_interrupt_reload_counter_zero(TPA6130_ABDAC_PDCA_CHANNEL);
    while (!(pdca_get_transfer_status(TPA6130_ABDAC_PDCA_CHANNEL) & PDCA_TRANSFER_COMPLETE));
    // Restore the reload callback function
    tpa6130_output_param.callback_opt = save_dac_reload_callback_opt;
  }
  else
  {
    // Re-enable the interrupts
    pdca_enable_interrupt_reload_counter_zero(TPA6130_ABDAC_PDCA_CHANNEL);
    // Un-mute the audio stream
    volume = volume & (~(MUTE_L | MUTE_R));
    tpa6130_write_data(TPA6130_VOLUME_AND_MUTE, volume);
  }
}
Exemple #7
0
/*! main function */
int main(void)
{
  init_sys_clocks();

  // Initialize RS232 debug text output.
  init_dbg_rs232(FOSC0);

  print_dbg(MSG_WELCOME);

  // Enable LED0 and LED1
  gpio_enable_gpio_pin(LED0_GPIO);
  gpio_enable_gpio_pin(LED1_GPIO);

  // Configure TWI as master
  twi_init();

  // Initialize TPA6130
  tpa6130_init();

  // Initialize DAC that send audio to TPA6130
  tpa6130_dac_start(DEFAULT_DAC_SAMPLE_RATE_HZ,
                    DEFAULT_DAC_NUM_CHANNELS,
                    DEFAULT_DAC_BITS_PER_SAMPLE,
                    DEFAULT_DAC_SWAP_CHANNELS,
                    master_callback,
                      AUDIO_DAC_OUT_OF_SAMPLE_CB
                    | AUDIO_DAC_RELOAD_CB,
                    FOSC0);

  tpa6130_set_volume(0x2F);
  tpa6130_get_volume();

  int count = 0;
  int i=0;

  while(true)
  {
    count = 0;

    // Store sample from the sound_table array
    while(count < (SOUND_SAMPLES)){
      samples[count++] = ((uint8_t)sound_table[i]+0x80) << 8;
      samples[count++] = ((uint8_t)sound_table[i]+0x80) << 8;
      i++;
      if (i >= sizeof(sound_table)) i = 0;
    }

    gpio_set_gpio_pin(LED0_GPIO);
    gpio_clr_gpio_pin(LED1_GPIO);

    // Play buffer
    tpa6130_dac_output((void *) samples,SOUND_SAMPLES/2);

    gpio_clr_gpio_pin(LED0_GPIO);
    gpio_set_gpio_pin(LED1_GPIO);

    /* Wait until the reload register is empty.
     * This means that one transmission is still ongoing
     * but we are already able to set up the next transmission
     */
     while(!tpa6130_dac_output(NULL, 0));
  }
}