본문 바로가기

컴퓨터 공학 자료(학부)/Assembly

ASSUME 디렉티브의 정의(MASM)


-. All the addressing modes which use BP register for specifying offset
address use SS register as the default segment register, and all other
addressing modes for memory operand use DS register.

-. ASSUME
ASSUME은 MASM에게 뒤따르는 코드내에서 어떤 세그먼트가 세그먼트 레지스터와
연관되는지 알려주거나, 간접 메모리 참조에 사용될 크기를 알려준다. 지정하는
형태는 segreg:name 인데, 여기서 segreg는 CS, DS, SS 및 ES 중의 하나이고,
name은 SEGMENT 지시어를 사용하여 정의한 세그먼트 이름이거나 GROUP 지시어에
의해 정의된 그룹의 이름, 또는 세그먼트 주소를 나타내는 수식(SEG연산자를 이용한)
이다. 세그먼트 레지스터가 어떤 세그먼트와도 관련이 없으면 name 대신에 키워드
NOTHING을 사용한다.

가령, es:eseg의 의미는 다음과 같다.
eseg 안에서 정의된 변수를 사용할 때, 세그먼트 레지스터 es가 사용되어야 한다.
즉, 필요하다면 assembler가 적절한 segment override prefix를 사용하면서 번역해야 한다.
실제 runtime에서, es 레지스터에 해당 변수의 세그먼트 값이 미리 로딩되어야 할 것이다.

cs : 레지스터에 값을 수동으로 로딩할 필요는 없다.
ds, es : runtime에서 직접 로딩해야 할 것이다.

cs, es : segment prefix가 machine code에 삽입될 것이다.
ds : 대부분의 경우, 별도의 segment prefix가 필요없을 것이다.

다시 말하면, assume은 번역시 메모리 변수와 함께 사용될 segment를 미리 정하는 것이고,
assume을 사용하지 않거나, assume에서 정한 것과 다르게 사용하려면,
메모리 변수가 사용되는 위치에서 ds: 와 같은 segment prefix를 붙여주면 된다.
즉, C에서 정의된 변수를 assembly language에서 사용하려면, DS 등을 붙여서 사용하면 될 것이다.

==[1st example]============================================================================

sseg segment stack
db 64 dup(?)
sseg ends

dseg segment
db 100h dup (0)
array db 34h, 7fh, 2d, 0a4h
dseg ends

cseg segment para
assume cs:cseg, ds:dseg
; cseg 안에서 정의된 변수를 사용할 때, segment cs가 사용되도록 번역되어야 한다.
; dseg 안에서 정의된 변수를 사용할 때, segment ds가 사용되도록 번역되어야 한다.

begin: mov ax, dseg
mov ds, ax
mov si, 2
mov al, array[si]
; array는 dseg 안에서 정의된 변수이고, segment ds가 사용되도록 번역된다.
; 그러나, machine code 상에서 ds: 에 해당하는 3e는 삽입되지 않는다.
; 만약, assume 라인을 생략한다면, mov al, ds:array[si]와 같이 변경하면 된다.
; 이렇게 해도, 3e 는 삽입되지 않는다.
mov ah, 4ch
int 21h
cseg ends
end begin

==[2nd example]============================================================================

sseg segment stack
db 64 dup(?)
sseg ends

cseg segment para
assume cs:cseg
; cseg 안에서 정의된 변수를 사용할 때, segment cs가 사용되도록 번역되어야 한다.

var dw 1122H, 3344H
video db 80*25 dup(?)

begin: mov ax, 0b800h
mov es, ax
mov cx, 80*25
mov si, 0
mov di, 0
back: mov al, es:[di]
mov video[si], al
; cseg 안에서 정의된 변수를 사용할 때, segment cs가 사용되도록 번역되어야 한다.
; 여기서는 cs:에 해당하는 machine code 2e 가 삽입된다.
; 이상한 것은, assume 라인을 생략하면서, cs:를 붙여주지 않고 그대로 둬도 에러가 발생하지 않는다.
; 물론, 이 경우에도 2e는 삽입된다.
add si, 1
add di, 2
loop back
mov ah, 4ch
int 21h
cseg ends
end begin

==[3rd example]============================================================================
_OSIntCtxSw PROC FAR
;
CALL FAR PTR _OSTaskSwHook ; Call user defined task switch hook
;
MOV AX, SEG _OSTCBCur ; Reload DS in case it was altered
MOV DS, AX ;
; _OSTCBCur 의 segment 값을 실제로 loading.

MOV AX, WORD PTR DS:_OSTCBHighRdy+2 ; OSTCBCur = OSTCBHighRdy
MOV DX, WORD PTR DS:_OSTCBHighRdy ;
; Segment로는 ds를 offset으로는 _OSTCBHighRdy를 사용하여 변수값을 접근.
; 실제로는 3E가 machine code로는 삽입되지 않을 것이다.

MOV WORD PTR DS:_OSTCBCur+2, AX ;
MOV WORD PTR DS:_OSTCBCur, DX ;
; Segment로는 ds를 offset으로는 _OSTCBCur를 사용하여 변수값을 접근.

MOV AL, BYTE PTR DS:_OSPrioHighRdy ; OSPrioCur = OSPrioHighRdy
MOV BYTE PTR DS:_OSPrioCur, AL
;
LES BX, DWORD PTR DS:_OSTCBHighRdy ; SS:SP = OSTCBHighRdy->OSTCBStkPtr
; segment로는 ds, offset으로는 _OSTCBHighRdy인 변수의 주소를 ES:BX 로 대입.
; 즉, DS -> ES, OFFSET OF _OSTCBHighRdy -> BX가 될 것이다.

MOV SS, ES:[BX+2] ;
MOV SP, ES:[BX] ;
;
POP DS ; Load new task's context
POP ES ;
POPA ;
;
IRET ; Return to new task
;
_OSIntCtxSw ENDP

PAGE ; /*$PAGE*/

출처: http://kldp.org/node/78935

'컴퓨터 공학 자료(학부) > Assembly' 카테고리의 다른 글

Segment란?  (0) 2010.07.11
어셈블리어 과제  (0) 2010.05.08
간단한 대소문자 변환  (0) 2010.04.28
C언어에서 인라인으로 어셈코드 이용  (0) 2010.04.28
MASM과 비쥬얼스튜디오 2008연동  (1) 2010.03.10