-
Sadrazamv4
ig:sadrazam_v4 tg: Sadrazam.spy
🚀 BAŞTAN SONA x86 ASSEMBLY BÖLÜM-5: Dizi Komutları (`MOVS`, `STOS`, `LODS`, `CMPS`) ve `REP` Önekleri 💻
Selamlar! Serimizin 5. bölümüne hoş geldiniz.
Önceki bölümde Yığın (Stack) mimarisini, `ESP` ve `EBP` yazmaçlarının işlevini, `PUSH` / `POP` kullanımını, `CALL` / `RET` mekanizmasını ve Fonksiyon Çerçevesi (Stack Frame) yapısını incelemiştik. Bu bölümde ise bellek blokları ve metinler üzerinde ultra hızlı işlem yapmamızı sağlayan **Dizi/String Komutlarını** ve bunları döngüye sokan **`REP` Öneklerini** öğreneceğiz.
---
📌 1. Dizi İşlemlerinde Kritik Yazmaçlar: `ESI` ve `EDI` 🧭
x86 mimarisinde bellek blokları veya metinsel veriler üzerinde işlem yapılırken iki özel indeks yazmacı kullanılır:
• **`ESI` (Source Index):** Kaynak bellek adresini tutar.
• **`EDI` (Destination Index):** Hedef bellek adresini tutar.
• **`ECX` (Count Register):** Kopyalanacak veya taranacak eleman sayısını (sayaç) tutar.
---
🚩 2. Yön Bayrağı (Direction Flag - DF) 🧭
Dizi komutları çalıştırıldığında `ESI` ve `EDI` yazmaçları otomatik olarak **artırılır** veya **azaltılır**. Bu yönü `EFLAGS` içindeki **Direction Flag (DF)** belirler:
• **`CLD` (Clear Direction Flag):** `DF = 0` yapar. Komut çalıştıkça `ESI` ve `EDI` **İLERİ** doğru (`+1`, `+2`, `+4` bayt) artar. *(Genelde tercih edilen varsayılan mod)*
• **`STD` (Set Direction Flag):** `DF = 1` yapar. Komut çalıştıkça `ESI` ve `EDI` **GERİ** doğru (`-1`, `-2`, `-4` bayt) azalır.
---
🧰 3. Temel Dizi Komutları Familyası 🔤
Dizi komutları işlem yapılan verinin boyutuna göre son takı alır:
- **`B` (Byte - 1 Bayt):** `MOVSB`, `LODSB`, `STOSB`
- **`W` (Word - 2 Bayt):** `MOVSW`, `LODSW`, `STOSW`
- **`D` (Double Word - 4 Bayt):** `MOVSD`, `LODSD`, `STOSD`
### A. `MOVS` (Move String):
`[ESI]` adresindeki veriyi `[EDI]` adresine kopyalar ve indisleri kaydırır.
### B. `STOS` (Store String):
`AL` / `AX` / `EAX` yazmacındaki değeri `[EDI]` adresine yazar. (Belleği belirli bir karakter veya 0 ile doldurmak/temizlemek için idealdir).
### C. `LODS` (Load String):
`[ESI]` adresindeki veriyi `AL` / `AX` / `EAX` yazmacına yükler.
### D. `CMPS` (Compare String):
`[ESI]` adresindeki veri ile `[EDI]` adresindeki veriyi karşılaştırır (`CMP`) ve bayrakları günceller.
---
🔁 4. Tekrarlama Öneki: `REP` (Repeat) 🔄
`REP` öneki, önün konulduğu dizi komutunu **`ECX` yazmacındaki değer `0` olana kadar** otomatik olarak döngüsel şekilde çalıştırır. Her adımda `ECX` değerini 1 azaltır (`DEC ECX`).
• **`REP`:** `ECX != 0` olduğu sürece tekrarlar (`MOVS` ve `STOS` ile kullanılır).
• **`REPE` / `REPZ`:** `ECX != 0` ve `ZF = 1` (Eşitlik devam ettiği) sürece tekrarlar.
• **`REPNE` / `REPNZ`:** `ECX != 0` ve `ZF = 0` (Eşitlik olmadığı) sürece tekrarlar.
---
🧪 5. Uygulama: Assembly İle Metin Kopyalama (`strcpy`) 🚀
Gelin `REP MOVSB` kullanarak bir metni hafızadaki başka bir alana kopyalayalım:
```nasm
section .data
kaynak db 'x86 Assembly Dizi Komutlari!', 0
uzunluk equ $ - kaynak
section .bss
hedef resb 50 ; Hedef için 50 baytlık boş alan ayırıyoruz
section .text
global _start
_start:
cld ; Direction Flag sıfırlanıyor (İleri yönlü okuma: ESI++, EDI++)
mov esi, kaynak ; ESI = Kaynak metnin adresi
mov edi, hedef ; EDI = Hedef bellek alanı adresi
mov ecx, uzunluk ; ECX = Kopyalanacak bayt sayısı (Sayaç)
rep movsb ; ECX sıfırlanana kadar [ESI] -> [EDI] kopyala!
; Kopyalama bitti! Hedef metni ekrana yazdıralım (sys_write)
mov eax, 4 ; sys_write
mov ebx, 1 ; stdout
mov ecx, hedef ; Yazdırılacak adres (hedef)
mov edx, uzunluk ; Yazdırılacak uzunluk
int 0x80
; Programdan Çıkış (sys_exit)
mov eax, 1
xor ebx, ebx
int 0x80
Selamlar! Serimizin 5. bölümüne hoş geldiniz.
Önceki bölümde Yığın (Stack) mimarisini, `ESP` ve `EBP` yazmaçlarının işlevini, `PUSH` / `POP` kullanımını, `CALL` / `RET` mekanizmasını ve Fonksiyon Çerçevesi (Stack Frame) yapısını incelemiştik. Bu bölümde ise bellek blokları ve metinler üzerinde ultra hızlı işlem yapmamızı sağlayan **Dizi/String Komutlarını** ve bunları döngüye sokan **`REP` Öneklerini** öğreneceğiz.
---
📌 1. Dizi İşlemlerinde Kritik Yazmaçlar: `ESI` ve `EDI` 🧭
x86 mimarisinde bellek blokları veya metinsel veriler üzerinde işlem yapılırken iki özel indeks yazmacı kullanılır:
• **`ESI` (Source Index):** Kaynak bellek adresini tutar.
• **`EDI` (Destination Index):** Hedef bellek adresini tutar.
• **`ECX` (Count Register):** Kopyalanacak veya taranacak eleman sayısını (sayaç) tutar.
---
🚩 2. Yön Bayrağı (Direction Flag - DF) 🧭
Dizi komutları çalıştırıldığında `ESI` ve `EDI` yazmaçları otomatik olarak **artırılır** veya **azaltılır**. Bu yönü `EFLAGS` içindeki **Direction Flag (DF)** belirler:
• **`CLD` (Clear Direction Flag):** `DF = 0` yapar. Komut çalıştıkça `ESI` ve `EDI` **İLERİ** doğru (`+1`, `+2`, `+4` bayt) artar. *(Genelde tercih edilen varsayılan mod)*
• **`STD` (Set Direction Flag):** `DF = 1` yapar. Komut çalıştıkça `ESI` ve `EDI` **GERİ** doğru (`-1`, `-2`, `-4` bayt) azalır.
---
🧰 3. Temel Dizi Komutları Familyası 🔤
Dizi komutları işlem yapılan verinin boyutuna göre son takı alır:
- **`B` (Byte - 1 Bayt):** `MOVSB`, `LODSB`, `STOSB`
- **`W` (Word - 2 Bayt):** `MOVSW`, `LODSW`, `STOSW`
- **`D` (Double Word - 4 Bayt):** `MOVSD`, `LODSD`, `STOSD`
### A. `MOVS` (Move String):
`[ESI]` adresindeki veriyi `[EDI]` adresine kopyalar ve indisleri kaydırır.
### B. `STOS` (Store String):
`AL` / `AX` / `EAX` yazmacındaki değeri `[EDI]` adresine yazar. (Belleği belirli bir karakter veya 0 ile doldurmak/temizlemek için idealdir).
### C. `LODS` (Load String):
`[ESI]` adresindeki veriyi `AL` / `AX` / `EAX` yazmacına yükler.
### D. `CMPS` (Compare String):
`[ESI]` adresindeki veri ile `[EDI]` adresindeki veriyi karşılaştırır (`CMP`) ve bayrakları günceller.
---
🔁 4. Tekrarlama Öneki: `REP` (Repeat) 🔄
`REP` öneki, önün konulduğu dizi komutunu **`ECX` yazmacındaki değer `0` olana kadar** otomatik olarak döngüsel şekilde çalıştırır. Her adımda `ECX` değerini 1 azaltır (`DEC ECX`).
• **`REP`:** `ECX != 0` olduğu sürece tekrarlar (`MOVS` ve `STOS` ile kullanılır).
• **`REPE` / `REPZ`:** `ECX != 0` ve `ZF = 1` (Eşitlik devam ettiği) sürece tekrarlar.
• **`REPNE` / `REPNZ`:** `ECX != 0` ve `ZF = 0` (Eşitlik olmadığı) sürece tekrarlar.
---
🧪 5. Uygulama: Assembly İle Metin Kopyalama (`strcpy`) 🚀
Gelin `REP MOVSB` kullanarak bir metni hafızadaki başka bir alana kopyalayalım:
```nasm
section .data
kaynak db 'x86 Assembly Dizi Komutlari!', 0
uzunluk equ $ - kaynak
section .bss
hedef resb 50 ; Hedef için 50 baytlık boş alan ayırıyoruz
section .text
global _start
_start:
cld ; Direction Flag sıfırlanıyor (İleri yönlü okuma: ESI++, EDI++)
mov esi, kaynak ; ESI = Kaynak metnin adresi
mov edi, hedef ; EDI = Hedef bellek alanı adresi
mov ecx, uzunluk ; ECX = Kopyalanacak bayt sayısı (Sayaç)
rep movsb ; ECX sıfırlanana kadar [ESI] -> [EDI] kopyala!
; Kopyalama bitti! Hedef metni ekrana yazdıralım (sys_write)
mov eax, 4 ; sys_write
mov ebx, 1 ; stdout
mov ecx, hedef ; Yazdırılacak adres (hedef)
mov edx, uzunluk ; Yazdırılacak uzunluk
int 0x80
; Programdan Çıkış (sys_exit)
mov eax, 1
xor ebx, ebx
int 0x80
🔒 Bu içeriği görmek için giriş yapın