• AVR Freaks

Impossible I/O result.

Author
Brax10
New Member
  • Total Posts : 17
  • Reward points : 0
  • Joined: 2009/12/23 01:09:53
  • Location: 0
  • Status: offline
2010/01/04 07:35:47 (permalink)
0

Impossible I/O result.

Project with pic 16F1936.
MPLAB IDE 8.43 + HI-TECH C PRO for the PIC10/12/16 MCU family (Lite) V9.65PL1
Step by step debug Pickit 3
backup proto's reacts the same, no hardware connection between pins (megaohms)

RB4 is open and disconnected from everything.
RB5 only has a pulldown resistor (10K) to GND and is disconncted from everything
Very simple code. (first part)

void main(void)
di();
TRISA = 0xFF; // Input
PORTA = 0;

TRISB = 0xFF; // Input
PORTB = 0;
TRISC = 0xFF; // Input
PORTC = 0;

TRISBbits.TRISB4 = 0; // Output
TRISBbits.TRISB5 = 0; // Output

// RESULT AFTER INSTR RB4 RB5

PORTBbits.RB4 = 1; 1 0
PORTBbits.RB4 = 0; 0 0
PORTBbits.RB4 = 1; 1 0

PORTBbits.RB5 = 1; 0 1

PORTBbits.RB4 = 1; 1 0
PORTBbits.RB4 = 0; 0 0
PORTBbits.RB4 = 1; 1 0

PORTBbits.RB5 = 1; 0 1

PORTBbits.RB5 = 0; 0 0


How can this be true?
Is there anything i am doing wrong or anything i can do to futher debug the code.
I hope this is a very simple user error but i can't see which one.


The translation from the C-compiler looks OK.
(from *.lst, only last part of I/O toggeling)

line 382
333+ ;main.c: 382: PORTBbits.RB4 = 1;
334+ 00CB 0020 movlb 0 ; select bank0
335+
336+ 00CC 160D bsf (13),4 ;volatile
337+ line 383
338+ ;main.c: 383: PORTBbits.RB4 = 0;
339+
340+ 00CD 120D bcf (13),4 ;volatile
341+ line 384
342+ ;main.c: 384: PORTBbits.RB4 = 1;
343+
344+ 00CE 160D bsf (13),4 ;volatile
345+ line 386
346+ ;main.c: 386: PORTBbits.RB5 = 1;
347+
348+ 00CF 168D bsf (13),5 ;volatile
349+ line 388
350+ ;main.c: 388: PORTBbits.RB4 = 1;
351+
352+ 00D0 160D bsf (13),4 ;volatile
353+ line 389
354+ ;main.c: 389: PORTBbits.RB4 = 0;
355+
356+ 00D1 120D bcf (13),4 ;volatile
357+ line 390
358+ ;main.c: 390: PORTBbits.RB4 = 1;
359+
360+ 00D2 160D bsf (13),4 ;volatile
361+ line 392
362+ ;main.c: 392: PORTBbits.RB5 = 1;
363+
364+ 00D3 168D bsf (13),5 ;volatile
365 line 394
366 ;main.c: 394: PORTBbits.RB5 = 0;
367
368 00D4 128D bcf (13),5 ;volatile
#1

