Menu

Two analog input problem on 16F877

Help
2014-04-02
2014-04-10
  • Pinocchio Faken

    Pinocchio Faken - 2014-04-02

    Hi guys Good day~

    I'm Pinocchio Faken, this is the first time I use the forum.

    I'm new in GCbasic just a month, and not good in English either....(my mother tongue is Chinese)So I hope you forgive me to make some mistake....

    I've using two LM35(temp sensor) to link on 16F877's PORTA.0 & PORTA.3 and display on 16x2 LCD.
    I'm using ISIS simulator to check it. And it works with an error.

    ISIS

    I've set the two temp sensor to 86℃ & 30℃.
    Then save the converted analog port PORTA.0 & PORTA.3 data in string var cTemp1 & cTemp2.

    PORTA.0 →cTemp1
    PORTA.3 →cTemp2

    And use cTemp0 & cTemp1 to display on LCD screen.

    Print on LCD:
    T1=cTemp0 r T2=cTemp1 r

    The normal state may be T1=86r T2=30r. But the screen shows both 86 on it, here is the problem.

    I think the problem is in ADCON0 register.
    ADCON0 register is used to configure the analog input channel.
    But it is Auto setted in the function ReadAD10().
    So I don't know where the bug is.

    Here's the ADCON register's datasheet.
    ADCON0
    ADCON1

    ===================Here is the code===================

    ;Chip Settings
    #chip 16F877,4

    ;Defines (Constants)
    #define LCD_IO 4
    #define LCD_RS PORTB.0
    #define LCD_NO_RW
    #define LCD_Enable PORTB.1
    #define LCD_DB4 PORTB.2
    #define LCD_DB5 PORTB.3
    #define LCD_DB6 PORTB.4
    #define LCD_DB7 PORTB.5
    #define AnalogA PORTA.0
    #define AnalogB PORTA.3

    ;Variables
    Dim cTemp1 As string
    Dim cTemp2 As string

    STARTUP
    Do Forever

    'Read Analog Input and use var to save it.
    cTemp1 = ReadAD10(AnalogA)*49 / 100
    cTemp2 = ReadAD10(AnalogB)*49 / 100

    'Fill 16 Blank to Second line and move the cursor back.
    Locate 1, 0
    Print " "
    Locate 1, 0

    'Display two Temperature data in second line
    Print "T1="
    Print cTemp1
    Print "r"
    Locate 1, 8
    Print "T2="
    Print cTemp2
    Print "r"
    Wait 1000 ms
    Loop

    Sub STARTUP
    'Set input
    Dir PORTA.0 IN
    Dir PORTE.0 IN

    'Set ADCON1 to 10000010, direct PORTA0~5 to Analog input
    Set ADCON1.ADFM 1
    Set ADCON1.PCFG3 0
    Set ADCON1.PCFG2 0
    Set ADCON1.PCFG1 1
    Set ADCON1.PCFG0 0

    'Set LCDOUT pin
    Dir PORTB b'00000000'
    Wait 500 ms

    'Test Display
    Locate 0, 0
    Print "Temp System"
    Wait 500 ms
    Locate 1, 0
    Print "Good Day!"
    Wait 500 ms
    CLS

    'Display title "Temperature" on first line
    Locate 0, 0
    Print "Temperature"
    End Sub

    ===================End of the code===================

     

    Last edit: Pinocchio Faken 2014-04-02
  • Anobium

    Anobium - 2014-04-02

    Welcome Pinocchio to the forum.

    I think, your issue is the incorrect use of the readadc10 command. I made the same error.

    See http://gcbasic.sourceforge.net/help/readad10.htm You need to use the ANx not the port address. I hope this fixes your issue.

    You code should read

    'Read Analog Input and use var to save it.
    cTemp1 = ReadAD10(AN0)*49 / 100
    cTemp2 = ReadAD10(AN3)*49 / 100
    
     

    Last edit: Anobium 2014-04-02
    • Pinocchio Faken

      Pinocchio Faken - 2014-04-02

      I change it and get the same result.
      I read the #define in gcbasic manual, it just used to define a word(like AN0 or Analog0 et al) to replace object or pin.
      So I think that is not the problem on this case.
      I guess the problem is on ADCON0's chennal select.
      But I have no idea to on assembly code...

       
  • Anonymous

    Anonymous - 2014-04-02

    Hello,

    Here's some code I wrote a year ago for a book I'm writing. I'm using a PIC16F88 and the similar LM34. Maybe this will give you an idea:

    ;Project 42
    ;A program to read the temperature using the LM34DZ
    ;and display it on an LCD in Fahrenheit.
    
    ;----- Configuration
    
    #chip 16F88, 8              ;PIC16F88 running at 8 MHz
    #config mclr=off            ;reset handled internally
    #config osc=int             ;use internal clock
    
    ;----- Constants
    
    #define LCD_IO      4       ;4-bit mode
    #define LCD_RS      PortB.2 ;pin 8 is Register Select
    #define LCD_Enable  PortB.3 ;pin 9 is Enable
    #define LCD_DB4     PortB.4 ;DB4 on pin 10
    #define LCD_DB5     PortB.5 ;DB5 on pin 11
    #define LCD_DB6     PortB.6 ;DB6 on pin 12
    #define LCD_DB7     PortB.7 ;DB7 on pin 13
    #define LCD_NO_RW   1       ;ground RW line on LCD
    
    ;----- Variables
    
    dim temp1, temp2 as word              
    
    ;----- Program
    
    dir PortA in                ;only A.0 is used
    dir PortB 0b00000011        ;top six bits are outputs
    
    cls
    print "Temperature:"        ;print this on top line
    
    do
      temp2 = readAD10(AN0)     ;get temperature reading
      temp1 = 125 * temp2       ;now alter the scale.
      temp2 = temp1 / 256       ;quotient stored in temp2
      temp1 = temp1 % 256       ;remainder stored in temp1
    
      if temp1 > 127 then       ;is remainder past the midpoint?
        temp2 ++                ;if so, bump to the next degree
      end if
    
      locate 0,13               ;clear old value
      print "   "
      locate 0,13               ;print new value
      print temp2
    
      wait 1 S                  ;update once a second
    loop
    
     
  • Anobium

    Anobium - 2014-04-02

    Just checking. What version of the compiler are you using? The version is shown when you compile the code.

     
    • Pinocchio Faken

      Pinocchio Faken - 2014-04-02

      OK I see.
      I haven't thought about different versions will make mistakes on compiling.
      This is a way to solve the problem.
      I'll try it.

       
  • Anobium

    Anobium - 2014-04-02

    @Pinocchio

    I just looked at your code. I do not think the code here will compile. Did you get any error messages when compiling?

    You variables are incorrect. They should read.

    ;Variables
    Dim cTemp1 As Word
    Dim cTemp2 As Word
    

    You code work in my simulator with these changes.

    Anobium

    Code I used.

      'Chip Settings
      #chip 16F877,4
      ;Defines (Constants)
      #define LCD_IO 4
      #define LCD_RS PORTB.0
      #define LCD_NO_RW
      #define LCD_Enable PORTB.1
      #define LCD_DB4 PORTB.2
      #define LCD_DB5 PORTB.3
      #define LCD_DB6 PORTB.4
      #define LCD_DB7 PORTB.5
      #define AnalogA PORTA.0
      #define AnalogB PORTA.3
      ;Variables
      Dim cTemp1 As Word
      Dim cTemp2 As Word
      STARTUP
      Do Forever
      'Read Analog Input and use var to save it.
      cTemp1 = ReadAD10(AN0)*49 / 100
      cTemp2 = ReadAD10(AN3)*49 / 100
      'Fill 16 Blank to Second line and move the cursor back.
      Locate 1, 0
      Print " "
      Locate 1, 0
      'Display two Temperature data in second line
      Print "T1="
      Print cTemp1
      Print "r"
      Locate 1, 8
      Print "T2="
      Print cTemp2
      Print "r"
      Wait 1000 ms
      Loop
      Sub STARTUP  
      'Set input
      Dir PORTA.0 IN
      Dir PORTE.0 IN
    
      Dir PORTB b'00000000'
      Wait 500 ms
      'Test Display
      Locate 0, 0
      Print "Temp System"
      Wait 500 ms
      Locate 1, 0
      Print "Good Day!"
      Wait 500 ms
      CLS
      'Display title "Temperature" on first line
      Locate 0, 0
      Print "Temperature"
      End Sub
    
     
    • Pinocchio Faken

      Pinocchio Faken - 2014-04-02

      I don't see any error messages during compile.
      Whatever!
      Thanks for testing Anobium ~
      I'll try it tomorrow in my own PC.

       
    • Pinocchio Faken

      Pinocchio Faken - 2014-04-07

      I tried the code.
      It has run with same problem using modified code.

      I change the code like this:

      =============================================================
      ;Variables
      Dim cTemp1 As String
      Dim cTemp2 As String

      'Read Analog Input and use string var to save it.
      cTemp1 = str(ReadAD10(AnalogA)* 49 / 100)
      cTemp2 = str(ReadAD10(AnalogB)* 49 / 100)
      =============================================================
      I didn't change others.
      Both I test the dim var with String and word had same display result.

      And as Anobium said the compiler may be affect on these kind of problem.
      I have checked my compiler's version.
      GCGB ver0.9 , download on this page http://gcbasic.sourceforge.net/download.html
      And update with the file "Update-GCGB.ZIP" 23/06/2012

      I also use the IDE in the same download page "GCB@Syn.zip" to compile my code.
      Unfortunately, I got the same error.

       
  • Anobium

    Anobium - 2014-04-07

    Please try. This is the documented method to address the ports - but, this may work for you.

    cTemp1 = str(ReadAD10(AN0) 49 / 100)
    cTemp2 = str(ReadAD10(AN3)
    49 / 100)

     
    • Pinocchio Faken

      Pinocchio Faken - 2014-04-07

      Thanks a lot Anobium, I solve the problem. But not on this way.

      My own PC is working on Windows 7.
      I want to preclude the effect on operating system.
      So I try on my laptop in Windows XP environment.
      And use GCB@Syn to compile the same code.
      It just run in the right way!!
      And I tried all of the code you ask me to change.
      All of them can run correctly. (Include AN0, String, Word, AnalogA ... et al)
      So I think the problem is on .NET framework or something Microsoft-based toolbox...

       
    • Pinocchio Faken

      Pinocchio Faken - 2014-04-10

      Today I try to change the code and do testing again on my own PC (Windows 7 32 bit).
      I found a solution on this troble.
      Move off the analog define code and use AN# to do coding.
      It will run on correct way to do A2D.

      ============Original code start============

      #define AnalogA PORTA.0 ←delete
      #define AnalogB PORTA.3 ←delete

      'Read Analog Input and use var to save it.
      cTemp1 = ReadAD10(AnalogA)49 / 100
      cTemp2 = ReadAD10(AnalogB)
      49 / 100

      ============Original code End ============

      ============Modified code start============

      'deleted
      'deleted

      'Read Analog Input and use var to save it.
      cTemp1 = ReadAD10(AN0) * 49 / 100
      cTemp2 = ReadAD10(AN3) * 49 / 100

      ============Modified code End ============

       

Log in to post a comment.

Want the latest updates on software, tech news, and AI?
Get latest updates about software, tech news, and AI from SourceForge directly in your inbox once a month.