source: xtideuniversalbios/trunk/Assembly_Library/Src/Display/DisplayFormat.asm @ 223

Last change on this file since 223 was 223, checked in by krille_n_@…, 12 years ago

Changes:

  • Fixed what appears to be a mistake in EBIOS.inc
  • Added a 'release' option to the makefile of the Serial Server (invokes UPX)
  • Some very minor optimizations
  • Removed the eSEG macro and did some other cleanups (fixed typos etc)
File size: 11.1 KB
RevLine 
[41]1; Project name  :   Assembly Library
2; Description   :   Functions for displaying formatted strings.
3
4; Section containing code
5SECTION .text
6
7;--------------------------------------------------------------------
8; DisplayFormat_ParseCharacters
9;   Parameters:
10;       DS:     BDA segment (zero)
[44]11;       SS:BP:  Pointer to first format parameter (-=2 updates to next parameter)
[41]12;       CS:SI:  Pointer to string to format
13;       ES:DI:  Ptr to cursor location in video RAM
14;   Returns:
[44]15;       CS:SI:  Ptr to end of format string (ptr to one past NULL)
[41]16;       DI:     Updated offset to video RAM
17;   Corrupts registers:
[44]18;       AX, BX, CX, DX, BP
[41]19;--------------------------------------------------------------------
20ALIGN JUMP_ALIGN
21DisplayFormat_ParseCharacters:
[44]22    call    ReadCharacterAndTestForNull
[101]23    jz      SHORT ReturnFromFormat
[44]24
25    ePUSH_T cx, DisplayFormat_ParseCharacters   ; Return address
26    xor     cx, cx                              ; Initial placeholder size
27    cmp     al, '%'                             ; Format specifier?
[101]28    jne     SHORT DisplayPrint_CharacterFromAL
29    ; Fall to ParseFormatSpecifier
[44]30
[41]31;--------------------------------------------------------------------
[44]32; ParseFormatSpecifier
[41]33;   Parameters:
[44]34;       CX:     Placeholder size
35;       DS:     BDA segment (zero)
36;       SS:BP:  Pointer to first format parameter (-=2 for next parameter)
37;       CS:SI:  Pointer to string to format
38;       ES:DI:  Ptr to cursor location in video RAM
39;   Returns:
40;       SI:     Updated to first unparsed character
41;       DI:     Updated offset to video RAM
42;       BP:     Updated to next format parameter
43;   Corrupts registers:
44;       AX, BX, CX, DX
45;--------------------------------------------------------------------
46ParseFormatSpecifier:
47    call    ReadCharacterAndTestForNull
48    call    Char_IsDecimalDigitInAL
[101]49    jc      SHORT ParsePlaceholderSizeDigitFromALtoCX
[44]50    call    GetFormatSpecifierParserToAX
51    call    ax              ; Parser function
52    dec     bp
53    dec     bp              ; SS:BP now points to next parameter
[181]54    inc     cx
55    loop    PrependOrAppendSpaces
[101]56ReturnFromFormat:
[44]57    ret
58
59;--------------------------------------------------------------------
[101]60; ParsePlaceholderSizeDigitFromALtoCX
[44]61;   Parameters:
62;       AL:     Digit character from format string
63;       CX:     Current placeholder size
64;       DS:     BDA segment (zero)
65;   Returns:
66;       CX:     Current placeholder size
67;       Jumps back to ParseFormatSpecifier
68;   Corrupts registers:
69;       AX
70;--------------------------------------------------------------------
71ALIGN JUMP_ALIGN
[101]72ParsePlaceholderSizeDigitFromALtoCX:
[44]73    mov     [VIDEO_BDA.displayContext+DISPLAY_CONTEXT.fpCursorPosition], di
74    sub     al, '0'             ; Digit '0'...'9' to integer 0...9
75    mov     ah, cl              ; Previous number parameter to AH
76    aad                         ; AL += (AH * 10)
77    mov     cl, al              ; Updated number parameter now in CX
78    jmp     SHORT ParseFormatSpecifier
79
80
81;--------------------------------------------------------------------
82; ReadCharacterAndTestForNull
83;   Parameters:
[41]84;       CS:SI:  Pointer next character from string
85;   Returns:
86;       AL:     Character from string
87;       SI:     Incremented to next character
88;       ZF:     Set if NULL, cleared if valid character
89;   Corrupts registers:
90;       Nothing
91;--------------------------------------------------------------------
92ALIGN JUMP_ALIGN
[44]93ReadCharacterAndTestForNull:
[223]94    cs lodsb                                ; Load from CS:SI to AL
[41]95    test    al, al                          ; NULL to end string?
96    ret
97
98
99;--------------------------------------------------------------------
[44]100; GetFormatSpecifierParserToAX
[41]101;   Parameters:
[44]102;       AL:     Format specifier character
[41]103;   Returns:
[44]104;       AX:     Offset to parser function
[41]105;   Corrupts registers:
[44]106;       AX, BX
[41]107;--------------------------------------------------------------------
108ALIGN JUMP_ALIGN
[44]109GetFormatSpecifierParserToAX:
110    mov     bx, .rgcFormatCharToLookupIndex
111ALIGN JUMP_ALIGN
112.CheckForNextSpecifierParser:
113    cmp     al, [cs:bx]
114    je      SHORT .ConvertIndexToFunctionOffset
115    inc     bx
116    cmp     bx, .rgcFormatCharToLookupIndexEnd
117    jb      SHORT .CheckForNextSpecifierParser
118    mov     ax, c_FormatCharacter
119    ret
120ALIGN JUMP_ALIGN
121.ConvertIndexToFunctionOffset:
122    sub     bx, .rgcFormatCharToLookupIndex
123    shl     bx, 1               ; Shift for WORD lookup
124    mov     ax, [cs:bx+.rgfnFormatSpecifierParser]
125    ret
[41]126
[44]127.rgcFormatCharToLookupIndex:
[134]128%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[184]129    db      "aIAduxsSct-+%"
[134]130%else
[184]131    db      "IAuxsc-"       ; Required by XTIDE Universal BIOS
[134]132%endif
[44]133.rgcFormatCharToLookupIndexEnd:
134ALIGN WORD_ALIGN
135.rgfnFormatSpecifierParser:
[134]136%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[44]137    dw      a_FormatAttributeForNextCharacter
[134]138%endif
[184]139    dw      I_FormatDashForZero
[44]140    dw      A_FormatAttributeForRemainingString
[134]141%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[44]142    dw      d_FormatSignedDecimalWord
[134]143%endif
[44]144    dw      u_FormatUnsignedDecimalWord
145    dw      x_FormatHexadecimalWord
146    dw      s_FormatStringFromSegmentCS
[134]147%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[44]148    dw      S_FormatStringFromFarPointer
[134]149%endif
[44]150    dw      c_FormatCharacter
[134]151%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[44]152    dw      t_FormatRepeatCharacter
[134]153%endif
[44]154    dw      PrepareToPrependParameterWithSpaces
[134]155%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[44]156    dw      PrepareToAppendSpacesAfterParameter
157    dw      percent_FormatPercent
[134]158%endif
[41]159
[44]160
[41]161;--------------------------------------------------------------------
[44]162; PrependOrAppendSpaces
[41]163;   Parameters:
[44]164;       CX:     Minimum length for format specifier in characters
[41]165;       DS:     BDA segment (zero)
166;       ES:DI:  Ptr to cursor location in video RAM
167;   Returns:
[44]168;       Nothing
[41]169;   Corrupts registers:
170;       AX, BX, CX, DX
171;--------------------------------------------------------------------
172ALIGN JUMP_ALIGN
[44]173PrependOrAppendSpaces:
174    mov     ax, di
175    sub     ax, [VIDEO_BDA.displayContext+DISPLAY_CONTEXT.fpCursorPosition]
176    test    cx, cx
177    js      SHORT .PrependWithSpaces
178    ; Fall to .AppendSpaces
[41]179
180;--------------------------------------------------------------------
[44]181; .AppendSpaces
[41]182;   Parameters:
[44]183;       AX:     Number of format parameter BYTEs printed
184;       CX:     Minimum length for format specifier in characters
[41]185;       DS:     BDA segment (zero)
186;       ES:DI:  Ptr to cursor location in video RAM
187;   Returns:
[44]188;       Nothing
[41]189;   Corrupts registers:
[44]190;       AX, CX, DX
[41]191;--------------------------------------------------------------------
[44]192.AppendSpaces:
193    call    DisplayContext_GetCharacterOffsetToAXfromByteOffsetInAX
194    sub     cx, ax
195    jle     SHORT .NothingToAppendOrPrepend
[41]196    mov     al, ' '
[44]197    jmp     DisplayPrint_RepeatCharacterFromALwithCountInCX
[41]198
199;--------------------------------------------------------------------
[44]200; .PrependWithSpaces
[41]201;   Parameters:
[44]202;       AX:     Number of format parameter BYTEs printed
203;       CX:     Negative minimum length for format specifier in characters
[41]204;       DS:     BDA segment (zero)
205;       ES:DI:  Ptr to cursor location in video RAM
206;   Returns:
[44]207;       Nothing
[41]208;   Corrupts registers:
[44]209;       AX, BX, CX, DX
[41]210;--------------------------------------------------------------------
211ALIGN JUMP_ALIGN
[44]212.PrependWithSpaces:
213    xchg    ax, cx
214    neg     ax
215    call    DisplayContext_GetByteOffsetToAXfromCharacterOffsetInAX
216    sub     ax, cx              ; AX = BYTEs to prepend, CX = BYTEs to move
217    jle     SHORT .NothingToAppendOrPrepend
[41]218
[47]219    std
220    push    si
[41]221
[47]222    lea     si, [di-1]          ; SI = Offset to last byte formatted
223    add     di, ax              ; DI = Cursor location after preceeding completed
224    push    di
225    dec     di                  ; DI = Offset where to move last byte formatted
226    xchg    bx, ax              ; BX = BYTEs to prepend
[48]227    call    .ReverseCopyCXbytesFromESSItoESDI
[47]228    xchg    ax, bx
229    call    .ReversePrintAXspacesStartingFromESDI
230
231    pop     di
232    pop     si
233    cld                         ; Restore DF
234.NothingToAppendOrPrepend:
235    ret
236
237;--------------------------------------------------------------------
[48]238; .ReverseCopyCXbytesFromESSItoESDI
[47]239;   Parameters:
[48]240;       CX:     Number of bytes to copy
[47]241;       DS:     BDA segment (zero)
[48]242;       ES:SI:  Ptr to old location
243;       ES:DI:  Ptr to new location
[47]244;   Returns:
[48]245;       DI:     Updated to before last character copied
[47]246;   Corrupts registers:
247;       AX, CX, DX, SI
248;--------------------------------------------------------------------
249ALIGN JUMP_ALIGN
[48]250.ReverseCopyCXbytesFromESSItoESDI:
251    test    BYTE [VIDEO_BDA.displayContext+DISPLAY_CONTEXT.bFlags], FLG_CONTEXT_ATTRIBUTES
252    jz      SHORT .CopyWithoutDisplayProcessing
[47]253
[48]254    WAIT_RETRACE_IF_NECESSARY_THEN rep movsb
255    dec     di                  ; Point to preceeding character instead of attribute
256    ret
257ALIGN JUMP_ALIGN
258.CopyWithoutDisplayProcessing:
[44]259    eSEG_STR rep, es, movsb
[47]260    ret
261
262;--------------------------------------------------------------------
263; .ReversePrintAXspacesStartingFromESDI
264;   Parameters:
265;       AX:     Number of spaces to print
266;       DS:     BDA segment (zero)
267;       ES:DI:  Ptr to destination in video RAM
268;   Returns:
269;       DI:     Updated
270;   Corrupts registers:
271;       AX, CX, DX
272ALIGN JUMP_ALIGN
273.ReversePrintAXspacesStartingFromESDI:
[44]274    call    DisplayContext_GetCharacterOffsetToAXfromByteOffsetInAX
275    xchg    cx, ax              ; CX = Spaces to prepend
276    mov     al, ' '
[47]277    jmp     DisplayPrint_RepeatCharacterFromALwithCountInCX
[44]278
279
280
281;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
282; Formatting functions
[41]283;   Parameters:
284;       DS:     BDA segment (zero)
[44]285;       SS:BP:  Pointer to next format parameter (-=2 updates to next parameter)
[41]286;       ES:DI:  Ptr to cursor location in video RAM
287;   Returns:
[44]288;       SS:BP:  Points to last WORD parameter used
[41]289;   Corrupts registers:
290;       AX, BX, DX
[44]291;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;
[134]292%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[41]293ALIGN JUMP_ALIGN
[44]294a_FormatAttributeForNextCharacter:
[41]295    mov     bl, [bp]
296    xchg    bl, [VIDEO_BDA.displayContext+DISPLAY_CONTEXT.bAttribute]
[44]297    push    bx
298    push    cx
299    push    di
300    call    DisplayFormat_ParseCharacters   ; Recursive call
301    pop     WORD [VIDEO_BDA.displayContext+DISPLAY_CONTEXT.fpCursorPosition]
302    pop     cx
303    pop     bx
[41]304    mov     [VIDEO_BDA.displayContext+DISPLAY_CONTEXT.bAttribute], bl
[44]305    ret
[134]306%endif
[41]307
308ALIGN JUMP_ALIGN
[44]309A_FormatAttributeForRemainingString:
[41]310    mov     al, [bp]
311    mov     [VIDEO_BDA.displayContext+DISPLAY_CONTEXT.bAttribute], al
[44]312    ret
[41]313
[134]314%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[41]315ALIGN JUMP_ALIGN
[44]316d_FormatSignedDecimalWord:
[41]317    mov     ax, [bp]
[44]318    mov     bx, 10
319    jmp     DisplayPrint_SignedWordFromAXWithBaseInBX
[134]320%endif
[41]321
[223]322ALIGN JUMP_ALIGN
[44]323u_FormatUnsignedDecimalWord:
[41]324    mov     ax, [bp]
325    mov     bx, 10
[44]326    jmp     DisplayPrint_WordFromAXWithBaseInBX
[41]327
328ALIGN JUMP_ALIGN
[44]329x_FormatHexadecimalWord:
[41]330    mov     ax, [bp]
331    mov     bx, 16
332    call    DisplayPrint_WordFromAXWithBaseInBX
333    mov     al, 'h'
[44]334    jmp     DisplayPrint_CharacterFromAL
[41]335
336ALIGN JUMP_ALIGN
[184]337I_FormatDashForZero:
338    mov     ax, [bp]
339    test    ax,ax
[223]340    jnz     u_FormatUnsignedDecimalWord
[184]341    mov     [bp], word g_szDashForZero
342;;; fall-through
[223]343
[184]344ALIGN JUMP_ALIGN
[44]345s_FormatStringFromSegmentCS:
[41]346    xchg    si, [bp]
347    call    DisplayPrint_NullTerminatedStringFromCSSI
[44]348    mov     si, [bp]
349    ret
[41]350
[134]351%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[41]352ALIGN JUMP_ALIGN
[44]353S_FormatStringFromFarPointer:
354    mov     bx, [bp-2]
[41]355    xchg    si, [bp]
356    call    DisplayPrint_NullTerminatedStringFromBXSI
[44]357    mov     si, [bp]
358    dec     bp
359    dec     bp
360    ret
[134]361%endif
[41]362
363ALIGN JUMP_ALIGN
[44]364c_FormatCharacter:
[41]365    mov     al, [bp]
[44]366    jmp     DisplayPrint_CharacterFromAL
[41]367
[134]368%ifndef EXCLUDE_FROM_XTIDE_UNIVERSAL_BIOS
[41]369ALIGN JUMP_ALIGN
[44]370t_FormatRepeatCharacter:
371    push    cx
[41]372    mov     cx, [bp-2]
373    mov     al, [bp]
374    call    DisplayPrint_RepeatCharacterFromALwithCountInCX
[44]375    pop     cx
376    dec     bp
377    dec     bp
378    ret
[41]379
380ALIGN JUMP_ALIGN
[44]381percent_FormatPercent:
[41]382    mov     al, '%'
[44]383    jmp     DisplayPrint_CharacterFromAL
[134]384%endif
[41]385
386ALIGN JUMP_ALIGN
[44]387PrepareToPrependParameterWithSpaces:
388    neg     cx
389    ; Fall to PrepareToAppendSpacesAfterParameter
[41]390
391ALIGN JUMP_ALIGN
[44]392PrepareToAppendSpacesAfterParameter:
393    add     sp, BYTE 2              ; Remove return offset
394    jmp     ParseFormatSpecifier
Note: See TracBrowser for help on using the repository browser.