如何在MASM(MS-DOS)中分配超过64字节的内存?
DOS实模式下分配大内存的替代方案
你提到的INT 21h, 48h每次分配的是64KB的内存段(不是64字节),遇到“仅支持4段”的问题,大概率是系统剩余的连续空闲段不足,或者常规内存中没有更大的连续块。以下是几种能获取更大内存的方法:
1. 调整已分配段的大小(INT 21h, 4Ah)
如果已经通过48h分配了一个段,可以用4Ah函数尝试扩大它,只要目标地址后有连续的空闲内存。这种方式不需要额外的内存管理器,适合常规内存内的扩容需求:
; AX = 需要的新段大小(以节为单位,1节=16字节) ; ES = 已分配的段地址 MOV AH, 4Ah MOV BX, [new_size_in_paragraphs] MOV ES, [allocated_segment] INT 21h JC error_handler ; 进位标志置位表示扩容失败
2. 使用XMS扩展内存(需HIMEM.SYS)
如果系统加载了HIMEM.SYS,可以通过XMS规范访问超过1MB的扩展内存。步骤如下:
- 检测XMS驱动是否存在:
MOV AX, 4300h INT 2Fh CMP AL, 80h JNE no_xms_found ; 不存在XMS驱动
- 获取XMS驱动入口并分配内存:
MOV AX, 4310h INT 2Fh ; ES:BX 指向XMS驱动入口 PUSH ES MOV AH, 01h MOV DX, [size_in_kilobytes] ; 要分配的内存大小(KB) CALL DWORD PTR [ES:BX] JC allocation_failed ; AX 返回分配的内存块句柄 POP ES
3. 使用EMS扩展内存(需EMM386.EXE)
如果系统加载了EMM386.EXE,可以利用EMS规范分配内存块,通过页帧映射到常规内存访问:
- 检测EMS驱动:
MOV AX, 0000h INT 67h CMP AH, 00h JNE no_ems_found
- 分配EMS内存块:
MOV AX, 0100h MOV BX, [number_of_pages] ; 每页16KB INT 67h JC allocation_failed ; AX 返回内存块句柄
4. 直接遍历内存控制块(MCB)获取大块内存
通过INT 21h, 52h获取MCB链表的起始地址,手动遍历找到最大的空闲连续块,直接接管该块内存(需手动维护MCB,风险较高):
MOV AH, 52h INT 21h ; ES:BX+2 指向第一个MCB ; 遍历MCB,寻找标记为'FREE'的大块
注意:如果仅处理不超过64KB的文件,优先用4Ah调整段大小;若文件更大,建议使用XMS或EMS,这两种方式能访问远超常规内存的空间。
内容的提问来源于stack exchange,提问作者Gene Adam Oker
相关产品推荐
相关产品推荐

