Continue to Site

Welcome to EDAboard.com

Welcome to our site! EDAboard.com is an international Electronics Discussion Forum focused on EDA software, circuits, schematics, books, theory, papers, asic, pld, 8051, DSP, Network, RF, Analog Design, PCB, Service Manuals... and a whole lot more! To participate you need to register. Registration is free. Click here to register now.

I2C using CCS (PIC16F877A)

Status
Not open for further replies.

Chullaa

Advanced Member level 4
Joined
Aug 27, 2010
Messages
113
Helped
17
Reputation
34
Reaction score
17
Trophy points
1,298
Activity points
2,019
Hi
I am trying to interface external memory 24c02 in proteus 7.7.
But can't figure out what is the problem.

Objective is to Write some data on memory, then retrieve it and display on LCD.

Do i need to add this line in <main.h> file
#use i2c(Master,sda=PIN_C4,scl=PIN_C3)

schematic


Code:
#include "I:\Data\UIT WORK\QL WORK\i2c\code\main.h"

void i2c_dly(void);
void i2c_start(void);
void i2c_stop(void);
unsigned char i2c_rx(char ack);
void i2c_tx(unsigned char d);

void lcd_init();
void lcd_data(char x);
void lcd_comm();
#define rs portc0
#define rw portc1
#define e  portc2

#define SCL     trisc3   // I2C bus
#define SDA     trisc4   //
#define SCL_IN  portc3    //
#define SDA_IN  portc4    //
int     bit0;

void main()
{

   setup_adc_ports(NO_ANALOGS);
   setup_adc(ADC_OFF);
   setup_psp(PSP_DISABLED);
   setup_spi(SPI_SS_DISABLED);
   setup_timer_0(RTCC_INTERNAL|RTCC_DIV_1);
   setup_timer_1(T1_DISABLED);
   setup_timer_2(T2_DISABLED,0,1);
   setup_comparator(NC_NC_NC_NC);
   setup_vref(FALSE);

SDA = SCL = 1;
SCL_IN = SDA_IN = 0;
trise0=0;
TRISD=0x00;
trisc0=0;
trisc1=0;
trisc2=0;
lcd_init();
   // TODO: USER CODE!!
   i2c_start();              // send start sequence
   i2c_tx(0x00);             // SRF08 command register address
   i2c_tx('A');             // command to start ranging in cm
   i2c_stop();               // send stop sequence
   i2c_tx(0x00);
   lcd_data(i2c_rx(true));
}

//We use a small delay routine between SDA and SCL changes to give a clear sequence on the I2C bus. This is nothing more than a subroutine call and return.
void i2c_dly(void)
{
}

//The following 4 functions provide the primitive start, stop, read and write sequences. All I2C transactions can be built up from these.

void i2c_start(void)
{
  SDA = 1;             // i2c start bit sequence
  i2c_dly();
  SCL = 1;
  i2c_dly();
  SDA = 0;
  i2c_dly();
  SCL = 0;
  i2c_dly();
}
void i2c_stop(void)
{
  SDA = 0;             // i2c stop bit sequence
  i2c_dly();
  SCL = 1;
  i2c_dly();
  SDA = 1;
  i2c_dly();
}

unsigned char i2c_rx(char ack)
{
char x, d=0;
  SDA = 1; 
  for(x=0; x<8; x++) {
    d <<= 1;
    do {
      SCL = 1;
    }
    while(SCL_IN==0);    // wait for any SCL clock stretching
    i2c_dly();
    if(SDA_IN) d |= 1;
    SCL = 0;
  } 
  if(ack) SDA = 0;
  else SDA = 1;
  SCL = 1;
  i2c_dly();             // send (N)ACK bit
  SCL = 0;
  SDA = 1;
  return d;
}

void i2c_tx(unsigned char d)
{
char x;
  for(x=8; x; x--) 
  {
    if(d&0x80) SDA = 1;
    else SDA = 0;
    SCL = 1;
    d <<= 1;
    SCL = 0;
  }
  SDA = 1;
  SCL = 1;
  i2c_dly();
  porte0 = SDA_IN;          // possible ACK bit
  bit0 = SDA_IN;
  SCL = 0;
}

void init()
 {
    ADCON1=0X07;               //a port as ordinary i/o.
    TRISA=0X00;                //a port as output.
    TRISD=0X00;                //d port as output.
 }
 void lcd_init()
 {
    PORTD=0X10;                 //clr screen 
    lcd_comm();
    PORTD=0X38;                //8 bits 2 lines 5*7 mode.  
    lcd_comm();
    PORTD=0X0e;                //display on,cursor on,blink on.
    lcd_comm();
    PORTD=0X06;                //character not move,cursor rotate right.
    lcd_comm();
    PORTD=0X80;                //¡°WWW.PIC16.COM"
    lcd_comm();
 }
 void lcd_data(char x)
 {
  PORTD=x;                   //data send to PORTD
  rs=1;                      //is data not command.
  rw=0;                      //is write not read.
  e=0;                       //pull low enable signal.
  delay_ms(5);                   //for a while.
  e=1;                       //pull high to build the rising edge.
 }
 void lcd_comm()
 {
   rs=0;                     //is command not data
   rw=0;                     //is write not read. 
   e=0;                      //pull low enable signal.           
   delay_ms(5);                  //for a while.                      
   e=1;                      //pull high to build the rising edge
 }
 

Status
Not open for further replies.

Similar threads

Part and Inventory Search

Welcome to EDABoard.com

Sponsor

Back
Top