|
MCU=M128, TLV2544 5V供电、选内部基准
在相对正确转换结果时: 信号输入=0V 转换结果=0x015
信号输入=0.4V 转换结果=0x45E左右( 理论值应0x333 )
信号输入=1.99V 转换结果=0xFFF
问题 1: 转换结果值偏高!!!!
问题 2: 内部基准无论选2V 还是4V对转换结果无影响
问题 3: 新的芯片换上去,开始有相对正确的转换结果,但次日再试,在信号输入=0V时 转换结果=0xFFF (已换3片了)
急!!请用过TLV2544的高手指点,感谢!!
![](http://cache.amobbs.com/bbs_upload782111/files_34/ourdev_589256Q533AN.jpg)
(原文件名:tlv2544.jpg)
主程序中:
data = SingeShotMode(0x0E84, TLV2544_CH_0 );
头文件
#ifndef _TLV2544_H
#define _TLV2544_H
#define _BV(bit) (1 << (bit))
#define TLV_SPI_ON SPCR = 0x50 //50
#define TLV_SPI_OFF SPCR = 0x00
#define TLV_PORT PORTB // 2544引脚占用口
#define TLV_CSTART_PORT PORTD // 采样控制,PD7
#define TLV_EOC_INT_PORT PORTE // 中断,PE7
#define TLV_CSTART PD7 // 采样控制引脚
#define TLV_SDO PINB&_BV(PB3) // MISO PB3
#define TLV_SDI PB2 // MOSI
#define TLV_SCK PB1 // SCK
#define TLV_CS PB0 // 片选引脚
#define TLV_EOC_INT PINE&_BV(PE7) // 中断引脚
#define TLV_SELECT TLV_PORT &= ~_BV(TLV_CS)
#define TLV_DESELECT TLV_PORT |= _BV(TLV_CS)
#define TLV_CSTART_ON TLV_CSTART_PORT &= ~_BV(TLV_CSTART)
#define TLV_CSTART_OFF TLV_CSTART_PORT |= _BV(TLV_CSTART)
#define TLV_SDI_L TLV_PORT &= ~_BV(TLV_SDI)
#define TLV_SDI_H TLV_PORT |= _BV(TLV_SDI)
#define TLV_SCK_L TLV_PORT &= ~_BV(TLV_SCK)
#define TLV_SCK_H TLV_PORT |= _BV(TLV_SCK)
#define TLV2544_CH_0 0x0000
#define TLV2544_CH_1 0x2000
#define TLV2544_CH_2 0x4000
#define TLV2544_CH_3 0x6000
#define SW_PWR_DWN 0x8000 // SW电源跌落(模拟+参考)
#define READ_CFR 0x9000 // 读配置寄存器
#define WRITE_CFR 0xA000 // 写配置寄存器
#define TEST_HALF 0xB000 // 选择测试电压=(REFP+REFM)/2
#define TEST_MINUS 0xC000 // 选择测试电压=REFM
#define TEST_PLUS 0xD000 // 选择测试电压=REFP
#define FIFO_Read 0xE000 // FIFO读,将FIFO内容送SDO D(15~4),D(3~0)=0000
/* NOTE: The status of the CFR can be read with a read CFR command
when the device is programmed for one-shot conversion mode (CFR D[6,5] = 00)*/
/****************************************************/
/* 配置寄存器(CFR)位定义 */
/****************************************************/
#define REF_SEL 11 //
//
#define INTER_REF_VOL_SEL 10
#define SAMPLE_PERIOD_SEL 9
#define CCSS_H 8
#define CCSS_L 7
#define CMS_H 6
#define CMS_L 5
#define SASS_H 4
#define SASS_L 3
#define EOC_INT 2
#define FTL_H 1
#define FTL_L 0
/****************************************************/
/* 配置寄存器(CFR)位命令定义 */
/****************************************************/
/* 基准选择 D11 */
#define EXTER_REF 0x0000 // 0: External
#define INTER_REF _BV(REF_SEL) // 1: Internal
/* 内部基准电压选择 D10 */
#define INTER_REF_4V 0x0000 // 0: Internal ref = 4 V
#define INTER_REF_2V _BV(INTER_REF_VOL_SEL) // 1: internal ref = 2 V
/* 采样周期选择 D9 */
#define SHORT_SAMPLING 0x0000 // 0: Short sampling 12 SCLKs
// (1x sampling time)
#define LONG_SAMPLING _BV(SAMPLE_PERIOD_SEL) // 1: Long sampling 24 SCLKs
// (2x sampling time)
/* 转换时钟源选择 D8-D7 */
#define INTERNAL_OSC 0x0000 // 转换时间=内OSC 00
#define SCLK_1 _BV(CCSS_L) // 转换时钟=SCLK 01
#define SCLK_4 _BV(CCSS_H) // 转换时钟=SCLK/4 10
#define SCLK_2 _BV(CCSS_H)|_BV(CCSS_L) // 转换时钟=SCLK/2 11
/* 转换模式 D6-D5 */
#define SINGLE_SHOT_MODE 0x0000 //单次模式 00
#define REPEAT_MODE _BV(CMS_L) //重复模式 01
#define SWEEP_MODE _BV(CMS_H) //扫描模式 10
#define REPEAT_SWEEP_MODE _BV(CMS_H)|_BV(CMS_L) //重复扫描模式 11
/* 扫描自动序列选择 D4-D3 */
#define SWEEP_AUTO_SEQUENCE_SEL_0 0x0000 //00: N/A
#define SWEEP_AUTO_SEQUENCE_SEL_1 _BV(SASS_L) //01: 0–1–2–3–0–1–2–3
#define SWEEP_AUTO_SEQUENCE_SEL_2 _BV(SASS_H) //10: 0–0–1–1–2–2–3–3
#define SWEEP_AUTO_SEQUENCE_SEL_3 _BV(SASS_H)|_BV(SASS_L) //11: 0–1–0–1–0–1–0–1
/* EOC/INT引脚功能选择 D2*/
#define INT_PIN 0x0000 // 0: 引脚用作INT
#define EOC_PIN _BV(EOC_INT) // 1:引脚用作EOC
/* FIFO触发器电平(扫描序列长度)D1-D0 */
#define FIFO_TRIGGER_LEVEL_FULL 0x0000 //00 全部(FIFO level 7填满后产生INT)
#define FIFO_TRIGGER_LEVEL_3_4 _BV(FTL_L) //01:3/4(FIFO level 5填满后产生INT)
#define FIFO_TRIGGER_LEVEL_1_2 _BV(FTL_H) //10:1/2(FIFO level 3填满后产生INT)
#define FIFO_TRIGGER_LEVEL_1_4 _BV(FTL_H)|_BV(FTL_L) //11:1/4(FIFO level 1填满后产生INT)
extern uint SPI_2544(unsigned char data);
extern uint SingeShotMode( uint config_command, uchar channel );
extern void InitRepeatSweepMode(void);
extern void InitSingleShotMode(void);
extern void InitSweepMode(void);
#endif /* _TLV2544_H */
TLV2544.C程序代码
#include "include.h"
/***** 配置寄存器(CFR)的位定义 *******************
内部基准 D11=1 INTER_REF
基准电压选择 D10=0 INTER_REF_4V
采样周期选择 D9=0 SHORT_SAMPLING 短期采样12SCLKs(1x采样时间)
转换时钟源选择 D8-D7 SCLK_1 转换时钟=SCLK 01
转换模式 D6-D5 SINGLE_SHOT_MODE 单次模式 00
扫描自动序列选择 D4-D3
EOC/INT引脚功能选择 D2=0 INT_PIN
***************************************/
//单次模式(模式00)不用FIFO,转换结束EOC/INT引脚拉低
/*
1.CS拉低,写A000h,再写AXXXh(配置命令),尽量使用内部OSC;
2.读CFR,验证spi的正常;
3.如果是扩展采样:拉高cs,然后拉低CSTART,延时一段时间,拉高CSTART,开始转换;
4.等待EOC有效
5.CS拉低再拉高,再拉低,即CS拉低两次,并保持低。当然这时CSTART保持高电平。
6.写0000h,即可读出结果。
*/
uint SingeShotMode( uint config_command, uchar channel )
{
uint select_channel;
volatile uint Conv_result;
volatile uchar result1,result2;
switch( channel ) {
case 0: select_channel = TLV2544_CH_0;
break;
case 1: select_channel = TLV2544_CH_1;
break;
case 2: select_channel = TLV2544_CH_2;
break;
case 3: select_channel = TLV2544_CH_3;
break;
}
// return 0x08AF; //为仿真
CLI();
TLV_SPI_ON;
TLV_CSTART_OFF;
TLV_SELECT; //CS拉低
SPI_2544(0xA0); //初始化命令 A000H
SPI_2544(0x00);
TLV_DESELECT;
TLV_SELECT;
SPI_2544((uchar)(config_command>>8)); //写配置字
SPI_2544((uchar)(config_command&0x00FF));
TLV_DESELECT;
TLV_SELECT;
// result1 = SPI_2544(0x90); //读CFR数据以此检测2544是否工作
// result2 = SPI_2544(0x00); //生成SCLK
// TLV_DESELECT;
// TLV_SELECT;
SPI_2544((uchar)(select_channel>>8)); //选通道
SPI_2544((uchar)(select_channel&0x00FF)); //生成SCLK
TLV_DESELECT;
TLV_CSTART_ON;
delay_us(2);
TLV_CSTART_OFF;
while(TLV_EOC_INT);
TLV_DESELECT;
TLV_SELECT;
TLV_DESELECT;
TLV_SELECT;
result1 = SPI_2544(0x00); //写0000h,即可读出结果
result2 = SPI_2544(0x00);
SEI();
TLV_CSTART_OFF;
TLV_DESELECT;
TLV_SPI_OFF;
Conv_result = ((uint)(result1)<<4) | (uint)((result2>>4)&0x0f);
return (Conv_result-0x333);
}
uint SPI_2544(unsigned char data)
{
SPDR = data;
while (!(SPSR & (1<<SPIF))); //等待完成
return SPDR;
} |
阿莫论坛20周年了!感谢大家的支持与爱护!!
知道什么是神吗?其实神本来也是人,只不过神做了人做不到的事情 所以才成了神。 (头文字D, 杜汶泽)
|