PDA

View Full Version : Help - where is write( i2c addr, val ) , which is used in control_sgtl5000.cpp



garytennyson
06-09-2016, 01:55 AM
I'm trying to code up a simple Stereo In --> Teensy 3.2 CPU --> Stereo Out using the Audio Board. I'm trying to do this outside the Arduino/Teensyduino framework. I thought I could get a good start looking at the 'control_sgtl5000.cpp' code on the GitHub/Audio page. There is a function (write) called there that apparently writes a value to an i2c register on the chip. This looks like a function that I will need to understand, but I can't seem to find it.

It may be defined in 'Wire.h', but my Arduino/Teensyduino distribution doesn't have a 'Wire.h'. I also don't see it on the GitHub/Audio page. There is a header 'Wire.h' in the generic Arduino distribution, and it has prototypes for write functions, but these don't seem to have the same arguments.

Can somebody give me a pointer to the write functions used in 'control_sgtl5000.cpp' ?

Thanks

Gary Tennyson

MichaelMeissner
06-09-2016, 05:38 AM
If you look in control_sgtl5000.h, you will see:



class AudioControlSGTL5000 : public AudioControl
{
public:
AudioControlSGTL5000(void) : i2c_addr(0x0A) { }
void setAddress(uint8_t level);
bool enable(void);
bool disable(void) { return false; }
bool volume(float n) { return volumeInteger(n * 129 + 0.499); }
bool inputLevel(float n) {return false;}
bool muteHeadphone(void) { return write(0x0024, ana_ctrl | (1<<4)); }
bool unmuteHeadphone(void) { return write(0x0024, ana_ctrl & ~(1<<4)); }
bool muteLineout(void) { return write(0x0024, ana_ctrl | (1<<8)); }
bool unmuteLineout(void) { return write(0x0024, ana_ctrl & ~(1<<8)); }
bool inputSelect(int n) {
if (n == AUDIO_INPUT_LINEIN) {
return write(0x0020, 0x055) // +7.5dB gain (1.3Vp-p full scale)
&& write(0x0024, ana_ctrl | (1<<2)); // enable linein
} else if (n == AUDIO_INPUT_MIC) {
return write(0x002A, 0x0173) // mic preamp gain = +40dB
&& write(0x0020, 0x088) // input gain +12dB (is this enough?)
&& write(0x0024, ana_ctrl & ~(1<<2)); // enable mic
} else {
return false;
}
}
bool volume(float left, float right);
bool micGain(unsigned int dB);
bool lineInLevel(uint8_t n) { return lineInLevel(n, n); }
bool lineInLevel(uint8_t left, uint8_t right);
unsigned short lineOutLevel(uint8_t n);
unsigned short lineOutLevel(uint8_t left, uint8_t right);
unsigned short dacVolume(float n);
unsigned short dacVolume(float left, float right);
bool dacVolumeRamp();
bool dacVolumeRampLinear();
bool dacVolumeRampDisable();
unsigned short adcHighPassFilterEnable(void);
unsigned short adcHighPassFilterFreeze(void);
unsigned short adcHighPassFilterDisable(void);
unsigned short audioPreProcessorEnable(void);
unsigned short audioPostProcessorEnable(void);
unsigned short audioProcessorDisable(void);
unsigned short eqFilterCount(uint8_t n);
unsigned short eqSelect(uint8_t n);
unsigned short eqBand(uint8_t bandNum, float n);
void eqBands(float bass, float mid_bass, float midrange, float mid_treble, float treble);
void eqBands(float bass, float treble);
void eqFilter(uint8_t filterNum, int *filterParameters);
unsigned short autoVolumeControl(uint8_t maxGain, uint8_t lbiResponse, uint8_t hardLimit, float threshold, float attack, float decay);
unsigned short autoVolumeEnable(void);
unsigned short autoVolumeDisable(void);
unsigned short enhanceBass(float lr_lev, float bass_lev);
unsigned short enhanceBass(float lr_lev, float bass_lev, uint8_t hpf_bypass, uint8_t cutoff);
unsigned short enhanceBassEnable(void);
unsigned short enhanceBassDisable(void);
unsigned short surroundSound(uint8_t width);
unsigned short surroundSound(uint8_t width, uint8_t select);
unsigned short surroundSoundEnable(void);
unsigned short surroundSoundDisable(void);
void killAutomation(void) { semi_automated=false; }

protected:
bool muted;
bool volumeInteger(unsigned int n); // range: 0x00 to 0x80
uint16_t ana_ctrl;
uint8_t i2c_addr;
unsigned char calcVol(float n, unsigned char range);
unsigned int read(unsigned int reg);
bool write(unsigned int reg, unsigned int val);
unsigned int modify(unsigned int reg, unsigned int val, unsigned int iMask);
unsigned short dap_audio_eq_band(uint8_t bandNum, float n);
private:
bool semi_automated;
void automate(uint8_t dap, uint8_t eq);
void automate(uint8_t dap, uint8_t eq, uint8_t filterCount);
};


Note under the protected section is the function write. In the file hardware/teensy/avr/libraries/Audio/control_sgtl5000.cpp, you will see:



bool AudioControlSGTL5000::write(unsigned int reg, unsigned int val)
{
if (reg == CHIP_ANA_CTRL) ana_ctrl = val;
Wire.beginTransmission(i2c_addr);
Wire.write(reg >> 8);
Wire.write(reg);
Wire.write(val >> 8);
Wire.write(val);
if (Wire.endTransmission() == 0) return true;
return false;
}


So, it basically connects to the i2c device, sends 2 bytes from the first argument, and 2 bytes from the second argument in a big endian fashion (most significant byte first), and then ends the i2c message, and returns true/false depending on if there are errors.

garytennyson
06-09-2016, 01:24 PM
Thanks for the quick -- and helpful -- reply.
Gary