SNAD01 Library for Arduino

I am trying to write my first library for the Arduino and am having some trouble with it. The library is for the Sonix ADC chip SNAD01A. I used Tod E. Kurt’s ( as my base.

First, here is the compiler output:
SNAD01.cpp: In member function 'uint8_t SNAD01::SNAD01_Convert(uint8_t)':
SNAD01.cpp:113: error: 'SNAD01_sendChan' was not declared in this scope
SNAD01.cpp: In member function 'uint8_t SNAD01::SNAD01_readbit()':
SNAD01.cpp:245: error: '_DIOpinRegister' was not declared in this scope
SNAD01.cpp: At global scope:
SNAD01.cpp:269: error: no 'void SNAD01::SNAD01_sendChan(uint8_t)' member function declared in class 'SNAD01'
SNAD01.cpp:284: error: no 'void SNAD01::SNAD01_sendReg(uint8_t)' member function declared in class 'SNAD01'

But I can’t figure out what is wrong. Perhaps I am just going cross-eyed here. Could anyone lend a hand?
Here is my header:
/*
* SONIX SNAD01x Series ADC library for Arduino
* Modified version of SoftI2CMaster written by Tod E. Kurt, http://todbot.com/blog/
* Mod written by Scott McDonnell 01/2013
*/

#ifndef SNAD01_h
#define SNAD01_h

#include

#define _SNAD01_VERSION 0 // software version of this library

class SNAD01
{
private:
// per object data
uint8_t _DIOpin;
uint8_t _CLKpin;
uint8_t _STARTpin;
uint8_t _DIOBitMask;
uint8_t _CLKBitMask;
uint8_t _STARTBitMask;

volatile uint8_t *_DIOPortRegister;
volatile uint8_t *_CLKPortRegister;
volatile uint8_t *_STARTPortRegister;
volatile uint8_t *_DIOPortModeRegister;
volatile uint8_t *_CLKPortModeRegister;
volatile uint8_t *_STARTPortModeRegister;
volatile uint8_t *_DIOPinRegister;

// private methods
void setPins(uint8_t DIOpin, uint8_t CLKpin, uint8_t STARTpin);
void SNAD01_writebit( uint8_t c );
uint8_t SNAD01_readbit(void);
void SNAD01_start(void);
void SNAD01_stop(void);
void PulseClock(void);
void SNAD01_writebyte( uint8_t c );
uint8_t SNAD01_readbyte( );
void SNAD01_sendCMD(uint8_t c);
void SNAD01_SendChan(uint8_t c);
void SNAD01_SendReg(uint8_t c);

public:
// public methods
SNAD01(uint8_t DIOpin, uint8_t CLKpin, uint8_t STARTpin);
void SNAD01_init(uint8_t reg, uint8_t mode, uint8_t Wkup);
void SNAD01_PWRDN();
uint8_t SNAD01_Convert(uint8_t chan);
uint8_t SNAD01_getDigital();

};

#endif

And here is my library:
/*
* SONIX SNAD01x Series ADC Library for Arduino
* Modified version of SoftI2CMaster by Tod E. Kurt, http://todbot.com/blog/
* Mod written by scott McDonnell 01/2013
*/

#include "Arduino.h"
#include "pins_arduino.h"
#include "SNAD01.h"

#include
#include

#define SNAD01bitdelay 50

//Define commands (in binary)
#define cmd_Reg 0x60
#define cmd_PDN 0x00
#define cmd_wkup 0x40
#define cmd_attrib 0x20
#define cmd_conv 0x80
#define cmd_dig 0xa0

//_XXXPortModeRegister = DDR register
//_XXXPortRegister = Port data register
//_XXXPinRegister = Input Register

//macro for setting DIO pin HIGH
#define SNAD01_DIO_hi() \
*_DIOPortModeRegister &=~ _DIOBitMask; \
*_DIOPortRegister |= _DIOBitMask;

//macro for setting DIO pin Low
#define SNAD01_DIO_lo() \
*_DIOPortRegister &=~ _DIOBitMask; \
*_DIOPortModeRegister |= _DIOBitMask;

//Macro for setting CLK pin HIGH
#define SNAD01_CLK_hi() \
*_CLKPortModeRegister &=~ _CLKBitMask; \
*_CLKPortRegister |= _CLKBitMask;

//Macro for setting CLK pin Low
#define SNAD01_CLK_lo() \
*_CLKPortRegister &=~ _CLKBitMask; \
*_CLKPortModeRegister |= _CLKBitMask;

//Macro for setting START pin HIGH
#define SNAD01_start_hi() \
*_STARTPortRegister &=~ _STARTBitMask; \
*_STARTPortModeRegister |= _STARTBitMask;

//Macro for setting START pin Low
#define SNAD01_start_lo() \
*_STARTPortRegister &=~ _STARTBitMask; \
*_STARTPortModeRegister |= _STARTBitMask;

//Macro for setting DIO as input
#define SNAD01_DIO_IN() \
*_DIOPortModeRegister |= _DIOBitMask;

//Macro for setting DIO pin as output
#define SNAD01_DIO_OUT() \
*_DIOPortModeRegister &=~ _DIOBitMask;

//
// Constructor
//

//Usage: ADC = SNAD01(2,3,4); DIO = pin 2, CLK = pin 3, START = pin 4
SNAD01::SNAD01(uint8_t DIOpin, uint8_t CLKpin, uint8_t STARTpin)
{
setPins(DIOpin, CLKpin, STARTpin);
}

//****************************************************************
//External Functions
//****************************************************************

//Usage: ADC.SNAD_init(reg,attrib,wkup);
void SNAD01::SNAD01_init(uint8_t reg, uint8_t attrib, uint8_t wkup)
{
//Write registers
//Write attributes
//Write wkup

// //I2C_PORT &=~ (_BV( I2C_SDA ) | _BV( I2C_SCL ));
// *_CLKPortRegister &=~ (_DIOBitMask | _CLKBitMask);

// SNAD01_CLK_hi();
// SNAD01_DIO_hi();

_delay_us(SNAD01bitdelay);
}

void SNAD01::SNAD01_PWRDN(){
//Prepare for power down (set RF and MB bits to 0)
//send cmd for powerdown (0x000b)
}

//--------------------------------------------------------------------
//Get Readings (Digital and Analog Routines)
//--------------------------------------------------------------------
uint8_t SNAD01::SNAD01_Convert(uint8_t chan){
//Send command for analog conversion
//read one byte and return byte

uint8_t res;

SNAD01_start();
SNAD01_sendCMD(cmd_conv);
SNAD01_sendChan(chan);
SNAD01_CLK_hi();
SNAD01_CLK_lo();
//SNAD01_DIO_IN;
SNAD01_CLK_hi();
SNAD01_CLK_lo();
res=SNAD01_readbyte();
SNAD01_stop();

return res;

}

uint8_t SNAD01::SNAD01_getDigital(){
//send command for digital reading
//read one byte, return byte

uint8_t res;

SNAD01_start();
SNAD01_sendCMD(cmd_dig);
res=SNAD01_readbyte();
SNAD01_stop();

return res;
}

//***************************************************************
//Internal Functions
//***************************************************************

//--------------------------------------------------------------------
//Set pins and register configuration
//--------------------------------------------------------------------
//
// Turn Arduino pin numbers into PORTx, DDRx, and PINx
//
void SNAD01::setPins(uint8_t DIOpin, uint8_t CLKpin, uint8_t STARTpin)
{
//Define pins for CLK, START, DIO

uint8_t port;

_DIOpin = DIOpin;
_CLKpin = CLKpin;
_STARTpin = STARTpin;

_DIOBitMask = digitalPinToBitMask(DIOpin);
_CLKBitMask = digitalPinToBitMask(CLKpin);
_STARTBitMask = digitalPinToBitMask(STARTpin);

port = digitalPinToPort(CLKpin);
_CLKPortRegister = portOutputRegister(port);
_CLKPortModeRegister = portModeRegister(port);

port = digitalPinToPort(DIOpin);
_DIOPortRegister = portOutputRegister(port);//Port Register
_DIOPortModeRegister = portModeRegister(port); //DDR register
_DIOPinRegister = portInputRegister(port);//Pin Register (input)

port = digitalPinToPort(STARTpin);
_STARTPortRegister = portOutputRegister(port);
_STARTPortModeRegister = portModeRegister(port);

}
// START Conditions
//
void SNAD01::SNAD01_start(void)
{

// set both to high at the same time
//I2C_DDR &=~ (_BV( I2C_SDA ) | _BV( I2C_SCL ));

SNAD01_DIO_lo();//set to low before switching between input to output
// *_DIOPortModeRegister &=~ (_DIOBitMask); //Set DIO DDR as output

SNAD01_DIO_OUT();

_delay_us(SNAD01bitdelay);

SNAD01_start_lo();
_delay_us(SNAD01bitdelay);

}

// STOP Conditions
//
void SNAD01::SNAD01_stop(void)
{
SNAD01_start_hi();//deactivate chip select
_delay_us(SNAD01bitdelay);

SNAD01_DIO_lo(); //set DIO to low before switching directions

SNAD01_DIO_IN(); //set DIO for input (HIz)
_delay_us(SNAD01bitdelay);
}

void SNAD01::SNAD01_writebit( uint8_t c )
{

if ( c > 0 ) {
SNAD01_DIO_hi();
} else {
SNAD01_DIO_lo();
}

PulseClock();

// if ( c > 0 ) {
// SNAD01_DIO_lo();
// }

_delay_us(SNAD01bitdelay);

}

//
uint8_t SNAD01::SNAD01_readbit(void)
{

SNAD01_DIO_lo();//set dio pin low before switching directions
SNAD01_DIO_IN(); //set to input

SNAD01_CLK_hi();
_delay_us(SNAD01bitdelay);

uint8_t port = digitalPinToPort(_DIOpin);
volatile uint8_t* pinReg = portInputRegister(port);
uint8_t c = *pinReg;

SNAD01_CLK_lo();

_delay_us(SNAD01bitdelay);

return ( c & _DIOBitMask) ? 1 : 0;
}

void SNAD01::SNAD01_sendCMD(uint8_t c )
{
SNAD01_start();

for ( uint8_t i=0;i<3;i++)
{
SNAD01_writebit( c & 128 );

c<<=1;
}

SNAD01_stop();

}

void SNAD01::SNAD01_sendChan(uint8_t c )
{
SNAD01_start();

for ( uint8_t i=0;i<3;i++)
{
SNAD01_writebit( c & 128 );

c<<=1;
}

SNAD01_stop();

}

void SNAD01::SNAD01_sendReg(uint8_t c )
{
SNAD01_start();

for ( uint8_t i=0;i<4;i++)
{
SNAD01_writebit( c & 128 );

c<<=1;
}

SNAD01_stop();

}

// write a byte to theSNAD01
//
void SNAD01::SNAD01_writebyte( uint8_t c )
{
SNAD01_start();

for ( uint8_t i=0;i<8;i++)
{
SNAD01_writebit( c & 128 );

c<<=1;
}

SNAD01_stop();
}

// read a byte from the SNAD01
//
uint8_t SNAD01::SNAD01_readbyte( )
{
uint8_t res = 0;

SNAD01_start();

for ( uint8_t i=0;i<8;i++)
{
res <<= 1;
res |= SNAD01_readbit();
}

_delay_us(SNAD01bitdelay);

SNAD01_stop();

return res;

}

void SNAD01::PulseClock(){
//Send one clock transition

SNAD01_CLK_lo();
_delay_us(SNAD01bitdelay);
SNAD01_CLK_hi();
_delay_us(SNAD01bitdelay);
}

2 thoughts on “SNAD01 Library for Arduino

Leave a comment