This thread has been locked.

If you have a related question, please click the "Ask a related question" button in the top right corner. The newly created question will be automatically linked to this question.

[参考译文] ADS1298:ADC 测试信号的 SPI 读数不一致

Guru**** 1630180 points
Other Parts Discussed in Thread: ADS1298
请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

https://e2e.ti.com/support/data-converters-group/data-converters/f/data-converters-forum/1039151/ads1298-inconsistent-spi-readout-of-test-signal-from-adc

器件型号:ADS1298
主题中讨论的其他器件:ADS1296ADS1294ADS1296RADS1294R

你(们)好。

背景
在此主题 中进行了一些更改:https://e2e.ti.com/support/data-converters-group/data-converters/f/data-converters-forum/1018492/ads1298-cannot-establish-spi-communications、 我们在 SPI 通信方面取得了一些进展。

在将 RESV1连接到 DGND 之后、电压线现在变得稳定、我们对 MOSI 和 MISO 信号进行了范围分析、它们看起来正常。

但是、与开发套件相比、我们看到设计中的测试信号值存在差异。

问题

我们尝试根据我们的设计对 ADSx98 FE Rev C DEG 套件进行基准测试、该设计几乎相同、但有一些偏差。

我们尝试执行内部生成的信号来从内部寄存器读取值。 下面 是一个头文件、其中包含寄存器设置的更多详细信息:

#ifndef ADS1298_H
#define ADS1298_H

