【问题标题】:Character Block is not showing the right output in Turbo Assembler字符块未在 Turbo Assembler 中显示正确的输出
【发布时间】:2021-07-19 19:19:04
【问题描述】:

我试图创建一个只有字符串中的字符块的燃油泵,但是当我使用 TASM 编译它时,这是 dosbox 给我的输出。

我存储的数据主要是字符块,其中一些是上下半块,我使用的最多字符是完整块。

.model small
.stack
.data

    fuelpump0 db     "    ▄█████████████████▄$"
    fuelpump1 db     "   █▀                 ▀█$"
    fuelpump2 db     "   █  ▄▄▄▄▄▄▄▄▄▄▄▄▄▄▄  █  ▄▄▄$"
    fuelpump3 db     "   █  █             █  █    ██▄$"
    fuelpump4 db     "   █  █             █  █    ▀██$"
    fuelpump5 db     "   █  █             █  ███▄   █$"
    fuelpump6 db     "   █  █             █  █  ▀▀█ █$"
    fuelpump7 db     "   █  █             █  █    █ █$"
    fuelpump8 db     "   █  ▀▀▀▀▀▀▀▀▀▀▀▀▀▀▀  █    █ █$"
    fuelpump9 db     "   █                   █    █ █$"
    fuelpumpa db     "   █                   █    █ █$"
    fuelpumpb db     "   █                   █    █ █$"
    fuelpumpc db     "   █                   █    █ █$"
    fuelpumpd db     "   █                   █    █ █$"
    fuelpumpe db     "   █                   █    █ █$"
    fuelpumpf db     "   █                   █    ▀█▀$"
    fuelpumpg db     " ▄▄█                   █▄▄$"
    fuelpumph db     " █                       █$"
    fuelpumpi db     " █████████████████████████$"

.code
    begin:
        mov ax, @data
        mov ds,ax

        mov dx, offset fuelpumpn
        mov ah,09h                 
        int 21h

        mov dx, offset fuelpump1
        mov ah,09h
        int 21h

        mov dx, offset fuelpump2
        mov ah,09h
        int 21h

        mov dx, offset fuelpump3
        mov ah,09h
        int 21h


        mov dx, offset fuelpump4
        mov ah,09h
        int 21h


        mov dx, offset fuelpump5
        mov ah,09h
        int 21h

        mov dx, offset fuelpump6
        mov ah,09h
        int 21h

        mov dx, offset fuelpump7
        mov ah,09h
        int 21h

        mov dx, offset fuelpump8
        mov ah,09h
        int 21h

        mov dx, offset fuelpump9
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpa
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpb
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpc
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpd
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpe
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpf
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpg
        mov ah,09h
        int 21h

        mov dx, offset fuelpumph
        mov ah,09h
        int 21h

        mov dx, offset fuelpumpi
        mov ah,09h
        int 21h

        mov ah, 4ch
        int 21h

    end begin

我开始怀疑我的字符是否不是 ASCII 表的一部分,因为它们都是扩展 ASCII 字符的一部分。我希望我能得到一些提示来解决这个问题。

【问题讨论】:

  • 看来您使用的是 utf8 编码。切换到纯 8 位。
  • 您还需要回车和换行才能从一行前进到下一行。
  • 实际字符取决于您的代码页和字体。见wikipedia for codepage 437。确保不要使用 utf8。
  • 将每一行设为单独的字符串是对代码的巨大浪费,尤其是因为您甚至没有使用循环。就像 ecm 所说,使用 CR LF,但在除最后一行之外的每一行的末尾使用 而不是 $。然后一个单一的输出字符串 DOS 调用将循环整个事情。 (当然,您仍然可以在源代码中使用多行代码;DOS 调用不知道也不关心字节是如何进入内存的,只知道它们就在那里。)
  • 类似于Print special character in assembly bootloader。这没有提到 UTF-8,但源代码的复制/粘贴显示它以发布到 SO 的形式使用 UTF-8。如果需要,您可以发布自己对此问题的答案,并附上详细信息以帮助未来的读者解决同样的问题。

