COM1_GetTxCount  and  COM1_GetTxFree

Purpose: Determine how many BYTEs (or characters) are enbuffered in the COM1 Transmit Buffer OR
how many unused character positions are open in the COM1 Transmit Buffer.
Assumes:   Nothing.
Passed: Nothing.
Returns: R24   BYTE   bCount   how many BYTEs are in the Transmit Buffer OR
how many BYTEs could be written to the Transmit Buffer without blocking
Alters: R25, R30, R31, and the FLAGs (SREG)
 

COM1_TxPeekHead  and  COM1_TxPeekTail

Purpose: COM1_TxPeekTail: get the first (i.e., next out) BYTE in the COM1 Trasmit Buffer OR
COM1_TxPeekHead: get the last (most recently placed) BYTE in the COM1 Transmit Buffer.
Assumes:   Nothing.
Passed: Nothing.
Returns: R24   BYTE   bCharacter   The BYTE or character in that position; may be (perhaps "most often") 0.
Alters: R25, R30, R31, and the FLAGs (SREG)

Example:  
.ORG  0x3980

ShowTxStata:
   CALL    APushAll               ; A way to use R2 through R6 as a temporary
   CALL    ACOM1_GetTxCount       ;  tiny data passing buffer
   MOV     R4, R24
   CALL    ACOM1_GetTxFree
   MOV     R5, R24                ; These are our variables of interest
   CALL    ACOM1_TxPeekHead
   MOV     R6, R24
   CALL    ACOM1_TxPeekTail
   LDI     R31, bCOM1TxHeadPtr >> 8      ; Point to the Low Order BYTEs of the
   LDI     R30, bCOM1TxHeadPtr & 0xFF    ;  COM1 Transmit Buffer FIFO pointers

StatusMerge:
   MOV     R7, R24                ; Store the last BYTE obtained
   LD      R2, Z                  ; Load R2 and R3 with the Low Order BYTEs
   LDD     R3, Z+1                ;  of the Buffer FIFO pointers
   LDI     R25, 0x0002 >> 8       ; SRAM address 0x0002 selects Register R2
   LDI     R24, 0x0002 & 0xFF     ;  as the starting point
   LDI     R22, 6                 ; Set the number of BYTEs to display
   LDI     R20, PORTC             ; Set the PORT and PIN to use
   LDI     R18, 1 << PORTC2       ; This is the bit pattern B00000100 (= 4)
   CALL    AWS2812_GRBDebugRange  ; User routine; see the WS2812_Command page
   RJMP    ALocalPopAll           ;  (same location as above)
Test it: Attach an 8x8 WS2812 GRB LED array to one of the outputs and power it in order to view the example below. This is a real-time debugging tool using WS2812 LEDs that can be used for other purposes (i.e., other data.) Although it does slow the system down a little, it should still be responsive and very functional. This is perhaps the least intrusive way of debugging this type of thing. Be sure to disable this demo code when done testing in order to restore (or improve) system performance.
An example of that device is the Adafruit® NeoPixel NeoMatrix, Product ID 1487 or 2612.
m>@ 0x3980
m>@ 0x3980         ; Note the change in the first two rows of LEDs
m>@ 0x3980         ; These are the FIFO Head pointer and Tail pointer
>                  ; Logout (not required, but shortens lines)
>EW 0x42 = 0x3980  ; Set the EEbEachMain_UVIndex ("each main") pointer
>E 1 ^= 4          ; Update the display on each pass through main()
>; The timers (e.g., seconds tick) still perform their normal timing,
>E 0x19 = 0x25     ; To demonstrate this, first set EEbLED_Heartbeat
>                  ; Notice what happens when BYTEs are transmitted:
>E
>                                                                              
Notes: The Operating System handles COM1 Transmit buffering as a circular FIFO queue.
Its *bHead (SRAM address 0x180) is the LSByte of the address of the next available position in the queue.
Its *bTail (SRAM address 0x181) is the LSByte of the address of the first (oldest) BYTE in the queue.
Technically, reading *bHead would get garbage, since it points the NEXT position, but the COM1_TxPeekHead backs up one BYTE, to read the prior BYTE, which can then mean reading from a higher address, since it is implemented as a circular queue.
When *bHead = *bTail, there is nothing in the COM1 Transmit queue, in which case both COM1_TxPeekHead and COM1_TxPeekTail return 0.
These are the most useful when trying to decide whether to call a serial output routine or wait, as the background SRAM, EEPROM and FLASH display routines do.
Dropin: 
(setup
code)
;   Setup for the COM1_GetTxCount() or COM_GetTxFree() call:
; Passed:  Nothing.
; Returns: R24 BYTE bCount number of BYTEs either enbuffered or available
; Alters:  R25, R30, R31, and the FLAGs

;   Setup for the COM1_TxPeekHead() or COM1_TxPeekTail call:
; Passed:  Nothing.
; Returns: R24 BYTE bChar BYTE at the head or tail of the FIFO (0 if empty)
; Alters:  R25, R30, R31, and the FLAGs
Also see:  The COM1 Receive Status group and the WS2812 System Functions, the EEbSystemMode configuration variable, and the EEfptrEachMain routine pointer.
The WS2812ComStat.Asm file has the complete source code for this example, with both COM1 Transmit and Receive stata and the WS2812 access subroutine.