mirror of
https://github.com/eddyem/IR-controller.git
synced 2025-12-06 02:35:14 +03:00
264 lines
9.3 KiB
C
264 lines
9.3 KiB
C
/*
|
|
* AD7794.h
|
|
*
|
|
* Copyright 2013 Edward V. Emelianoff <eddy@sao.ru>
|
|
*
|
|
* This program is free software; you can redistribute it and/or modify
|
|
* it under the terms of the GNU General Public License as published by
|
|
* the Free Software Foundation; either version 2 of the License, or
|
|
* (at your option) any later version.
|
|
*
|
|
* This program is distributed in the hope that it will be useful,
|
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
* GNU General Public License for more details.
|
|
*
|
|
* You should have received a copy of the GNU General Public License
|
|
* along with this program; if not, write to the Free Software
|
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
|
|
* MA 02110-1301, USA.
|
|
*/
|
|
#pragma once
|
|
#ifndef __AD7794_H__
|
|
#define __AD7794_H__
|
|
|
|
#include "main.h"
|
|
|
|
// in function read_AD7794 zero returning means error, so we should do something
|
|
// to detect "data not ready yet"; 24 bits of ADC allow us to use some
|
|
// big values as flags
|
|
#define AD7794_NOTRDY ((uint32_t)0xffffffff)
|
|
|
|
uint8_t setup_AD7794(uint16_t config, uint8_t io);
|
|
uint8_t AD7794_calibration(uint8_t channel);
|
|
uint32_t read_AD7794(uint8_t channel);
|
|
uint8_t reset_AD7794();
|
|
uint8_t change_AD7794_gain(uint8_t gain);
|
|
|
|
// error codes of reset_AD7794()
|
|
enum {
|
|
ADC_NO_ERROR,
|
|
ADC_ERR_NO_DEVICE,
|
|
ADC_ERR_OTHER
|
|
};
|
|
|
|
/*
|
|
* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
|
* in case of communication error set DIN high and give to SCLK >=32 pulses
|
|
* !!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!!
|
|
*/
|
|
|
|
/*
|
|
* Communication register
|
|
* | CR7 | CR6 | CR5 | CR4 | CR3 | CR2 | CR1 | CR0 |
|
|
* !WEN R/!W RS2 RS1 RS0 CREAD 0 0
|
|
*
|
|
* - WEN (write enable) : 1 - ignore all bits in packet
|
|
* - R/!W (next operation): 0 - write, 1 - read
|
|
* - RS2..RS0 (reg choice) :
|
|
* (RS2RS1RS0)
|
|
* 000: CR - write / SR - read (8 bit)
|
|
* 001: Mode register (16 bit)
|
|
* 010: Configuration register (16 bit)
|
|
* 011: Data register (24 bit)
|
|
* 100: ID register - read only (8 bit)
|
|
* 101: IO register (8 bit)
|
|
* 110: Offset register (24 bit)
|
|
* 111: Full-Scale register(24 bit)
|
|
* - CREAD (continious read): 1 - enable continious reading (put 01011100 to
|
|
* CR & take DIN in zero state
|
|
* to reset this mode write to CR 01011000 or make ADC reset
|
|
* CR1&CR0 always should be 0!
|
|
*/
|
|
// masks for CR:
|
|
#define NOT_WEN U8(0x80)
|
|
#define WRITE_TO_REG U8(0)
|
|
#define READ_FROM_REG U8(0x40)
|
|
#define CONT_READ U8(0x04)
|
|
#define STAT_REGISTER U8(0)
|
|
#define MODE_REGISTER U8(0x08)
|
|
#define CONF_REGISTER U8(0x10)
|
|
#define DATA_REGISTER U8(0x18)
|
|
#define ID_REGISTER U8(0x20)
|
|
#define IO_REGISTER U8(0x28)
|
|
#define OFFSET_REGISTER U8(0x30)
|
|
#define FS_REGISTER U8(0x38)
|
|
#define REGISTER_MASK U8(0x38) // (REGISTER_MASK & CR) >> 3 gives register number
|
|
|
|
/*
|
|
* Status register
|
|
* | SR7 | SR6 | SR5 | SR4 | SR3 | SR2 | SR1 | SR0 |
|
|
* !RDY ERR NOXREF 0 1 CH2 CH1 CH0
|
|
*
|
|
* - !RDY (data ready) : ==0 when data is ready for reading
|
|
* - ERR (ADC error flag) : ==1 in case of some error (cleared by hardware in ADC starting)
|
|
* - NOXREF (no ref voltage): ==1 in cese of REFIN1/REFIN2 less than threshold
|
|
* SR4&SR3 are always 01
|
|
* - CH2..CH0 (channel number): number of current channel
|
|
*/
|
|
// masks for SR:
|
|
#define DATA_NOTRDY U8(0x80)
|
|
#define DATA_ERROR U8(0x40)
|
|
#define STATUS_NOREF U8(0x20)
|
|
#define DATA_CHANNEL_MASK U8(0x07) // Channel selection: DATA_CHANNEL_MASK & ch. number
|
|
|
|
/*
|
|
* Mode register (16 bit)
|
|
* | MRf | MRe | MRd | MRc | MRb | MRa | MR9 | MR8 | MR7 | MR6 | MR5 | MR4 | MR3 | MR2 | MR1 | MR0 |
|
|
* MD2 MD1 MD0 PSW 0 0 AMP-CM 0 CLK1 CLK0 0 CHOP-DIS FS3 FS2 FS1 FS0
|
|
*
|
|
* - MD2..MD0 (mode) : mode selection
|
|
* 000 - continuous mode
|
|
* 001 - single mode
|
|
* 010 - idle mode
|
|
* 011 - power-down mode
|
|
* 100 - internal zero-scale calibration
|
|
* 101 - internal full-scale calibration
|
|
* 110 - system zero-scale calibration
|
|
* 111 - system full-scale calibration
|
|
* - PSW (PSW mode) : ==1 to disconnect PSW and ground, ==0 to connect (!!! limit current is 30mA !!!)
|
|
* - AMP-CM (amplify) : ==0 to wide amplification (badly disables synphase signal)
|
|
* - CLK1, CLK0 (CLCsrc): CLC source
|
|
* 00 - inner 64kHz, CLK out is off
|
|
* 01 - inner 64kHz, CLK out is on
|
|
* 10 - outer 64kHz connected to CLK in
|
|
* 11 - outer (freq/2) connected to CLK in
|
|
* CHOP-DIS (syn dis) : used to disable synphase signal, sets together with AMP-CM
|
|
* FS3..FS0 (fltr per.) : period of filter update rate
|
|
*/
|
|
// masks for MR:
|
|
// modes:
|
|
#define MODE_MASK U16(0xe000)
|
|
#define CONT_MODE U16(0)
|
|
#define SINGLE_MODE U16(0x2000)
|
|
#define IDLE_MODE U16(0x4000)
|
|
#define POWERDOWN_MODE U16(0x6000)
|
|
#define INT_ZS_CAL U16(0x8000)
|
|
#define INT_FS_CAL U16(0xa000)
|
|
#define SYS_ZS_CAL U16(0xc000)
|
|
#define SYS_FS_CAL U16(0xe000)
|
|
// other
|
|
#define PSW_DISCONN U16(0x1000)
|
|
#define AMPCM_RESET U16(0x0200)
|
|
// clocking
|
|
#define CLK_IN_NOOUT U16(0)
|
|
#define CLK_IN_SYNC U16(0x0040)
|
|
#define CLK_OUT_64 U16(0x0080)
|
|
#define CLK_OUT_DIV2 U16(0x00c0)
|
|
// other
|
|
#define CHOP_DISABLE U16(0x0010)
|
|
#define FILTER_MASK U16(0x000f)
|
|
|
|
/*
|
|
* Configuration register
|
|
* | CRf | CRe | CRd | CRc | CRb | CRa | CR9 | CR8 | CR7 | CR6 | CR5 | CR4 | CR3 | CR2 | CR1 | CR0 |
|
|
* VBIAS1/0 BO U/!B BOOST G2 G1 G0 REFSEL1/0 REF_DET BUF CH3..0
|
|
*
|
|
* - VBIAS1/0 (enable bias voltage generator):
|
|
* 00 - VBIAS disabled
|
|
* 01 - connect to AIN1
|
|
* 10 - connect to AIN2
|
|
* 11 - connect to AIN3
|
|
* - BO (burnout current) : enable 100nA current source (buffer or in-amp should be active)
|
|
* - U/!B (uni/bipolar) : ==1 for unipolar coding (full-scale from 0x000000 to 0xffffff)
|
|
* ==0 for bipolar coding (0x800000 is zero, > - positive)
|
|
* - BOOST (increase curnt): ==1 to increase inner VREF current consuming to reduce power-up time
|
|
* - G2..G0 (gain) : select ADC ampl. gain, GAIN = 1<<G, input ranges are
|
|
* 2.5V, 1.25V, 625mV, 312.5mV, 156.25mV, 78.125mV, 39.06mV, 19.53mV
|
|
* - REFSEL1/0 (ref.select): reference voltage
|
|
* 00 - external between REFIN1(+) and REFIN1(-)
|
|
* 01 - external between REFIN2(+) and REFIN2(-)
|
|
* 10 - internal 1.17V
|
|
* 11 - reserved
|
|
* - REF_DET (detect ref) : enable reference detection by set/reset bit NOXREF
|
|
* - BUF (buffered mode) : configure ADC for buffered (1) mode (==1 automatically for gain > 2)
|
|
* - CH3..0 (chnnl select) : select channel (reserved are non-shown)
|
|
* [CHANNEL] - [Calibration pair]
|
|
* 0000 - AIN1 - 0
|
|
* 0001 - AIN2 - 1
|
|
* 0010 - AIN3 - 2
|
|
* 0011 - AIN4 - 3
|
|
* 0100 - AIN5 - 3
|
|
* 0101 - AIN6 - 3
|
|
* 0110 - Temp sensor - int. 1.17VREF + gain=1
|
|
* 0111 - ADVV monitor - int. 1.17VREF + gain=1/6
|
|
* 1000 - AIN1(-)/AIN1(-) - 0
|
|
*/
|
|
// masks for SR
|
|
// vbias source
|
|
#define VBIAS_1 U16(0x4000)
|
|
#define VBIAS_2 U16(0x8000)
|
|
#define VBIAS_3 U16(0xc000)
|
|
// other
|
|
#define INT_CURRENT_SRC U16(0x2000)
|
|
#define UNIPOLAR_CODING U16(0x1000)
|
|
#define BOOST_UP U16(0x0800)
|
|
// gain mask
|
|
#define GAIN_MASK U16(0x0700) // gain == 1<<G
|
|
// refin selection
|
|
#define EXTREFIN_1 U16(0)
|
|
#define EXTREFIN_2 U16(0x0040)
|
|
#define INTREFIN U16(0x0080)
|
|
// other
|
|
#define REF_DETECTION U16(0x0020)
|
|
#define BUFFERED_OP U16(0x0010)
|
|
// channel selection mask
|
|
#define CHANNEL_MASK U16(0x000f) // CHANNEL_MASK & (channel number - 1)
|
|
#define INR_TEMP_SENSOR U16(0x0006) // inner thermometer
|
|
#define AVDD_MONITOR U16(0x0007) // monitor avdd
|
|
#define CHANNEL1_MINUS U16(0x0008) // AIN1(-)/AIN1(-)
|
|
|
|
/*
|
|
* Data register stores the conversion result: 24bits
|
|
* on completion reading !RDY is set
|
|
*/
|
|
|
|
/*
|
|
* ID register is read-only register storing identification number of ADC: 8bits
|
|
*/
|
|
|
|
/*
|
|
* IO register
|
|
* | IO7 | IO6 | IO5 | IO4 | IO3 | IO2 | IO1 | IO0 |
|
|
* 0 IOEN IODAT IEXCDIR IEXCEN
|
|
*
|
|
* - IOEN (digital out) : ==1 to configure AIN6 as digital output pins P1/P2
|
|
* - IODAT (P2/P1 data) : when IOEN==1 this is a data for digital ports
|
|
* - IEXCDIR (cur.src dir): direction of currens sources
|
|
* 00 - IEXC1 connected to IOUT1, IEXC2 connected to IOUT2
|
|
* 01 - IEXC1 connected to IOUT2, IEXC2 connected to IOUT1
|
|
* 10 - both sources connected to IOUT1 (only for 10/210uA)
|
|
* 11 - both sources connected to IOUT2 (-//-)
|
|
* - IEXCEN (en. cur.src) : enable/disable current sources
|
|
* 00 - currents are disabled
|
|
* 01 - 10uA
|
|
* 10 - 210uA
|
|
* 11 - 1mA
|
|
*/
|
|
// masks for IOR
|
|
#define IOEN U8(0x40)
|
|
#define IODAT_MASK U8(0x30)
|
|
#define IEXC_DIRECT U8(0)
|
|
#define IEXC_SWAPPED U8(0x04)
|
|
#define IEXC_BOTH1 U8(0x08)
|
|
#define IEXC_BOTH2 U8(0x0c)
|
|
#define IEXC_DISABLE U8(0)
|
|
#define IEXC_10UA U8(0x01)
|
|
#define IEXC_210UA U8(0x02)
|
|
#define IEXC_1MA U8(0x03)
|
|
|
|
/*
|
|
* Offset register holds the offset calibration coefficient (R/W, 24bit)
|
|
* Each calibration channel has its own offset registry
|
|
* Value automatically overwtitten on calibration
|
|
* To directly write into that registry ADC should be placed in power-down or idle mode
|
|
*/
|
|
|
|
/*
|
|
* Full-scale register (R/W, 24 bit)
|
|
* It holds the full-scale calibration coefficients fir ADC
|
|
* Each calibration channel has its own full-scale registry
|
|
* To directly write into that registry ADC should be placed in power-down or idle mode
|
|
*/
|
|
#endif // __AD7794_H__
|