Geçenlerde devrenin şemasını çizdim. Yalnız EasyEda ile yıldızımız pek barışamadı, biraz erken terkettim bu uygulamayı. Eagle'da şematik çizme konusunda biraz bir şeyler kapmıştım, onda devam ettim. Pcb tasarım kısmında da şimdilik autorouter üç kağıdından faydalandım.
Şematik aşağıdaki gibi,

Eagle schematic ve board dosyaları da şurada :
http://www.tepetaklak.com/data/7kernalmod.zipOla ki biri açıp derse, daha sonra pcb'nin alt ve üst katmanlarına ground layer ekledim. Tamamen gözümden kaçmış

Pcb tasarımından memnun kalırsam prototip amaçlı üretime göndereceğim. (Henüz sipariş söz konusu değil)
Bir yandan da attiny üstünde nasıl bir kod yazacağım onu şekillendirmeye çalışıyorum kafamda. Sürekli adres hatlarını dinlemesini istemiyorum. Kullanıcının kernal seçimi yapacağı zaman dilimi oldukça kısa olacak, geri kalan zamanda düşük güç moduna geçsin istiyorum. Tabii burada da uzun süre uyursa gelecek komutları kaçırma durumu olacak. Interrupt ile uyansın desek dinleyeceğimiz bit sayısı 1 olduğu için bununla karşılaşma olasılığı çok yüksek olduğu için çok mantıklı olmayacak.
Açılışta 3-5 dakika çalışsın sonra uyusun desek aslında çok da mantıksız değil. Ortada üretilen bir şey yok bu arada sadece yazılı düşünüyorum

C64'de çalışan programın özenle yaptığı adres erişimleri için de fuzzy (bulanık mantık) bir state machine (durum makinesi) kullanmayı düşünüyorum.
Örneğin benim dinleyeceğim adres hattı A0 olsun.
Fuzzy olmasından kasıt şu : A0 adres hattının 0 yahut 1 olması durumundan ziyade. Belli bir zaman diliminde A0=0 olan erişimlerin toplam erişim sayısına oranı esas input olacak.
Bu arada devre şemasını çizerken geçici olarak karar verdiğim A0 seçiminin çok da doğru bir seçim olmadığını anlamış bulunuyorum. Zira işlemci yazdığım programı çalıştırırken de bellekten komutları ve komutların operand'larını getirmek için belleğe erişiyor. Anlamlı bir şeyler yapabilmek için en 2 byte'lık opcode'lar kullanmak gerektiği için kod çalışırken A0'ın toggle etmesi kaçınılmaz. Bu da hataya sebep olacağı için dinleyeceğimiz adres hattının yüksek adres hatlarından birinde yeralması gerekiyor.
Beri yandan attiny'e /OE de bağlı, yani aslında /OE=1 iken yani rom seçilmemişken bunu sayacağım erişim olarak kabul etmeyebilirim. Programın rom'dan çalışması durumunda /OE de sürekli toggle edeceği için yine aynı şey geçerli. Ancak kullanacağım biti A13 seçersem ve kodumu da 8K'lık kernal rom alanının alt 4k'lık bölümünde çalıştırırsam A13'ün programın çalışmasından dolayı toggle etmesinin önüne geçerim.
Şimdilik ona A13 diyelim.
İyi ki aceleye getirip pcb'yi sipariş etmemişim

Neyse ne diyorduk, bilgi girişimiz fuzzy olacak. Birim zamanda A13 adres hattının 1 olduğu adreslere gelen erişim sayısı / birim zamandaki toplam erişim sayısı benim girişim olacak.
Durum makinesinin şu durumlarının olması gerekiyor.
- Bilgi almayı bekle
- Senkronizasyon * N
- Bilgi almaya başla
- Kernal 1 * M
- Kernal 2 * M
- Kernal 3 * M
- ....
Burada öncelikle senkronizasyon kısmını açayım. Microcontroller ile işlemci arasında bahsettiğimiz örnekleme diliminin başlangıcı için bir senkronizasyon olmadığı için kabaca bunu sağlamak gerekiyor. Kabaca çünkü fuzzy lojik çalışacağımız için belli sapma değerlerini kabul edebiliyor olacağız. C64 ilk açıldığında ister istemez kernal devreye girdiği için ve A13 hattını toggle edecek erişimler yapacağı için durum makinemizin c64'de çalışacak programla bir senkronizasyonu olmayacak. Tasarlayacağımız durum makinesinin senkronizasyon durumları bu zaman kaymasını azaltmaya yönelik olacak. C64'de çalışan program da durum makinesini "Bilgi almaya başla" durumuna getirene kadar senkronizasyonu sağlayacak durumları atlatacak şekilde erişimlerini yapacak ve sonrasında bilgi göndermeye başlayacak. (C64'de teyp turbolarında kullanılan pilot sinyali de aşağı yukarı bu şekilde çalışıyor sanırım)
Sonrasında da her bir kernal seçiminin durum makinesinde birbirinden farklı şekilde kodlanması gerekiyor. Bunun için durum makinesinde bir kernal seçimini kabul etmek için N adet örneğin uymasını bekleyeceğiz. N ne kadar yüksek olursa herhangi bir programın açılışta kazara kernal'i değiştirme ihtimali o kadar düşüyor.
Senkronizasyonu yaptığımızı kabul edelim,
Misal kernal 1'i seçmek için programımız,
birim zaman diliminde,
1. 100 erişim yapıp 25'ini A13 = 1 iken yapıyor,
2. 100 erişim yapıp 50'sini A13 = 1 iken yapıyor,
3. 100 erişim yapıp 75'ini A13 = 1 iken yapıyor,
4. 100 erişim yapıp 25'ini A13 = 1 iken yapıyor,
5. 100 erişim yapıp 50'sini A13 = 1 iken yapıyor,
6. 100 erişim yapıp 100'ünü A13 = 1 iken yapıyor,
7. 100 erişim yapıp 0'ını A13 = 1 iken yapıyor
...
...
N. 100 erişim yapıp 50'sini A13 = 1 iken yapıyor
Burada örneğin
0 erişimi >=0, <=Threshold gibi algılamak lazım.
aynı şekilde,
25 erişimi >=25-Threshold <25+Threshold
Kernal seçimini tanıyacak geçişe uygun olmayan tüm girdileri de "Bilgi almayı bekle" durumuna göndereceğiz.
0, 25, 50, 75, 100 şeklinde 5 fuzzy girdimiz olduğunda N tane sıralı girdi kabulu için 5^N girdiyi doğru göndermesi gerekiyor herhangi bir programın. Örneğin N'i 6 yapsak toplam 5^10 = 9.765.625 adet girdiyi bizim beklediğimiz sırada göndermesi gerekiyor herhangi bir çalışan programın. Senkronizasyon aşamasını düzgün geçse bile bu aralıkta seçeceğimiz 7 değişik kernal seçimine uygun bilgi geliyor olması çok düşük ihtimal.
Muhtemelen çok daha basit bir çözümle de aynı sonuca ulaşabiliriz ancak bu çözümün şöyle bir avantajı var. Bu algoritmayı kurup çalıştırmanın ciddi realtime yani hassas zamanlama gereksinimleri yok.
Mikroişlemci değil de CPLD gibi bir şey kullansaydık realtime ve tüm adres hatlarını kullanarak yine bir sonlu durum makinesi ile de aynı çözümü uygulayabilirdik. Fuzzy logic uygulamamıza da gerek kalmazdı. Tabii ortaya çıkan hardware biraz daha tuzlu olurdu ve zaten bu işi yapmak için de CPLD kullanma becerisine sahip olmak lazım
