
;                             FILE SERIAL3.ASM
;
;              Sample Program Demonstrating Setup and Use
;              of Internal Serial Port Using Mode 1. This
;              program polls the serial port for incoming
;              characters then sends them back to the  
;              sending program along with a message.
;              The program is initially configured for a
;              baud rate of 9600 but other rates can be
;              used by changing the timer reload values.
;
;              This program uses timer 0 to generate a
;              square wave signal in timer mode 1 (16 bit)
;              which can be turned on or off by sending
;              the character '+' for on and '-' for off.
;
;                     Written By S.C.T.  1/29/99

  $MOD52                        ; Include 8052 Definitions

; ----------  DEFINE Timer 1 Reload Constants ------------

  Rate9600      EQU  0FDh       ; 9600 Baud Setup
  Rate4800      EQU  0FAh       ; 4800 Baud Setup
  Rate2400      EQU  0F4h       ; 2400 Baud Setup
  Rate1200      EQU  0E8h       ; 1200 Baud Setup

; ---------- SET A Particular Baud Rate ------------------

  BaudRateCount EQU  Rate9600  ; Setup Timer 1 Reload Value

  ORG  4000h                    ; Start Program at SDK Code Space Base

; ------ INITIALIZE program variables and registers ------

  CLR   EA                      ; Disable Global Interrupts
  MOV   TMOD, #22h              ; Set Timers 0 and 1 for mode 1
                                ; auto reload operation

  MOV   SCON, #50h              ; Setup Serial Port for
                                ; Mode 1 and Enable Receive
  
  MOV   TL1, #BaudRateCount     ; Setup Timer with Desired
  MOV   TH1, #BaudRateCount     ; Baud Rate

  MOV   TL0, #80h               ; Setup Timer 0 Count Interval
  MOV   TH0, #80h                       

  SETB  TR1                     ; Start Timer 1
  SETB  TI                      ; Set XMIT Buffer Empty Flag
  CLR   TR0                     ; Stop Timer 0
  CLR   P1.0                    ; Turn Pin 1.0 Off

; ***************** MAIN PROGRAM LOOP *********************

mainloop:
  JBC   RI,ProcessChar          ; Go to Character Processing Routine
  JBC   TF0,toggle_output       ; Toggle Pin 1.0 output
  JMP   mainloop                ; repeat main loop until bit set

toggle_output:
  CPL   P1.0                    ; Complement P1.0
  JMP   mainloop                ; Return to Loop

ProcessChar:
  MOV   A,SBUF                  ; Retrieve Character From SBUF
  CJNE  A,#2Bh,contproc1        ; Check for '+' character

; The '+' char sent, turn on timer

  SETB  TR0                     ; Start Timer 0

; Send Turn On Message

  MOV   DPTR,#OnMessage         ; Point to On Message
  CALL  SENDSTR                 ; Call String Send Routine
  JMP   exitprocchar            ; Jump to exit of Process Character

contproc1:
  CJNE  A,#2Dh,exitprocchar     ; Check for '-' character

; The '-' char sent, turn off timer

  CLR   TR0                     ; Stop Timer 0

; Send Turn Off Message

  MOV   DPTR,#OffMessage        ; Point to Off Message
  CALL  SENDSTR                 ; Call String Send Routine

exitprocchar:
  JMP   mainloop                ; Return to main loop

; ***********************************************************
;               SUBROUTINE SENDSTR  (Send String)
;
;   This subroutine sends a string which is terminated by an
;   ASCII '$' character (24h).
;
;   The String should be stored in the code space and should
;   be pointed to by DPTR on entry to this subroutine.
;
;   This routine saves and restores the accumulator. It also
;   uses R0 but does not save it.
; ************************************************************

SENDSTR:
  PUSH  ACC                     ; Store Accumulator on Stack

sendloop:
  CLR   A                       ; Clear Accumulator
  MOVC  A,@A+DPTR               ; Get Message Byte
  MOV   R0,A                    ; Move character to R0
  XRL   A,#24h                  ; Check for Terminating String
  JZ    exitsendstr             ; A has terminating '$' so exit
  MOV   A,R0                    ; Restore Character from R0
  
loop2:
  JNB   TI,loop2                ; Wait till Transmit Buffer is Empty
  CLR   TI                      ; Clear TI bit

  MOV   SBUF,A                  ; Load Character to XMIT Buffer and Send
  INC   DPTR                    ; Point to Next Character in String
  JMP   sendloop                ; Repeat Loop

exitsendstr:
  POP   ACC                     ; Restore Accumulator
  RET                           ; Return to Calling Code


; *********************** MESSAGES ********************************

OnMessage:
  db    0Dh,0Ah,'Output Timer Started $'

OffMessage:
  db    0Dh,0Ah,'Output Timer Stopped $'

  END

