Şimdi hemen başlayalım, şimdiye kadar neler yaptım?
1. C64 disk imajlarından dosyaları extract ettim. 127 dosya var. Buradaki sorun şu, hiçbir arşivde c64 pirates disklerinin orjinal haline rastlamadım. Tosec dahil tüm oyun arşivlerinde aynı ESI (başta kartal imajı ile başlayan) paketleri mevcut. Ben de bunu kullandım. Crack meselesi çok şaşırtıcı çünkü amiga/spectrum komünitesi bu konuda çok titizdir, c64 komünitesi sınıfta kaldı. Demoscene'i altından çeksek c64 diye birşey kalmayacak sanki. Ayrıca ileride bahsedeceğim Nostalgia release'i var, bu çok iyi bir paket, orjinal makinede oynamak isteyenler bunu kullanmalılar. Bu release 2013 yılında çıkmış ve orjinalinde 2 disket olan oyunu tek yüzlü tek disket haline getiriyor. Emülatörde çalışıyor, daha hızlı yükleniyor, düzgün cracklenmiş ve trainer ile şenlendirilmiş. Süper paketlendiği için bu sürümle ilgilenmedim.
2. İlk olarak disketlerde üç adet BASIC dosyasını çıktı aldım. Fakat cbm basic her kelimenin ilk iki harfini kullanıyor. Yani var=5 demek va=5 demek aslında. Ayrıca ifadeler arasında boşluk olmasına gerek yok. Eh ram da az olduğundan Sid kardeşimiz bunları belleğe zumuşturmuş adeta. Örnek:
1010 f=192:t=228:l=8:gosub10:bf=192*kp:f$="chars.dta":gosub17790
1012 ifsn<0thenc=0:t(c)=peek(prs):goto1040
1015 z=0:gosub8700:ifsn>1thenfori=5tosn*4:readx:nexti
1020 fori=1to4:readx:t(i)=x:nexti
1021 ifsn<6thenfori=sn*4to23:readx:nexti
1025 t$="are you an¿":fori=1to4:a=bf+t(i)*80-80:ift(i)=0then1035
1030 t$=t$+" ":forj=0to19:t$=t$+chr$(peek(a+j)):nextj:t$=t$+"£"
1035 nexti:x=10:y=5:gosub8000:pokeprs,t(c)
pek okunaklı değil... toplamda 2000 satır kod ve 5-6bin kadar ifade olduğundan elle düzeltmek de çok iş. Bu durumda yardımımıza 10 sene önce yazılmış bir programcık geliyor ama tabiiki çalıştıramadım ben onu, sonra kodunu paylaşmışlar neyse ki, fork ettim, güncelledim ve çalıştırdım:
https://github.com/ref-xx/CommodoreBasicReformatter1012 if sn<0 then c = 0 : t(c)= peek(prs) : goto 1040
1015 z = 0 : gosub 8700 : if sn>1 then for i = 5 to sn*4 : read x : next i
1020 for i = 1 to 4 : read x : t(i)= x : next i
1021 if sn<6 then for i = sn*4 to 23 : read x : next i
1025 t$ = "are you an?" : for i = 1 to 4 : a = bf+t(i)*80-80 : if t(i)= 0 then 1035
1030 t$ = t$+" " : for j = 0 to 19 : t$ = t$+chr$(peek(a+j)) : next j : t$ = t$+"?"
1035 next i : x = 10 : y = 5 : gosub 8000 : poke prs,t(c)
Tamam şimdi biraz daha okunur oldu. Yetmez ama evet. Başta bunları bir text editörde comment etmeye başlamıştım ama heryer pokeler, fonksiyonlar, sublar karmakarışık oldu. Dedim bu kod içinde kolayca gezebilmeliyim, Önce akıllı bir textbox iken bir anda kontrolü kaybedip başka birşey yazıverdim.
https://github.com/ref-xx/BasicFlowgenBu goto/gosub/return gibi zıplamalarla gidip gelmeleri kendisi işaretliyor. üstelik tek tıkla o satıra zıplayabiliyorsunuz. Takibi kolay oluyor.
1025 t$ = "are you an?"
: for i = 1 to 4
: a = bf+t(i)*80-80
: if t(i)= 0 then 1035
1030 t$ = t$+" "
: for j = 0 to 19
: t$ = t$+chr$(peek(a+j))
: next j
: t$ = t$+"?"
1035 next i 1025:3
: x = 10
: y = 5
: gosub 8000
: poke prs,t(c)
1040 poke 53269,0 1012:2
: a = bf+t(c)*80-80
: for j = 0 to 12
: poke pty+3+j,peek(a+20+j)
: next j
Sonuçta basic kodunu incelemeye başladım, rutinlerin ne yaptığını öğrendikçe işaretleyip tanımını yazıyorum.
Basic bulguları:
# RND
Pirates rastgele sayı oluşturmak için sid çipinin gürültü üretecini kullanıyor. Bu sebeple oyunun başında sid çipinden bir noise ürettirip test yapıyor, eğer değer değişmezse çipin arızalı olduğunu bildiriyor. Bu bana epey enteresan geldi. Ve noise hattı arızalı bir sürü Sid varmış, hatta bir yayıncı pirates oyununu incelerken kendi c64'ünün arızalı olduğunu bu sayede farketmiş.
6000 t$ = "the random number generatoRin this
computer (sid chip -?"
6010 t$ = t$+"osc. 3) is not functioninGcorre
ctly. program will noT"
6020 t$ = t$+"work unless this is repaired?"
6030 gosub 12500
: poke 53280,10
: x = 3
: y = 6
: gosub 8000
: return
# SidTran
Anladığım kadarıyla oyun aslında Basic ile yazılmamış. Sid Meier'in kendi kullandığı bir programlama dili olan SIDTRAN ile yazılmış. Bu dil daha sonra gerekli basic kodunu üretebiliyor. Bu basic kodunun karmaşa sebebini açıkıyor gibi, insan okusun diye üretilmemiş. Bu işi detaylı öğrenmek için sid meier'in kitabını sipariş ettim, halen okuyorum.
Oyunun kendine ait değişkenleri (altın, karakter detayları vb) bir basic değişkeninde değil bellekteki adreslerde tutuluyor. Yani para kazandığınızda:
para=para+100
demiyor, onun yerine index=3, value=100 diyip bir subrutin çağırıyor, bu rutin de bellekteki uygun pozisyonu güncelliyor.
Aslında son derece basit ve etkili ama korkunç bir karmaşa bu. Sonuç olarak bunun sebebi makine kodu rutinlerinin de değişkenlere kolayca erişmesi aslında.
devam edecek...