לדלג לתוכן

1.4 המחסנית פתרון

תרגיל 1 – PUSH / POP,‏ PUSHA / POPA

stack_ex1.asm

IDEAL
MODEL small
STACK 100h

DATASEG
; אין נתונים קבועים

CODESEG
start:
    mov ax, @data
    mov ds, ax

    ; ----- חלק א: PUSH / POP -----
    mov ax, 1111h
    mov bx, 2222h
    push ax
    push bx

    pop cx        ; CX = 2222h
    pop dx        ; DX = 1111h

    ; הערה: אילו היינו כותבים כאן pop ax פעמיים ברצף
    ;‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑‑
    ; ה‑CPU היה מושך «זבל» מה־Stack (Underflow).

    ; ----- חלק ב: PUSHA / POPA -----
    pusha         ; דוחף AX CX DX BX SP BP SI DI (16 בתים)
    ; … ניתן לשנות רגיסטרים כרצוננו …
    popa          ; משחזר את כולם

exit:
    mov ax, 4C00h
    int 21h
END start

תרגיל 2 – CALL ו‑RET

stack_ex2.asm

IDEAL
MODEL small
STACK 100h

CODESEG
start:
    ; כתובת הקפיצה תחזור לכאן
    call HelloFunc
    mov ax, 7777h     ; ריצה נמשכת אחרי החזרה

    ; בשלב זה ה‑Stack נקי – כתובת החזרה כבר נשלפה ע\"י RET

exit:
    mov ax, 4C00h
    int 21h

; פונקציה ריקה
HelloFunc:
    ret
END start


תרגיל 3 – פרמטרים באמצעות המחסנית

stack_ex3.asm

IDEAL
MODEL small
STACK 100h

CODESEG
start:
    ; --- Square(n) : n² ---
    mov ax, 4
    push ax
    call Square          ; AX = 16

    ; --- AddTwo(a,b) : a+b  (cdecl) ---
    push 2               ; param 2 (b)
    push 5               ; param 1 (a)
    call AddTwo
    add sp, 4            ; caller cleans (cdecl).  AX = 7

    ; --- AddTwoPascal(a,b) : a+b  (pascal) ---
    push 5               ; param 1
    push 3               ; param 2
    call AddTwoPascal    ; callee cleans.  AX = 8

exit:
    mov ax, 4C00h
    int 21h

; ---------- Functions ----------

Square:                  ; [BP+4] = n
    push bp
    mov  bp, sp
    mov  ax, [bp+4]
    mul  ax              ; AX = AX*AX
    pop  bp
    ret

AddTwo:                  ; cdecl – caller cleans
    push bp
    mov  bp, sp
    mov  ax, [bp+4]
    add  ax, [bp+6]
    pop  bp
    ret

AddTwoPascal:            ; pascal – callee cleans
    push bp
    mov  bp, sp
    mov  ax, [bp+4]
    add  ax, [bp+6]
    pop  bp
    ret 4                ; מנקה גם 2‑הפרמטרים
END start


תרגיל 4 – משתנים לוקליים עם BP

stack_ex4.asm

IDEAL
MODEL small
STACK 100h

CODESEG
start:
    call LocalVarsFunc   ; תוצאה חוזרת ב‑AX
exit:
    mov ax, 4C00h
    int 21h

; -------------------------------
; משריינת 4 בתים: var1=[BP‑2], var2=[BP‑4]
; מחזירה AX = var1² + var2
LocalVarsFunc:
    push bp
    mov  bp, sp
    sub  sp, 4

    mov  word ptr [bp-2], 3   ; var1 = 3
    mov  word ptr [bp-4], 7   ; var2 = 7

    mov  ax, [bp-2]
    mul  ax                   ; AX = var1²
    add  ax, [bp-4]           ; AX += var2

    mov  sp, bp
    pop  bp
    ret
END start


תרגיל 5 – שמירת רגיסטרים

stack_ex5.asm

IDEAL
MODEL small
STACK 100h

CODESEG
start:
    call SafeCalc
exit:
    mov ax, 4C00h
    int 21h

; SafeCalc משתמשת ב‑AX,BX ומבטיחה לא לשנות אותם
SafeCalc:
    push bp
    mov  bp, sp
    push ax
    push bx

    mov  ax, 10
    mov  bx, 3
    add  ax, bx             ; כל חישוב זמני

    pop  bx
    pop  ax
    pop  bp
    ret
END start


תרגיל 6 – פונקציה מלאה (Multiply)

stack_ex6.asm

IDEAL
MODEL small
STACK 100h

DATASEG
Product dw ?

CODESEG
start:
    push 3
    push 5
    call Multiply   ; AX = 15
    add sp, 4
    mov Product, ax
exit:
    mov ax, 4C00h
    int 21h

Multiply:                  ; cdecl  AX = a*b
    push bp
    mov  bp, sp
    mov  ax, [bp+4]
    mov  bx, [bp+6]
    mul  bx                ; DX:AX = AX*BX  → AX התוצאה התחתונה
    pop  bp
    ret
END start


תרגיל 7 – cdecl לעומת pascal

stack_ex7.asm

IDEAL
MODEL small
STACK 100h

CODESEG
start:
    ; --- cdecl ---
    push 4
    push 6
    call MulCdecl
    add sp, 4          ; caller cleans

    ; --- pascal ---
    push 6
    push 4
    call MulPascal     ; callee cleans

exit:
    mov ax, 4C00h
    int 21h

; ---------- Functions ----------

MulCdecl:                  ; AX = a*b   (caller cleanup)
    push bp
    mov  bp, sp
    mov  ax, [bp+4]
    mov  bx, [bp+6]
    mul  bx
    pop  bp
    ret

MulPascal:                 ; AX = a*b   (RET 4)
    push bp
    mov  bp, sp
    mov  ax, [bp+4]
    mov  bx, [bp+6]
    mul  bx
    pop  bp
    ret 4
END start


תרגיל 8 – אתגר

stack_ex8.asm

IDEAL
MODEL small
STACK 100h

DATASEG
ExprResult   dw ?    ; a + b*c
TempResult   dw ?    ; תוצאה זמנית

CODESEG
start:
    ; --------  a + b*c  --------
    push 3      ; c
    push 2      ; b
    push 1      ; a
    call APlusBtimesC       ; AX = 1 + 2*3 = 7
    add sp, 6
    mov ExprResult, ax

    ; --------  פונקציה עם Local tmp --------
    push 9
    call WithTemp
    add sp, 2
    mov TempResult, ax

exit:
    mov ax, 4C00h
    int 21h

; a + b*c   (cdecl)
APlusBtimesC:
    push bp
    mov  bp, sp
    mov  ax, [bp+6]     ; b
    mul  word ptr [bp+4] ; b * c   (c ב‑[bp+4])
    add  ax, [bp+8]     ; + a      (a ב‑[bp+8])
    pop  bp
    ret

; WithTemp(n): מחזיר (n+1)*2   עם משתנה לוקלי
WithTemp:
    push bp
    mov  bp, sp
    sub  sp, 2          ; tmp  = [bp‑2]

    mov  ax, [bp+4]
    inc  ax
    mov  [bp-2], ax     ; tmp = n+1
    add  ax, ax         ; (n+1)*2  → AX

    mov  sp, bp
    pop  bp
    ret
END start