Author Topic: Axon I2C Interface with DS1307 Real Time Clock  (Read 4348 times)

0 Members and 1 Guest are viewing this topic.

Offline airman00Topic starter

  • Contest Winner
  • Supreme Robot
  • ****
  • Posts: 3,650
  • Helpful? 21
  • narobo.com
    • Narobo.com - Mechatronics and related
Axon I2C Interface with DS1307 Real Time Clock
« on: August 28, 2009, 11:07:07 AM »
I'm attempting to use  the DS1307 clock with the Axon over I2C - http://www.sparkfun.com/datasheets/Components/DS1307.pdf

I've built the circuit they show in the datasheet and the Axon is internally pulling up the SDA and SCL ( I checked)


I do not have access to an o-scope until Monday, but I'd like to get this working over the weekend anyways.

Here is my code:
Code: [Select]
#define REGISTER              0x00
#define DS1307_ADDR 0x68
#define BUFFSIZE          0x08

int bytes[8];
int i;

rprintfInit(uart1SendByte);  // Set up rprintf to be USB

i2cInit();  //initialize I2C interface
i2cSetBitrate(100);  //set I2C transaction bit rate to 100 kHz


i2cSendStart(); //Send I2C start condition in Master mode
i2cSendByte(DS1307_ADDR | 0x00);    //Send (address|R/W) combination or a data byte over I2C
i2cSendByte(REGISTER);

i2cSendStart(); //Send I2C start condition in Master mode
i2cSendByte(DS1307_ADDR | 0x01);    //Send (address|R/W) combination or a data byte over I2C

for (i=0;i<8;i++) {
i2cReceiveByte(1);
bytes[i] = i2cGetReceivedByte();

}

i2cSendStop();      //Send I2C stop condition in Master mode

for (i=0;i<8;i++) {
rprintf("%d.",bytes[i]);
}
      
Check out the Roboduino, Arduino-compatible board!


Link: http://curiousinventor.com/kits/roboduino

www.Narobo.com

Offline Admin

  • Administrator
  • Supreme Robot
  • *****
  • Posts: 11,703
  • Helpful? 173
    • Society of Robots
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #1 on: August 28, 2009, 11:38:17 AM »
Quote
I do not have access to an o-scope until Monday, but I'd like to get this working over the weekend anyways.
You have two Axons, use the other with SoR Scope ;D

Anyway, you forgot to state the problem :P

Offline airman00Topic starter

  • Contest Winner
  • Supreme Robot
  • ****
  • Posts: 3,650
  • Helpful? 21
  • narobo.com
    • Narobo.com - Mechatronics and related
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #2 on: August 28, 2009, 12:50:41 PM »
Problem is that I keep getting only 0s.

My other Axon is unavailable right now ( embedded in another project I dont want to take apart)
Check out the Roboduino, Arduino-compatible board!


Link: http://curiousinventor.com/kits/roboduino

www.Narobo.com

Offline Admin

  • Administrator
  • Supreme Robot
  • *****
  • Posts: 11,703
  • Helpful? 173
    • Society of Robots
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #3 on: August 28, 2009, 01:02:42 PM »
Looking at the datasheet, I see this:
Quote
32.768kHz Crystal Connection

ICCA – SCL clocking at max frequency = 100kHz

and in your code I see this:
Code: [Select]
i2cSetBitrate(100);  //set I2C transaction bit rate to 100 kHz
Is that right? (I only quickly glanced at everything) Perhaps bringing it to 10kHz is better?

Does your I2C code work for your other hardware?

Put your multimeter at frequency and look for something when a transaction should occur.

Offline airman00Topic starter

  • Contest Winner
  • Supreme Robot
  • ****
  • Posts: 3,650
  • Helpful? 21
  • narobo.com
    • Narobo.com - Mechatronics and related
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #4 on: August 28, 2009, 01:40:20 PM »
Some slight progress. I brought it down to 2khz.  This is my first time playing with I2C.

I changed my code to this:
Code: [Select]
#define REGISTER          0x00
#define TARGET_ADDR   0x68

int bytes[7];
int i;
int buffer;
rprintfInit(uart1SendByte);  // Set up rprintf to be USB

i2cInit();  //initialize I2C interface
i2cSetBitrate(1);  //set I2C transaction bit rate to 100 kHz
buffer = 0;

i2cMasterSend(TARGET_ADDR, 0x01, &buffer);
i2cMasterReceive(TARGET_ADDR, 8, &bytes[0]);


for (i=0;i<8;i++) {
rprintfu08(bytes[i]);
rprintfChar('.');
}
rprintf("\r");

delay_ms(1500);


And now I get this out USB. The data remains the same, doesn't refresh.
Quote
00.00.00.00.01.00.1C.00.
00.00.00.00.01.00.1C.00.
00.00.00.00.01.00.1C.00.

