Hi,
I have been struggling for the past few days trying to interface an I2C pressure sensor from SensorTechnics with the PIC16F1827. I successfully bit banged the sensor using a Basic Stamp II a few weeks ago so I know that the sensor is working properly. However, even when I convert the bit banging code to the PIC it still doesn't work, so I know I am doing something simple incorrectly.
I can see clock and data when I connect my oscilloscope to the I/O pins so I know their is activity on the ports, but the result is always filled 0's.
I2C DataSheet for Pressure Sensor
DataSheet for the PIC16F1827 chip
- When you use the I2CREAD command does it send a START condition?
- Using this syntax
does the I2CREAD command send the device address? and an along with an Ack, Nak after the two bytes?Code:I2CRead sda,scl,$F1,[result1,result2]
Do I need to use an I2CWRITE command to write the address to the I2C slave after manually generating a START condition myself?
Here is the bit banging codeCode:DEFINE HSER_RCSTA 90h ' Define Receive Port DEFINE HSER_TXSTA 24h ' Define Transmit Port DEFINE HSER_BAUD 9600 ' Decalre 9600 Baud Rate for Serial Port DEFINE OSC 20 scl VAR PORTB.4: TRISB.4 = 1 ' I2C clock input sda VAR PORTB.1: TRISB.1 = 1 ' I2C data input LED VAR PORTB.0 ' Assign name "LED" to PORTB.0 addr VAR Byte ' I2C Address Variable result1 VAR BYTE ' I2C Result Variable result2 VAR BYTE ' I2C Result Variable result VAR WORD ADDR = %11110001 'Reset Digi Xbee Module LOW PORTB.3 HIGH PORTB.3 mainloop: ' *** Flash LED (HeartBeat) High LED ' Turn on LED connected to PORTB.0 Pause 1000 ' Delay for .5 seconds ' *** Read I2C Low LED ' Turn off LED connected to PORTB.0 Pause 1000 ' Delay for .5 seconds TRISB.1 = 1 TRISb.4 = 1 HIGH SDA HIGH SCL LOW sda I2CRead sda,scl,addr,[result1,result2], i2c_error PAUSE 1000 ' Pause 1 Second for Read Operation to complete HSEROUT ["Value:", BIN8 result1, BIN8 result2] ' Output Pressure reading through Serial Port Goto mainloop ' Go back to loop and blink LED forever End ' Trasnmit Error if Reading unable to occur i2c_error: HSEROUT ["Error"] GOTO mainloop
Any help would be appreciated, thanks in advance!Code:DEFINE HSER_RCSTA 90h ' Define Receive Port DEFINE HSER_TXSTA 24h ' Define Transmit Port 'DEFINE HSER_SPBRG 129 DEFINE OSC 20 DEFINE HSER_BAUD 9600 ' Declare 9600 Baud Rate for Serial Port 'Include Basic Stamp II Command Support INCLUDE "modedefs.bas" ' ------------------------------------------------------------------------------ ' ' I/O Definitions ' ------------------------------------------------------------------------------ ' SDA VAR PORTB.1 ' I2C serial data line SCL VAR PORTB.4 ' I2C serial clock line ' ------------------------------------------------------------------------------ ' ' Constants ' ------------------------------------------------------------------------------ ' Ack CON 0 ' acknowledge bit Nak CON 1 ' no ack bit slaveAddress CON %11110001 'SensorTechnics Slave Address ' ------------------------------------------------------------------------------ ' ' Variables ' ------------------------------------------------------------------------------ ' i2cData VAR Word ' data to/from device i2cWork VAR Byte ' work byte for TX routine i2cAck VAR Bit ' Ack bit from device ' ------------------------------------------------------------------------------ ' ' Initialization '------------------------------------------------------------------------------ ' Init: PAUSE 250 i2cACK = 0 ' Reset XBee LOW PORTB.3 HIGH PORTB.3 TRISB.1 = 0 TRISB.4 = 0 PAUSE 5000 ' ------------------------------------------------------------------------------ ' ' Program Code ' ------------------------------------------------------------------------------ ' Main: GOSUB Read_Word Hserout ["Current Pressure Reading (16 BITS): " , BIN16 i2cData] PAUSE 1000 GOTO Main END ' ------------------------------------------------------------------------------ ' ' SensorTechnics Access Subroutines ' ------------------------------------------------------------------------------ ' ' Read i2cData (16 bits) from Sensor Read_Word: GOSUB I2C_Start ' Send START Condition i2cWork = slaveAddress ' Set Slave Address GOSUB I2C_TX_Byte ' Send Slave Address GOSUB I2C_RX_Byte i2cData.HIGHBYTE = i2cWork ' Read high byte of data / send ack GOSUB I2C_RX_Byte_Nak i2cData.LOWBYTE = i2cWork ' Read low byte of data /send nack GOSUB I2C_Stop ' Send STOP Command RETURN ' ------------------------------------------------------------------------------ ' ' Low Level I2C Subroutines ' ------------------------------------------------------------------------------ ' ' --- Start --- I2C_Start: ' I2C start bit sequence TRISB.1 = 1 TRISB.4 = 1 'HIGH SDA ' Pull SDA High 'HIGH SCL ' Pull SCL High LOW SDA ' SDA -> low while SCL high Hserout ["Waiting for Clock"] Clock_Hold: IF (PORTB.4 = 0) THEN Clock_Hold ' device ready? PAUSE 500 RETURN ' --- Transmit --- I2C_TX_Byte: SHIFTOUT SDA,SCL,MSBFIRST,[i2cWork\8] ' send byte to device SHIFTIN SDA,SCL,MSBPRE,[i2cAck\1] ' get acknowledge bit RETURN ' --- Receive --- I2C_RX_Byte_Nak: i2cAck = Nak ' no Ack = high GOTO I2C_RX I2C_RX_Byte: i2cAck = Ack ' Ack = low I2C_RX: i2cWork = %00000000 SHIFTIN SDA,SCL,MSBPRE,[i2cWork\8] ' get byte from device SHIFTOUT SDA,SCL,LSBFIRST,[i2cAck\1] ' send ack or nak RETURN ' --- Stop --- I2C_Stop: ' I2C stop bit sequence LOW SDA TRISB.1 = 1 TRISB.4 = 1 HIGH SCL HIGH SDA ' SDA --> high while SCL high RETURN
Ben





Bookmarks