Tam Sürümünü Görmek İçin : dinamik bellek kullanimi
quasimodo
22/04/2007, 18:06
char * ch = (char *)malloc(5 * sizeof(char));
gibi bir kodda ch isaretcisi char tipinde bir sabit konulabilcek
5 tane adresin baslangic adresini gosteriyor.
Benim sorum su malloc() fonksiyonunun yaptigi is ne?
Yaptigi is bellekte zaten guvenli olan ve char tipinin konulabilecegi yeri
bulup baslangic adresini ch isaretcisine atamak mi ?
Yoksa guvenli olmayan bir yeri once guvenilir hale
getirip sonra isaretciye atamak mi?
malloc yalnızca Heapalloc fonksiyonuna çağrıda bulunur. Heapalloc ise Virtualalloc fonksiyonuna. Malloc'un ne iş yaptığını anlamak için virtualalloc fonksiyonunun yaptığı işi anlamalısın.
Euclides
23/04/2007, 00:21
malloc yalnızca Heapalloc fonksiyonuna çağrıda bulunur. Heapalloc ise Virtualalloc fonksiyonuna. Malloc'un ne iş yaptığını anlamak için virtualalloc fonksiyonunun yaptığı işi anlamalısın.
Hiç biri doğru değil
:)
Keşke doğrusunu da söylese idin.
acehreli
23/04/2007, 01:43
sysdev, malloc'un ne oldugunu ancak belgesinden anlayabiliriz. Hangi islevleri cagirdigini nerden bilebilir veya guvenebiliriz? :) Zaten kaynak kodlari da olmayabilir...
quasimodo, malloc'un yaptigi is, belirtildigi kadar bellek ayirmak ve o ayirdigi bellegin adresini dOndurmektir. Basarili olamazsa 0 (NULL) dOndUrur.
O bellekle ne yapilacagi malloc'u cagirana kalmistir.
Ali
Doğru haklısın o zaman belgesine bakalım.
Msvcrt.dll disassembly etsem bana çok da kızmazsınız inşallah. Genel itibari ile:
1-) Malloc -_nh_malloc 'u çağırıyormuş
2-) _nh_malloc HeapAlloc
3-)HeapAlloc old_sbh_alloc_block üzerinden VirtualAlloc fonsiyonunu çağırıyor. Genel olarak böyle daha da detaya inersek daha fazla call'ları yazmak lazım.
Daha az detaya çıkarsak o zaman benim ilk mesajıma bakmak lazım.
Yani quasimodo (http://forum.ceviz.net/member.php?u=56425) sen iyisi mi virtualalloc'un ne yaptığına bir bak. Cdernek'in win32 dosyası işini görür.
Görüşmek üzere dostlar...
quasimodo
23/04/2007, 02:10
peki
char * ch = (char*)malloc(sizeof(char));
burada ayrilan bolgeyi free ile geri vermezsem bolgenin
guvenilirligi nezaman biter?
yada
malloc(sizeof(char));
bu sekilde kullanirsam yani dondurdugu degeri
herhangi bir isaretciye atamazsam bu ayrilan
bolgenin guvenligi ne zaman yok olur?
Euclides
23/04/2007, 02:13
Doğru haklısın o zaman belgesine bakalım.
Msvcrt.dll disassembly etsem bana çok da kızmazsınız inşallah. Genel itibari ile:
1-) Malloc -_nh_malloc 'u çağırıyormuş
2-) _nh_malloc HeapAlloc
3-)HeapAlloc old_sbh_alloc_block üzerinden VirtualAlloc fonsiyonunu çağırıyor. Genel olarak böyle daha da detaya inersek daha fazla call'ları yazmak lazım.
Daha az detaya çıkarsak o zaman benim ilk mesajıma bakmak lazım.
Yani quasimodo (http://forum.ceviz.net/member.php?u=56425) sen iyisi mi virtualalloc'un ne yaptığına bir bak. Cdernek'in win32 dosyası işini görür.
Görüşmek üzere dostlar...
gene 3'te 0 olmuyor böyle
disassembly ettiğimizi de anlamıyoruz her halde :) ayırca ona da lüzüm yok zaten visual c++'ı alınca crt library'ın kodları beraberinde geliyor. Oradan da bakabiliriz. Ama illa disasm diyorsanız o da olur...
Göreceksiniz ki malloc sizin dediğiniz gibi "yanlız" kernel32.dll.HeapAlloc'u çağırmaz, ayrıca HeapAlloc'da VirtualAlloc'u çağırmaz.
Crt'ini özelliği hafızayı yönetmesidir ve zatende yönetir... Windows'dan aldığı büyük (page boundry'de) hafıza parçalarını sizin için ufak parçalar haline getirirki 4 byte için 0x1000 byte kurban etmeyin ;)
Yani malloc her çağırdığınızda aslında illa yeni hafıza almazsınız :)
Tabii sizin bunu araştırmanız daha iyi olur. Crt büyük dezavantajlar meydana getirdiğinden dolayı sadece server sistemleri için özel üretilmiş malloc library'leri var. Hele onlardan birini kullanıryorsanız bu dediklerimizin hepsi boş :)
Yani malloc her çağırdığınızda aslında illa yeni hafıza almazsınız
Azizim.
Her çağrıldığında illaki yeni hafıza alınır dememiş ve mümkün mertebe korumalı modda bellek yönetimi bilgilerine ulaştımak için arkadaşı genel bir cevap vermiş olsam da bu ayrıntıyı bize gösterdiğiniz için teşekkür ederim.
Selamlar...
hasanyasin
23/04/2007, 03:20
Sevgili quasimodo, malloc ile talep ettiğiniz belleğin adresini alırsınız. Bu adresi kullanıp kullanmamanız durumu değiştirmez, yani adres ayrılmış olur. Programınız sonlanana kadar da bir daha boşaltılmaz.
Ayırıp aldığınız belleği boşaltmamanızda ortaya çıkan, kullanılmayan belleğin meşgul edilmesi durumuna da hafıza taşması, memory leakage diyoruz. Bu sorunu yaşamamak için de free(pointer) kullanıyoruz. Tabii elimizde olmayan bir pointer'ı free etmeye çalışmamız da ayrı bir sorun...
Fonksiyonun hangi fonksiyonları çağırdığı ya da nasıl olup da ram'e ulaştığımız işletim sistemine, derleyiciye, malloc implementasyonuna (ne çirkin bir Türkçe oldu, özür dilerim) bağlı olarak değişebilir; ama burada bizi doğrudan ilgilendiren şeyler bunlar değil. En azından quasimodo'nun sorusu bunlarla ilgili bir soru değil...
Nasıl otomobil kullanırım diyen adama Audi ve Mercedes motorlarındaki enjeksiyon sistemlerini anlatmaya başlıyorsak işimiz zor doğrusu...
acehreli
23/04/2007, 19:46
encodeum, hasanyasin'in dedigi gibi: bir islevin belgesi derken onun kullanim belgesinden (documentation, manual page, vs.) bahsediyoruz. Kaynak dosyasi bile degil...
hasanyasin, implementation'in karsiligi olarak 'gercekleme'yi duyuyorum ve ben hep oyle kullaniyorum.
Ali
hasanyasin
23/04/2007, 19:57
Gerçekleştirme dense belki olabilir; ama gerçekleme kesinlikle çok yanlış bir çeviri... Yazılımcılar olarak terimlerimize yaptığımız çevirilerinden çokça bîzârım... TDK'den (Teedeekaa diye okunmaz bu da mesela, Türkçe'de Kaa diye bir harf yok, Kee var) de hiç ama hiç hoşlanmıyorum. İğğğ... :)
Neyse encodeum'u ilgisiz alakasız şeyler yazdı diye eleştirdik ya şimdi biz de aynısını yaptık. Eden bulur :P
acehreli
23/04/2007, 20:12
Dogru, Turk Dil Kurumu'nda "gerceklemek" soyle veriliyor: "Bir şeyin doğruluğunu herhangi bir şeyle ortaya koymak, teyit etmek."
Aradigimiz sozcuk "gerceklestirmek" galiba. TDK de boyle listelemis. Ben bundan sonra "gerceklestirme" diyecegim cunku daha iyisini bilmiyorum. :)
Ali
Neyse encodeum'u ilgisiz alakasız şeyler yazdı diye eleştirdik ya şimdi biz de aynısını yaptık. Eden bulur :P
İlgisiz alaksız şeyler mi?
Mümkün mertebe bu tarz şahsi mesajlardan kaçınmakta fayda var.
gibi bir kodda ch isaretcisi char tipinde bir sabit konulabilcek
5 tane adresin baslangic adresini gosteriyor.
Benim sorum su malloc() fonksiyonunun yaptigi is ne?
diyerek malloc'un kendi belgesinde yazan şeyi zaten bildiğini ama tam olarak internal olarak nitelendirebileceğimiz kısmını soran arkadaşımıza verilcek cevabın malloc fonksiyonunun gerçekte hangi fonksiyonlarla çalıştığını belirtmek olduğunu düşünüyorum nacizane. Cevap; zaten kendi yaptığı açıklamayı tekrardan yazmak olmasa gerek.
Bu durumu çok güzelce açıklamış benim de daha öncelerden okuduğum yerin linkini bırakmakta fayda var.
http://www.catch22.net/tuts/bigmem01.asp
Zaten burda da benim dediğimin benzeri bir ifade vardır malloc'un gerçekte ne yaptığını açıklanan bölümünde:
In Visual C++ 6.0, malloc and new[] use VirtualAlloc internally.
Keza Cdernek'in win32 dosyasına bakarsa da aynı şekilde bir ifade ile karşılaşacağı aşikar:
Bu durumda win32 sistemlerinde çalışan c++ derleyicilerinin çoğunda malloc operator new gibi tahsisat fonsiyonları HEAP**** fonksiyonlarını çağırmakta HEAP**** fonksiyonları kendi içerisinde Virtual**** fonksiyonlarını çağırarak işlem yapmaktadır
Selamlar....
hasanyasin
23/04/2007, 23:35
Hâlen ilgisiz alâkasız... Bu yorumum şahsi değil, şahsi olması için aramızda şahsi bir şeyler olması gerekir ki ben sizi tanımıyorum dâhi. Mesajınızı ilk okuduğumda şöyle düşünmüştüm: Rastgele bir Google sonucuna tıklandı, orada yazan birkaç fonksiyon ismi alındı ve buraya yazıldı...
Dürüst olalım. Sizce "malloc() fonksiyonunun yaptığı iş ne?" sorusuna "malloc yalnızca Heapalloc fonksiyonuna çağrıda bulunur. Heapalloc ise Virtualalloc fonksiyonuna. Malloc'un ne iş yaptığını anlamak için virtualalloc fonksiyonunun yaptığı işi anlamalısın." diye cevap vermek gerçekten cevap vermek midir? (:
Son olarak, C++ Visual C++'tan ya da 'işletim sistemi' windows'tan ibaret değil, tıpkı 'otomobil'in Audi ya da Tofaş'tan ibaret olmadığı gibi...
Sevgili Hasan
Yaptigi is bellekte zaten guvenli olan ve char tipinin konulabilecegi yeri
bulup baslangic adresini ch isaretcisine atamak mi ?
Yoksa guvenli olmayan bir yeri once guvenilir hale
getirip sonra isaretciye atamak mi?
sorusunun cevabı sence
Sevgili quasimodo, malloc ile talep ettiğiniz belleğin adresini alırsınız. Bu adresi kullanıp kullanmamanız durumu değiştirmez, yani adres ayrılmış olur. Programınız sonlanana kadar da bir daha boşaltılmaz.
Ayırıp aldığınız belleği boşaltmamanızda ortaya çıkan, kullanılmayan belleğin meşgul edilmesi durumuna da hafıza taşması, memory leakage diyoruz.
Bu mu?
Birincisi memory leakage hafıza taşması değildir. İkincisi sorduğu soru ile alakalı şu açıklamaya bakarsak:
Bir sayfa için sayfa dosyasında yer ayrılma işlemine sayfanın comit edilmesi denmektedir. (...) Şüphesiz heap alanı içerisinde malloc yada operatornew gibi fonksiyonlarla tahsis edilmiş alanlar commit edilmektedir. Commit etme bir disk işlemi olduğuna göre büyük blokların dinamil tahsis edilmesi sırasında commit işleminin ciddi zaman alacağı söylenebilir(...)dendikten sonra sayfa düzeyinde tahsisat işlemlerinin virtual*** fonksiyonları ile yapıldığı aktarılmaktadır.
Soruda ne denmişti?
"guvenli olmayan bir yeri once guvenilir hale
getirip sonra isaretciye atamak mi"
Virtual alloc ile güvenli bir şekilde tahsis edilmiş bölge commit eilmektedir desem alaka kurma konusundaki sıkıntıyı aşabilir misin? Böylece Virtualalloc'un ne olduğunu anlaması gerektiği açıklaması ile sorunun tam cevabını bulma yolunu kendsine nacizane gösterdiğim konusunda hakkı teslim eder misin.
Neyse çok uzatmaya değmez bu tip konuları..
Bu arada Google araması sonucu bulunan fonksiyonları yazılması kısmı hakikaten komikmiş :)
Görüşmek üzere...
hasanyasin
24/04/2007, 00:33
Taşma ifadem için özür dilerim, sızma uygun çeviri.
Geri kalanı için sadece peki diyorum...
quasimodo
24/04/2007, 00:41
commit etmek demek
Buyuk bir bellek adresini bizim istedigimiz kucuk
parcalara bolmek mi demek?
hasanyasin
24/04/2007, 00:50
Size eldeki imkanlar dahilinde talep ettiğiniz miktarda belleğin ayrılması ve adresinin sunulması demek.
peki
char * ch = (char*)malloc(sizeof(char));
burada ayrilan bolgeyi free ile geri vermezsem bolgenin
guvenilirligi nezaman biter?
yada
malloc(sizeof(char));
bu sekilde kullanirsam yani dondurdugu degeri
herhangi bir isaretciye atamazsam bu ayrilan
bolgenin guvenligi ne zaman yok olur?
ayırdığın bellek program sonlandığında yok olur. işlevler için de işlev bittiği zaman. (static değilse).
acehreli
24/04/2007, 19:20
quasimodo'nun "guvenlik" ile ne kasdettiginden hAlA emin degilim...
malloc ile ayrilan bellek, biz onu geri verene kadar bizim sorumlulugumuzdadir. free ile geri verirsek sisteme geri dOner, vermezsek dOnmez. (Arada realloc'a da gOnderebiliriz.)
Program sonlandiginda yok olacagi da ancak kendi isletim sisteminizde oyle oldugunu bildiginiz icin olabilir. (Evet, bilinen butun isletim sistemlerinde pratikte oyledir.) Ben kendim bir isletim sistemi yazsam ve C kurallari dahilinde kalsam, program sonlandiginda bellegi geri vermeyebilirim ve bununla tamamen yasal davranmis olurum.
eezgu, islev bittiginde sonlananlar yalnizca otomatik nesnelerdir degil mi...
void foo()
{
BirTur otomatikNesne; // sonlanir
BirTur * banaAitNesne = (BirTur *)malloc(sizeof(BirTur)); // sonlanMAZ
}
foo'da bellek sizintisi var, cunku malloc ile ayirdigim bellegi geri vermiyorum.
Ali
quasimodo
25/04/2007, 00:52
Guvenlikten kastedtigim o bellek gozune istedigim
turden bir sabiti koyabiliyor ve bunun bir sorun cikarmiyor
olmasidir.
Zaten malloc islevinin yaptigida tam olarak bu degilmi.
(Aslinda bu noktada da sorum vadi ama...)
Aslinda ben malloc isleviyle guvenli hale getirdigim
bir bellek gozunu bir isaretciye atamadigimda
ne olabilecegini tartismakti.
Simdi bu adresi bir isaretciye atamadigimdan
dolayi free ile sisteme geri vermem mumkun degil.
e hepimizin duydugu program sonlaninca sisteme
geri verme islemi de sistem bagimli oldugunu ogrenince
standartlar bu konuda ne diyor onu dahada merak ettim...
acehreli
25/04/2007, 05:27
malloc 'void*' dOndurdugu icin, ve 'void*' da "herhangi turden nesneyi gosterebilen isaretci" anlamina geldigi icin, o ayirdigin bolgeye istedigin nesneyi koyabilirsin.
Sen free ile geri vermedigin surece malloc'la ayirdigin (ve belki de realloc ile yeniledigin) sana aittir. Hic geri vermezsen, hAlA ihtiyacin oldugu dusunulur.
O sisteme geri verilmeyebilme konusu kafani karistirmasin; butun yaygin sistemlerde senin geri vermeyi unuttugunu sistem program sonlaninca geri alir.
Ama buna guvenerek yazmamalisin. Eninde sonunda bu kodu baska bir projecde kullanmaya baslarsin, o kod bir dOngU icinden cagrilir; ve senin eski programda sisteme kendiliginden giden bellegin yeni programda bellek sizintisi olarak karsina cikar. :)
Ali
quasimodo'nun "guvenlik" ile ne kasdettiginden hAlA emin degilim...
malloc ile ayrilan bellek, biz onu geri verene kadar bizim sorumlulugumuzdadir. free ile geri verirsek sisteme geri dOner, vermezsek dOnmez. (Arada realloc'a da gOnderebiliriz.)
Program sonlandiginda yok olacagi da ancak kendi isletim sisteminizde oyle oldugunu bildiginiz icin olabilir. (Evet, bilinen butun isletim sistemlerinde pratikte oyledir.) Ben kendim bir isletim sistemi yazsam ve C kurallari dahilinde kalsam, program sonlandiginda bellegi geri vermeyebilirim ve bununla tamamen yasal davranmis olurum.
eezgu, islev bittiginde sonlananlar yalnizca otomatik nesnelerdir degil mi...
void foo()
{
BirTur otomatikNesne; // sonlanir
BirTur * banaAitNesne = (BirTur *)malloc(sizeof(BirTur)); // sonlanMAZ
}
foo'da bellek sizintisi var, cunku malloc ile ayirdigim bellegi geri vermiyorum.
Ali
evet haklısınız ben karıştırdım. ancak göstericinin kendisi sonlanabilir işaret ettiği bellek sonlanmaz.
Forum Yazılımı : vBulletin v3.6.8, Copyright ©2000-2008, Jelsoft Enterprises Ltd.