无法在NASM中包含文件

The*_*eus 6 assembly nasm

我尝试使用包含一个文件到我的boot.asm文件中

%include "input.asm"
Run Code Online (Sandbox Code Playgroud)

但每次我尝试编译它时都会收到错误消息,说nasm无法打开包含文件.
input.incIS与boot.asm在同一目录中我在这里和谷歌寻找答案,但没有人帮助我.

是否有一种特殊的方式包含文件应该在包含之前编译/格式化?或者只是我的鼻子在咆哮?

编辑:这是包含的代码:

mov ax, 0x07C0  ; set up segments
mov ds, ax    mov es, ax
mov si, welcome
call print_string
mov si, welcome2    
call print_string    
mov si, welcome4    
call print_string  
jmp .mainloop

%include 'input.asm'
mainloop:    ;loop here
Run Code Online (Sandbox Code Playgroud)

input.asm:

 ; ================
 ; calls start here
 ; ================

 print_string:
   lodsb        ; grab a byte from SI

   or al, al  ; logical or AL by itself
   jz .done   ; if the result is zero, get out

   mov ah, 0x0E
   int 0x10      ; otherwise, print out the character!

   jmp print_string

 .done:
   ret

 get_string:
   xor cl, cl

 .loop:
   mov ah, 0
   int 0x16   ; wait for keypress

   cmp al, 0x08    ; backspace pressed?
   je .backspace   ; yes, handle it

   cmp al, 0x0D  ; enter pressed?
   je .done      ; yes, we're done

   cmp cl, 0x3F  ; 63 chars inputted?
   je .loop      ; yes, only let in backspace and enter

   mov ah, 0x0E
   int 0x10      ; print out character

   stosb  ; put character in buffer
   inc cl
   jmp .loop

 .backspace:
   cmp cl, 0    ; beginning of string?
   je .loop ; yes, ignore the key

   dec di
   mov byte [di], 0 ; delete character
   dec cl       ; decrement counter as well

   mov ah, 0x0E
   mov al, 0x08
   int 10h      ; backspace on the screen

   mov al, ' '
   int 10h      ; blank character out

   mov al, 0x08
   int 10h      ; backspace again

   jmp .loop    ; go to the main loop

 .done:
   mov al, 0    ; null terminator
   stosb

   mov ah, 0x0E
   mov al, 0x0D
   int 0x10
   mov al, 0x0A
   int 0x10     ; newline

   ret

 strcmp:
 .loop:
   mov al, [si]   ; grab a byte from SI
   mov bl, [di]   ; grab a byte from DI
   cmp al, bl     ; are they equal?
   jne .notequal  ; nope, we're done.



   cmp al, 0  ; are both bytes (they were equal before) null?
   je .done   ; yes, we're done.

   inc di     ; increment DI
   inc si     ; increment SI
   jmp .loop  ; loop!

 .notequal:
   clc  ; not equal, clear the carry flag
   ret

 .done:     
   stc  ; equal, set the carry flag
   call print_string
   ret
Run Code Online (Sandbox Code Playgroud)

错误消息:

D:\ ASMT\boot.asm:14:致命:无法打开包含文件`input.asm'

And*_*man 9

NASM 为您提供了将其他源文件包含到您的代码中的功能。实现这一点的方法是使用%include指令,如下所示:

%include "input.asm"

一个警告是,NASM 假定所有文件都在当前工作目录中,例如运行 NASM 的目录。如果将文件传递给%include指令,并且该文件不能位于当前工作目录中,则 NASM 将返回以下错误:

fatal: unable to open include file

正如已接受的答案中已经给出的那样,一种解决方案是使用该-i选项在 NASM 命令行上指定任何额外引用的目录。例如,让我们假设一个名为“print_string”的“include”文件位于目录“procedure_library”中,并且该目录不是NASM 的“launch”目录。在这种情况下,我们只需告诉 NASM 可以在哪里查找其他源文件,如下所示:

nasm -i/home/user/asmwork/procedure_library/ -f elf64 -g -F dwarf sourecode.asm

* -i允许和路径名之间有空格,并且是可选的)

这是维护项目的首选方式。然而,就击键而言,这是一个相当长的命令。虽然,使用 aMakefile可以解决这个问题。

nb NASM 不了解运行它的操作系统的文件命名约定;您提供给-i选项的参数的字符串将完全按照写入的方式进行解析。因此,上例中的尾随正斜杠是必要的。在 Windows 下,尾随反斜杠同样是必要的。

还要注意,工作目录,即您从中调用 NASM 的目录,仍然需要包含您的“主”源代码文件,即命令本身需要一个输入文件作为参数。例如,上面的调用仍然需要工作目录中的“sourcecode.asm”,而不管附加的-i选项参数如何。如果“sourcecode.asm”驻留在可选目录“procedure_library”中,NASM 将返回fatal: unable to open input file. 该i选项可以被认为是一个%include文件搜索参数。


硬编码文件路径:

作为给定方法的替代方法,您可以直接在源文件中简单地对文件路径进行硬编码。只需将文件的相对或绝对路径传递给%include指令。例如:

%include “/home/user/asmwork/procedure_library/input.asm”

或者,假设您调用 NASM 的当前工作目录是/home/user/asmwork/

%include “/procedure_library/input.asm"


外部库:

管理代码复杂性的另一种选择,也许是更好的选择,是在外部组装过程库作为它自己的目标文件,并在创建最终的可执行程序时链接这两个文件。后者也可能使您的程序可在不同程序中重用。

请记住,如果要链接的文件不在工作目录中,则需要在链接描述文件中提供相对/绝对路径。根据您使用的程序,您可能需要也可能不需要在调用期间传递额外的参数。例如,GNU 链接器不需要任何额外的可选参数,它只是要求您传递一个可行的文件路径:

executable: sourcecode.o ld -o executable sourcecode.o /home/case/asmwork/procedure_library/input.o


指令位置:

尽管在这种情况下,在源代码中的任何位置包含指令绝对没问题,但在源代码%include顶部附近使用指令通常是一种很好的做法。考虑例如,如果您要包含一个宏文件,那么在这种情况下,NASM 会向您发送一个错误error: parser: instruction expected,类似于 ,因为所有宏必须在调用之前完全定义。

  • 注意:Nasm 需要“-I”参数值尾部斜杠[实际上是一个错误](https://bugzilla.nasm.us/show_bug.cgi?id=3392205),从 Nasm 2.14 开始已修复。 (2认同)

Pie*_*aud 8

似乎NASM包含当前目录中的文件:

在当前目录中搜索包含文件(运行NASM时所在的目录,而不是NASM可执行文件的位置或源文件的位置),以及使用NASM命令行上指定的任何目录. -i选项.

如果您正在NASMD:\ASMT您的情况下的另一个目录执行,那么它是不正常的是正常的.

资料来源:http://www.nasm.us/doc/nasmdoc4.html#section-4.6.1

  • 哦,谢谢,将 -ID:/ASMT 添加到 nasm 启动命令有效。 (2认同)