CCS C Software and Maintenance Offers
FAQFAQ   FAQForum Help   FAQOfficial CCS Support   SearchSearch  RegisterRegister 

ProfileProfile   Log in to check your private messagesLog in to check your private messages   Log inLog in 

CCS does not monitor this forum on a regular basis.

Please do not post bug reports on this forum. Send them to support@ccsinfo.com

Need help for i2c communication with FDC2214
Goto page Previous  1, 2, 3, 4, 5  Next
 
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion
View previous topic :: View next topic  
Author Message
ressas



Joined: 15 Nov 2019
Posts: 135

View user's profile Send private message

PostPosted: Sat Nov 30, 2019 3:27 am     Reply with quote

That's right, and you said it pretty well. but the code doesn't work Wink
let me try a little more
Thank you
Ttelmah



Joined: 11 Mar 2010
Posts: 19195

View user's profile Send private message

PostPosted: Sat Nov 30, 2019 5:54 am     Reply with quote

OK. Try doing the second read as well, but just throw away what it returns.
As I mentioned, there is this odd reference in the data sheet suggesting
that you must do both reads or there will be issues.
temtronic



Joined: 01 Jul 2010
Posts: 9081
Location: Greensville,Ontario

View user's profile Send private message

PostPosted: Sat Nov 30, 2019 10:07 am     Reply with quote

This is a great example of why it'd be nice to have the module on my bench and a LOT of time to diagnose what is going on. Having a 1/2 written 'datasheet' for any peripheral is bad, but for a COMPLICATED device like this is a horror story.
Hopefully just a few more hours and the OP will get the correct numbers....
Sad thing is it's less trouble than programming a 5KW Chinese diesel heater using their LCD interface.....I still can't find a well worded English version of how to program it.......though someone's hacked it ...

Jay
Ttelmah



Joined: 11 Mar 2010
Posts: 19195

View user's profile Send private message

PostPosted: Sat Nov 30, 2019 12:20 pm     Reply with quote

You do realise that CH0_RCOUNT should be set to a different value for
the 12bit chip?. What is this being set to?. Wants 0x400 for the 12bit
chip.
ressas



Joined: 15 Nov 2019
Posts: 135

View user's profile Send private message

FDC2214 to FDC2112
PostPosted: Mon Dec 02, 2019 12:19 am     Reply with quote

Hello to everyone.
This is the final version of the code. But it still doesn't work.
FDC2112.h
Code:

///////////////////fdc221 datasheet page 22///////////////////////

// Address is 0x2A = 0x54 (default) or 0x2B = 0x55 (if ADDR is high)
#define FDC2214_I2C_ADDR_0   0x54
#define FDC2214_I2C_ADDR_1   0x55
//bitmasks
#define FDC2214_CH0_UNREADCONV 0x0008         //denotes unread CH0 reading in STATUS register
#define FDC2214_CH1_UNREADCONV 0x0004         //denotes unread CH1 reading in STATUS register
#define FDC2214_CH2_UNREADCONV 0x0002         //denotes unread CH2 reading in STATUS register
#define FDC2214_CH3_UNREADCONV 0x0001         //denotes unread CH3 reading in STATUS register
//registers
#define FDC2214_DEVICE_ID               0x7F
#define FDC2214_MUX_CONFIG              0x1B
#define FDC2214_CONFIG                  0x1A
#define FDC2214_RCOUNT_CH0              0x08 //0x400
#define FDC2214_RCOUNT_CH1              0x09
#define FDC2214_RCOUNT_CH2              0x0A
#define FDC2214_RCOUNT_CH3              0x0B
#define FDC2214_OFFSET_CH0              0x0C
#define FDC2214_OFFSET_CH1              0x0D
#define FDC2214_OFFSET_CH2              0x0E
#define FDC2214_OFFSET_CH3              0x0F
#define FDC2214_SETTLECOUNT_CH0         0x10
#define FDC2214_SETTLECOUNT_CH1         0x11
#define FDC2214_SETTLECOUNT_CH2         0x12
#define FDC2214_SETTLECOUNT_CH3         0x13
#define FDC2214_CLOCK_DIVIDERS_CH0      0x14
#define FDC2214_CLOCK_DIVIDERS_CH1      0x15
#define FDC2214_CLOCK_DIVIDERS_CH2      0x16
#define FDC2214_CLOCK_DIVIDERS_CH3      0x17
#define FDC2214_STATUS                  0x18
#define FDC2214_DATA_CH0_MSB            0x00
#define FDC2214_DATA_CH0_LSB            0x01
#define FDC2214_DATA_CH1_MSB              0x02
#define FDC2214_DATA_CH1_LSB            0x03
#define FDC2214_DATA_CH2_MSB              0x04
#define FDC2214_DATA_CH2_LSB            0x05
#define FDC2214_DATA_CH3_MSB              0x06
#define FDC2214_DATA_CH3_LSB            0x07
#define FDC2214_DRIVE_CH0               0x1E
#define FDC2214_DRIVE_CH1               0x1F
#define FDC2214_DRIVE_CH2               0x20
#define FDC2214_DRIVE_CH3               0x21
// mask for 28bit data to filter out flag bits
#define FDC2214_DATA_CHx_MASK_DATA_2        0b00000000000000000000111111111111
#define FDC2214_DATA_CHx_MASK_DATA          0x0FFF
#define FDC2214_DATA_CHx_MASK_ERRAW         0x1000
#define FDC2214_DATA_CHx_MASK_ERRWD         0x2000
//------------------------------------------------
///////////////////////////////////////////////////////////////////
#define CHAN_COUNT 2 // channel number,

