HEXADECIMAL VE ASCII MEMORY DUMP

;=======================================================================================; 
; hexadecimal ve ascii memory dump programı 
     ; 
; C64 TÜRKİYE dergisi sayı 8 için hazırlanmıştır 
     ; 
; 10-05-2005 / ismail "hades" şahin  
     ; 
; hades@amigaturk.com 
www.c64turkiye.com  www.amigaturk.com  c64turkiye@amigaturk.com ; 
;=======================================================================================; 
*=$0801 
prg 
.word nextline 
.word 2005 
.byte $9e 
.text "2061" 
.byte 0 
nextline 
.word 0
start etiketli yere kadar olan kısımda LIST komutuyla göreceğiniz 2005 SYS2061 
satırını oluşturuyoruz. 
start  
lda 
#$0d  
;yeşil renk kodu 
jsr 
$e536 
dex 
stx 
$d020 
stx 
$d021 
stx 
$fb 
stx 
$fc

Yukarıdaki bölümde karakter rengi yeşil olacak şekilde ekranı siliyoruz ve ekran silindikten sonra X registerinin değerini 1 azaltarak "0" yapıyoruz. Bu değeri $D020 ve $D021 adreslerine vererek ekran renklerini siyah yapıyoruz. Ayrıca daha sonra kullanacağımız $FB ve $FC adreslerini sıfırlıyoruz. lda #<text1 ldy #>text1 jsr $ab1e lda #$3a jsr $ffd2 lda #$24 jsr $ffd2

Önce ekrana biraz yazı yazıyoruz sonra ":" ve "$" karakterlerini basıyoruz. adres_gir jsr hex_byte_in sta $fc ;high bayt jsr hex_byte_in sta $fb ;low bayt

Bu bölümde ilk önce adresin HIGH baytını klavyeden girip $FC adresine saklıyoruz. 
Sonrada LOW baytını girip $FB adresinde saklıyoruz. 
ldy 
#$00 
ldx 
#$06 
clc 
jsr 
$fff0

Yukarıdaki komutlarla kursörün yerini belirliyoruz. Y registerine kursörü koyacağımız yerin sütun değerini, X registerine ise satır değerini vererek Kernal Rom’daki PLOT rutinine sıçrıyoruz.

C64 TÜRKİYE  #8                                                                                                                                                5 
lda 
#<text2 
ldy 
#>text2 
jsr 
$ab1e 
lda 
#<text3 
ldy 
#>text3 
jsr 
$ab1e
Ekrana birşeyler yazdırıyoruz ve asıl bölüme geçiyoruz. 
dumper 
lda 
#$10 
sta 
line
Ekranda bir seferde kaç satır gösterileceğini ayarlıyoruz. 
line_dump 
lda 
#$20 
jsr 
$ffd2 
lda 
$fc 
jsr 
mem_to_scr 
lda 
$fb 
jsr 
mem_to_scr 
lda 
#$3a 
jsr 
$ffd2 
lda 
#$20 
jsr 
$ffd2
Önce bir adet "boşluk" basıyoruz. Programın başında girdiğimiz adresin önce HIGH 
baytını, sonrada LOW baytını hex olarak ekrana yazdırıyoruz. Son olarak ":" ve "boşluk" 
karakterlerini basıyoruz 
one_line_dump 
ldy 
#$00 
loop1  
lda 
($fb),y 
sta 
temp_scr,y 
jsr 
mem_to_scr 
lda 
#$20 
jsr 
$ffd2 
iny 
cpy 
#$08 
bne 
loop1

Bu bölümde bir satıra hex dump yapıyoruz. Y registerini sıfırlayıp bayt sayacı olarak kullanıyoruz. LDA komutuyla hafızadan o anki baytı alıyoruz ve geçici olarak saklıyoruz. Hafızadan okuduğumuz baytı JSR komutuyla HEX formatlı olarak ekrana yazdırıyoruz. Ekrana bir baytı yazdırdıktan sonra bir adet "boşluk" basıyoruz. Y registerini (bayt sayacı) 1 arttırıp 8 ile karşılaştırıyoruz. 8 olmadıysa hafızadaki bir sonraki bayt için LOOP1 etiketli yere sıçrıyoruz. 8 olduysa program aşağıdan devam ediyor. ascii ldy #$00 ascii_dump lda temp_scr,y cmp #$20 bcc no_ascii cmp #$60 bcs no_ascii .byte $2c no_ascii lda #$2e jsr $ffd2 iny cpy #$08 bne ascii_dump

