SoFunction
Updated on 2025-03-04

Detailed explanation of the role of assembly language learning assume

The function of assume is to associate segment names and segment registers.

If you define variable names in the data segment, for example:

x   db  0

And in your code, you need to use this variable name directly, such as:

mov   al,  x

Then, an error will be reported when the assembler is assembled.

Because when the variable name x is encountered in the mov instruction, the assembler does not know which segment register it wants to use as the segment address.

so:

To access directly with variable names, or use statement labels (such as the label start in your example), you must associate the segment names of the segments where these variables or labels are located with the segment register name in the assume directive, otherwise an error will occur.

If you do not use the variable name in the segment, you can not associate the segment name and register of the segment.

If you specify the segment span prefix when accessing variables, the association is not necessary. For example, you can use mov al, ds:x to access the variable x .

I've been watching Wang Shuang's assembly language these days. But I don't understand the assume pseudo directive.

For example, assume cs:code, ds:data has been defined

However, when using debug to observe, it was found that the ds segment register had no associated data.

Must state in cs: mov ax,data

                            mov ds,ax
Then I can find outdsThere is correct data in。

So I wondered, isn’t assume already associated with ds?

Go online to ask for help = =, and then find the answer.

Programs are written to compile software. It compiles the software, compiles it into machine code, and then controls the CPU. However, when compiling the software, the assume statement does not generate machine code.

Therefore, there must be mov ax, data, mov ds, ax, so that the CPU can be controlled.

--The assume statement is a pseudo-instruction, which is only written to the compiled software. Compile the software and do not generate machine code.

Assume only associates the segment name for other segment registers other than CS, so that the program can know which segment register to use when accessing variables in the segment, and does not load the segment address into the segment register when the program is loaded.

Therefore, the work of loading segment addresses into segment registers must be written by the user in the program and execute the code to complete the loading work when the program starts to run.
For CS segment registers only, the segment address will be automatically loaded into the segment register when the program is loaded while the segment name is associated.
----Addition: After knowing the answer the day before yesterday, I thought that the likessume ds:data and other references were of no use, they were just for programmers to see.

But today I found that this is not the case. If you use labels in data, assume ds:data cannot be omitted.

for example:

data segment
a db 1,2,3,4 ,5,6,7,8
b dw 0
data ends

There is no ":" after a, b.

If you want to access data with data labels in the cs segment, you must add assume ds:data at the beginning, otherwise an error will be reported

Arror A2068:Can not address with segment register

However, even if assume ds:data is added at the beginning, mov ax, data, mov ds, ax cannot be missing in the code segment.

Function: Used to identify the default segment prefix

Explanation: assume cannot change the value of ds and other segment registers, but it can change the assembly code generated by the compiler. for example:

assume ss:stack

stack segment

x :db 0

stack ends

If the program needs mov ax, [x], then how does the program locate [x]? We know that x is just an offset address 0, so at this time assume is equivalent to telling the compiler that all labels of the stack segment are associated with ss, so at this time [x] is equivalent to ss:[0]. If we directly change this sentence to mov ax,ss:[0], then it is OK to not add assume before it. This is also why [0] is forced to be understood by the compiler as an immediate number, while [label] is understood as the content in the label, because the label must be with the segment assume, otherwise an error will be reported cannot address with segment register. If [0] has no default segment, it can only be considered as an immediate number.

Therefore, we still need to modify the value of ss in the program to stack with instructions. The reason is that assume will not modify the segment register. This is determined by the dos system. If the dos system decides to compile the segment value into the .exe file header and modify the segment value according to the file header when loading into memory, then assume will be equivalent to changing the segment value. But the reality I debugged is that ds and es point to the psp header (see the 16-bit exe program loading process for psp), ss points to ds+0:00f0, and cs points to ds+0:0100.

The above is a detailed explanation of the role of assembly language learning assume. For more information about the role of assembly language assume, please pay attention to my other related articles!