void write16FDC(unsigned int16 address, unsigned int16 data);
unsigned int16 read16FDC(char address);
int1 FDC2214_begin(char chanMask,char autoscanSeq, char deglitchValue, int1 intOsc);
void loadSettings(char chanMask, char autoscanSeq, char deglitchValue, int1 intOsc);
unsigned int32 getReading28(char channel);
               

FDC2112.c
Code:

#include "Pic16f1824_fdc2214.h"

char dev_adds = FDC2214_I2C_ADDR_0; //dev_adds = 0x54

// fdc2214 datasheet steps on page 22 followed
void write16FDC(unsigned int16 address, unsigned int16 data) {
 
  i2c_start();
  i2c_write(dev_adds);         //first, sending integrated address
  i2c_write(address & 0xff);   //secondly, sending register address
                       // (?) Masked with 0xff, to ensure that 8 bits are sent
  i2c_write(data >>8); //i2c communicates with 8 bits. But data = 16 bits.
                       //so we're shifting
  i2c_write(data);
                       //other 8 bits
  i2c_stop();
}

// fdc2214 datasheet steps on page 22 followed
unsigned int16 read16FDC(char address) {
   unsigned int16 data;
   i2c_start();
   i2c_write(dev_adds);
   i2c_write(address);
   i2c_start();
   i2c_write(dev_adds + 1);           // Set R/W bit = 1 to read bytes
   char datahigh=i2c_read(); //two pieces made from 8 bits to 16 bits
   char datalow=i2c_read(0);
   data=make16(datahigh,datalow);
   i2c_stop();
   return data;
}

int1 FDC2214_begin(char chanMask,char autoscanSeq, char deglitchValue, int1 intOsc) {

  printf("FDC2214_begin");
  int devId = read16FDC(FDC2214_DEVICE_ID);
  //Checking the lighting of the device on the i2c line (sda, scl).
  //If the values 0x3054 and 0x3055 are displayed; connected to the correct device
  if (devId != 0x3054) {
    if (devId != 0x3055) {
      //two valid device ids for FDC2214 0x3054 and 0x3055
      return false;
    }
  }
  loadSettings(chanMask, autoscanSeq, deglitchValue, intOsc);

  return true;
}

void loadSettings(char chanMask, char autoscanSeq, char deglitchValue, int1 intOsc) {
  //Adjusting configuration settings
  // When the FDC powers up, it enters into Sleep Mode and will wait for configuration.
  //Once the device is configured, exit Sleep Mode by setting CONFIG.
  printf("loadSettings");
  if (intOsc) {
    write16FDC(FDC2214_CONFIG, 0x1C81); //set config 0x1C81
    printf("0x1C81");
  } else {
    write16FDC(FDC2214_CONFIG, 0x1E81);  //set config 0x1E81
    printf("0x1E81");
  }
  //FDC2214 HAVE 2 CHANNEL
  //We make configuration settings for each channel.
  //If channel 1 selected, init it..
  if (chanMask & 0x01) {
    //settle count maximized, slow application
    write16FDC(FDC2214_SETTLECOUNT_CH0, 0x6400); // 0x6400
    //rcount maximized for highest accuracy
    write16FDC(FDC2214_RCOUNT_CH0, 0xFFFF); //0xFFFF
    //no offset
    write16FDC(FDC2214_OFFSET_CH0, 0x0000);
    // Set clock dividers
    write16FDC(FDC2214_CLOCK_DIVIDERS_CH0, 0x2001); //0x2001
    //set drive register
    write16FDC(FDC2214_DRIVE_CH0, 0xF800); //0xF800
  }
  // Init chan2, if selected by channel init mask
  if (chanMask & 0x02) {
    write16FDC(FDC2214_SETTLECOUNT_CH1, 0x6400);
    write16FDC(FDC2214_RCOUNT_CH1, 0xFFFF);
    write16FDC(FDC2214_OFFSET_CH1, 0x0000);
    write16FDC(FDC2214_CLOCK_DIVIDERS_CH1, 0x2001);
    write16FDC(FDC2214_DRIVE_CH1, 0xF800);
  }

  /////////////////////////////////////////////////////////////////////////////
  unsigned int16 muxVal = 0x0208 | ( (unsigned int16)autoscanSeq << 13) | deglitchValue;
  //(?) I have no idea what's going on here.
 
  write16FDC(FDC2214_MUX_CONFIG, muxVal);  //set mux config for channels
}

