view include/PRU.h @ 528:5c8f46fcd4d0 API-update

Updated BelaContext to use separate values for in/ou channels
author Giulio Moro <giuliomoro@yahoo.it>
date Thu, 23 Jun 2016 18:17:35 +0100
parents 493a07f6ec09
children
line wrap: on
line source
/*
 * PRU.h
 *
 *  Created on: May 27, 2014
 *      Author: andrewm
 */

#ifndef PRU_H_
#define PRU_H_

#include <stdint.h>
#include <native/intr.h>
#include "../include/Bela.h"

/**
 * Internal version of the BelaContext struct which does not have const
 * elements, so it can be modified by the code. When it's passed to the user
 * code, it is typecast to the standard BelaContext.
 *
 * Important: make sure this retains the same structure as BelaContext!
 */
typedef struct {
	/// \brief Buffer holding audio input samples
	///
	/// This buffer may be in either interleaved or non-interleaved format,
	/// depending on the contents of the BelaInitSettings structure.
	/// \b Note: this element is available in render() only.
	float *audioIn;

	/// \brief Buffer holding audio output samples
	///
	/// This buffer may be in either interleaved or non-interleaved format,
	/// depending on the contents of the BelaInitSettings structure.
	/// \b Note: this element is available in render() only.
	float *audioOut;

	/// \brief Buffer holding analog input samples
	///
	/// This buffer may be in either interleaved or non-interleaved format,
	/// depending on the contents of the BelaInitSettings structure.
	/// \b Note: this element is available in render() only.
	float *analogIn;

	/// \brief Buffer holding analog output samples
	///
	/// This buffer may be in either interleaved or non-interleaved format,
	/// depending on the contents of the BelaInitSettings structure.
	/// \b Note: this element is available in render() only.
	float *analogOut;

	/// \brief Buffer holding digital input/output samples
	///
	/// \b Note: this element is available in render() only.
	uint32_t *digital;

	/// Number of audio frames per period
	uint32_t audioFrames;
	/// Number of input audio channels
	uint32_t audioInChannels;
	/// Number of output audio channels
	uint32_t audioOutChannels;
	/// Audio sample rate in Hz (currently always 44100.0)
	float audioSampleRate;

	/// \brief Number of analog frames per period
	///
	/// This will be 0 if analog I/O is disabled.
	uint32_t analogFrames;

	/// \brief Number of input analog channels
	///
	/// This will be 0 if analog I/O is disabled.
	uint32_t analogInChannels;

	/// \brief Number of output analog channels
	///
	/// This will be 0 if analog I/O is disabled.
	uint32_t analogOutChannels;

	/// \brief Analog sample rate in Hz
	///
	/// The analog sample rate depends on the number of analog channels used. If
	/// 8 channels are used, the sample rate is 22050. If 4 channels are used, the sample
	/// rate is 44100. If 2 channels are used, the sample rate is 88200. If analog I/O
	/// is disabled, the sample rate is 0.
	float analogSampleRate;

	/// Number of digital frames per period
	uint32_t digitalFrames;
	/// \brief Number of digital channels
	///
	/// Currently this will always be 16, unless digital I/O is disabled, in which case it will be 0.
	uint32_t digitalChannels;
	/// Digital sample rate in Hz (currently always 44100.0)
	float digitalSampleRate;

	/// \brief Number of elapsed audio frames since the start of rendering.
	///
	/// This holds the total number of audio frames as of the beginning of the current period. To
	/// find the current number of analog or digital frames elapsed, multiply by the ratio of the
	/// sample rates (e.g. half the number of analog frames will have elapsed if the analog sample
	/// rate is 22050).
	uint64_t audioFramesElapsed;

	/// \brief Other audio/sensor settings
	///
	/// Binary combination of flags including:
	///
	/// BELA_FLAG_INTERLEAVED: indicates the audio and analog buffers are interleaved
	///
	/// BELA_FLAG_ANALOG_OUTPUTS_PERSIST: indicates that writes to the analog outputs will
	/// persist for future frames. If not set, writes affect one frame only.
	uint32_t flags;
} InternalBelaContext;


class PRU
{
private:
	static const unsigned int kPruGPIODACSyncPin;
	static const unsigned int kPruGPIOADCSyncPin;
	static const unsigned int kPruGPIOTestPin;
	static const unsigned int kPruGPIOTestPin2;
	static const unsigned int kPruGPIOTestPin3;

public:
	// Constructor
	PRU(InternalBelaContext *input_context);

	// Destructor
	~PRU();

	// Prepare the GPIO pins needed for the PRU
	int prepareGPIO(int include_test_pin, int include_led);

	// Clean up the GPIO at the end
	void cleanupGPIO();

	// Initialise and open the PRU
	int initialise(int pru_num, int frames_per_buffer,
				   int spi_channels, int mux_channels = 0, 
				   bool xenomai_test_pin = false);

	// Run the code image in pru_rtaudio_bin.h
	int start(char * const filename);

	// Loop: read and write data from the PRU
	void loop(RT_INTR *pru_interrupt, void *userData);

	// Wait for an interrupt from the PRU indicate it is finished
	void waitForFinish();

	// Turn off the PRU when done
	void disable();

	// For debugging:
	void setGPIOTestPin();
	void clearGPIOTestPin();

private:
	InternalBelaContext *context;	// Overall settings

	int pru_number;		// Which PRU we use
	bool running;		// Whether the PRU is running
	bool analog_enabled;  // Whether SPI ADC and DAC are used
	bool digital_enabled; // Whether digital is used
	bool gpio_enabled;	// Whether GPIO has been prepared
	bool led_enabled;	// Whether a user LED is enabled
	int  mux_channels;   // How many mux channels are used (if enabled)
	bool gpio_test_pin_enabled; // Whether the test pin was also enabled


	volatile uint32_t *pru_buffer_comm;
	uint16_t *pru_buffer_spi_dac;
	uint16_t *pru_buffer_spi_adc;
	uint32_t *pru_buffer_digital;
	int16_t *pru_buffer_audio_dac;
	int16_t *pru_buffer_audio_adc;

	float *last_analog_out_frame;
	uint32_t *digital_buffer0, *digital_buffer1, *last_digital_buffer;

	int xenomai_gpio_fd;	// File descriptor for /dev/mem for fast GPIO
	uint32_t *xenomai_gpio;	// Pointer to GPIO registers
};


#endif /* PRU_H_ */