top of page
Yazarın fotoğrafıUmut Pisken

Yığın Kullanım Analizi (Stack Usage Analysis)

Güncelleme tarihi: 10 Haz

Yığın (stack), son gelen verinin ilk çıktığı (LIFO) bir yapıya sahip veri yapılarına verilen genel bir isimdir. İşletim sistemleri, iç içe fonksiyon çağrıları esnasında, farklı fonksiyon çağrılarına geçiş yaparken ve geri dönerken, yerel değişkenler ile dönüş adreslerini yığın (stack) yapısını kullanarak RAM üzerinde saklamaktadırlar. Bu yapıya “çalıştırma yığını (run time stack)" veya kısaca “yığın (stack)” denilmektedir.


Bir yazılımın çalışması sırasında, o esnada kodun içerisinde çağırılan fonksiyon/prosedüre ait parametreler ve yerel değişkenler “yığın (stack)” içerisine yazılır. İlgili fonksiyon/prosedür çalışmasını tamamlayıp dönüş yaptığında ise, bu fonksiyon/prosedüre ait parametre ve yerel değişkenler “yığın (stack)” ‘dan silinir. Yazılım çalışması esnasında aktif olan herbir fonksiyon/prosedür için “yığın (stack)” alanına yazılan veri öbeğine “yığın çerçevesi (stack frame)” adı verilmektedir. Çoklu görevli (multi-tasking) sistemlerde, genellikle her bir görev(task) için ayrı bir “yığın (stack)” alanı ayrılmaktadır [1]. Aşağıdaki şekilde örnek bir yazılım kodu için çalışma esnasında “yığın (stack)” üzerinde meydana gelen değişiklikler gösterilmektedir.


Örnek yazılım kodu


“Yığın (stack)” için RAM’de ayrılan alan sabit boyutludur, ancak yukarıdaki örnekte görüldüğü üzere, yazılımın çalışması esnasında her bir fonksiyon/prosedür çağrısında “yığın (stack)” üzerine yeni veriler yazılmakta ve ilgili fonksiyon/prosedür çalışmasını tamamlayana kadar bu veriler saklanmaktadır. Dolayısıyla sabit boyutlu olan “yığın (stack)” için ayrılan alanın yazılımın çalışması esnasında oluşabilecek en kötü senaryolara göre tasarlanması gerekmektedir. Aksi halde “yığın taşması (stack overflow)” olarak isimlendirilen durum oluşabilir. Bu durum ilgili yazılımın hatalı çalışmasına sebebiyet verecektir.  Örneğin 2009-2011 yılları arasında Toyota’nın ürettiği araçlarda görülen istemsiz hızlanma problemine yönelik yapılan analiz çalışmaları esnasında, problemin altında yatan sebeplerden birisinin de “yığın taşması (stack overflow)” olabileceği değerlendirmesi yapılmıştır [2]. Buna göre, Toyota’nın şirket içerisinde yaptığı analizlerde araçlarda bulunan motor kontrol yazılımının “yığın (stack)” kullanım oranı %41 olarak hesaplanmışken, istemsiz hızlanma problemi sonrası Barr tarafından yapılan analizlere göre “yığın (stack)” kullanım oranının %94’ler seviyesine kadar ulaştığı görülmüştür. Ayrıca motor kontrol yazılımı içerisinde “recursion” kullanıldığı için “yığın taşması (stack overflow)” durumunun aracın kullanımı esnasında oluşabileceği değerlendirilmiştir [2]. Benzer bir olay 1995 yılında Almanya’da yer alan Altona tren istasyonunda meydana gelmiştir.  İstasyonda yer alan tren trafiğini düzenleyen yazılımda “yığın (stack)” boyutu 3500 byte olarak hesaplanmışken, yazılımın çalışması esnasında 4000 byte’lık “yığın (stack)” alanına ihtiyaç olduğu için, “yığın taşması (stack overflow)” meydana gelmiş ve ilgili hata düzeltilene kadar tren seferlerinde ciddi gecikmeler yaşanmıştır [3].