标签: assembly dos tasm codepages codepage-437


【解决方案1】:

我解决了这个问题,它可能不是最好的解决方案,但这是我所做的:

  • TASM 能够在扩展 ASCII 表中回显特殊字符,只需简单地键入每个特殊字符的十进制值,例如 ▐ (222)、█ (219)、▀ (223) 和 ▄ (220)。只需确保它们每个都有逗号,并且不能在引号内。

  • 您可以在要存储的每个数据字符串中混合字符串和整数,只需确保为每个字符串和整数添加逗号,并添加 13,10 作为返回键,并在末尾添加“$”。

【讨论】:

  • 以十进制或十六进制写出字符代码是非常合理的,特别是如果您想使用不易处理 CP437 文本文件的编辑器编辑源代码。它将源代码编码完全排除在等式之外,因此源可以是 UTF-8 的纯 ASCII 子集,但代价是使源源不“看起来像”屏幕上的内容,因此您需要 cmets。 (或字符形状的宏定义。)
【解决方案2】:

扭曲的输出来自于

  • 未插入必要的换行符
  • 编辑器和 DOS 控制台之间的代码页不匹配

由于您对燃油泵的表示包含大量图形字符,因此将所有这些替换为正确的扩展 ASCII 代码将相当乏味,并且还会破坏自记录的良好布局。
我建议您将不同的 Block 字符替换为 ASCII 字符集下半部分的相似字符。

将 ▀ (223) 替换为 ' (39)
将 █ (219) 替换为 | (124)
将 ▄ (220) 替换为 , (44)

这样做会产生下一个仍然类似于燃油泵的数据:

fuelpump db     "    ,|||||||||||||||||,", 13, 10
         db     "   |'                 '|", 13, 10
         db     "   |  ,,,,,,,,,,,,,,,  |  ,,,", 13, 10
         db     "   |  |             |  |    ||,", 13, 10
         db     "   |  |             |  |    '||", 13, 10
         db     "   |  |             |  |||,   |", 13, 10
         db     "   |  |             |  |  ''| |", 13, 10
         db     "   |  |             |  |    | |", 13, 10
         db     "   |  '''''''''''''''  |    | |", 13, 10
         db     "   |                   |    | |", 13, 10
         db     "   |                   |    | |", 13, 10
         db     "   |                   |    | |", 13, 10
         db     "   |                   |    | |", 13, 10
         db     "   |                   |    | |", 13, 10
         db     "   |                   |    | |", 13, 10
         db     "   |                   |    '|'", 13, 10
         db     " ,,|                   |,,", 13, 10
         db     " |                       |", 13, 10
         db     " |||||||||||||||||||||||||", 13, 10, 0

当然,现在显示需要一些额外的处理,但这并不重要!

        ...
        mov     si, offset fuelpump
        jmp     Fetch
Subst:  mov     dl, 223   ; TopBlock
        cmp     al, 39    ; SingleQuote
        je      Print
        mov     dl, 219   ; FullBlock
        cmp     al, 124   ; Pipe
        je      Print
        mov     dl, 220   ; BottomBlock
        cmp     al, 44    ; Comma
        je      Print
        mov     dl, al    ; Space (32), Carriage Return (13), Linefeed (10)
Print:  mov     ah, 02h   ; DOS.PrintCharacter
        int     21h
Fetch:  mov     al, [si]
        inc     si
        cmp     al, 0
        jne     Subst
        ...

【讨论】:

    猜你喜欢
    • 2019-01-05
    • 1970-01-01
    • 2023-03-29
    • 2013-05-15
    • 2023-03-26
    • 1970-01-01
    • 2021-10-01
    • 2017-04-04
    • 2015-06-24
    相关资源
    最近更新 更多