Reading Data from LK404-55 over I2C serial bus.

LK/ELK/VK/PK/OK/MX/GLK/EGLK/GVK/GLT Series

Moderators: Henry, Mods

Miles
Matrix Orbital
Matrix Orbital
Posts: 1105
Joined: Mon Mar 04, 2002 4:00 pm

Post by Miles »

Thanks for the excellent example...!!! :D
Miles Y.
Head of Technical Support
Product Manager
Matrix Orbital

RussCA
LCD!
Posts: 13
Joined: Tue Nov 09, 2004 9:59 am
Location: Ontario, Canada

Post by RussCA »

Miles,

No problem, glad to help.

It would be nice to have a facility to share files here.

Russ
Russ

Have you tried Renewable Energy yet?

Miles
Matrix Orbital
Matrix Orbital
Posts: 1105
Joined: Mon Mar 04, 2002 4:00 pm

Post by Miles »

Interesting idea...Will have to look into that!! :D
Miles Y.
Head of Technical Support
Product Manager
Matrix Orbital

RussCA
LCD!
Posts: 13
Joined: Tue Nov 09, 2004 9:59 am
Location: Ontario, Canada

Post by RussCA »

There are a few problems in the I2C.C code posted earlier. Here is a corrected version.

Russ

===========================================

Code: Select all

/*
 * Routines to drive a standard I2C bus.
 */


#include <stdio.h>
#include "\JKMicro\H\i2c.h"
#include "\JKMicro\H\Ports186.h"

  #define SCL     PORTA
  #define SCLBIT  0x00
  #define SDA     PORTB
  #define SDABIT  0x00

/*
 * I2C Routines derived from the pseudo code by V. Himpe,
 * and are likewise released into the Public Domain by:
 *
 * Russell W. Ranshaw
 *
 * For more information, visit:
 *  http://www.ping.be/~ping0751/i2cfaq/i2cindex.htm
 *
 */

/* 
 * I2Cinit is to be called immediately after power up.
 * This is normally the only I2C routine to be called 
 * directly by the application.
 */

void I2Cinit (void) {
	int n;

	I2Chighsda ();
	I2Clowscl ();

	for (n = 0; n < 3; n++) {
		I2Cstop ();
	}
}

void I2Cstart (void) {
	I2Chighscl ();
	I2Chighsda ();
	I2Clowsda ();
	I2Clowscl ();
	I2Chighsda ();
}


void I2Cstop (void) {
	I2Clowsda ();
	I2Clowscl ();
	I2Chighsda ();
}

int I2Cgetbyte(void)
{
	int i_byte = 0, n;

	SetInputPort (SDA);

	for (n=0; n<8; n++)
	{
		I2Chighscl();
		
		if (GetPortBit (SDA, SDABIT))
		{
			i_byte = (i_byte << 1) | 0x01; /* msbit first */
		}
		else
		{
			i_byte = i_byte << 1;
		}

		I2Clowscl();
	}


	I2Chighsda ();
	return(i_byte);
}

void I2Cputbyte(int o_byte)
{
	int n;

	for(n=0; n<8; n++)
	{
		if(o_byte&0x80)
		{
			I2Chighsda();
		}
		else
		{
			I2Clowsda();
		}

		I2Chighscl();
		I2Clowscl();
		o_byte = o_byte << 1;
	}

	I2Chighsda();
}


void I2Cgiveack(void)
{
	I2Clowsda(); 
	I2Chighscl();
	I2Clowscl();
	I2Chighsda();
}

void I2Cgetack (void) {
	int n;

	I2Chighsda ();
	I2Chighscl ();

	SetInputPort (SDA);

	/* Wait until Slave pulls SDA low */
	/* Note:  The pseudocode does not have the for loop.  
	 * It was added to prevent a lock up situation. 
	 *
	 * Actually, there should be more error checking and reporting
	 * in this code.  For example, this routine should indicate a
	 * missed ACK.
	 */

	for (n = 0; n < 100; n--) {
		if (GetPortBit (SDA, SDABIT) == 0)
			break;
	}

	I2Clowscl ();
	SetOutputPort (SDA);
}


void I2Chighsda(void)
{
	SetOutputPort (SDA);
	SetPortBit (SDA, SDABIT);
}

void I2Clowsda(void)
{
	SetOutputPort (SDA);
	ClearPortBit (SDA, SDABIT);
}

void I2Chighscl(void)
{
	SetOutputPort (SCL);
	SetPortBit (SCL, SCLBIT);
}

void I2Clowscl(void)
{
	SetOutputPort (SCL);
	ClearPortBit (SCL, SCLBIT);
}

/*
 * Routine to send an address on the I2C bus.  To indicate
 * adr is a 10-bit address, set the high-order bit (0x8000).
 */
void I2Csendadr (int adr, int rw) {
	I2Cstart ();

	if ((adr & 0x8000) != 0) {
		/* Send two MSBs of the ten bit address */
		I2Cputbyte (0xF0 | rw | ((adr > 8) & 0x06));
		I2Cgetack ();
		I2Cputbyte (adr & 0xFF);
	} else {
		I2Cputbyte (adr | rw);
	}

	I2Cgetack ();
}

/* Read num bytes from device adr into buf */
void I2Cread (int adr, int num, char *buf) {

	I2Csendadr (adr, 1);

	while (num-- > 0) {
		*buf++ = I2Cgetbyte ();

		if (num > 0) I2Cgiveack ();
	}

	I2Cstop ();
}


/* Write num bytes to device adr from buf */
void I2Cwrite (int adr, int num, char *buf) {
	I2Csendadr (adr, 0);

	while (num-- > 0) {
		I2Cputbyte (*buf++);
		I2Cgetack ();
	}

	I2Cstop ();
}


Russ

Have you tried Renewable Energy yet?

Post Reply