In the datasheet is says that you have to enable the oscillator which is Bit 7 on register 0x00. I think I am enabling it when I do this:
Code: [Select]
buffer = 0;
i2cMasterSend(TARGET_ADDR, 0x01, &buffer);

Many thanks in advance
Check out the Roboduino, Arduino-compatible board!


Link: http://curiousinventor.com/kits/roboduino

www.Narobo.com

Offline Admin

  • Administrator
  • Supreme Robot
  • *****
  • Posts: 11,703
  • Helpful? 173
    • Society of Robots
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #5 on: August 28, 2009, 01:53:26 PM »
I almost feel like your buffer is way too small.

Try changing
int buffer;
to
#DEFINE BUFFER 0x50

Look at how I did my compass code:
http://www.societyofrobots.com/robotforum/index.php?topic=8393.0

But to be honest, I don't really understand I2C myself so hopefully someone else can chime in!

Offline airman00Topic starter

  • Contest Winner
  • Supreme Robot
  • ****
  • Posts: 3,650
  • Helpful? 21
  • narobo.com
    • Narobo.com - Mechatronics and related
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #6 on: August 28, 2009, 03:06:20 PM »
Look at how I did my compass code:
http://www.societyofrobots.com/robotforum/index.php?topic=8393.0
From what I understand, your compass code sends a command through I2C and is replied to with 6 bytes. In my case I'm not sending a command at all, rather I'm trying to read one of the registers on the DS1307.
Check out the Roboduino, Arduino-compatible board!


Link: http://curiousinventor.com/kits/roboduino

www.Narobo.com

Offline airman00Topic starter

  • Contest Winner
  • Supreme Robot
  • ****
  • Posts: 3,650
  • Helpful? 21
  • narobo.com
    • Narobo.com - Mechatronics and related
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #7 on: August 29, 2009, 06:53:15 PM »
Update:
I put on some code that (I think) sends out a I2C byte and checks for ACK . It also should read the values of 6 registers. My sending code checks out because I get the confirming messages out through UART. But my receiving code is just returning 0s.
 
Output from UART:
Quote
STA-SLA+W-DATA-STO 0= 0  1= 0  2= 0  3= 0  4= 0  5= 0

My code:
Code: [Select]
void i2cMasterSendDiag(u08 deviceAddr, u08 length, u08* data)
{
// this function is equivalent to the i2cMasterSendNI() in the I2C library
// except it will print information about transmission progress to the terminal

// disable TWI interrupt
cbi(TWCR, TWIE);

// send start condition
i2cSendStart();
i2cWaitForComplete();
rprintf("STA-");

// send device address with write
i2cSendByte( deviceAddr&0xFE );
i2cWaitForComplete();
rprintf("SLA+W-");

// send data
while(length)
{
i2cSendByte( *data++ );
i2cWaitForComplete();
rprintf("DATA-");
length--;
}

// transmit stop condition
// leave with TWEA on for slave receiving
i2cSendStop();
while( !(inb(TWCR) & BV(TWSTO)) );
rprintf("STO");

// enable TWI interrupt
sbi(TWCR, TWIE);
}

