Announcement

Collapse
No announcement yet.

Disable transmit on serial port

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

  • Disable transmit on serial port

    Hi all,
    on my PIC18f67K22 I use the serial port2 as a debug line to output comments during program execution.
    So here and there I have an "Hserout2 ["I'm doing this",13,10]
    Also I receive data from a terminal connected to serial port2 (I use Instant_Interrupt by the great Darrel R.I.P.).

    Now I need that when some condictions occours, all the Hserout2 line are skipped and no strings come out from serial port2, while receiving continues to work. Lets' say this is a "ghost mode".
    Then, I need that when I receive a particular string in the serial port2, the Hserout2 debug line is re-enabled and works again.

    Look like it is simple by disabling the TX on the serial port2 -->> txsta2.5=0 but it doesnt't work and the program enter in a strange condition that I still have to understand. Looks like it freezes somewhere.

    Do you have another smart idea on how to stop Hserout2 ?
    p.s. I can't put a "If then" in every parto f the code where I use Hserout2, too much job.

  • #2
    Originally posted by marcick View Post
    Look like it is simple by disabling the TX on the serial port2 -->> txsta2.5=0 but it doesnt't work and the program enter in a strange condition that I still have to understand. Looks like it freezes somewhere.
    When you set TXEN = 0 (TXSTA2.5) that clears the TXIF status flag, and the first thing the library does is loop waiting for TXIF to be set so it can load the TXREG2, creating an infinite loop:

    From PBPPIC18.LIB and PBPPI18L.LIB files:
    Code:
    HSEROUT2 movlb    15        ; Set bank select to 15 to pick up any SFRs not in Access bank
    hserout2loop CLRWDT?        ; Keep Watchdog clear
            btfss   PIR3, TX2IF    ; Wait till ready
            bra     hserout2loop
    You could try setting the TX pin to input mode using the TRISG.1 = 1, but all devices don't work the same so having SPEN = 1 may over-ride this. If you do that you would want to have a pullup on the TXD output pin.


    You could always modify the library file(s) to check for TXEN:
    Code:
    HSEROUT2 movlb    15        ; Set bank select to 15 to pick up any SFRs not in Access bank
            btfss   TXSTA2, TXEN   ; **ADDED - check for TXEN set... return if clear
            goto    DUNN                 ; exit
    hserout2loop CLRWDT?        ; Keep Watchdog clear
            btfss   PIR3, TX2IF    ; Wait till ready
            bra     hserout2loop

    Comment


    • #3
      Wow, thanks for a so detailed explanation, now it's clear what happens.
      I am not thrilled to modify the library. Maybe I could replace all the Hserout2s with a macro that tests a variable and decides whether to run Hserout2 or not. But maybe it's too complicated.....
      Any other ideas?

      Comment


      • #4
        Did you try setting/clearing TRISG.1 when you want to disable/enable the port?
        As I said, it might not work with this device... didn't try it, but it's worth a shot.

        If you have the pins available you could also run the TXD output into one of the comparator inputs and then use the CMxOUT as the TXD pin.
        Bit of a kludge since you'd have to setup and enable/disable the comparator output.

        If it were me, I'd modify the library. You'd have to keep a note if you ever update in the future, though.

        Comment


        • #5
          Originally posted by tumbleweed View Post
          Did you try setting/clearing TRISG.1 when you want to disable/enable the port?
          I didn't try yet. I will do all the experiments in the next days and be back here.
          Thank you very much for now :-)

          Comment


          • #6
            Another option (if you don't mind changing the hdw and have a spare IO pin) is to add a resistor inline with the TXD pin (several K ohms), and connect the spare IO pin to the "output" side of the resistor.

            To enable TX set the spare IO pin as an input (TRISx = 1), and to disable the TX output set the IO pin high (LAT = 1, TRIS = 0).

            Comment


            • #7
              Ok I found the time to make some tests.

              Setting Tx pin as an input does not work. Hserout2 continues to send data.

              Modifying the library half works: setting Txsta2.5=0 stop the output and the program run normally, but then Txsta2.5=1 does not restart the output.

              Comment


              • #8
                I don't have a 67K22 handy, so I tried this with an 18F26K22.

                It's dangerous to compare different devices, but one thing I noticed is that after re-enabling TXEN (setting TXSTA2.5=1), it can take a bit of time before the TXIF becomes set again. From what I can tell the time appears to vary with the baudrate setting, so maybe it's related somehow.

                Try adding a several msec delay after setting TXEN and see if that fixes it, perhaps start with 10ms and work down from there (9600 baud is approx 1msec/char)

                Comment


                • #9
                  mmmmhhhh ... looks like it doesn't solve.
                  If TXIF weren't set, the program should be here forever

                  Code:
                  hserout2loop CLRWDT? ; Keep Watchdog clear
                  btfss PIR3, TX2IF ; Wait till ready
                  bra hserout2loop
                  and instead the program run normally after setting again TXSTA2.5=1 (I'm in a loop where I flash a led and I see it) but Hserout2 (in the same loop) no longer works

                  I show you my full code to do this test. I flash a led and wait for a char on the serial port to disable Hserout2. Then, after 5 seconds the Hserout2 should restart to work but not.

                  Code:
                  y=0
                  Main_Loop:
                      Hserin2 50, ML00, [x]
                      if x="z" then
                          Hserout2[13,10,"zzz ... detected",13,10]
                          txsta2.5=0
                          y=1
                      endif
                  
                      if y>0 then y=y+1
                  
                      if y>5 then
                          Txsta2.5=1
                          y=0
                          pause 100
                      endif
                  
                  ML00:
                      pause 1000
                      toggle led
                      Hserout2["loop ",#y,13,10]
                      goto main_loop

                  Comment


                  • #10
                    Try this and see if it has any effect...

                    Code:
                    ; enable clear input overrun error
                    define HSER2_CLROERR 1
                    
                    y=0
                    Main_Loop:
                        Hserin2 50, ML00, [x]
                        if x="z" then
                            Hserout2[13,10,"zzz ... detected",13,10]
                            ; wait for last char to finish and disable TX
                            while TXSTA2.1 = 0 : wend       ; wait TRMT
                            TXSTA2.5 = 0    ; clear TXEN
                            y=1
                        endif
                    
                        if y>0 then y=y+1
                    
                        if y>5 then
                            TXSTA2.5 = 1    ; set TXEN
                            ; wait for TXIF to re-assert
                            while PIR3.4 = 0 : wend     ; wait TX2IF
                            y=0
                            pause 100
                        endif
                    
                    ML00:
                        pause 1000
                        toggle led
                        Hserout2["loop ",#y,13,10]
                        goto main_loop

                    Comment


                    • #11
                      Thanks a lot for your support but ...... it doesn't work ....

                      Comment


                      • #12
                        That figures. Now I'm really curious as to why it doesn't work.

                        I thought I had a board with a 67K22 on it, but it seems not..
                        I do have some 87K22 hdw around somewhere... at least that one shares the same datasheet as the 67.
                        I'll have to do some digging...

                        Comment


                        • #13
                          I finally got around to trying this on an 18F87K22, and the following code works.
                          The trick seems to be to wait for any chars in the TX buffer to be sent before enabling/disabling TXEN.
                          I did this as an output-only test so that no other code interferes with/clouds how it works.

                          Code:
                          ; 18F87K22
                          ; test enabling and disabling uart2 TXEN
                          ; this assumes that HSEROUT2 routine in the PBPPIC18.LIB/PBPPI18L.LIB library
                          ; has been change to add a check for TXEN:
                          ;   HSEROUT2 movlb    15        ; Set bank select to 15 to pick up any SFRs not in Access bank
                          ;        btfss   TXSTA2, TXEN   ; **ADDED - check for TXEN... return if not set
                          ;        goto    DUNN           ; **ADDED
                          ;   hserout2loop CLRWDT?        ; Keep Watchdog clear
                          
                          define OSC 64
                          #define FOSC 64     ; set FOSC=OSC... used by set_intosc
                          
                          ; set baudrate
                          define HSER2_BAUD 115200
                          ; enable clear input overrun error
                          define HSER2_CLROERR 1
                          
                          ; setup K22 intosc
                          call set_intosc
                          
                          ; loop forever... should see "12345678" over and over
                          ; should never see any alpha chars (ie "ABCD")
                          call TX2_enable
                          while (1)
                              hserout2["1234"]
                              call TX2_disable
                              hserout2["ABCD"]    ; tx disabled... should not see this
                              call TX2_Enable
                              hserout2["5678"]
                          wend
                          
                          TX2_Disable:
                              ; wait for any current TX to finish
                              while TXSTA2.1 = 0 : wend       ; wait TRMT
                              ; disable TX
                              TXSTA2.5 = 0                    ; clear TXEN
                              return
                              
                          TX2_Enable:
                              ; wait for any current TX to finish
                              while TXSTA2.1 = 0 : wend       ; wait TRMT
                              ; enable TX
                              TXSTA2.5 = 1                    ; set TXEN
                              ; wait for TXIF to re-assert
                              while PIR3.4 = 0 : wend         ; wait TX2IF
                              return
                          
                          set_intosc:
                              OSCTUNE = 0
                              #if FOSC = 64
                                OSCCON = $70      ; 16 + 4xPLL
                                OSCTUNE.6 = 1     ; enable pll
                              #endif
                              #if FOSC = 32
                                OSCCON = $60      ; 8 + 4xPLL
                                OSCTUNE.6 = 1     ; enable pll
                              #endif
                              #if FOSC = 16
                                OSCCON = $70
                              #endif
                              #if FOSC = 8
                                OSCCON = $60
                              #endif
                              return
                          
                          #CONFIG
                           config RETEN = ON         ; Enabled
                           config INTOSCSEL = HIGH   ; LF-INTOSC in High-power mode during Sleep
                           config SOSCSEL = HIGH     ; High Power SOSC circuit selected
                           config XINST = OFF        ; Disabled
                           config FOSC = INTIO2      ; Internal RC oscillator
                           config PLLCFG = OFF       ; Disabled
                           config FCMEN = OFF        ; Disabled
                           config IESO = OFF         ; Disabled
                           config PWRTEN = OFF
                           config BOREN = SBORDIS    ; Enabled in hardware SBOREN disabled
                           config BORV = 3           ; 1.8V
                           config BORPWR = ZPBORMV   ; ZPBORMV instead of BORMV is selected
                           config WDTEN = OFF        ; WDT disabled in hardware; SWDTEN bit disabled
                           config WDTPS = 1048576    ; 1:1048576
                           config RTCOSC = SOSCREF   ; RTCC uses SOSC
                           config EASHFT = ON        ; Address Shifting enabled
                           config ABW = MM           ; 8-bit address bus
                           config BW = 16            ; 16-bit external bus mode
                           config WAIT = OFF         ; Disabled
                           config CCP2MX = PORTC     ; RC1
                           config ECCPMX = PORTE     ; Enhanced CCP1/3 [P1B/P1C/P3B/P3C] muxed with RE6/RE5/RE4/RE3
                           config MSSPMSK = MSK7     ; 7 Bit address masking mode
                           config MCLRE = ON         ; MCLR Enabled RG5 Disabled
                           config STVREN = ON        ; Enabled
                           config BBSIZ = BB2K       ; 2K word Boot Block size
                           config DEBUG = OFF        ; Disabled
                          #ENDCONFIG

                          Comment


                          • #14
                            Wow, amazing, it works perfectly !
                            Thank you very much guy, would like me to offer you a beer ? (paypal)

                            Comment


                            • #15
                              Great. I was hoping it would work on the 67K22 since they're basically the same. Should probably work on most others too as long as you account for where the PIRx TXIF is located. Plus, some of the other 18F's use different library files.

                              A virtual beer is fine...

                              Comment

                              Working...
                              X