Home  Articles  Programs 

GEOS I

Eğer C-64 kullanıcısıysanız, hele bir de disk drive'ınız varsa mutlaka GEOS (Graphic Environment Operating System = Grafik Ortam İşletim Sistemi) adını duymuşsunuzdur. Bu yazı dizimizde size GEOS'un kullanımını ve GEOS tarafından çalıştırılabilecek programların (Application = uygulama) nasıl yazılabileceğini anlatacağım. Eğer sürekli Commodore Dergisi okuruysanız daha önce de bu konuya değindiğimizi hatırlarsınız. Fakat konumuz açısından hayati önem taşıdığı için bu yazıların kısa bir özetiyle başlayacağım dizimize. (Daha ayrıntılı bilgi için Commodore Dergisi sayı 49'u gözden geçirin.)

Bildiğiniz gibi GEOS, bit-mapped ekran üzerinde menüler, ikonlar, diyalog kutulan gibi yüksek düzeyde kullanım rahatlığı getiren işleri kullanmakta ve programlarında oldukça rahatlık sağlamaktadır. Eğer sizin programlarınızda da bu rahatlığa sahip olmak isterseniz, GEOS'u kullanmanız size büyük bir avantaj ve rahatlık sağlayacaktır.

Peki ama bütün bu rahatlığı sağlayan GEOS nedir? GEOS, tıpkı C-64'ünüzün sahip olduğu kernal gibi kendi kernal'ına sahip, bu kernal'da pull-down menü, ikon, normalin dört katı hızlı bir disket işletim sistemi, string I/O rutinleri gibi, program yazarken en çok ihtiyaç du-yacağınız rutinleri saklayan bir işletim sistemidir. (49. sayıda kernal daha ayrıntılı biçimde işlenmiştir.) Aslında Desk-Top, yani GEOS'u çalıştırdığınızda karşınıza çıkan ve dosyaları ikon ve menüler yardımıyla kullanmanızı sağlayan program GEOS'a dahil değildir, yalnızca ilerde sizin de yazmayı öğreneceğiniz türden bir uygulama'dır. GEOS yalnızca bu tür uygulama'ları destekleyen bir işletim sistemidir.

GEOS kernal'ının içinde iki düzeyde kod çalışmaktadır. Bunlar ana döngü (Main loop) ve interrupt düzeyidir (Interrupt level). Ana döngü, eventleri tarayarak gerekli rutinleri çağıran ve bu arada sizin uygulamalarınızı çalıştıran uzun bir koddur. Interrupt düzeyi kodu ise saniyede 60 kere main kodu keserek donanımı okur. Bu sayede, ana döngü ne ile uğraşırsa uğraşsın, sizin bastığınız tuşun veya oynattığınız joystick'in hatasız olarak okunabilmesi sağlanır. Bunun yanında eğer programınızda interrupt düzeyini kullanmak istiyorsanız yalnızca GEOS'a kendi interrupt düzeyinin arkasına sizinkini eklemesini istediğinizi söylemeniz yeterlidir. Gördüğünüz gibi GEOS gerekli olan bütün yükü kendi üstüne almıştır. Eğer makine dili biliyorsanız, GEOS'la program yazmaktan daha kolay bir iş olmadığını göreceksiniz. Tabii bu arada belirtmem gerekir ki bu iş de dünyanın en kolay işi değil. Özellikle GEOS dosyalarının standartlardan farklı olması yüzünden bazı zorluklar çıkıyor karşımıza. Fakat gelecek ayki yazımızla vereceğimiz ‘THE ULTIMATE GEOS CONVERTER' programı ile bu problemi halledeceğiz.

Bu kadar özetten sonra daha ciddi konulara, yani GEOS kemal rutinlerinin kullanılmasına gelelim:

GEOS yaratıcıları her şeyden önce zero page'de kendilerine bazı bölgeler ayırmışlar. Bunun sebebi ise 6502 komutlarının zero page kullanımında daha az yer tutması ve daha az zaman alması. Bununla birlikte, bu bölgeler yardımıyla değerlerin kernal rutinlerine yollanması ve rutinlerin bu bölgelerde hesap yaparak sonuçlarını yine aynı bölgeler yardımıyla göndermesi, programcının belleğin hangi kısmının kullanıldığını hatırlatması konusunda büyük kolaylık sağlar.

Bunun sonucunda GEOS'un programcıları $02'den başlayan 30 baytlık bir bölgeyi pseudoregister olarak ayırmışlar. Bu bölge 15 adet çift baytlık değişkendin oluşur. Bu değişkenlerin isimleri, r0, r1, r2, ..., r15'tir. Yazımızda bu psoundoregisterlerin low-baytları rN veya rNL olarak adlandırılacaklar. (Burada N, register numarasıdır: r0, r0L.. gibi). High baytlar ise rNH olarak isimlendirilecekler.

Bu pseuderegisterler yardımıyla GEOS Kernal rutinleriyle haberleşmeniz mümkün olacağı için bu bölgelere yazımızda sık sık değineceğim. Bu bölgeler GEOS kernal'ının işlem yaptığı tek bölgedir. Bu sayede hiç korkmadan belleğin bize ayrılan kısmını rahatlıkla kullanabiliriz.

GEOS Kernal rutinlerine değer yollamanın tek yolu bu pseudoregisterler değildir. Hız gerektiği zamanlar A, X, Y ve hatta carry flag kullanılabilir. Fakat bunlar arasında özellikle sık çağrılan rutinlerde kullanılan in-line çağrımlar en kullanışlısıdır. In-line çağıranlarda rutine gönderilecek değerler doğrudan doğruya jsr komutunun arkasına eklenir. Buna şöyle bir örnek verebiliriz:

jsr i-rectangle  ; şu anki sistem motifiyle bir dikdörtgen çiz
.by 0            ; üst y koordinatı (0-199)
.by 199          ; alt y koordinatı (0-199)
.wo 0            ; sol kenar (0-319)
.wo 319          ; sağ kenar (0-319)

Program jsr komutundan döndüğünde 6 baytı atlar ve buradan işlemeye devam eder. In-line çağrımlarda daha sonra gelen byt sayısına dikkat etmezseniz programınız kilitlenebilir. Yukarıdaki programı çalıştırdığınızda tüm ekranı sistemin son kullandığı 8x8 ebatlarındaki motif ile doldurur. Bu tür çağrımların tek zararı normal çağrımlardan daha yavaş olmasıdır. Ama örnek programı incelersek toplam 9 bayt aldığını görürüz. Oysa aynı programı pseudo registerler yardımıyla yapsaydık 27 bayt uzunluğunda olacaktı. Sanırım bu kadar büyük bir bellek tasarrufu için birkaç mikrosaniye feda etmekten çekinmezsiniz. Bu arada ekleyeyim, bundan sonra rutin adlarından önce gelecek bir i- ifadesi bu rutinin bir inline sistemiyle çağrılması gerektiği manasına gelecek.

Şimdiye kadarki kısımlarda yalnızca ana döngü ve Interrupt düzeyinden bahsettik. Oysa bazen (pek tavsiye etmememe rağmen) ana döngü ve interrupt düzeyini değiştirmeniz gerekebilir. Bu gibi durumlar düzeltmesi çok zor olan senkronizasyon bozukluklarına yol açabileceği için çoğu programcı bu yolu tercih etmez.

Bu kod cinsine non-event kodu denir. Zorluğu ve gereksizliği yüzünden pek tercih edilmeyen bir yoldur. Eğer özel bir donanım eklemek için ana döngüden bağımsız bir interrupt rutini çalıştırmak istiyorsanız, non-event kodu tercih etmeniz gerekecektir. Bunu yapabilmek için belirli bazı sistem değişkenlerinin değerleriyle oynamanız gerekmektedir. Bu sistem değişkenlerinin isimleri interrupt TopVector, interrupt BottomVector, ve applicationMain'dir. (Şu anda yeterli bilgiye sahip olmadığımız için bu değişkenlerin adreslerini yazmayacağım fakat ileride GEOS'un tüm sabit değerlerini, değişken adreslerini ve rutin adreslerini içeren tablolar yayınlayacağız). Eğer interruptTopVector'ün değeri değiştirilirse sizin kodunuz (tahmin ettiğiniz gibi) GEOS interrupt düzeyinden önce çağrılacaktır. Bu yolu seçtiyseniz önceden bu adreste saklanan InterruptMain adresine bir jump yaparak programınızı terk etmelisiniz. Değiştirdiğiniz vektör interrupt BottomVector ise programınız normal interrupt düzeyinden sonra çağrılacaktır. GEOS bu vektörün değerinin 0'dan farklı olması sayesinde sizin burayı kullandığınızı anlar. Burada dikkat etmeniz gereken en önemli husus ise programınızın sonunda RTS kullanmanız gerektiğidir. Eğer yanılıp da RTI kullanırsanız programınız ve GEOS kilitlenir. Eğer applicationMain vektörünü değiştirirseniz ana döngü sonunda programınıza atlama yapılır. Burada da RTS ile ana döngüye dönebilirsiniz.

Şimdiye kadar öğrendiklerinizle bir uygulama yazmanız mümkün olmasa bile, ileride devam edecek yazımız için çok önemli bir temel oluşturmaktadır. Bu yüzden 49. sayıda yazılanları ve bu yazıyı çok iyi anlamazsanız daha ileride büyük zorluklarla karşılaşırsınız.

Gelecek sayımızda bir uygulama yazmanın temel adımları konusunu işleyeceğiz ve bir de basit GEOS bellek haritası yayınlayacağız. Gelecek ay bu köşede buluşmak üzere...

kaynak: Teleteknik Commodore Dergisi, Sayı 53, Sayfa 24-26

Teleteknik
01.07.1990

Keywords: GEOS, İşletim Sistemleri, Commodore, C64


C64 Projects Twitter Page

İlker Fıçıcılar's CBM Page