#ifdef __cplusplus
extern "C" {
#endif


#include "../common.h"


typedef enum {
  // system commands
  ADS_CMND_WAKEUP    = 0x02,   // wake-up from standby mode
  ADS_CMND_STANDBY   = 0x04,   // enter standby mode
  ADS_CMND_RESET     = 0x06,   // reset the device registers
  ADS_CMND_START     = 0x08,   // start/restart (synchronize) conversions
  ADS_CMND_STOP      = 0x0A,   // stop conversion
  // data read commands
  ADS_CMND_RDATAC    = 0x10,   // enable Read Data Continuous mode. 
                               // - this mode is the default mode at power-up.
  ADS_CMND_SDATAC   = 0x11,   // stop Read Data Continuously mode
  ADS_CMND_RDATA    = 0x12,   // read data by command; supports multiple read back.
  // register read/write commands
  ADS_CMND_RREG     = 0x20,   // read n nnnn registers starting at address r rrrr
                               //  - first byte 001r rrrr (2xh)(2) - second byte 000n nnnn(2)
  ADS_CMND_WREG     = 0x40    // write n nnnn registers starting at address r rrrr
                               //  - first byte 010r rrrr (2xh)(2) - second byte 000n nnnn(2)
} ADS1298Command_t;


typedef enum {
  // device settings
  ADS_REG_ID        = 0x00,   // device ID information
  // global settings
  ADS_REG_CONFIG1     = 0x01,
  ADS_REG_CONFIG2     = 0x02,
  ADS_REG_CONFIG3     = 0x03,
  ADS_REG_LOFF        = 0x04,
  // channel specific settings
  ADS_REG_CH1SET      = 0x05,
  ADS_REG_CH2SET      = 0x06,
  ADS_REG_CH3SET      = 0x07,
  ADS_REG_CH4SET      = 0x08,
  ADS_REG_CH5SET      = 0x09,
  ADS_REG_CH6SET      = 0x0A,
  ADS_REG_CH7SET      = 0x0B,
  ADS_REG_CH8SET      = 0x0C,
  ADS_REG_RLD_SENSP   = 0x0D,
  ADS_REG_RLD_SENSN   = 0x0E,
  ADS_REG_LOFF_SENSP  = 0x0F,
  ADS_REG_LOFF_SENSN  = 0x10,
  ADS_REG_LOFF_FLIP   = 0x11,
  // lead off status
  ADS_REG_LOFF_STATP  = 0x12,
  ADS_REG_LOFF_STATN  = 0x13,
  // others
  ADS_REG_GPIO        = 0x14,
  ADS_REG_PACE        = 0x15,
  ADS_REG_RESP        = 0x16,
  ADS_REG_CONFIG4     = 0x17,
  ADS_REG_WCT1        = 0x18,
  ADS_REG_WCT2        = 0x19

} ADS1298Register_t;


typedef enum {
  // ID control register bits
  DEV_ID7 = 0x80,
  DEV_ID6 = 0x40,
  DEV_ID5 = 0x20,
  DEV_ID2 = 0x04,
  DEV_ID1 = 0x02,
  DEV_ID0 = 0x01,

  ID_ADS129x = DEV_ID7,
  ID_ADS129xR = (DEV_ID7 | DEV_ID6),

  ID_4CHAN = 0,
  ID_6CHAN = DEV_ID0,
  ID_8CHAN = DEV_ID1,

  ID_ADS1294 = (ID_ADS129x | ID_4CHAN),
  ID_ADS1296 = (ID_ADS129x | ID_6CHAN),
  ID_ADS1298 = (ID_ADS129x | ID_8CHAN),
  ID_ADS1294R = (ID_ADS129xR | ID_4CHAN),
  ID_ADS1296R = (ID_ADS129xR | ID_6CHAN),
  ID_ADS1298R = (ID_ADS129xR | ID_8CHAN),

  ID_const = ID_ADS1298

} ID_bits_t;


typedef enum {
  // config1 register bits
  HR = 0x80,
  DAISY_EN = 0x40,
  CLK_EN = 0x20,
  DR2 = 0x04,
  DR1 = 0x02,
  DR0 = 0x01,

  // ADS1298
  HIGH_RES_32k_SPS  = (HR),
  HIGH_RES_16k_SPS  = (HR | DR0),
  HIGH_RES_8k_SPS   = (HR | DR1),
  HIGH_RES_4k_SPS   = (HR | DR1 | DR0),
  HIGH_RES_2k_SPS   = (HR | DR2),
  HIGH_RES_1k_SPS   = (HR | DR2 | DR0),
  HIGH_RES_500_SPS  = (HR | DR2 | DR1),

  CONFIG1_const = HIGH_RES_500_SPS

} CONFIG1_bits_t;


typedef enum {
  // config2 register bits
  WCT_CHOP = 0x20,
  INT_TEST = 0x10,
  TEST_AMP = 0x04,
  TEST_FREQ1 = 0x02,
  TEST_FREQ0 = 0x01,

  // ADS1298
  INT_TEST_4HZ = INT_TEST,
  INT_TEST_8HZ = (INT_TEST | TEST_FREQ0),
  INT_TEST_DC = (INT_TEST | TEST_FREQ1 | TEST_FREQ0),  

  CONFIG2_const = INT_TEST_DC

} CONFIG2_bits_t;


typedef enum {
  // config3 register bits
  PD_REFBUF = 0x80,
  Bit7 = 0x40,
  VREF_4V = 0x20,
  RLD_MEAS = 0x10,
  RLDREF_INT = 0x08,
  PD_RLD = 0x04,
  RLD_LOFF_SENS = 0x02,
  RLD_STAT = 0x01,

  // ADS1298
  CONFIG3_const = PD_REFBUF | RLD_MEAS | RLDREF_INT | PD_RLD | Bit7

} CONFIG3_bits_t;


typedef enum {
  // Lead-off control register bits
  COMP_TH2 = 0x80,
  COMP_TH1 = 0x40,
  COMP_TH0 = 0x20,
  VLEAD_OFF_EN = 0x10,
  ILEAD_OFF1 = 0x08,
  ILEAD_OFF0 = 0x04,
  FLEAD_OFF1 = 0x02,
  FLEAD_OFF0 = 0x01,

  // ADS1298
  LOFF_const = FLEAD_OFF1 | FLEAD_OFF0

} LOFF_bits_t;


typedef enum {
  // n-th channel setting register bits
  PDn = 0x80,
  GAINn2 = 0x40,
  GAINn1 = 0x20,
  GAINn0 = 0x10,
  MUXn2 = 0x04,
  MUXn1 = 0x02,
  MUXn0 = 0x01,

  // ADS1298
  ADS1298_GAIN_1X = GAINn0,
  ADS1298_GAIN_2X = GAINn1,
  ADS1298_GAIN_3X = (GAINn1 | GAINn0),
  ADS1298_GAIN_4X = GAINn2,
  ADS1298_GAIN_6X = 0x00,
  ADS1298_GAIN_8X = (GAINn2 | GAINn0),
  ADS1298_GAIN_12X = (GAINn2 | GAINn1),
  
  ELECTRODE_INPUT = 0x00,
  SHORTED = MUXn0,
  RLD_INPUT = MUXn1,
  MVDD = (MUXn1 | MUXn0),
  TEMP = MUXn2,
  TEST_SIGNAL = (MUXn2 | MUXn0),
  RLD_DRP = (MUXn2 | MUXn1),
  RLD_DRN = (MUXn2 | MUXn1 | MUXn0),

  //CHnSET_const = ELECTRODE_INPUT
  CHnSET_const = MVDD | ADS1298_GAIN_1X

} CHnSET_bits_t;


typedef enum {
  // RLD positive signal derivation register bits
  RLD8P = 0x80,
  RLD7P = 0x40,
  RLD6P = 0x20,
  RLD5P = 0x10,
  RLD4P = 0x08,
  RLD3P = 0x04,
  RLD2P = 0x02,
  RLD1P = 0x01,

  // ADS1298
  RLD_SENSP_const = 0x00

} RLD_SENSP_bits_t;


typedef enum {
  // RLD negative signal derivation register bits
  RLD8N = 0x80,
  RLD7N = 0x40,
  RLD6N = 0x20,
  RLD5N = 0x10,
  RLD4N = 0x08,
  RLD3N = 0x04,
  RLD2N = 0x02,
  RLD1N = 0x01,

  // ADS1298
  RLD_SENSN_const = 0x00

} RLD_SENSN_bits_t;


typedef enum {
  // positive signal lead-off detection register bits
  LOFF8P = 0x80,
  LOFF7P = 0x40,
  LOFF6P = 0x20,
  LOFF5P = 0x10,
  LOFF4P = 0x08,
  LOFF3P = 0x04,
  LOFF2P = 0x02,
  LOFF1P = 0x01,

  // ADS1298
  LOFF_SENSP_const = 0xFF

} LOFF_SENSP_bits_t;


typedef enum {
  // negative signal lead-off detection register bits
  LOFF8N = 0x80,
  LOFF7N = 0x40,
  LOFF6N = 0x20,
  LOFF5N = 0x10,
  LOFF4N = 0x08,
  LOFF3N = 0x04,
  LOFF2N = 0x02,
  LOFF1N = 0x01,

  // ADS1298
  LOFF_SENSN_const = 0x02

} LOFF_SENSN_bits_t;


typedef enum {
  // lead-off flip register bits
  LOFF_FLIP8 = 0x80,
  LOFF_FLIP7 = 0x40,
  LOFF_FLIP6 = 0x20,
  LOFF_FLIP5 = 0x10,
  LOFF_FLIP4 = 0x08,
  LOFF_FLIP3 = 0x04,
  LOFF_FLIP2 = 0x02,
  LOFF_FLIP1 = 0x01,

  // ADS1298
  LOFF_FLIP_const = 0x00

} LOFF_FLIP_bits_t;


typedef enum {
  // lead-off positive signal status register bits
  IN8P_OFF = 0x80,
  IN7P_OFF = 0x40,
  IN6P_OFF = 0x20,
  IN5P_OFF = 0x10,
  IN4P_OFF = 0x08,
  IN3P_OFF = 0x04,
  IN2P_OFF = 0x02,
  IN1P_OFF = 0x01,

  // ADS1298
  LOFF_STATP_const = 0xFE

} LOFF_STATP_bits_t;


typedef enum {
  // lead-off negative signal status register bits
  IN8N_OFF = 0x80,
  IN7N_OFF = 0x40,
  IN6N_OFF = 0x20,
  IN5N_OFF = 0x10,
  IN4N_OFF = 0x08,
  IN3N_OFF = 0x04,
  IN2N_OFF = 0x02,
  IN1N_OFF = 0x01,

  // ADS1298
  LOFF_STATN_const = 0x06

} LOFF_STATN_bits_t;


typedef enum {
  // general-purpose I/O register bits
  GPIOD4 = 0x80,
  GPIOD3 = 0x40,
  GPIOD2 = 0x20,
  GPIOD1 = 0x10,
  GPIOC4 = 0x08,
  GPIOC3 = 0x04,
  GPIOC2 = 0x02,
  GPIOC1 = 0x01,

  // ADS1298
  GPIO_const = 0x00

} GPIO_bits_t;


typedef enum {
  // pace detect register bits
  PACEE1 = 0x10,
  PACEE0 = 0x08,
  PACEO1 = 0x04,
  PACEO0 = 0x02,
  PD_PACE = 0x01,

  PACEE_CHAN2 = 0x00,
  PACEE_CHAN4 = PACEE0,
  PACEE_CHAN6 = PACEE1,
  PACEE_CHAN8 = (PACEE1 | PACEE0),

  PACEO_CHAN1 = 0x00,
  PACEO_CHAN3 = PACEE0,
  PACEO_CHAN5 = PACEE1,
  PACEO_CHAN7 = (PACEE1 | PACEE0),

  // ADS1298
  PACE_const = 0x00

} PACE_bits_t;


typedef enum {
  // respiration control register bits
  RESP_DEMOD_EN1 = 0x80,
  RESP_MOD_EN1 = 0x40,
  RESP_PH2 = 0x10,
  RESP_PH1 = 0x08,
  RESP_PH0 = 0x04,
  RESP_CTRL1 = 0x02,
  RESP_CTRL0 = 0x01,

  RESP_PH_22_5 = 0x00,
  RESP_PH_45 = RESP_PH0,
  RESP_PH_67_5 = RESP_PH1,
  RESP_PH_90 = (RESP_PH1 | RESP_PH0),
  RESP_PH_112_5 = RESP_PH2,
  RESP_PH_135 = (RESP_PH2 | RESP_PH0),
  RESP_PH_157_5 = (RESP_PH2 | RESP_PH1),

  RESP_NONE = 0x00,
  RESP_EXT = RESP_CTRL0,
  RESP_INT_SIG_INT = RESP_CTRL1,
  RESP_INT_SIG_EXT = (RESP_CTRL1 | RESP_CTRL0),

  // ADS1298 (not support)
  RESP_const = 0x00

} RESP_bits_t;


typedef enum {
  // configuration register 4 bits
  RESP_FREQ2 = 0x80,
  RESP_FREQ1 = 0x40,
  RESP_FREQ0 = 0x20,
  SINGLE_SHOT = 0x08,
  WCT_TO_RLD = 0x04,
  PD_LOFF_COMP = 0x02,

  RESP_FREQ_64k_Hz = 0x00,
  RESP_FREQ_32k_Hz = RESP_FREQ0,
  RESP_FREQ_16k_Hz = RESP_FREQ1,
  RESP_FREQ_8k_Hz = (RESP_FREQ1 | RESP_FREQ0),
  RESP_FREQ_4k_Hz = RESP_FREQ2,
  RESP_FREQ_2k_Hz = (RESP_FREQ2 | RESP_FREQ0),
  RESP_FREQ_1k_Hz = (RESP_FREQ2 | RESP_FREQ1),
  RESP_FREQ_500_Hz = (RESP_FREQ2 | RESP_FREQ1 | RESP_FREQ0),

  // ADS1298
  CONFIG4_const = PD_LOFF_COMP

} CONFIG4_bits_t;


typedef enum {
  // WCT1: wilson central terminal and augmented lead control register bits
  aVF_CH6 = 0x80,
  aVL_CH5 = 0x40,
  aVR_CH7 = 0x20,
  avR_CH4 = 0x10,
  PD_WCTA = 0x08,
  WCTA2 = 0x04,
  WCTA1 = 0x02,
  WCTA0 = 0x01,

  WCTA_CH1P = 0x00,
  WCTA_CH1N = WCTA0,
  WCTA_CH2P = WCTA1,
  WCTA_CH2N = (WCTA1 | WCTA0),
  WCTA_CH3P = WCTA2,
  WCTA_CH3N = (WCTA2 | WCTA0),
  WCTA_CH4P = (WCTA2 | WCTA1),
  WCTA_CH4N = (WCTA2 | WCTA1 | WCTA0),

  // ADS1298
  WCT1_const = PD_WCTA | WCTA1

} WCT1_bits_t;


typedef enum {
  // WCT2: wilson central terminal control register bits
  PD_WCTC = 0x80,
  PD_WCTB = 0x40,
  WCTB2 = 0x20,
  WCTB1 = 0x10,
  WCTB0 = 0x08,
  WCTC2 = 0x04,
  WCTC1 = 0x02,
  WCTC0 = 0x01,

  WCTB_CH1P = 0x00,
  WCTB_CH1N = WCTB0,
  WCTB_CH2P = WCTB1,
  WCTB_CH2N = (WCTB1 | WCTB0),
  WCTB_CH3P = WCTB2,
  WCTB_CH3N = (WCTB2 | WCTB0),
  WCTB_CH4P = (WCTB2 | WCTB1),
  WCTB_CH4N = (WCTB2 | WCTB1 | WCTB0),

  WCTC_CH1P = 0x00,
  WCTC_CH1N = WCTC0,
  WCTC_CH2P = WCTC1,
  WCTC_CH2N = (WCTC1 | WCTC0),
  WCTC_CH3P = WCTC2,
  WCTC_CH3N = (WCTC2 | WCTC0),
  WCTC_CH4P = (WCTC2 | WCTC1),
  WCTC_CH4N = (WCTC2 | WCTC1 | WCTC0),

  // ADS1298
  WCT2_const = PD_WCTC | PD_WCTB | WCTB_CH3P | WCTC_CH2N

} WCT2_bits_t;



#ifdef __cplusplus
}
#endif