Emniyet kritik yazılım geliştirme standartlarında, “yığın taşması (stack overflow)” durumlarının oluşmasını önlemek adına “Yığın Kullanım Analizi (Stack Usage Analysis)” yapılmasına dair beklentiler tanımlanmaktadır.  Örneğin demiryolu sinyalizasyon yazılımları için kullanılan  EN 50128:2011 standardında “Table A.18 – Performance Testing” başlığı altında yapılması istenilen stres testleri kapsamında “Yığın Kullanım Analizi (Stack Usage Analysis)” yapılması beklenilmektedir [4]. Benzer şekilde otomotiv sektöründe emniyet kritik yazılım geliştirmede kullanılan ISO 26262-6 standardında “Table 10 - Methods for verification of software integration” tablosunda yer alan 1d maddesinde “Yığın Kullanım Analizini(Stack Usage Analysis)” de içeren kaynak kullanım değerlendirmesi ("Resource usage evaluation") işleminin tüm ASIL seviyeleri için yapılması beklenilmektedir [6]. Aviyonik yazılım geliştirmede kullanılan RTCA/DO-178C rehber dokümanında da “Table A-5 Verification of Outputs of Software Coding & Integration Processes"  tablosunda yer alan 6 numaralı amaç “Yazılım kaynak kodu doğru ve tutarlıdır” (Source code is accurate and consistent) için gerçekleştirilmesi gereken aktiviteler arasında “Yığın Kullanım Analizinin(Stack Usage Analysis)” yapılması da beklenilmektedir. RTCA/DO-178C rehber dokümanı buna ek olarak “Table A-6 Testing of Outputs of Integration Processes” tablosunda yer alan 5 numaralı amaç “Çalışabilir nesne kodu hedef bilgisayar ile uyumludur” (Executable object code is compatible with target computer) kapsamında da yapılacak yazılım testleri esnasında olası yığın taşması (stack overflow)” durumlarının tespit edilmesini beklemektedir [7].


Olası “Yığın taşması (stack overflow)” durumları siber saldırılarda bir açık olarak kullanılabilmektedir. “Yığın parçalaması (stack smashing)” adı verilen siber saldırı türünde “yığın taşması (stack overflow)” durumu oluşturularak saldırıyı yapanlar tarafından kendi hazırladıkları kötü amaçlı kod parçaları çalıştırılabilmektedir. Buna önlem olarak “yığın kanaryası (stack canary)” olarak adlandırılan bir yöntem kullanılabilmektedir. Bu yöntemde yazılım kodu çalışmaya başladığı esnada rastgele üretilen bir sayı “yığın (stack)” üzerindeki belirli bölgelere yazılmakta ve değerin korunup korunmadığı sürekli kontrol edilmektedir. “Yığın taşması (stack overflow)” oluşması durumunda ilgili değerin de üzerine yazılacağı ve değer bozulacağı için durum fark edilebilmekte ve gerekli önlemler alınarak kontrolün kötü amaçlı yazılımlara geçmesi engellenebilmektedir.


