virtual memory,sanal
hafıza günümüz modern işletim sistemleri tarafından kullanılan
hafıza yönetim tekniğidir.
peki ama neden ?
sisteminizdeki ram den kapasitece daha fazla olan bir programı çalıştırmak istediğinizi düşünelim bu durumda- yapılması gerekilen iş programı bölümlemek/sayfalamak ve ardından ihtiyaç duyulanları ram içerisine yerleştirmek o anlık ihtiyaç duyulmayanları ise virtual memory de bulundurmak ileride ihtiyaç duyulduğunda bunlarıda ram içerisine yerleştirmek diyebiliriz.
virtual memory ile
prosesler birbirlerinden izole edilmiş şekildedir yani her process
kendi sanal adres uzayına sahip ve bir proses başka bir prosesin
alanına müdahalede bulunamaz.
virtual memory ile
hard-diskin belirli bir kısmı memory olarak kullanılmaktadır ve
bu alan işletim sistemi tarafından pagelere ayrılmaktadır.
eğer linux işletim
sistemi kullanıyorsanız pagelerin boyutunu şu şekilde
bulabilirsiniz
root@kali:~# getconf
PAGESIZE
4096
----------------------------->>>>> 4K
buradan da
anlaşılacağı üzerine işletim sistemi sanal hafızayı bu sistem
için 4096 bytelık pagelere bölümleyecek ve ayrıca fiziksel
hafızayıda(RAM) 4K olarak bölümlere ayıracaktır.fiziksel
hafızadaki bu pageler frame olarak da adlandırılabilinmektedir.
işletim sistemi
için geriye kalan tek şey bunların birbirlerine iz düşürülmesi
yani sanal hafızadaki adresin fiziksel hafızada neye karşılık
geldiğini belirlemek.
bir tablo düşünün
sanal hafızadaki adreslerin fiziksel hafızada nereye karşı
düştüğünü belirtsin işte buna page tablosu denilmektedir.işte
en sade hali ile bunun gösterimi şu şekilde olacaktır.
peki page table
nerede tutulacak ?
sanal hafızanın
hard-diskten bir parça olduğu biliyoruz ve hard-diske işlemci
tarafından
erişim süresi rame
erişim süresinden çok daha yavaştır.o halde bu page tablosunu
tutmamız gereken yer RAM gibi duruyor.her ne kadar bu düşünce
gerçekte yeterli gibi görünsede bu işi bilen insanlar için
yeterli görünmemiş kısacası page tablosunu sadece ram üzerinde
saklamanın yeterli olmadığı düşüncesinden dolayı bir takım
optimizasyonlara(en iyilemeye) ihtiyaç duyulmuş.
MMU(Memory
Management Unit),sanal adreslerin fiziksel adreslere
izdüşürülmesinden sorumlu olan birimdir.CPUnun içerisinde
bulunabileceği gibi(günümüzde daha çok bu şekilde) CPU dan ayrı
da olabilir.
TLB(Translation
lookaside buffer),güncel olarak kullanılan sanal adreslerin
fiziksel adreslerini tutan bir cache veya MMU için lookup table
vazifesi görmektedir.
TLB ve MMU biriminin
Fiziksel Adres üretiminde kabaca yaptığı işi aşağıdaki şekil ile
anlayabiliriz.
yukarıdaki resmi
açıklayacak olursak,CPU sanal adresi MMU birimine gönderir ve TLB
içerisinde bir arama gerçekleştirilir bulunması durumunda gerçek
adres elde edilmiş olunur ve page tablosuna erişim yapılmasına
ihtiyaç yoktur.aksi durumda sanal adres için RAM içerisinde
bulunan Page tablosuna bakılır ve bulunması durumunda gerçek
adres page tablosundaki ilgili kayıttan elde edilmiş olunur.Eğer
bu virtual adrese sahip page ram içerisinde yoksa işletim sistemi
uyarılır(yazılımsal kesme) ve işletim sistemi ilgili sanal
adresi barındıran sayfayı RAME mapler(yerleştirir) daha sonra
page tablosunun güncellemelerini yapar bu işlemler sonucu istenilen
sanal adres için fiziksel/gerçek adres elde edilmiş olunur.
buraya kadar
anlatılanlar gerçekte tek seviyeli bir page tablosu kullanımına
dayalı olarak anlatılmıştır fakat günümüz işletim sistemleri
tek seviyeli page tablosu yerine çok seviyeli paging mekanizmasını
kullanmaktadırlar.
Çok seviyeli
tabloların neden kullanıldığı ile ilgili olarak bir açıklama
yaparak konuya giriş yapmak yerinde olacaktır.
bildiğiniz gibi
işletim sistemleri birden fazla prosesi,prosesi run kuyruğunda
bulundurabilirler ve kısa süreli zamanla bunları çalıştırırlar
ve kullanıcı sistem eşzamanlı olarak çalışıyormuş hissine
kapılır,aslında bu çok çekirdekli ve çok işlemcili sistemler
için bir anlığına his değil gerçek olsa da biz tek işlemci
tek çekirdekli sistemler için arka planda çok sayıda proses
çalıştırdığımızdan dolayı context switch yapıldığını
biliyoruz.sanırım prosesler ile ilgili kısmı burada bırakmalıyız
eğer prosesler konusunda bilgi sahibi değilseniz bu konular
hakkında genel bilgi sahibi olmanız faydanıza olacaktır.
x86 mimaride işlemci 4GBlık bir adres alanını adresleyebilir.
x86 mimarinin
kullandığı flat memory model ile bir proses belleği(ram) 4GBlık
bir dizi veya düz bir alan gibi görebilir.
kısacası bir
proses 0.....2^32-1 adres aralığını adresleyebilir.o halde 4GB lık alanı 4K parçalara ayırmaya çalıştığımızı
düşünelim.
4GB/4KB=1 milyon
adet sayfa
bu anlatılanları
aklımızda tutalım ve bir prosesin sahip olduğu kaynaklardan
birininde kendisine ait page tablosu olduğunu hatırlayalım.
peki bu durumda
nasıl bir sorun karşımıza çıkar diye düşünücek olursak bunu
demeden önce bir prosesin 4GBlık bir adres alanı için ne kadarlık
bir page tablosuna sahip olması gerektiğini hesaplayalım.
yukarıdaki
hesaplamada da görüldüğü gibi 4GBlık bir adres alanının 4Klık
pagelere bölmek istediğimizde 1 milyon tane 4Klık page elde
ederiz.
tablodaki her bir
page için bir kayıt tutmalıyız ve minimum gereksinimler göz
önünde bulundurulduğunda her bir kayıt için 4 bytelık bir
alana ihtiyaç duyduğumuzu düşünelim.
bir kayıt için
gereksinimlerden bazıları o an da page'in ram de bulunup
bulunmadığı veya yazılabilir olup olmadığı gibi bilgiler
olabilir.tüm bunlardan sonra page tablomuzdaki bir kayıtın
uzunluğunu 4 byte olduğunu kabul ederek,bir page tablomuzun 4MBlık
bir alana sahip olacağınıda kabul etmiş oluyoruz.
4MB = 1 MİLYON * 4
BYTE
görüldüğü gibi
yalnızca bir prosesin page tablosu için 4MBlık bir alan ihtiyacı
gerekmektedir.
eş zamanlı(kimi
zaman eş,kimi zaman ayrık ama bize göre eş zamanlı) olarak 200
processin çalıştığını düşünücek olursak neredeyse 1 GB lık
bir alan ihtiyacı ortaya çıkacaktır.Bu alanın RAM den
karşılanması gerektiğini yazının yukarı kısımlarında
belirtmiştik,sanırım buradaki sorun belirginleşti ve o sorun page
tablosunun boyutu.
işte page
tablosunun boyutundan sebep günümüz modern işletim sistemleri çok
seviyeli paging mekanizmasını kullanmaktadırlar.
Umarım konu
anlatılırken zihinsel olarak bir dağınıklık
yaşamıyorsunuzdur,kimi zaman anlatılanların birbirinden kopuk
olmamasına dikkat etsem bile yeni anlatılacak olan kavram
içerisinde yeni bir kavramın belirmesi konuyu ister istemez
dağıtıyor olabilir.
Paging işlemlerinin
donanım tarafından nasıl desteklendiğini anlatmadan önce PAEden
bahsetmemiz gerekiyor.
normal şartlarda
x86 mimari ile uyumlu bir işletim sistemi kullanıyorsanız 4GB den
daha fazla bir RAMiniz varsa maalesef işletim sistemi 4GBlık
alandan daha fazlasını adresleyemeyecektir bu kısıt göz önünde
bulundurularak X86 mimariye PAE desteği eklenilmiştir.
kısacası PAE
desteğini göz önünde bulundurarak yazılmış 32-bit işletim
sistemleri 4GB den daha fazla olan bir RAM ile
çalışabilir/adresleyebilir.
PAE ile x86 mimaride
32-bit adres bacağı 36-bit olarak genişletmiştir.
Yazıda 3 tür
pagingden bahsetilmiştir.
1.)NON-PAE PAGING
2.)PAE PAGING
3.)LONG MODE
PAGING
Ayrıca anlatımlarda
pagelerin boyutu 4K olarak ele alınmıştır.
normal(NON-PAE)
paging mekanizması :
non-PAE paging x86
mimaride PAEnin aktif olmaması durumunda kullanılmaktadır.aşağıdaki
şekilde 32-bit sanal adresin x86 non-PAE paging kullanılrıken
nasıl yorumlandığını göstermektedir.
İki tablonun
entrylerinin/kayıtlarının formatları ise aşağıdaki şekildeki
gibidir.
Page Directory
kayıtındaki 31:12 bitleri Page Tablosunun Base adresini
göstermektedir sizinde fark edebileceğiniz gibi burası yalnızca
Page Tablosunun ilk en yüksek 20 bitini göstermektedir geriye kalan
12 bitin ise 0 olduğunu biliyoruz çünkü bir page tablosu 4K ve
katlarından oluşmaktadır.
Her iki kayıt da
geriye kalan diğer bitler(31:12 bitleri hariçinde olanlar)
page-protection için kullanılmakta veya bazı denetimler için
kontrol edilmektedir.
Örneğin P biti
istenilen PAGE’in o an için ram de olup olmadığını
belirtirken,U/S biti ise PAGE’in usera mı yoksa kernela mı ait
olduğunu göstermektedir.
Bu tablolar
aracılığı ile adres çevriminin nasıl gerçekleştiğini
anlamamız bizim için yeterlidir.
şekil üzerinden de
görebileceğiniz gibi CR3 registerı çok seviyeli paging için en
üstteki page directory tablosunu işaret ediyor ve bu adresin
fiziksel adres olduğunu unutmuyoruz.
(hiyerarşik olarak
düşünürseniz en üst kısımda page directory tablosu vardır.)
daha sonra virtual
adres 3 gruba ayrılıyor ve ilk 10-bit Page-Directory tablosu için
offset olarak kullanıyorken ikinci 10 bit Page-Table için offset
ve son 12-bit ise 4K Page için offset olarak kullanılıyor,peki
buradaki yapı ile tek seviyeli paging mekanizması arasındaki fark
nedir diye bir soru kafamıza takılabilir.
Çok seviyeli paging
mekanizmasında her proses için bir page tablosu yerine her proses
için bir page directory gerekmektedir ve page directoryinin işaret
ettiği page tabloları mevctuttur.
dikkat ederseniz
page tabloları dedik page tablosu değil,bu durumda bir proses
birden fazla page tablosuna sahip olabilir.
Çok seviyeli paging
ile tek seviyeli paging arasındaki ayrım page tablosunun parçalara
ayrılması, artık birden fazla page tablomuzun olması ve ihtiyaç
duyulanın ram içerisinde bulunmasının yeterli olduğudur. Bazı
uygulamaları göz önünde bulundurduğumuzda gerçekten de
uygulamanın 4GB lik bir alana ihtiyacı olmadığını
görebiliriz.4GB adres alanının tamamına ihtiyaç duymayan bir
proses neden tüm alanın haritasına sahip olsun.
(kernel space/user
space gibi bir ayrımın yazı boyunca yapılmadığına dikkat
ediniz.)
çok seviyeli
pagingde bir prosesin sanal-fiziksel adres alanının dönüşümünü
gerçekleştirmek için elimizde bulunması gereken kaynağın
boyutunu hesaplayalım.
bir proses için bir
page directory ihtiyacımız var ve page directory tablosu 2^10 --->
1024 adet kayıt barındırır ve her biri 4 byte uzunluğundadır.
Bu durumda bir page
directory 4K (1024 * 4 BYTE) boyutundadır.
yine page
directoryinin işaret ettiği bir page tablosu ise 2^10 ---> 1024
adet kayıt barındırır ve her biri 4 byte uzunluğundadır.
o halde bir page
tablosuda 4K boyutundadır.
Bu iki sonucu
birleştirirsek,bir prosesin sanal-fiziksel adres alanının dönüşümü
için o an ihtiyaç duyulan kaynağın boyutu = 4K+4K=8K olarak
hesaplanır.
hatırlarsanız tek
seviyeli paging mekanizmasında bir prosesin sanal-fiziksel adres
alanının dönüşümü için o an ram de bulunan 4MB lık bir page
tablosuna ihtiyacımız vardı.
peki ikinci seviyede
bulunan page tablolarından her biri ile ne kadarlık bir adres
alanını adresleyebiliriz.
Her bir page tablosu
ile 4MB lık bir adres alanını adresleyebiliz,ve bunlardan 1024
tane olması ile 4096 MB yani 4GB lık bir adres alanını
adresleyebiliriz.
bir proses 4GB adres
alanının tamamını 1024 adet page tablosunun tamamını kullanarak
adresleyebilir ama bir prosesin aynı anda 4GB lık bir adres alanını
adreslemesi gerçekten uzaktır ve ayrık page tablo kullanma fikri
buradan çıkmıştır.
paging hardware
seviyesinde desteklendiğinden sistem programlamacının yapması
gereken tek iş proses için page directory adresini crc3 registerına
yüklemesidir.
PAE Aktif iken
Paging :
PAE aktifken paging
mekanizması değişiklik gösteriyor yazının yukarıki
kısımlarında bahsettiğimiz gibi PAE aktif iken x86 mimaride 4GB
den daha fazla bir adres alanını adresleyebiliriz.bu bilgiden
sonra x86 mimaride PAE aktif iken paging mekanizması nasıl
çalışıyor buna göz atalım.
PAE aktifleştirmek
için CR4 registerında PAE bitine karşı düşen bit 1 değerine
setlenir.
Buradaki 52* mimari
limitidir.Biz x86 mimari ve PAE biti etkinleştirildiğini göz
önünde bulundurduğumuzdan fiziksel adresimizin 36 bit olduğunu
biliyoruz.Resim AMD64 Manualinden alıntı olduğundan dolayı bir an
için kafanızı karıştırabilir bu yüzden 36 bit adres bacağına
sahip olduğumuzu unutmuyoruz.
Page-Directory ve
Page-Table dışında yeni bir tablonun daha geldiğini görmekteyiz
Page-Directory-Pointer Table ve yine tablodaki kayıt sayımızdaki
değişiklik olduğunu fark ettik ve her bir kayıtın uzunluğu
32-bit den 64-bite çıktı.
PAE bitinin
etkinleştirilmesiyle adres bacaklarımız 32-bit den 36-bite
yükseldi.peki bu tablolar üzerinden bir hesaplama yapsak gerçekten
bir proses 2^36 yani 64 GB tamamını adresleyebilirmi paging
mekanizması üzerinden ?
sistemdeki her
proses 4 kayıtı olan Page-Directory-Pointer tablosuna
ve 512 adet kayıt
içeren maximum 4 taneye sahip olabileceği Page-Directory-Tablosuna
ve bunlarla da işaret edebileceği 512 adet page tablosuna sahip
olabilir.
Bu durumda bir
prosesin adresleyebileceği toplam alan = 4*512*512*4K kısacası
4GB lık bir alandır.
Burada yine non-PAE
deki gibi bir prosesin bir kerede yalnızca 4GB lık bir adres
alanını adresleyebileceğidir.
Peki o zaman non-PAE
ve PAE arasındaki fark nedir ve nasıl 64 GB lık bir alanı PAE
adresleyebilir diyorsanız,PAE paging kullanılırken her tablodaki
kayıt genişletilmiştir. Non-PAE de kullanılan 31:12 bitleri
yerine artık 35:12 bitleri base adres olarak kullanılmaktadır.
35:12 bitleri ile bir tablonun base adresinin en yüksek ilk 24
bitini gösterirken(geriye kalan 12-bit 0 değerine setlenmiştir)
virtual adresin son 12-biti de bu base adrese ilave edilerek
36-bitlik bir fiziksel adres elde edilmiş olunur.
PAE aktif iken
sistemdeki tüm prosesler için işletim sisteminin elinde bulunan
maximum alan 2^36 dan 64 GB lık bir alandır.
non-PAE de ise
işletim sistemi sistemdeki tüm prosesler için ancak paging
üzerinden 4GB lık bir alan adreslemesi yapabilirdi.
non-PAE deki tablo
boyutları ile PAE pagingdeki tablo boyutlarının aynı olduğuna
dikkat ediniz.
Örneğin 1024 adet
kayıt kullanan Page Directory Tablomuzda her bir kayıtımızın
uzunluğu 32-bit yani 4 byte boyutundaydı ve page directory
tablomuzun non-PAE deki toplam boyutunu 4K(1024*4 byte) olarak
hesaplamıştık.
PAE paginde bir page
directory tablosu 512 adet kayıt tutmakta ve her bir kayıt 64 bit
uzunluğunda bu durumda yine page directory boyutu 4K (512*8 byte)
olarak kalıcaktır..burada her ne kadar tablomuzdaki kayıtların
uzunluğu artmış olsa da tablomuzun toplam boyutu non-PAE paging
deki ile aynı tutulmuştur.
Long Mode Paging :
x86-64 veya AMD64
veya x64 (veya siz onu nasıl adlandırmak isterseniz isteyin)
mimarinin default çalışma modu olan long mode(iki ayrı modun
birleşimidir,64-bit mod ve compatibility mod) içerisinde paging
nasıl yapıldığına göz atalım.
4-seviyeli paging için kullanılan tablolara ait kayıtların formatları aşağıdaki gibidir.
Long mode içerisinde
PAE mod içerisindeki paging mekanizması kullanılmaya devam
ediliyor ama biraz farklı bu farklardan birisi 4-seviyeli olması ve
hiyerarşinin en üstünde yeni gelen tablomuz page-map level-4
tablomuz bulunması ve yine fark edebileceğiniz gibi virtual adres
olarak 48 bit kullanılması.
Virtual adres 5
parçaya ayrılmış durumda bunlardan ilk dört-9 bit tablolar için
index olarak kullanılırken yine son 12 bit 4K lık page için
offset olarak kullanılmaktadır.
bu 4 seviyeli
tabloları göz önünde bulundurduğumuzda bir prosesin ne kadarlık
bir alanı adresleyebileceğini bilmek istersek yine basit bir
hesaplama yapmamız gerekecektir.
Toplam alan = 4 *
512 * 512 * 512 * 512 = 2^48 byte karşılık gelmektedir.
2^48 bayt ,
281,474,976,710,656 bayta
karşılık gelmektedir bu ifadeyi TB cinsinden ifade edecek olursak
256 TB karşılık gelmektedir.
Çok seviyeli paging mekanizmasında işletim sistemi prosesi
çalıştırmadan önce CR3 registerına prosese ait hiyerarşik
olarak en üstte bulunan tablonun adresini setler bundan sonrası
yine hardware tarafından gerçekleştirilmektedir.tabi burada
tablolar arası ilişki yine işletim sistemi tarafından önceden
hazırlanmıştır.
Virtual memory kavramını elimizden geldiğince anlatmaya çalıştık
umarım faydalı bir yazı olmuştur.
Fakat
bazı konulara hiç değinmedik örneğin PAGE REPLACEMENT
algoritmaları gibi fakat buradaki amacımız temel kavramlar üzerine
olduğundan,virtual ve fiziksel adreslemelerin ne olduğu ,
proseslerin page tabloları
aracılığıyla sanal adreslerinin nasıl fiziksel adreslere
dönüştürüldüğü ve çok seviyeli paging mekanizmasına göz
atmaktı.
ve
son olarak konu ile direk olarak bir bağlantısı olmasada amdnin
manualinde bahsettiği bir
adres formu mevcut.
yukarıda hesaplarkende gördüğümüz gibi x64 mimaride virtual adres 64 bit olarak kullanılmıyor, şu an için
48 bit kullanımı adresleme için yeterli olarak görülmekte.bu
yüzden kullanılmayan bitler için(48.bit ile 63.bit arasındaki tüm
bitler ve kendileri) ise en yüksek bitin 47.bitin(0.bit den başladık
saymaya) kendisini 63.bite kadar tekrarlamasına canonical adres
formu denilmektedir.x64 mimari bu kurala uygun virtual adres
görmediği takdirde exception meydana geleceğini söylüyor.
Referanslar :
AMD64 Architecture Programmer's Manual Volume 2 : System Programming
EOF
EOF
Hiç yorum yok:
Yorum Gönder