我已经成功使用SEGMENT
指令在TASM下创建了单独的堆栈,数据和代码段,但仍有些困扰我。当使用Turbo Assembler 2.0汇编以下代码时,TLINK会生成一个大小约为90KB的二进制文件。
.286
myStack segment para stack 'stack'
db 0FFFFh dup (?)
ends myStack
myData segment para 'data'
msg db 'Memes!$'
db 7FFFh dup (?)
ends myData
myCode segment para 'code'
assume cs:myCode
assume ss:myStack
start:
mov ax,myData
mov ds,ax
push offset msg
call write
add sp,2
mov ah,4ch
int 21h
write:
push bp
mov bp,sp
mov dx,[bp+4]
mov ah,9h
int 21h
pop bp
ret
ends myCode
end start
现在在我看来,MZ文件格式应该允许.exe指定它需要超出二进制映像实际包含的内存分配(通过除代码大小之外分配的内存的最小/最大段落)我猜错了。
所以我的问题是:如何哄骗汇编器/链接器生成带有适当标头的.exe来分配内存而不直接在二进制映像中包含占位符值?
答案 0 :(得分:3)
过了一段时间,但我认为你可以通过首先放置代码段来实现你想要做的事情。然后将所有初始化数据放在data
段的开头,然后是data
段中的所有未初始化数据,接着是未初始化的堆栈段。由于所有未初始化的数据都被强制结束,因此无需分配文件中的任何空间。
如果代码如下所示,您的代码可能会为您提供所需的结果:
.286
myCode segment para 'code'
assume cs:myCode
assume ss:myStack
start:
mov ax,myData
mov ds,ax
push offset msg
call write
add sp,2
mov ah,4ch
int 21h
write:
push bp
mov bp,sp
mov dx,[bp+4]
mov ah,9h
int 21h
pop bp
ret
ends myCode
myData segment para 'data'
msg db 'Memes!$' ; Initialized data first
db 7FFFh dup (?) ; Uninitialized data after all initialized data
ends myData
myStack segment para stack 'stack'
; Leave blank, this will allow the stack to
; to use the full 64k segment
ends myStack
end start