Ehdolliset hypyt ja silmukat
Toteuttakaa päätöksenteko ja toistuvat tehtävät vertailukäskyillä (CMP, TEST) ja ehdollisilla hyppykäskyillä (JMP, JE, JNE, JL, JG jne.).
Ehdolliset hypyt ja silmukat on ilmainen Assembly-kieli ja x86-tason järjestelmäohjelmointi-oppitunti CoddyKitissä. Tämä on oppitunti 3/4. Voit lukea koko oppitunnin alta ilmaiseksi ja harjoitella sen jälkeen käytännössä selaimessa sisäänrakennetulla koodieditorilla ja ympäri vuorokauden käytettävissä olevan tekoälytuutorin avulla. Oppitunti kuuluu Assembly-kieli ja x86-tason järjestelmäohjelmointi-oppimispolkuun, ja edistymisesi synkronoituu verkon ja CoddyKit-sovelluksen välillä. Assembly-kieli ja x86-tason järjestelmäohjelmointi-kurssilla on yhteensä 4 oppituntia.
Ohjelman suorituksen ohjaaminen
Ohjelmat suoritetaan harvoin alusta loppuun suoraviivaisesti. Meidän on tehtävä päätöksiä ja toistettava toimintoja. Tätä kutsutaan suorituksen ohjaukseksi.
Assembly-kielessä on erityisiä käskyjä, joilla voidaan muuttaa käskyjen suoritusjärjestystä. Näin ohjelmat voivat toimia dynaamisesti ja reagoida erilaisiin ehtoihin.
Ajatelkaa sitä kuin tarinaa, jossa valitsette itse seuraavan tapahtumapolun: päätätte, mitä reittiä kuljette seuraavaksi!
Hyppy suoritetaan aina
Yksinkertaisin tapa muuttaa ohjelman suorituksen kulkua on käyttää ehdotonta hyppyä JMP-käskyllä. Se siirtää ohjauksen aina määritettyyn tunnisteeseen.
Tämä vastaa ylemmän tason kielten "goto"-lausetta. Ohjelma alkaa välittömästi suorittaa kohdetunnisteesta alkavia käskyjä.
section .data
msg1 db "Hello!", 0xA
len1 equ $ - msg1
msg2 db "Skipped!", 0xA
len2 equ $ - msg2
msg3 db "End.", 0xA
len3 equ $ - msg3
section .text
global _start
_start:
mov rax, 1 ; syscall write
mov rdi, 1 ; stdout
mov rsi, msg1
mov rdx, len1
syscall ; Print "Hello!"
jmp skip_message ; Unconditional jump
mov rax, 1
mov rdi, 1
mov rsi, msg2
mov rdx, len2
syscall ; This part is skipped!
skip_message:
mov rax, 1
mov rdi, 1
mov rsi, msg3
mov rdx, len3
syscall ; Print "End."
mov rax, 60 ; syscall exit
mov rdi, 0
syscallVertailujen tekeminen (CMP)
Ennen päätösten tekemistä meidän on verrattava arvoja. CMP-käsky tekee tämän puolestamme.
CMP destination, source toimii kuten SUB destination, source, mutta se hylkää tuloksen. Sen sijaan se päivittää vain suorittimen liput vertailun perusteella.
Tämä on ratkaisevan tärkeää ehdollisille hypyille!
; Compare AX with BX
cmp ax, bx
; Compare value in memory with 10
cmp [my_var], 10
; Compare AL with 0
cmp al, 0Suorittimen lippurekisteri
CMP-käskyn (tai useimpien aritmeettisten ja loogisten operaatioiden) jälkeen lippurekisterin erityiset bitit päivitetään. Nämä bitit kertovat operaation tuloksesta.
- ZF (Zero Flag): Asetetaan, jos tulos oli nolla tai operandit olivat yhtä suuret.
- SF (Sign Flag): Asetetaan, jos tulos oli negatiivinen.
- CF (Carry Flag): Asetetaan, jos tapahtui etumerkitön ylivuoto.
- OF (Overflow Flag): Asetetaan, jos tapahtui etumerkillinen ylivuoto.
Ehdolliset hypyt tarkistavat nämä liput!
Hyppy yhtäsuuruuden perusteella (JE, JNE)
Kun CMP on asettanut liput, voimme käyttää ehdollisia hyppykäskyjä. Kaksi yleistä käskyä ovat JE (Jump if Equal) ja JNE (Jump if Not Equal).
JE label: Hyppää, jos nollalippu (ZF) on asetettu eli operandit olivat yhtä suuret.JNE label: Hyppää, jos nollalippu (ZF) ei ole asetettu eli operandit eivät olleet yhtä suuret.
Katsotaan esimerkkiä.
section .data
eq_msg db "Numbers are equal!", 0xA
eq_len equ $ - eq_msg
ne_msg db "Numbers are not equal!", 0xA
ne_len equ $ - ne_msg
section .text
global _start
_start:
mov rax, 10
mov rbx, 10 ; Try changing this to 5
cmp rax, rbx ; Compare RAX and RBX
je are_equal ; If equal, jump to are_equal
; Else (not equal)
mov rax, 1
mov rdi, 1
mov rsi, ne_msg
mov rdx, ne_len
syscall
jmp end_program
are_equal:
mov rax, 1
mov rdi, 1
mov rsi, eq_msg
mov rdx, eq_len
syscall
end_program:
mov rax, 60
mov rdi, 0
syscallSuurempi tai pienempi (etumerkilliset luvut)
Etumerkillisille luvuille käytämme erilaisia ehdollisia hyppyjä tarkistaessamme suurempi kuin- tai pienempi kuin -suhteita.
JG label: Hyppää, jos suurempi (ZF=0 ja SF=OF)JGE label: Hyppää, jos suurempi tai yhtä suuri (SF=OF)JL label: Hyppää, jos pienempi (SF!=OF)JLE label: Hyppää, jos pienempi tai yhtä suuri (ZF=1 tai SF!=OF)
Nämä perustuvat Sign Flag (SF)-, Overflow Flag (OF)- ja Zero Flag (ZF) -lippujen yhdistelmiin.
section .data
gt_msg db "RAX is greater!", 0xA
gt_len equ $ - gt_msg
lt_msg db "RAX is less!", 0xA
lt_len equ $ - lt_msg
eq_msg db "RAX is equal!", 0xA
eq_len equ $ - eq_msg
section .text
global _start
_start:
mov rax, 5
mov rbx, 10 ; Compare 5 with 10
cmp rax, rbx
jg is_greater ; If RAX > RBX
jl is_less ; If RAX < RBX
; Else, they must be equal
mov rsi, eq_msg
mov rdx, eq_len
jmp print_msg
is_greater:
mov rsi, gt_msg
mov rdx, gt_len
jmp print_msg
is_less:
mov rsi, lt_msg
mov rdx, lt_len
jmp print_msg
print_msg:
mov rax, 1
mov rdi, 1
syscall
mov rax, 60
mov rdi, 0
syscallEtumerkittömät vertailut (JA, JB)
Etumerkittömiä lukuja käsiteltäessä lippuja tulkitaan eri tavalla. Carry Flag (CF) on tällöin keskeinen.
JA label: Hyppää, jos suurempi (etumerkitön vertailu) (CF=0 ja ZF=0)JAE label: Hyppää, jos suurempi tai yhtä suuri (etumerkitön vertailu) (CF=0)JB label: Hyppää, jos pienempi (etumerkitön vertailu) (CF=1)JBE label: Hyppää, jos pienempi tai yhtä suuri (etumerkitön vertailu) (CF=1 tai ZF=1)
Huomioikaa aina, vertailetteko etumerkillisiä vai etumerkittömiä arvoja!
IF-ELSE-lohkon rakentaminen
Voimme yhdistää CMP-käskyn ja ehdolliset hypyt if-else-logiikan luomiseksi aivan kuten ylemmän tason kielissä.
Yleinen rakenne on seuraava: vertaile, hyppää ehdon ollessa EPÄTOSI "else"-lohkoon, suorita "if"-lohko ja hyppää sitten "else"-lohkon ohi.
section .data
if_msg db "Condition is TRUE!", 0xA
if_len equ $ - if_msg
else_msg db "Condition is FALSE!", 0xA
else_len equ $ - else_msg
section .text
global _start
_start:
mov rax, 20
mov rbx, 10
cmp rax, rbx ; Is RAX > RBX?
jle else_block ; If not (less or equal), jump to else
; IF block (RAX > RBX)
mov rsi, if_msg
mov rdx, if_len
jmp print_and_exit
else_block:
; ELSE block (RAX <= RBX)
mov rsi, else_msg
mov rdx, else_len
print_and_exit:
mov rax, 1
mov rdi, 1
syscall
mov rax, 60
mov rdi, 0
syscallSilmukoiden luominen hypyillä
Silmukat ovat keskeisiä koodin toistamisessa. Assemblyssa ne luodaan yhdistämällä tunniste, vertailu ja ehdollinen hyppy.
Yleiseen rakenteeseen kuuluu laskurin alustaminen, silmukan tunnisteen määrittäminen, operaatioiden suorittaminen, laskurin pienentäminen tai kasvattaminen, vertailu ja hyppääminen takaisin tunnisteeseen, jos ehto täyttyy.
section .data
msg db "Looping... ", 0xA
len equ $ - msg
section .text
global _start
_start:
mov rcx, 3 ; Initialize loop counter
loop_start:
cmp rcx, 0 ; Check if counter is 0
je loop_end ; If it is, exit loop
; Print message
mov rax, 1
mov rdi, 1
mov rsi, msg
mov rdx, len
syscall
dec rcx ; Decrement counter
jmp loop_start ; Jump back to start of loop
loop_end:
mov rax, 60
mov rdi, 0
syscallHyppyehdon tarkistus
Tarkastelkaa seuraavaa assembly-koodikatkelmaa. Mitä tulostetaan, jos RAX sisältää arvon 5 ja RBX sisältää arvon 10?
section .data
msg_a db "Result A", 0xA
len_a equ $ - msg_a
msg_b db "Result B", 0xA
len_b equ $ - msg_b
section .text
global _start
_start:
; Assume RAX = 5, RBX = 10
cmp rax, rbx
jg print_a
jmp print_b
print_a:
mov rax, 1
mov rdi, 1
mov rsi, msg_a
mov rdx, len_a
syscall
jmp end_program
print_b:
mov rax, 1
mov rdi, 1
mov rsi, msg_b
mov rdx, len_b
syscall
end_program:
mov rax, 60
mov rdi, 0
syscallKertaus: hypyt ja silmukat
Hienoa työtä! Olette oppineet ohjaamaan ohjelman suorituksen kulkua assemblyssa!
JMPon tarkoitettu ehdottomiin hyppyihin.CMPvertailee arvoja ja päivittää suorittimen lippurekisterin.- Ehdolliset hypyt, kuten
JE,JNE,JG,JL,JAjaJB, tarkistavat nämä liput päättääkseen, hypätäänkö. - Yhdistämällä nämä voitte luoda tehokkaita if-else-lauseita ja silmukoita.
Seuraavaksi perehdymme proseduureihin ja pinon hallintaan, jotta voitte jäsentää koodianne entistä paremmin!
Opi Assembly tekoälytuutorin avulla — ilmaiseksi
Kirjoita ja suorita oikeaa koodia selaimessa, saa välitöntä apua tekoälytuutorilta ympäri vuorokauden ja jatka siitä, mihin jäit, verkossa tai sovelluksessa.
- Kurssit
- 12
- Oppitunnit
- 48
Usein kysytyt kysymykset
Onko oppitunti ”Ehdolliset hypyt ja silmukat” ilmainen?
Kyllä – oppitunnin ”Ehdolliset hypyt ja silmukat” koko tekstin voi lukea täällä verkossa ilmaiseksi. Jos haluat harjoitella interaktiivisesti sisäänrakennetulla koodieditorilla ja ympäri vuorokauden käytettävissä olevan tekoälytuutorin avulla sekä avata koko Assembly-kieli ja x86-tason järjestelmäohjelmointi-kurssin, päivitä CoddyKit PROhon. Assembly-kieli ja x86-tason järjestelmäohjelmointi-kurssilla on yhteensä 4 oppituntia.
Mitä opin oppitunnilla ”Ehdolliset hypyt ja silmukat”?
Toteuttakaa päätöksenteko ja toistuvat tehtävät vertailukäskyillä (CMP, TEST) ja ehdollisilla hyppykäskyillä (JMP, JE, JNE, JL, JG jne.). Harjoittelet Assembly-kieli ja x86-tason järjestelmäohjelmointi-aihetta koodilla, jonka suoritat suoraan selaimessa. Ympäri vuorokauden käytettävissä oleva tekoälytuutori vastaa kysymyksiisi oppitunnin aikana.
Tarvitsenko kokemusta aloittaakseni Assembly-kieli ja x86-tason järjestelmäohjelmointi-opiskelun?
Aiempi kokemus ei ole tarpeen. CoddyKitin Assembly-kieli ja x86-tason järjestelmäohjelmointi-oppimispolku sopii vasta-alkajista edistyneisiin, joten voit aloittaa tästä tai alusta ja edetä omaan tahtiisi. Tämä on oppitunti 3/4.
Kuinka kauan ”Ehdolliset hypyt ja silmukat”-oppitunnin suorittaminen kestää?
Useimmat CoddyKitin oppitunnit kestävät noin 5–10 minuuttia. Jokainen oppitunti on lyhyt ja interaktiivinen, joten edistyt tasaisesti ja voit jatkaa siitä, mihin jäit – sekä verkossa että sovelluksessa.
Voinko kirjoittaa ja suorittaa koodia tällä Assembly-kieli ja x86-tason järjestelmäohjelmointi-oppitunnilla?
Kyllä. Jokainen Assembly-kieli ja x86-tason järjestelmäohjelmointi-oppitunti sisältää sisäänrakennetun koodieditorin, joten voit kirjoittaa ja suorittaa oikeaa koodia suoraan selaimessa ja saada välitöntä palautetta tekoälyltä – paikallista asennusta ei tarvita.
Kaikki tämän kurssin oppitunnit
- Datan siirtokäskyt (MOV, PUSH, POP)
- Aritmeettiset ja loogiset operaatiot
- Ehdolliset hypyt ja silmukat
- Bittikohtaiset ja siirtokäskyt