x86 işlemci mimarisinde bayrak (flag) yapısı

13:34 ,


     Dünya genelinde hala en yaygın işlemci mimarisi olan x86 işlemci ailesinin bayrak (flag) yapısını öğrenmemiz assembly dilinde kod yazmak isteyenler için birazda zorunlu bir konu başlığıdır. En basitinden bir for döngüsünü yazabilmek için flag değerine başvurmamız gerekmektedir. Bayrak (flag) yazmaçları CPU'nun çalışmasını (real/protected mod gibi) belirlediği gibi çalışma sırasındaki durumlarını da öğrenmemizi sağlayan yazmaç değerleridir. İşlem sonucu 0 ise şunu yap şuraya dallan gibi işlemleri gerçekleştirebilmemiz için öğrenmemiz gerekmektedir. Şimdi sırası ile yazmaçları ve ne işe yaradıklarına kısaca bakalım;

Direction flag (DF)

Bir tane kontrol bayrağı (Control Flag) bulunmaktadır. Bu bayrak Direction flag (DF) bayrağıdır. String komutları denilen bir grup makine komutu bu bayrağa bakarak işlemin yönüne karar vermektedir (sağdan sola mı yoksa soldan sağa doğru mu). STD ( set direction flag ) ile set (yani 1) ve CLD (clear direction flag) ile reset (yani 0) işlemi yapılır. 

Durum bayrakları (Status Flag)

Aşağıda görüleceği üzere altı tane durum bayrağı (Status Flag) bulunmaktadır. Bunlar;

  • Carry flag (CF)
  • Parity flag (PF) 
  • Auxiliary carry flag (AF) 
  • Zero flag (ZF)
  • Sign flag (SF)
  • Trap flag (TF)
  • Interrupt flag (IF)
  • Overflow flag (OF)



Carry flag (CF)

İşaretsiz tamsayılar üzerinde işlemler yapılırken işlem sonucunda taşma ya da borç oluşursa bu bayrak set edilmektedir.

MOV         AH, 3F
MOV         AL, F4
ADD         AH, AL

Burada 3F ile F4 toplandığında sonuç 8 bite sığmamaktadır. Bu nedenle taşmadan dolayı carry flag set edilmiştir. İşaretsiz sayıların çıkartılması durumunda borç oluşursa da bu bayrak set edilmektedir. CF bayrağı işaretsiz düzeydeki çıkartma işleminde borç oluşuyorsa set edilir, borç oluşmuyorsa reset edilir.

MOV         AH, 3F
MOV         AL, F4
SUB         AH, AL

Yukarıda 8 bitlik çıkarma işlemi yapılmıştır. İşaretsiz düzeyde AH’taki değer AL’deki değerden (işaretsiz olarak) daha küçük olduğu için borç oluşur. Dolayısıyla işlem sonucunda CF bayrağı set edilecektir.

Parity flag (PF) 

Bir işlemin sonucundaki değerde 1 olan bitlerin sayısı çift ise PF bayrağı set (1) edilmektedir, Tek ise reset (0) edilmektedir. PF bayrağı “parity” denilen hata kontrol (error check) mekanizması için düşünülmüştür.

Auxiliary carry flag (AF) 

Bu bayrak 3’üncü bit'ten 4’üncü bit'e taşma oluşmuşsa set edilir, taşma yoksa reset edilir. Yani bu bayrak düşük anlamlı 4 bitteki taşmaya bakmaktadır.

Zero flag (ZF)

Son yapılan işlemin sonucu sıfır ise bu bayrak set edilir, sıfır değilse reset edilir. Örneğin:

MOV         EAX, 1
DEC         EAX

Buradaki DEC makine komutu EAX yazmacının içerisindeki değeri 1 eksiltir. EAX yazmacındaki değer 1 olduğuna göre DEC komutundan sonra işlem sonucu sıfır olduğu için ZF bayrağı set edilmektedir.

Sign flag (SF)

