(组件x86实模式)数据被“切断".在程序结束时? [英] (assembly x86 real mode) Data gets "cut off" at the end of the program?

查看:69
本文介绍了(组件x86实模式)数据被“切断".在程序结束时?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

这是(nasm x86实模式)如何在引导加载的扇区中写入/读取字符串的后续操作?

.

我正在为NASM中的x86实模式开发玩具OS. 512B引导扇区将其余代码加载到另一个扇区.问题是程序结束时我似乎空间不足.

I'm working on a toy OS for x86 real mode in NASM. The 512B boot sector loads another sector with the rest of the code. The problem is that I seem to run out of space at the end of the program.

这是源文件的开头:

;;; nasm -f bin -o boot.bin os.asm
;;; qemu-system-x86_64 boot.bin

    bits 16

    section boot, vstart=0x0000

    ;; Load next sector.
    ;; adapted from:
    ;; https://blog.benjojo.co.uk/post/interactive-x86-bootloader-tutorial
    mov ah, 0x02
    mov al, 1   
    mov ch, 0    
    mov cl, 2    
    mov dh, 0   
    mov bx, newsector 
    mov es, bx  
    xor bx, bx
    int 0x13
    jmp newsector:0

    newsector equ 0x0500

    times 510-($-$$) db 0
    db 0x55
    db 0xaa

    section os, vstart=0x0000
    mov ax, newsector
    mov ds, ax

这是源文件的末尾,我在其中存储数据.有一个键盘映射,可根据Dvorak键盘布局转换输入.但是该程序似乎在fu之后被切断".

And here's the end of the source file, where I store the data. There's a keymap to convert input according to the Dvorak keyboard layout. But the program seems to get "cut off" after fu.

    input times 16 db 0
    repl_prompt times 16 db 0

    dvorak db 1

dvorak_keymap:
    db "aa"
    db "nb"
    db "ic"
    db "hd"
    db "de"
    db "yf"
    db "ug"
    db "jh"
    db "gi"
    db "cj"
    db "vk"
    db "pl"
    db "mm"
    db "ln"
    db "so"
    db "rp"
    db "xq"
    db "or"
    db ";s"
    db "kt"
    db "fu"
    db ".v"     ; FIXME: gets cut off here
    db ",w"
    db "bx"
    db "ty"
    db "/z"
    db 0

因此,在启动操作系统时,可以在Dvorak中键入键a-u,但不能键入v-z.此外,在dvorak_keymap字符串上调用程序的print函数可确认该字符串在fu之后终止.

So when you boot the OS, you can type keys a-u in Dvorak but not v-z. Furthermore, calling the program's print function on the dvorak_keymap string confirms that the string terminates after fu.

但更重要的是,这表明我的程序空间不足,因此无法再添加任何数据或代码.我无法达到1 MB的内存限制,因为源文件只有282 sloc.

But more importantly, this indicates that I've run out of space in my program so I can't add any more data or code. I can't have hit the 1 MB memory limit because the source file is only 282 sloc.

我猜测这与我如何加载扇区有关?我是汇编语言和底层编程的新手,所以将非常感谢您的帮助.

I'm guessing it has something to do with how I load the sectors? I'm new to assembly and low-level programming so any help would be greatly appreciated.

来源: https://github.com/jtherrmann/os/blob /master/os.asm

原始: https://raw.githubusercontent.com/jtherrmann/os /master/os.asm

编辑:此外,当我在文件中的较高位置添加更多数据/代码时,键盘映射会被更早地切断,而当我删除较高的数据/代码时,按键映射将在稍后时被切断.还是根本没有.因此,我知道这与空间限制有关.

Additionally, when I add more data/code higher up in the file, the keymap gets cut off earlier, and when I remove higher up data/code, the keymap gets cut off later or not at all. So I know that this has something to do with space limitations.

推荐答案

您的代码有多个错误.

a)它没有在已知位置建立堆栈,然后在可能覆盖堆栈的地址(可能在同一地址)上从磁盘加载数据.

a) It doesn't set up a stack at a known location, and then loads data from disk at an address that might overwrite the stack (that might be at the same address).

b)假设从磁盘加载数据无需检查BIOS是否返回错误即可.

b) It assumes that loading data from disk worked without checking if the BIOS returned an error.

c)它仅加载一个扇区,而无法确定实际大小和自我调整";因此,随着文件的增长,它将是一个持续的维护工作.这很可能是您的数据中断"的原因(前512个字节未加载后的所有内容)

c) It only loads one sector without any way to determine the actual size and "self-adjust"; so as the file grows it's going to be a continual maintenance chore. This is likely to be the reason why your data gets "cut off" (everything after the first 512 bytes are not loaded)

d)在定义"newstart"之前先使用它,然后为时已晚就定义"newstart equa 0x0500".

d) You use "newstart" before it's been defined, and then define "newstart equa 0x0500" after it's too late.

e)您假定所有字符都是可打印的.不是(光标移动,功能键...)

e) You assume all characters are printable. They aren't (cursor movement, function keys, ...)

还要注意,将字符从QWERTY转换为Dvorak的代码效率极低(遍历所有条目以查找正确的字符,而不是将原始字符用作表的索引,例如movzx eax,al);并且当前在很多情况下都无法使用(例如,如果用户按下"shift + a"或启用了大写锁定).

Also note that your code to convert a character from QWERTY to Dvorak is incredibly inefficient (looping through all entries to find the right one instead of using the original character as an index into a table - e.g. like movzx eax,al, mov al,[table+eax]); and it currently won't work for a lot of cases (e.g. if the user presses "shift+a" or if they have capslock on).

这篇关于(组件x86实模式)数据被“切断".在程序结束时?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