unsigned int32 getReading28(char channel) {
//    Serial.println("getReading28");
  int timeout = 100;
  unsigned int32 reading = 0;
  int status = read16FDC(FDC2214_STATUS);
  char addressMSB;
  char addressLSB;
  char bitUnreadConv;
  // Set to channel selection, we match registers with variables.
  switch (channel) {
    case 0:
      addressMSB = FDC2214_DATA_CH0_MSB;
     // addressLSB = FDC2214_DATA_CH0_LSB;
      bitUnreadConv = FDC2214_CH0_UNREADCONV;
      break;
    case 1:
      addressMSB = FDC2214_DATA_CH1_MSB;
      bitUnreadConv = FDC2214_CH1_UNREADCONV;
      break;
      default: return 0;
  }
  //(?)
  while (timeout && !(status & bitUnreadConv)) {
    status = read16FDC(FDC2214_STATUS);
    timeout--;
  }
  if (timeout == 100) {
   
    reading = ((unsigned int32) read16FDC(addressMSB) & FDC2214_DATA_CHx_MASK_DATA)/*<<16*/;
    //reading |= read16FDC(addressLSB);
    while (timeout && !(status & bitUnreadConv)) {
      status = read16FDC(FDC2214_STATUS);
      timeout--;
    }
  }
  if (timeout) {
    reading = ((unsigned int32) read16FDC(addressMSB) & FDC2214_DATA_CHx_MASK_DATA)/*<<16*/;
   //reading |= read16FDC(addressLSB);
    return reading;
  } else {
    // Could not get data, chip readynes flag timeout
    return 0;
  }
}

Example Code:
Code:

#include <16f1824.h>
//#device ADC=10
#INCLUDE <stdlib.h> //Required to send make16()
#fuses XT,NOWDT,NOBROWNOUT,NOPUT,NOWRT,NODEBUG, NOMCLR//, NOPROTECT, NOWDT, NOLVP,INTRC_IO,

#use delay(clock=4000000) //When you do 8, 16 or 32 you do not get a result
#use  rs232(baud=9600,parity=N,xmit=PIN_C4,rcv=PIN_C5,bits=8)
#use i2c(Master,sda=PIN_c1,scl=PIN_c0,slow=400000,FORCE_HW)
#include "Pic16f1824_fdc2214.c"
void main() {
  output_high(pin_c2);
  setup_oscillator(OSC_4MHZ|OSC_INTRC|OSC_PLL_ON);   
  delay_ms(10000); // this not necessary
  int1 capOk = FDC2214_begin(0xF, 0x0006, 0x5, true); //again config
//setup all four channels, autoscan with 4 channels, deglitch at 10MHz, external oscillator

  if (capOk) //we check whether it is connected
    printf("open");
  else
    printf("close");

while(true) {
  unsigned int32 capa[CHAN_COUNT]; // variable to store data from FDC
  for (int i = 0; i < CHAN_COUNT; i++) { // for each channel
    // ### read 28bit data
    // getReading28(reading);
    capa[i] = getReading28(i); //
    // ### Transmit data to serial in simple format readable by SerialPlot application.
    printf("%lu ",capa[i]);
    if(i==1) // printing the data we read to the bottom line   
    {
    printf("\n");
    }
    if (i < CHAN_COUNT - 1) printf(",");
    else printf("");
  }
  delay_ms(100);
 
}}


#define FDC2214_RCOUNT_CH0 0x08 when
I read the following information from serial communications;
Quote:

-> FDC2214_beginloadSettings0x1C81open0 ,0
-> 0 ,0
-> 0 ,0
-> 0 ,0
-> 0 ,0
-> 0 ,0
-> 0 ,0
-> 0 ,0
-> 0 ,0
-> 0 ,0



#define FDC2214_RCOUNT_CH0 0x400 when

I read the following information from serial communications;

Quote:

-> FDC2214_beginloadSettings0x1C81open4095 ,4095
-> 4095 ,4095
-> 4095 ,4095
-> 4095 ,4095
-> 4095 ,4095
-> 4095 ,4095
-> 4095 ,4095
-> 4095 ,4095
-> 4095 ,4095