12 Replies Related Threads

    danish.ali
    Super Member
    • Total Posts : 1714
    • Reward points : 0
    • Joined: 2004/11/16 02:02:02
    • Location: Surrey, UK
    • Status: offline
    RE: Impossible I/O result. 2010/01/04 07:42:46 (permalink)
    +2 (1)
    I haven't bothered to check the data sheet; I'm just reporting a common "gotcha" with PIC pins:

    Do RB4 and RB5 have analog input capability? (ADC or comparator)
    If so, they will power-up in ANALOG mode.
    Unless you explicitly disable the analog mode, the digital input will always read as 0.
    And modifying PORTxBITS.Rxn does a read, sets bit n and then writes back. So any bit other than n will be cleared.

    This *might* be different with the extended 14-bit core, but I suspect not. PIC18 also have a "LAT" register corresponding to each PORT register which does not suffer from this problem.

    Hope this helps,
    Danish
    #2
    Stefan Uhlemayr
    Super Member
    • Total Posts : 4292
    • Reward points : 0
    • Joined: 2005/05/12 12:25:46
    • Location: Germany
    • Status: offline
    RE: Impossible I/O result. 2010/01/04 07:50:23 (permalink)
    0
    ORIGINAL: Brax10

    ... How can this be true? ...
    Well, you've just detected the read-modify-write "feature". The simplest way to solve it you should use the "LATx"-registers (which are available on the enhanced midrange-parts) for doing any write on an output and use the "PORTx"-register only for reading an input.

    An explanation of the rmw-feature you may find in the "HardWare"-gallery, see link in the signature.

    Hope this helps,wink
    Stefan
    #3
    Brax10
    New Member
    • Total Posts : 17
    • Reward points : 0
    • Joined: 2009/12/23 01:09:53
    • Location: 0
    • Status: offline
    RE: Impossible I/O result. 2010/01/04 08:23:58 (permalink)
    0
    Quick test: Solution is indeed working, changing the PORTBbits.RB4 to LATBbits.LATB4 works (same for B5)
    Still reading all of the "features" of RMW

    But may i make the conclusion that writing to portx is wrong on "enhanced midrange-parts" and should generate a compile error?
    (in my example RB4 was an output without any Pullup/down and it changed on modifying RB5)

    everywhere (in the datasheet) i read "Writes to PORTA are actually written to corresponding LATA register"
    If this is not true all existing sample code and own code will not work on enhanced midrange-parts.
    #4
    MBedder
    Circuit breaker
    • Total Posts : 6767
    • Reward points : 0
    • Joined: 2008/05/30 11:24:01
    • Location: Zelenograd, Russia
    • Status: offline
    RE: Impossible I/O result. 2010/01/04 08:35:22 (permalink)
    0
    You do not just write to the port. Your PORTXbits.RXx = 1/0 statements generate bcf/bsf PORTx,bit instructions which are Read-Modify-Write instructions (reading the PORT PIN, modifying, storing to LAT).
    #5
    BobK
    Super Member
    • Total Posts : 1404
    • Reward points : 0
    • Joined: 2008/04/16 12:13:38
    • Location: Worcester, MA
    • Status: offline
    RE: Impossible I/O result. 2010/01/04 08:36:17 (permalink)
    0
    There is nothing wrong with writing to the ports.  If youi use these instructions:

        movwf    PORTB
    or
        movwf   LATB

    The effect is the same.
     
    The problem occurs when you use an instruction like:

        bsf     PORTB, 5

    Since this instuction can change only 1 bit, it first reads the port, then sets the bit in the result, then writes this back to the port.  It is the read that causes you problems.  A read from an output port may or may not return the last value you wrote to it.  There are two reasons why it may not.  One is if the bit is set as an analog input, which will cause it to always read 0.  The other if is the pin is sinking or sourcing too much current and cannot maintain it's voltage high or low enough to read correctly, or it has been changed recently (within a few instruction cycles) and has not yet reached the desired voltage.
     
    Bob
    #6
    threedog
    Super Member
    • Total Posts : 998
    • Reward points : 0
    • Joined: 2009/12/04 12:28:11
    • Location: Boise
    • Status: offline
    RE: Impossible I/O result. 2010/01/04 09:08:46 (permalink)
    0

    ORIGINAL: BobK
    or it has been changed recently (within a few instruction cycles) and has not yet reached the desired voltage.


    Such as: the output has a large R/C load and it takes some time before the output reaches the desired level.
    #7
    Brax10
    New Member
    • Total Posts : 17
    • Reward points : 0
    • Joined: 2009/12/23 01:09:53
    • Location: 0
    • Status: offline
    RE: Impossible I/O result. 2010/01/05 02:29:12 (permalink)
    0
    Still not Ok.
    We've been using pic's since we started to debug windowed pic16c55.
    The last three posts of MBedder, BobK and threedog are known and exactly what i expect (and what we have been seeing with all our previous PIC projects).

    If B4 and B5 are outputs, and B4 is set high (no external connection now) how can it change to low by a rmw instruction?
    In my original schematic B4 even had a weak pull-up and even then it changed to low when B5 was set.

    So everything about the rmw worked on previous projects but now with the PIC16F1936 it doesn't (and it should according to your posts and the datasheet)

    don't get me wrong i am not trying to get an useless discussion but am i still missing something.

    and as i wrote before the LAT solution is indeed working, changing the PORTBbits.RB4 to LATBbits.LATB4 works (same for B5) so i will be using this, but the question remains about the rmw version.
    post edited by Brax10 - 2010/01/05 02:30:12
    #8
    danish.ali
    Super Member
    • Total Posts : 1714
    • Reward points : 0
    • Joined: 2004/11/16 02:02:02
    • Location: Surrey, UK
    • Status: offline
    RE: Impossible I/O result. 2010/01/05 03:14:44 (permalink)
    0
    PIC16F1936 has analog capability on RB4 and RB5

    My original assertion (carried over from earlier PICs) was that unless you configure the inputs to be digital, then digital reads of the port will return 0.

    Have you tried configuring them to be digital?
    Looking at the datasheet, I see that you need to set up ANSELB to be 0b00xxxx to program RB4 and RB5 to be digital inputs (as well as setting up TRISB appropriately). The power-on value is 0b111111 (only 6 bits wide).

    Please try this.
     - Danish
    #9
    Brax10
    New Member
    • Total Posts : 17
    • Reward points : 0
    • Joined: 2009/12/23 01:09:53
    • Location: 0
    • Status: offline
    RE: Impossible I/O result. 2010/01/05 03:39:15 (permalink)
    0
    ORIGINAL: danish.ali

    Please try this.
    - Danish

    Solved!
    I read your solution yesterday but for one reason i stopped reading the data sheet after:
    The state of the ANSELB bits has no affect on digital output functions.

    However there was indeed more (including sample code):
    A pin with TRIS clear and ANSELB set will still operate as a digital output, but the Input mode will be analog. This can cause unexpected behavior when executing read-modify-write instructions on the affected port.
     
    Maybe because the datasheet constantly talks over digital inputs (highlighted section) and the post about read-modify-write "feature" it went wrong for me.
    However learned another lesson and from now on i will always initialize the ANSELx (if available) register for every I/O pin.
     
     
    post edited by Brax10 - 2010/01/05 03:44:19
    #10
    Stefan Uhlemayr
    Super Member
    • Total Posts : 4292
    • Reward points : 0
    • Joined: 2005/05/12 12:25:46
    • Location: Germany
    • Status: offline
    RE: Impossible I/O result. 2010/01/05 04:47:40 (permalink)
    0
    ORIGINAL: Brax10

    ...
    I read your solution yesterday but for one reason i stopped reading the data sheet after:
    The state of the ANSELB bits has no affect on digital output functions.

    However there was indeed more (including sample code):
    A pin with TRIS clear and ANSELB set will still operate as a digital output, but the Input mode will be analog. This can cause unexpected behavior when executing read-modify-write instructions on the affected port.
     
    Maybe because the datasheet constantly talks over digital inputs (highlighted section) and the post about read-modify-write "feature" it went wrong for me.
    You're right, this cause (pin still in analog-input-mode) for the "read-modify-write-feature" is missing in the post in the hardware-gallery.[8|] I will add a link to Danish's pretty fine explanation in post #2 to this gallery.
    ORIGINAL: Brax10

    However learned another lesson and from now on i will always initialize the ANSELx (if available) register for every I/O pin.
    Good idea, and don't limit your initializations to the ANSELx-registers, some PIC's require the configuration of the CMCON-register for example, too.wink

    Greetings,
    Stefan
    #11
    danish.ali
    Super Member
    • Total Posts : 1714
    • Reward points : 0
    • Joined: 2004/11/16 02:02:02
    • Location: Surrey, UK
    • Status: offline
    RE: Impossible I/O result. 2010/01/05 05:38:47 (permalink)
    0
    Hi Stefan,

    Whilst I am flattered, I do not think my explanation was particularly good because I did not go into why analog mode disables digital input, and why PICs power-up in analog mode.

    Microchip made a conscious engineering decision to disable digital inputs for any pin that has (or might have) an analog voltage on it.

    It is all to do with how a digital input buffer (think of it as a CMOS inverter) behaves with analog signals.
    With an input that is not clearly high or low but somewhere between (i.e. an analog voltage), both input transistors turn on and the circuit draws current from the power supply.
    This wastes significant power - PICs would never achieve their impressively-low power-consumption if you apply an analog voltage with the digital input enabled. In a particularly low-power circuit, there might not be enough power for a PIC to get out of reset and actually configure pins as analog or digital, so pins start as analog.

    There is a further problem in that the (internal) output of the input buffer might feed back and cause oscillations when an input is very close to the logic threshold. This might cause unexpected behavior, possibly including permanent damage to the PIC. Whilst I do not believe such damage is likely, I respect those who have made such claims (other contributors to Microchip forum).

    An exception to the risk of oscillations is when an input has a Schmitt trigger. But such a digital input will still burn power when faced with an "analog" voltage.

    Regards,
    Danish

    ORIGINAL: Stefan Uhlemayr

    You're right, this cause (pin still in analog-input-mode) for the "read-modify-write-feature" is missing in the post in the hardware-gallery.[8|] I will add a link to Danish's pretty fine explanation in post #2 to this gallery.

    #12
    Stefan Uhlemayr
    Super Member
    • Total Posts : 4292
    • Reward points : 0
    • Joined: 2005/05/12 12:25:46
    • Location: Germany
    • Status: offline
    RE: Impossible I/O result. 2010/01/05 12:12:59 (permalink)
    0
    ORIGINAL: danish.ali

    Hi Stefan,

    Whilst I am flattered, I do not think my explanation was particularly good because I did not go into why analog mode disables digital input, and why PICs power-up in analog mode. ...
    Well, it was good enough for explaining, why rmw-instructions will fail, if analog-mode on the pin's isn't disabled, while non-rmw-instructions like "movwf PORTx" will still work fine. I wasn't aware of this point, as I'm making the pin's with analog-feature always digital if I don't need them as analog-ones.

    Anyway, your last answer for the question, "why pin's are analog by default" is even more detailled then Ric's post, so I will change this link in the hw-gallery, too.

    Thanks for your efforts,Smile
    Stefan
    #13
    Jump to:
    © 2019 APG vNext Commercial Version 4.5