void control(void) {
#define REGISTER          0x00
#define TARGET_ADDR   0x68

int bytes[7];
int i;
int temp;
u08 in[6];  //6 bytes = MSB heading, LSB heading, MSB pitch, LSB pitch, MSB roll, LSB roll
int buffer;
rprintfInit(uart1SendByte);  // Set up rprintf to be USB

i2cInit();  //initialize I2C interface
i2cSetBitrate(5);  //set I2C transaction bit rate to 5 kHz

i2cMasterSendDiag(0x68,0x01,0x00);
delay_ms(10);
i2cMasterReceive(0x68, 6, &in[0]);  //read 6 byte data from slave to master

for (i=0;i<6;i++) {
rprintf("%d= %d  ",i,in[i]);
}

delay_ms(1500);
Check out the Roboduino, Arduino-compatible board!


Link: http://curiousinventor.com/kits/roboduino

www.Narobo.com

Offline airman00Topic starter

  • Contest Winner
  • Supreme Robot
  • ****
  • Posts: 3,650
  • Helpful? 21
  • narobo.com
    • Narobo.com - Mechatronics and related
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #8 on: August 29, 2009, 09:51:31 PM »
Semi-success:
It seems like I'm getting I2C data now, but it doesnt look like the clock is starting. In the datasheet it says to write a 0 to bit 7 of register 0x00 to start the clock. I think I'm doing that , but the clock isnt starting. What is interesting as well is that Byte 0 returns 104 all the time - 104 being the decimal equivalent of the I2C Slave's address( 0x68 to hex is 104).

Any ideas?

I always get this out UART, it doesnt update
Quote
START   ADDR   REGISTER     DATA     STOP   SENT!!   
START   ADDR   REGISTER  START      ADDR    STOP
0 = 104  1 = 209  2 = 162  3 = 69  4 = 69  5 = 139  6 = 22  7 = 45 

Using this code:
Code: [Select]
i2cInit();  //initialize I2C interface
i2cSetBitrate(5);  //set I2C transaction bit rate to 5 kHz


delay_ms(10);

// disable TWI interrupt
cbi(TWCR, TWIE);

// START
i2cSendStart(); //Send I2C start condition in Master mode
i2cWaitForComplete();
rprintf("START");
// I2C ADDRESS OF SLAVE
i2cSendByte(TARGET_ADDR&0xFE);    //Send (address|R/W) combination or a data byte over I2C
i2cWaitForComplete();
rprintf("   ADDR");
// I2C DEVICE REGISTER
i2cSendByte(REGISTER);
i2cWaitForComplete();
rprintf("   REGISTER  ");
// DATA BYTE
i2cSendByte(0x00);
i2cWaitForComplete();
rprintf("   DATA  ");
// STOP
i2cSendStop();      //Send I2C stop condition in Master mode
rprintf("   STOP  ");
rprintf(" SENT!!    ");
delay_ms(10);


while(1) {

// START
i2cSendStart(); //Send I2C start condition in Master mode
i2cWaitForComplete();
rprintf("\rSTART");
// I2C SLAVE ADRESS
i2cSendByte(TARGET_ADDR&0xFE);    //Send (address|R/W) combination or a data byte over I2C
i2cWaitForComplete();
rprintf("   ADDR");
// REGISTER
i2cSendByte(REGISTER);
i2cWaitForComplete();
rprintf("   REGISTER  ");
// START
i2cSendStart(); //Send I2C start condition in Master mode
i2cWaitForComplete();
rprintf("START   ");
// I2C SLAVE ADDRESS
i2cSendByte(TARGET_ADDR&0xFF);    //Send (address|R/W) combination or a data byte over I2C
i2cWaitForComplete();
rprintf("   ADDR    ");
// DATA BYTES
for (i=0;i<8;i++) {
i2cReceiveByte(1);
bytes[i] = i2cGetReceivedByte();
}
// STOP
i2cSendStop();      //Send I2C stop condition in Master mode
rprintf("STOP\r");

for (i=0;i<8;i++) {
rprintf("%d = %d  ",i,bytes[i]);
}


delay_ms(1500);

}
Check out the Roboduino, Arduino-compatible board!


Link: http://curiousinventor.com/kits/roboduino

www.Narobo.com

Offline airman00Topic starter

  • Contest Winner
  • Supreme Robot
  • ****
  • Posts: 3,650
  • Helpful? 21
  • narobo.com
    • Narobo.com - Mechatronics and related
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #9 on: August 29, 2009, 10:00:35 PM »
To make things wierder, when I change the frequency , I get different readings. But notice how the numbers are pretty much the same, just in a different order. Interestingly Byte 0 always remains 104 ( decimal value of the I2C slave's address)
Quote
2khz : 0 = 104  1 = 162  2 = 69  3 = 22  4 = 90  5 = 180  6 = 104  7 = 162 
5 khz:  0 = 104  1 = 209  2 = 162  3 = 69  4 = 69  5 = 139  6 = 22  7 = 45 
10 khz :  0 = 104  1 = 162  2 = 69  3 = 22  4 = 90  5 = 180  6 = 104  7 = 162 
100khz :  0 = 104  1 = 209  2 = 209  3 = 162  4 = 69  5 = 69  6 = 139  7 = 22 

Check out the Roboduino, Arduino-compatible board!


Link: http://curiousinventor.com/kits/roboduino

www.Narobo.com

Offline Admin

  • Administrator
  • Supreme Robot
  • *****
  • Posts: 11,703
  • Helpful? 173
    • Society of Robots
Re: Axon I2C Interface with DS1307 Real Time Clock
« Reply #10 on: August 30, 2009, 07:37:16 AM »
To make things wierder, when I change the frequency , I get different readings. But notice how the numbers are pretty much the same, just in a different order. Interestingly Byte 0 always remains 104 ( decimal value of the I2C slave's address)
Quote
2khz : 0 = 104  1 = 162  2 = 69  3 = 22  4 = 90  5 = 180  6 = 104  7 = 162 
5 khz:  0 = 104  1 = 209  2 = 162  3 = 69  4 = 69  5 = 139  6 = 22  7 = 45 
10 khz :  0 = 104  1 = 162  2 = 69  3 = 22  4 = 90  5 = 180  6 = 104  7 = 162 
100khz :  0 = 104  1 = 209  2 = 209  3 = 162  4 = 69  5 = 69  6 = 139  7 = 22 

This could maybe be because its outputting data faster than you are reading it with UART. For example, your mcu spends time outputting it to USB while the chip is being ignored with the next set of data.

 


data_list