I'm waiting for your answer
Ttelmah



Joined: 11 Mar 2010
Posts: 19195

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 2:36 am     Reply with quote

Whoa.

You must not change the define for RCOUNT.

You need to change the value written to this register. Changing the
define means the value will be going to the wrong register. No wonder it
won't work.

The locations are the two places where you write to the RCOUNT registers:

write16FDC(FDC2214_RCOUNT_CH0, 0xFFFF); //0xFFFF
//no offset

The value here should be 0x400 for the 12bit chip, instead of 0xFFFF for the
28bit chip, and the same for CH1.
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 2:53 am     Reply with quote

Also, I found two compiler warnings that are important in FDC2112.c:
Quote:

>>> Warning 203 "C:\...\FDC2112.c" Line 40(1,1): Condition always TRUE
>>> Warning 203 "C:\...\FDC2112.c" Line 41(1,1): Condition always TRUE
>>> Warning 202 "C:\FDC2112.c" Line 100(8,18): Variable never used: addressLSB

In the code below, you have declared devId as an 'int'. In the PCM
compiler, an 'int' is an unsigned 8-bit integer. You can't successfully
compare it to a 16-bit constant. Change the declaration of 'devId' to an int16.
Quote:

int1 FDC2214_begin(char chanMask,char autoscanSeq, char deglitchValue, int1 intOsc) {

printf("FDC2214_begin");
int devId = read16FDC(FDC2214_DEVICE_ID);
//Checking the lighting of the device on the i2c line (sda, scl).
//If the values 0x3054 and 0x3055 are displayed; connected to the correct device
if (devId != 0x3054) {
if (devId != 0x3055) {
//two valid device ids for FDC2214 0x3054 and 0x3055
return false;
}

Example:
Code:
int16 devID = read16FDC(FDC2214_DEVICE_ID);
ressas



Joined: 15 Nov 2019
Posts: 135

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 4:18 am     Reply with quote

I did both of you, but the result hasn't changed.
Ttelmah



Joined: 11 Mar 2010
Posts: 19195

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 4:26 am     Reply with quote

You are sure you have put the FDC2214_RCOUNT_CH0 define back to the
correct value?.
ressas



Joined: 15 Nov 2019
Posts: 135

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 4:40 am     Reply with quote

Quote:

if (chanMask & 0x01) {
//settle count maximized, slow application
write16FDC(FDC2214_SETTLECOUNT_CH0, 0x6400); // 0x6400
//rcount maximized for highest accuracy
write16FDC(FDC2214_RCOUNT_CH0, 0x0400); //0xFFFF //0x400 //0x4000
//I try the all of them
//no offset
write16FDC(FDC2214_OFFSET_CH0, 0x0000);
// Set clock dividers
write16FDC(FDC2214_CLOCK_DIVIDERS_CH0, 0x2001); //0x2001
//set drive register
write16FDC(FDC2214_DRIVE_CH0, 0xF800); //0xF800
}
Ttelmah



Joined: 11 Mar 2010
Posts: 19195

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 6:10 am     Reply with quote

The point is have you set the #define back to it's correct value.
PCM programmer



Joined: 06 Sep 2003
Posts: 21708

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 6:16 am     Reply with quote

He wants you to put it like this, and leave it that way:
Code:
#define FDC2214_RCOUNT_CH0    0x08
ressas



Joined: 15 Nov 2019
Posts: 135

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 7:08 am     Reply with quote

YES I did it that way. I do exactly what you say. Rolling Eyes
Ttelmah



Joined: 11 Mar 2010
Posts: 19195

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 7:26 am     Reply with quote

OK. If is is reading 4095, then this is what the chip gives for 'over range':

0xfff = over range

You probably need to look at changing your selected Fref depending on how
your sense circuit is laid out.
temtronic



Joined: 01 Jul 2010
Posts: 9081
Location: Greensville,Ontario

View user's profile Send private message

PostPosted: Mon Dec 02, 2019 7:26 am     Reply with quote

Your last program( 4-5 posts above) doesn't appear to have 'setup' or 'loaded' any registers with 'configuration' data.
While you do include the 'driver', that only contains functions to access the device. Main() has to config or init a LOT of registers before you try to read data from it.
Please post your current program so that we can see exactly what you're doing. As pointed out ....rcount... has to be loaded with 0x400 as well.

Jay
Display posts from previous:   
Post new topic   Reply to topic    CCS Forum Index -> General CCS C Discussion All times are GMT - 6 Hours
Goto page Previous  1, 2, 3, 4, 5  Next
Page 3 of 5

 
Jump to:  
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum


Powered by phpBB © 2001, 2005 phpBB Group