5         copyright John Steggall 2009
 
  11   Copyright 2009  John Steggall (steggall.j@gmail.com)
 
  13   Permission to use, copy, modify, and distribute this software
 
  14   and its documentation for any purpose and without fee is hereby
 
  15   granted, provided that the above copyright notice appear in all
 
  16   copies and that both that the copyright notice and this
 
  17   permission notice and warranty disclaimer appear in supporting
 
  18   documentation, and that the name of the author not be used in
 
  19   advertising or publicity pertaining to distribution of the
 
  20   software without specific, written prior permission.
 
  22   The author disclaim all warranties with regard to this
 
  23   software, including all implied warranties of merchantability
 
  24   and fitness.  In no event shall the author be liable for any
 
  25   special, indirect or consequential damages or any damages
 
  26   whatsoever resulting from loss of use, data or profits, whether
 
  27   in an action of contract, negligence or other tortious action,
 
  28   arising out of or in connection with the use or performance of
 
  34 /* BITLENGTH is the time for a bit cycle worked out at F_CPU / BAUD. Gives a rough but usable figure. Wouldn't like to try
 
  35  * anything faster than 9600! */
 
  60 /*********************************************
 
  63  * RX pin has gone low.
 
  73         sbrc            r16,0           // anti glitch
 
  80         sbrc            r16,0           // just make sure
 
  89         // set trigger for RX timer (will need to add a little more though)
 
 100         // turn off interrupt, will get annoying.
 
 103         // turn on interrupt on compare match
 
 116 /*********************************************
 
 117  * interrupt routine, timer compare match.
 
 121         .global TIMER3_COMPB_vect
 
 130         // check if the last bit was sent
 
 161 // section handles the last bit (stop bit sent/received and sets the flag to say done //
 
 163         lds             r17,status              // get status
 
 164         ori             r17,SF_UART_TX          // set TXC/DRE flag
 
 168         andi            r16,~(1<<OCIE3B)
 
 171         rjmp            lastBitOut              // over and out
 
 175 /*********************************************
 
 176  * interrupt routine, timer compare match.
 
 180         .global TIMER3_COMPC_vect
 
 189         // check if the last bit has been recieved
 
 199         ldi             r18,3                   // set counter to 3
 
 202 //      cbi             0x0B,1                  // marker
 
 215 //      sbi             0x0B,1                  // marker
 
 228         lds             r17,status              // store status
 
 229         lds             r16,PIND                        // get status of stop bit
 
 231         ori             r17,0x02                        // set flag if stop bit was high
 
 234         lds             r16,rxShifter           // get contents of shifter
 
 235         sbrc            r17,1                   // check if we just received a valid byte
 
 236         sts             rxdata,r16              // if valid rxdata = shifter
 
 238         // switch interrupt back on to get another go
 
 240         sbi             0x1C,0                  // clear interrupt flag
 
 241         sbi             0x1D,0                  // enable external interrupt 0 (RX)
 
 243         // switch off rx bit timer
 
 245         andi            r16,~(1<<OCIE3C)
 
 248         rjmp            lastBitOut              // loud and clear
 
 254         subi            r16,lo8(BITLENGTH / 2)
 
 255         sbci            r17,hi8(BITLENGTH / 2)
 
 258         subi            r16,lo8(0xFFFF - BITLENGTH)
 
 259         sbci            r17,hi8(0xFFFF - BITLENGTH)
 
 267 /*********************************************
 
 268  * void SoftUART_Init(void)
 
 270  * initialises software uart and enables transmit
 
 272         .global SoftUART_Init
 
 283         ldi             r18,(1<<SFT_TX_EN)|SF_UART_TX
 
 286         ldi             r18,lo8(BITLENGTH)
 
 287         ldi             r19,hi8(BITLENGTH)
 
 292         ldi             r18,0b00001001                  // ctc count mode, clock div 1
 
 295         // Interrupt on low level INT0
 
 302 /*********************************************
 
 303  * char SoftUART_TxByte(char)
 
 305  * starts a byte send and returns the byte to be sent
 
 307         .global SoftUART_TxByte
 
 312         rjmp            uart_putchar_end
 
 314         andi            r18,0xFE                                                // clear tx empty flag
 
 327         // drop down tx line for start bit
 
 332         // set trigger for tx timer
 
 338         // clear interrupt flag and enable tx interrupt
 
 348 /*********************************************
 
 349  * char SoftUART_RxByte(void)
 
 351  * returns the received byte
 
 353         .global SoftUART_RxByte
 
 363 /*********************************************
 
 364  * char SoftUART_IsReceived(void)
 
 366  * checks if there is a byte in the receive buffer
 
 368         .global SoftUART_IsReceived
 
 377 /*********************************************
 
 378  * char SoftUART_IsReady(void)
 
 380  * Simulates polling UDRE to see if tx buffer is empty and ready
 
 382  * returns 1 if empty 0 if not
 
 384         .global SoftUART_IsReady