“Yığın Kullanım Analizi (Stack Usage Analysis)” yapmak ve bir yazılımın ihtiyaç duyabileceği en büyük yığın (stack) boyutunu bulabilmek için en kesin yöntem, yazılımı olası bütün girdi senaryolarında çalıştırıp kullanılan azami yığın (stack) boyutunu tespit etmektir. Ancak bu yöntem günümüzdeki karmaşık yazılımları düşündüğümüzde pratik açıdan uygulanabilir değildir [8]. Buna alternatif olarak statik ve dinamik yöntemler ortaya konulmuştur. Statik yöntemlerde, yazılım kaynak kodu çalıştırılmadan, araçlar yardımıyla fonksiyon/prosedür çağrıları analiz edilmekte ve yazılımın ihtiyaç duyacağı azami yığın (stack) boyutu belirlenmektedir. Ancak bu yöntemlerin en önemli dezavantajı derleyici(compiler) ve çevirici(assembler) etkilerini dikkate alamıyor olmalarıdır [1]. Benzer şekilde yazılıma entegre edilen ve farklı yerlerden temin edilen hazır kütüphane yazılımlarının yığın (stack) ihtiyacı da bu yöntemde analiz edilememektedir.  Ayrıca assembly dili ile kodlama yapılması durumunda statik yöntemler yetersiz kalabilmektedir [5]. Dolayısıyla statik yöntemlerin tek başına kullanılması doğru bir “Yığın Kullanım Analizi (Stack Usage Analysis)” için tek başına yeterli olamayacaktır. Bu noktada dinamik yöntemler adı verilen yöntemler devreye girmektedir. Bu yöntemlerde statik yöntemlerde tespit edilen ve en çok yığın (stack) kullanımına yol açacağı öngörülen senaryolar üzerinden testler geliştirilmekte ve kullanılan azami yığın (stack) boyutu tespit edilmektedir. Bunun için ilgili senaryolar koşturulmadan önce RAM’de yer alan yığın (stack) için ayrılmış bölgeye 0xABABABAB gibi özel kalıplar yazılmaktadır. İlgili test senaryoları koşturulduktan sonra, RAM’de yığın (stack) için ayrılmış bölgede yer alan değerler incelenerek kullanılmış olan azami yığın (stack) boyutu tespit edilmektedir. Dinamik yöntemler kullanılırken en önemli nokta azami yığın (stack) kullanımına yol açabilecek olan senaryoların doğru ve eksiksiz şekilde belirlenmesidir. Kesme (interrupt) kullanımları, hazır kütüphane kullanılması durumunda bunun yol açacağı olası etkilerin senaryolar hazırlanırken mutlaka göz önüne alınması gerekmektedir. Her durumda yapılan çalışmalar sonucunda tüm şartlar altında gerekli olabilecek azami yığın (stack) boyutu doğru olarak tespit edilememiş olabileceği için, yazılım tasarımı yapılırken statik ve dinamik yöntemlerin kullanılması sonucunda ulaşılan azami yığın (stack) boyutundan bir miktar fazla yer ayrılması güvenli bir yaklaşım olacaktır.


Emniyet kritik yazılım geliştirme standartları tarafından yapılması beklenilen “Yığın Kullanım Analizi (Stack Usage Analysis)” çalışmasının yazılım geliştirme projelerinde yeterli özen gösterilerek yapılması gerekmektedir. Gereğinden az yığın (stack) boyutu ayrılması durumunda yazılımda tahmin edilemeyen hata durumları oluşabilir. Gereğinden fazla yığın (stack) boyutu ayrılması ise ekonomik açıdan yanlış bir yaklaşım olacaktır. Ayrıca siber güvenlik kapsamında da yığın (stack) kullanımındaki olası açıklara ilişkin önlemlerin düşünülmesi gerekmektedir. Bu konular üzerine projelerin planlama döneminde düşünülmesi, gerekli altyapıların kurulması, tasarım ve test faaliyetlerinin bunlar dikkate alınarak yapılması gerekmektedir. Projelerin bitime yakın dönemde yığın (stack) kullanımı ile ilgili karşılaşılabilecek problemlerin çözümünün ciddi takvim ve maliyet etkilerinin olabileceği akıldan çıkarılmamalıdır.

 

Kaynaklar:


  1. Kastner, D. ve Ferdinand, C., “Proving the Absence of Stack Overflows”, SAFECOMP '14: Proceedings of the 33th International Conference on Computer Safety, Reliability and Security, 2014. 

  2. Dunn, M., “Toyota’s killer firmware: Bad design and its consequences", Erişim: 25 Mayıs 2024, ”https://www.edn.com/toyotas-killer-firmware-bad-design-and-its-consequences/ 

  3. Eslamimehr, M., Palsberg, J.: Testing versus static analysis of maximum stack size. In: 37th Annual Computer Software and Applications Conference. IEEE, pp. 619–626, 2013.

  4. CENELEC, “EN 50128:2011- Railway applications: software for railway control and protection systems”, 2011.

  5. ArmKeil, “AN316 – Determining the stack usage of applications(V 1.1)”, 2019.

  6. ISO,  “ISO 26262-6 Road vehicles - Functional safety - Part 6: Product development at the software level”, 2018. 

  7. RTCA, “DO-178C Software Considerations in Airborne Systems and Equipment Certification”, 2011. 

  8. Eslamimehr, M. ve Palsberg, J., "Testing versus Static Analysis of Maximum Stack Size", IEEE 37th Annual Computer Software and Applications Conference, 2013.

 

304 görüntüleme0 yorum

Son Yazılar

Hepsini Gör

Comments


bottom of page