Hello,
I tried to port this code from a BS2, to get it to work on a 16F877A. I am experiencing erratic
behavior. The display flickers terribly and the values are meaingless. What am I missing?
Code:INCLUDE "Modedefs.Bas" @ Device pic16F877A, HS_OSC, LVP_OFF, WDT_OFF,protect_off DEFINE OSC 20 ; Set port direction and turn off unused peripherals CMCON = 7 ' shut offcomparators TRISA = %00000000 ' Set PORTA to input "1" or output "0" TRISB = %00000000 ' set portB to output "0" or input "1" TRISC = %00000000 TRISD = %00000000 TRISE = %00000000 ; initialize all ports to low portA = %00000000 portB = %00000000 portC = %00000000 portD = %00000000 portE = %00000000 ; define LCD 4 line x 20, 4 bit interface Define LCD_DREG PORTD Define LCD_DBIT 0 Define LCD_RSREG PORTD Define LCD_RSBIT 4 Define LCD_EREG PORTD Define LCD_EBIT 5 Define LCD_BITS 4 Define LCD_LINES 4 define LCD_COMMANDUS 1500 DEFINE LCD_DATAUS 44 'main2: ' Lcdout $fe, 1, $fe, $80 ' Clear LCD screen ' Lcdout $FE, $80, "testing" ' Pause 2000 ' Wait .5 second ' goto main2 ' -----[ Pins/Constants/Variables ]------------------------------------------- SDA VAR portB.0 ' PB0 transceives to/from SDA SCL VAR portB.1 ' PB1 sends clock pulses HMC6352_READ CON $43 ' HMC6352 read address HMC6352_WRITE CON $42 ' HMC6352 write address GET_HEADING CON $41 ' Read in the calculated heading START_CALIB CON $43 ' Start the calibration routine END_CALIB CON $45 ' Finish the calibration routine Heading VAR Word ' Heading read from compass I2C_DATA VAR Byte ' Temporary I2C variable I2C_LSB VAR Bit ' Temporary I2C variable ' -----[ Main Routine ]------------------------------------------------------- DO pause 500 GOSUB Compass_Get_Heading ' Get angle ;DEBUG HOME, "Heading = ", DEC Heading / 10, " degrees" ' Print aingle Lcdout $fe, 1, $fe, $80 ' Clear LCD screen Lcdout $FE, $80, "Heading = ", DEC Heading / 10, " deg" LOOP ' -----[ Subroutines ]-------------------------------------------------------- Compass_Get_Heading: ' Compass module subroutine GOSUB I2C_Start ' Start communications on the I2C buss I2C_DATA = HMC6352_WRITE GOSUB I2C_Write ' Address the HMC6352 in write mode I2C_DATA = GET_HEADING GOSUB I2C_Write ' Send the get heading command GOSUB I2C_Stop ' End communications on the I2C buss GOSUB I2C_Start ' Start communications on the I2C buss I2C_DATA = HMC6352_READ GOSUB I2C_Write ' Address the HMC6352 in read mode PAUSE 6 ' Give the HMC6352 time to calculate the heading GOSUB I2C_Read Heading.HIGHBYTE = I2C_DATA ' Read in the high byte GOSUB I2C_ACK GOSUB I2C_Read Heading.LOWBYTE = I2C_DATA ' Read in the low byte GOSUB I2C_NACK GOSUB I2C_Stop ' End communications on the I2C buss RETURN I2C_Start: LOW SDA ' Pull SDA low LOW SCL ' Pull SCL low RETURN I2C_Stop: LOW SDA ' Pull SDA low INPUT SCL ' Let SCL float high INPUT SDA ' Let SDA float high RETURN I2C_ACK: LOW SDA ' Pull SDA low INPUT SCL ' Let SCL float high LOW SCL ' Pull SCL low INPUT SDA ' Let SDA float high RETURN I2C_NACK: INPUT SDA ' Let SDA float high INPUT SCL ' Let SCL float high LOW SCL ' Pull SCL low RETURN I2C_Read: SHIFTIN SDA, SCL, MSBPRE, [I2C_DATA] ' Read in 8 bits, MSB first RETURN I2C_Write: I2C_LSB = I2C_DATA.BIT0 ' Store the status of the LSB I2C_DATA = I2C_DATA / 2 SHIFTOUT SDA, SCL, MSBFIRST, [I2C_DATA\7] ' Write out the first 7 bits, MSB first IF I2C_LSB THEN INPUT SDA ELSE LOW SDA ' Write the 8th bit endif INPUT SCL ' Using an open collector output LOW SCL INPUT SDA ' Leave SDA as an input INPUT SCL ' Ignore the ACK bit LOW SCL RETURN




Bookmarks