#endif // ADS1298_H

问题是、通常两种设置之间的电压测量存在偏差。 以下是两种设置之间测量的电压汇总表:

通道编号 ADS1298 DevKit 和 GUI 软件(mV) 定制设计(mV)
1 -1.588392 -1.237154154
2. -0.723791122 -1.197433614
3. -1.223898 -1.365900203
4. -1.398134 -1.233053354
5. -1.174879 -0.781917665
6. -1.245832 350.5889834
7. -1.276207 79.24800864
8. -0.989675522 -76.67232474

在测量通道6、7和8上的测试数据时、我们的设计中读取的值也会出现很大的波动。 通过 GUI 在开发套件上读取的所有通道上的所有电压测量都是稳定的。 执行此测试是否存在任何硬件连接依赖项?

期待一些建议和/或故障排除步骤。

提前感谢您。

此致、

Eric

  • 请注意,本文内容源自机器翻译,可能存在语法或其它翻译错误,仅供参考。如需获取准确内容,请参阅链接中的英语原文或自行翻译。

    尊敬的 Eric:

    使用内部 TEST 信号时、不应存在与硬件连接相关的问题。 通过将 MUXn[2:0]设置为0b001、您能否通过输入短路测试验证所有通道是否正常运行? 使用内部测试信号时、CH6至 CH8的 ADC 输出波形是什么样的?

    谢谢

    -TC