MASM 错误 Unknown relocation type (1) with 16b code

MASM error Unknown relocation type (1) with 16b code

我用M68000还不错,但X86对我来说有点难。我正在尝试 assemble 使用 MASM

这个简单的程序
.MODEL SMALL
.data?
  ONE  dB ?
  TWO  dB ?
  stack db  100 dup(?)

.data
  MSG  db 13,10, 'Enter deree of polynomials:  $'
  MSG2 db 13,10, 'Enter coefficient of x^ $' 
  MSG3 db 13,10, 'The polynomial created is: $'
  MSG4 db 13,10, 'The first derivative is: $'
  STR1 db  255 DUP('$')

.code

_start:

            mov ax, offset MSG
            mov ds, ax  

end _start

而且我一直收到错误 符号 MSG 的未知重定位类型 (1)。 我知道这是什么(当位移大于模型允许的位移或类似的东西时会发生这种情况)但我不知道如何解决这个错误(我知道 MASM 是 32 位 assembler 而我我正在尝试编写 16 位代码)。我要做的是将指向 .data 的指针加载到 ds 寄存器中。

我的makeit.bat由MASM32IDE生成的是:

@echo off
if exist "derivative 1.obj" del "derivative 1.obj" 
if exist "derivative 1.exe" del "derivative 1.exe" 
\masm32\bin\ml /c /coff "derivative 1.asm" 
if errorlevel 1 goto errasm 
\masm32\bin\PoLink /SUBSYSTEM:CONSOLE "derivative 1.obj" 
if errorlevel 1 goto errlink dir "derivative 1.*" goto TheEnd 
:errlink 
  echo _ 
  echo Link error 
  goto TheEnd 

:errasm 
  echo _ 
  echo Assembly Error 
  goto TheEnd 

:TheEnd 
  pause

对于 16 位汇编,使用点指令(如 .model、.data、.code)的语法是:

        mov     ax, @data
        mov     ds, ax

MASM32 软件包不支持生成 16 位可执行文件,尽管更改此行为并不难。 MASM 程序包中的 MASM32 汇编器将生成 16 位代码,但提供的 linkers 不会生成 16 位可执行文件。这会导致您看到的错误类型。

您可以下载支持 16 位目标的旧 linker 的副本。我已经在我的服务器上提供了 link16.exe(1994 年 12 月 5 日版本 5.60.339)供下载。

link16.exe 放入 \masm32\bin 目录。您将必须修改生成的 makeit.bat 文件。调用 linker 的行(如 link.exepolink.exe)必须替换为:

\masm32\bin\link16.exe "filename.obj" ;

filename.obj是你要link的文件名。更改它以适合您的项目。末尾的分号将默认所有文件名并且不会提示输入它们。然后,您必须修改 makeit.bat 中的 ml 行,这样它就不会生成 coff 文件。为此,请删除 /coff 选项:

\masm32\bin\ml /c "filename.asm"

同样 filename.asm 可以替换为项目中文件的名称。


其他观察结果

一旦您能够生成 16 位可执行文件,您的代码就会出现一些问题:

  • 删除 stack db 100 dup(?) 并改用 .stack 指令

    .stack 100h
    
  • 您需要在DS中设置MSG的段值改为:

    mov ax, seg MSG
    mov ds, ax 
    

    .small 模型只有一个 data 段。在 .small 模型中,.data.data? 将合并为一个 .data 段。使用此内存模型,您还可以这样初始化 DS

    mov ax, @data
    mov ds, ax
    
  • 对于 DOS EXE 程序,您需要退出 DOS exit interrupt

    mov ax, 4c00h
    int 21h
    

如果您在 Windows 的 64 位版本上使用 MASM32,您将无法直接 运行 您使用的 16 位应用程序创造。你必须下载一个像 DOSBox 这样的模拟器到 运行 它,或者安装 DOS/Windows 版本的虚拟机(VMWare、VirtualBox、QEMU 等)软件可以 运行代码。

感谢所有为我回答上述简单问题的人。事实上,我的问题的答案是 link16.exe 是生成 16 位代码所必需的。 我可以 assemble 简单快速地使用我的代码的另一种方法是使用 WinAsm,它是我通过谷歌搜索找到的较旧的 IDE。