Bu bayrak işlem sonucunda elde edilen değerin en soldaki bitini (işaret bitini) tutar. Başka bir deyişle işlem sonucunda elde edilen değerin işaret bit'i (en soldaki biti) 0 ise bu bayrak reset edilir, 1 ise set edilir. Örneğin bu bayrak sayesinde biz son yapılan çıkarma veya işaretli toplama işlemden elde edilen değerin negatif olup olmadığını anlayabiliriz. Ayrıca CMP işleminden sonra kullanıldığında sayının büyük ya da küçük olup olmadığı kontrol edilebilir.

Trap flag (TF)

Trap flag debuggerlar için en önemli bayraktır. Set edilmişse (yani 1 değerinde ise) işlemci her bir makine komutundan sonra Single Step diye bilinen 1 numaralı kesmeyi çağırır. Set edildiğinde EI (Enable Interrupt); reset edildiğinde DI (Disable Interrupt) değerindedir. 

Interrupt flag (IF)

INTR girişini kontrol eder. Böylece IRQ kesmelerini kapatır ya da açar. 1 ise aktif 0 ise pasif durumdadır. Bu durumda iken gelen kesmelere cevap verilmez. Pasif durumdayken NMI (Non Maskable Interrupt) haricindeki bütün kesmeler iptal edilir. Reset etmek için CLI, set etmek için ise STI komutları kullanılır. Reset işleminden sonra DI (Disabled Interrupts), set edince EI (Enabled Interrupts) değerini alır. 

Overflow flag (OF)

Bu bayrak sıklıkla CF bayrağı ile karıştırılmaktadır. OF işaretli tamsayılarda bir taşma ya da borç oluştuğunda SET edilmektedir. Eğer bir işleme sokulan sayıların en soldaki bitleri (yani işaret biti) aynı ise fakat işlem sonucunda elde edilen değerin en soldaki biti bunlardan farklı ise OF set edilir aynıysa reset edilir. (İşleme sokulan sayıların işaret bitleri farklı ise OF bayrağının her durumda reset edildiğine dikkat ediniz.) Örneğin:

mov eax, 0xFFFFFFF0 ;       1111 1111  1111  1111 1111  1111 1111 0000
mov ebx, 0x000000FF ;       0000 0000 0000 0000 0000 0000 1111 1111
add  eax, ebx                 ; (1) 0000 0000 0000 0000 0000 0000 1110 1111

Yukarıdaki add işleminde OF bayrağı reset edilecektir. Çünkü sayıların işaret bitleri farklıdır. Ancak CF bayrağının set edileceğine dikkat ediniz. Örneğimizdeki 0xF0000000 sayısı işaretli olarak 10’luk sistemde -16’dır. 0x000000FF ise işaretli olarak 10’luk sistemde +255’tir. Toplama işleminin sonucunda 10’luk sistemde 239 sayısı elde edilecektir. Toplama işleminde işaretli düzeyde bir taşma olmadığına dikkat ediniz. 

Fakat örneğin:

mov eax, 0xFFFFFFF0 ;     1111 1111 1111 1111 1111 1111 1111 0000
mov ebx, 0x80000000 ;     1000 0000 0000 0000 0000 0000 0000 0000
add eax, ebx                 ;     (1) 0111 1111 1111 1111 1111 1111 1111 0000

Buradaki add komutunda sayıların işaret bitleri (yani en soldaki bitleri) 1’dir (yani aynıdır). Fakat işlem sonucunda elde edilen değerin işaret biti 0’dır. Bu durumda OF set edilecektir. (Ayrıca CF bayrağının da set edileceğine dikkat ediniz.) Pekiyi OF bayrağının programcı için anlamı nedir? OF bayrağı sayıların işaretli (signed) olduğu fikriyle işleme sokulması durumunda işlem sonucunda işaretli taşma ya da borç oluştuğunda set edilmektedir. OF bayrağı ile CF bayrağının birbirlerine benzediğine dikkat ediniz. CF bayrağı sayıların işaretsiz kabul edildiği durumda taşma ya da borç oluştuğunda set edilirken OF bayrağı sayıların işaretli kabul edildiği durumda taşma ya da borç olduğunda set edilmektedir.