; ======================================================================
; CS617 NUMERIC LIBRARY
; dec_append_u32.inc
;
; Incremental decimal-input primitive for a live key-driven application.
;
; Entry:
;   UDECAPP
;
; Preconditions:
;   $5 contains a numeric digit 0..9 (not ASCII).
;
; Input:
;   $15-$18  current unsigned 32-bit value
;   $5       next decimal digit, 0..9
;
; Output:
;   $15-$18  updated value on success
;             original value unchanged on overflow
;   $4       status:
;               0 = success
;               1 = overflow (> UINT32_MAX)
;
; Operation:
;   new_value = current_value * 10 + digit
;
; Overflow policy:
;   UINT32_MAX = 4294967295
;   Before multiplication:
;       current <  429496729  -> always safe
;       current >  429496729  -> overflow
;       current == 429496729  -> safe only for digit <= 5
;
; Dependencies:
;   UMUL32  from mul_u32_u32.inc
;   UADD32  from add_u32_u32.inc
;
; Historical arithmetic cores are not modified. This routine is new CS617
; composition built on accepted primitives.
;
; Clobbers:
;   $0-$11 as inherited from the arithmetic operations
;   $4 status/saved digit
;   $5-$8 arithmetic operand scratch
;
; $15-$18 are changed only on a successful append.
; ======================================================================

#LIST

UDECAPP:
        LD      $4,$5

; Compare current value with floor(UINT32_MAX/10) = 429496729
; 429496729 = &H19999999.
        LDW     $5,&H9999
        LDW     $7,&H1999

        SBCW    $17,$7
        JR      C,DAPP_SAFE
        JR      NZ,DAPP_OVF

        SBCW    $15,$5
        JR      C,DAPP_SAFE
        JR      NZ,DAPP_OVF

; At the exact threshold, only digits 0..5 are safe.
        SBC     $4,6
        JR      C,DAPP_SAFE
        JR      DAPP_OVF

DAPP_SAFE:
; value *= 10
        LDW     $5,10
        SBW     $7,$7
        CAL     UMUL32

; value += digit
        LD      $5,$4
        LD      $6,0
        SBW     $7,$7
        CAL     UADD32

        LD      $4,0
        RTN

DAPP_OVF:
        LD      $4,1
        RTN