Burada ise daha önce hafızadan okuyup geçici olarak sakladığımız baytların varsa ascii karşılığını ekrana yazdırıyoruz. İlk olarak Y registerini sayaç olarak kullanmak üzere sıfırlıyoruz. Sakladığımız ilk baytı alıyoruz. Önce "boşluk" karakterinden küçük olup olmadığını kontrol ediyoruz. Eğer küçükse "no_ascii" yazan yere gidiyoruz ve ekrana

C64 TÜRKİYE #8 6 "." karakterini basıyoruz. Eğer okunan bayt "boşluk" karakterinden büyükse bu sefer (Å) karakterinden büyük olup olmadığını kontrol ediyoruz. Eğer büyükse yine "no_ascii" yazan yere gidiyoruz. Eğer küçükse yani okunan bayt $20-$60 arasındaysa ekrana basıyoruz. Fakat burada $2C bayt'ı bilgisayarı kandırmak için kullanıyoruz. $2C değeri "BIT" komutunun kodu olup kullandığı parametre 2 baytlıktır. Bu parametreler ise "no_ascii" yazan yerdeki "LDA #$2E" komutunun baytlarıdır. Dolayısıyla "BIT $A92E" gibi bir komut yazmış oluyoruz. Bu durumda komut sırası .... BCS NO_ASCII - BIT $A92E - JSR $FFD2 şeklinde olmaktadır. Dolayısıyla Aküdeki değer değişmemiş olmakta ve bu değerin ASCII karşılığını yazdırmış oluyoruz. Normalde "no_ascii" yazan yere gelindiğinde Aküye $2E değeri yüklenmektedir ve $2E'nin ascii karşılığı "." karakteridir. Bu nedenle hafızadan okunan baytların ascii karakter karşılığı yoksa "." basılmaktadır. Bu işlemleri 8 defa tekrarlıyoruz ve sonra program aşağıdan devam ediyor. new_line lda #$0d jsr $ffd2

Yukarıdaki iki komutla bir alt satıra geçiyoruz. 
mem_setup 
lda 
$fb 
clc 
adc 
#$08 
sta 
$fb 
bcc 
no_inc_fc 
inc 
$fc 
no_inc_fc 
dec 
line 
bne 
line_dump

