Skip to content

Hafıza Sızıntısı* (Memory Leak) nasıl saptanır

Aşağıdaki adreste Sam Allen çeşitli tarayıcıların hafıza kullanımları ile ilgili güzel bir çalışma yapmış.safari-memory-usage

http://dotnetperls.com/Content/Browser-Memory.aspx

Makale içerisindeki grafikler ve anlatım, test altındaki uygulamaları uzun süre kullanıp hafıza kullanımlarını incelediğimizde mutlak hafıza sızıntılarını nasıl saptayabileceğimize mükemmel bir örnek sunuyor.

Makaledeki su götürmez hafıza sızıntılarını bir kenara bırakırsak, özellikle modern yazılım platformlarında gördüğümüz Garbage Collector’ların (GC), tembel programcılara neler yaptırabileceklerine bir bakalım.

GC’lerin keşfi babalarımızın çocukluğuna denk gelse de, popüler programcılık dünyasına seslerinin duyulması, bizlerin doğumundan hayli sonralara tekabul ediyor. 1972 yılında eli yüzü şekillenen bir C programlama dilini, 1983′leri bulan C++’yı ve bu platformların popülerliğini düşünürsek, GC sektörde hayli yeni bir kavram diyebiliriz. Belki de bu denli öne çıkmasını nesneye yönelik programlamanın ve hafıza dertsiz programlamanın popülerleşmesine de bağlayabiliriz, ve sanırım bağlarken de yanılmayız.

GC, geliştiricilere birçok avantaj sunmaktadır ve genel kanının aksine "yavaş", "verimsiz" yada "koşularak uzaklaşılası" bir kavram değildir.

İlk etapta GC’nin aşağıdaki faydaları ile geldiğini görüyoruz;

  1. Daha az hafıza sızıntısı problemi
  2. Daha az kod, yani daha az yazılım hatası :)
  3. Daha okunabilir kaynak kod, yani daha az yazılım hatası :)
  4. Bazı sorunların çözümünde menzilimizi arttırması

Bu kolaylıklar yadsınamaz elbette, lakin bir de evrenin yadsınamaz bir kuralı var;

Evrende bilinen tüm maddeler, minimum enerjiye ve maksimum düzensizliğe sahip olma eğilimindedir.

Eh, programcılar da bu yasaya uyduklarına göre, sadede gelelim;

Önceleri de söylemiştim, "farkındalık olmadan" geliştirilen yazılım kalitesiz olmaya mahkumdur. Bazı durumlarda ettiğimiz tembelliğin sonuçları, ne yazık ki GC gibi cennetten inme teknolojilerin bile sorgulanmasına yol açabiliyor. Örneğin buradaki [PDF] makaleden bir alıntı yapalım;

"One of the problems with Java for real-time and embedded real-time systems is the unpredictable behavior of garbage collection (GC). GC introduces unexpected load and causes undesirable delays for real-time applications."

Java’nın gerçek zamanlı gömülü sistemlerdeki sorunlarından birisi de Garbage Collector’un tahmin edilemez davranışıdır. GC beklenmeyen yükleri beraberinde getirmekte ve gerçek zamanlı uygulamalarda istenmeyen gecikmelere sebep olmaktadır. (Çeviri bana aittir, çeviri yanlışları için peşinen özür dilerim)

Benzer davranışları, yük testleri sırasında büyük ölçekli iş çözümlerinde biz de gözlemliyoruz. Zira temel prensibi gereği GC, uygulamanın erişemediği hafızayı bulup temizlemekte. Yada tersinden bakarsak, çalışma anında eğer çalışan kod belirli bir hafızaya erişebiliyor ise bu hafıza GC’nin ilgi alanı dışında kalmakta.

Ayrıca, hafıza yönetimi için ek kod yazmıyor olmak, hafızanın yönetilmediği anlamına da gelmiyor. Hatta belirli bir hafıza bloğunu sisteme geri vermek yerine GC’nin bunu bizim yerimize bulmasını ve ardından ondan kurtulmasını istemek daha fazla işlemci çevrimi de demektir. Uzun lafın kısası, dikkatsiz bir programcı için GC gibi bir özelliği alıp darboğaz haline getirmek o kadar da zor değildir.

Özellikle programcılığa yeni başlamış arkadaşlara gitsin; Yazılım mimarisini yer kürenin 124 mil üzerindeki bir yörüngeden takip eden civan gençlerin "abi şimdi her nod için şu klastan iki instıns yaratıp şuna basalım, alalım bunları da bi vayl luup içinde işleyip sonucu siriılayz edip MQ’ya çakalım" muhabbetlerinin heyecanı, bizim Java heap boyutunu monitörlememiz ile sonuçlanmaktadır.

imageEğer uygulama belirsiz zamanlarda "şöyle bir durup soluklanıyorsa" -ki benim deneyimlerim özellikle Java(**) platformunda- heap (yığın) hafızayı takip etmenizi öneririm. Modern yük testi araçlarındaki üretilen iş (İng. Throughput) miktarında da bu davranışı yakalamak mümkündür. Sadece bir iki kere karşılaşmış da olsam, sebebi bilinmeyen "Yetersiz Hafıza / Out of memory" hatalarının da benzer geliştirici pervasızlıklarına işaret edebileceğini de hatırlatalım.

Her ne kadar platform gelişmiş bir GC mekanizması sağlıyor olsa da yandakine benzer davranışları yığın hafıza kullanımında gördüğünüzde, kanı kaynayan o genci kulağından tutup "ne yaptın burda?" diye sormak sorunu çözmenizde faydalı olabilir.

Ama tabii ki genç arkadaşlara kızmanın yanlış olduğu bilinci ile buradaki IBM DeveloperWorks makalesini kendilerine vermenin ve sorunun ortaya çıktığı durumları açıklamanın daha doğru olduğunu da hatırlatmak isterim.

İyi testler!

 

(*) Memory Leak terimine Türkçe bir karşılık bulma gayretlerim sürecinde FriendFeed üzerinden bana destek olan Deniz Edincik, Burak Bayburtlu, Sarp Erdağ, Ahmet Alp Balkan, Cem Öztürk ve Levent Yalçın’a teşekkürler. (http://friendfeed.com/ozaycivelek)

(**) Benim bu soruna özellikle Java platformunda toslamamın yegane sebebi, kendilerinin yegane iş platformu (Günümüz COBOL’u) olmalarındandır. Java platformunun muadili platformlardan daha yavaş yada daha fazla soruna sebep olduğu gibi bir yargım kesinlikle yoktur.


EkleBunu 
Sosyal Paylasim Butonu


Post a Comment

Your email is never published nor shared.