Bu bölümde ilk olarak hafızadan okuyacağımız yeni yerin adresini hesaplıyoruz. $FB adresinde okuma yaptığımız adresin LOW baytı bulunmaktadır. Bu adresteki değeri 8 ile toplayıp geri yazıyoruz. (Her seferinde 8 bayt okuduğumuz için 8 ile topluyoruz). Toplama sonucunda elde biti varsa (yani sonuç 255'ten büyükse -"C" biti "1" ise-) bu sefer $FC adresindeki HIGH baytı bir arttırıyoruz. Eğer elde biti "0" ise yani sonuç 255 veya küçükse "no_inc_fc" yazan yere gidiyoruz. Burada ise daha önce tanımlamış olduğumuz ekranda bir seferde gösterilecek satır sayısını bir azaltıyoruz. “0” olmadıysa “line_dump” yazan yere gidip ekranda 16 satır gösterilinceye kadar işlemleri tekrarlıyoruz. f_keys jsr $ffe4 cmp #$85 ;F1 - Sonraki sayfa beq next_page cmp #$86 ;F3 - Önceki sayfa beq old_pages cmp #$87 ;F5 - Yeni adres beq restart cmp #$88 ;F7 - Çıkış bne f_keys jmp $a474 ;Basic'e geri dön restart jmp start next_page .byte $2c old_pages dec $fc ldy #$00 ldx #$08 clc jsr $fff0 jmp dumper

Burası ekranda 16 satır yani 16*8=128 bayt dump edildikten sonra basılması gereken "F(onksiyon)" tuşlarının kontrol edildiği bölümdür. Önce bir JSR komutuyla tuşları okuyoruz ve "F" tuşları olup olmadığını kontrol ediyoruz. "F1" ile "next_page" yazan yere gidiyoruz. Daha önce bahsettiğimiz şekilde "BIT" komutuyla bilgisayarı kandırıyoruz ve kursörün yerini belirleyip dump etme işine tekrar başlıyoruz. "F3" ile daha önceki sayfayı ekrana getiriyoruz. Bunun için o anki hafıza adresinin HIGH baytının tutulduğu $FC adresinin değerini 1 azalttıktan sonra kursörün yerini belirliyoruz ve başa dönüyoruz. "F5" ile farklı bir adresi dump etmek için programın en başına zıplıyoruz. "F7" ile programdan çıkıyoruz.

Burası altrutinlerin olduğu bölümdür. 
hex_byte_in  
jsr 
hex_key_in  
;high nibble 
jsr 
key_to_mem 
asl 
asl 
asl 
asl 
sta 
$fb 
jsr 
hex_key_in  
;low nibble 
jsr 
key_to_mem 
ora 
$fb 
sta 
$fb 
rts 
Klavyeden bir baytlık hex sayı girme ve bu sayıyı hafızaya saklama bölümüdür. Önce 
klavyeden hex karakter girilen alt rutine gidiyoruz. Geri dönüşte aküde bulunan tuş değe-
rinin sayısal karşılığını almak için bir başka alt rutine gidiyoruz. Buradan geri dönüşte 
ise elimizdeki sayıyı 4 kez sola kaydırıp high nibble olarak $FB adresine saklıyoruz.Aynı 
alt rutinlere bir kez daha uğruyoruz ve daha önce high nibble olarak sakladığımız değerle
R işlemi yaptıktan sonra aynı adrese yazıyoruz. 
O
hex_key_in  
jsr 
$ffe4 
ldx 
#$00 
control 
cmp 
key_table,x 
bne 
next 
jsr 
$ffd2 
rts 
next  
inx 
cpx 
#$10 
bne 
control 
jmp 
hex_key_in
Bu kısımda klavyeden sadece hex sistem tuşlarına basılıp basılmadığını kontrol edi-
yoruz. Önce klavye taranıyor. Tarama sonunda Aküdeki değeri bir sayaca göre tablodaki 
değerle karşılaştırıyoruz. Eğer karşılaştırma sonucunda basılan tuş tabloda varsa karak-
ter ekrana basılıyor ve rutinden çıkılıyor. Yoksa klavye tekrar taranıyor. 
key_to_mem  
ldx 
#$00 
loop0  
cmp 
key_table,x 
beq 
val_read 
inx 
cpx 
#$10 
bne 
loop0 
val_read 
lda 
val_table,x 
rts
Bu kısımda basılan tuşa göre hafızaya alınacak sayı elde ediliyor. Aküdeki değer 
bir tablo ile karşılaştırılıyor. Karşılaştırma sonucu eşitlik varsa, kullanılan sayacın 
değeri kullanılarak başka bir tablodan hafızaya yazılacak değer okunuyor ve rutinden 
çıkılıyor.  
mem_to_scr  
pha 
lsr 
lsr 
lsr 
lsr 
jsr 
convert 
pla 
and 
#$0f 
convert 
tax 
lda 
key_table,x 
jsr 
$ffd2 
rts

Geldik son alt rutine. Burada yapılan iş hafızadan okunan bir baytı hex olarak ekrana yazdırmak. İlk olarak hafızadan okunan bayt daha sonra tekrar kullanılmak üzere yığına atılıyor. Sonra HIGH nibble değerini ekrana yazdırmak için 4 kez sağa kaydırılıyor. Elde edilen değer sayaç olarak kullanılarak, sayaca göre tablodan okunan değer ekrana yazdırılıyor. Daha sonra yığındaki değer geri alınarak $0F sayısı ile AND işlemi yapılıyor. Böylece LOW nibble elde ediliyor. Sayaç işlemleri bir kez daha yapılıp hafızadaki bir sayı hex olarak ekrana yazdırılmış oluyor.

key_table 
.text "0123456789abcdef" 
;basılması gereken tuş tablosu 
val_table 
.byte 0,1,2,3,4,5,6,7,8,9 
;tuşlara göre sayısal değerler 
.byte 10,11,12,13,14,15 
line  
.byte 16 
;ekrana basılacak satır sayısı 
text1  
.text "   c64 turkiye hex-ascii dump program" 
.byte $0d 
.text " 10-may-2005    code: hades of ascraeus" 
.byte $0d,$0d 
.text "f1:next    f3:prev.   f5:new     f7:exit" 
.byte 13,13 
text2  
.text " adres" 
.byte 0 
text3  
.text " hexadecimal memory dump  ascii " 
.byte $0d 
.text " ===== ======================= ========" 
.byte $0d,0 
temp_scr 
.byte 0,0,0,0,0,0,0,0 
;geçici saklama bölgesi 
.end