Tam zamanında derleme - Just-in-time compilation

Olarak işlem , sadece zamanında ( tam zamanında ) derleme (aynı zamanda dinamik için veya çalışma zamanı derlemeleri ) uygulanması için bir yöntemdir , bilgisayar kodu içeren derleme (bir programın çalıştırılması sırasında çalışma süresi ) yerine daha önce uygulanması. Bu, kaynak kodu çevirisinden oluşabilir, ancak daha yaygın olarak, daha sonra doğrudan yürütülen makine koduna bayt kodu çevirisidir . Bir JIT derleyicisini uygulayan bir sistem, tipik olarak yürütülmekte olan kodu sürekli olarak analiz eder ve kodun, derleme veya yeniden derlemeden elde edilen hızlanmanın, bu kodu derlemenin ek yükünden daha ağır basacağı kısımlarını tanımlar.

JIT derlemesi, makine koduna çeviriye yönelik iki geleneksel yaklaşımın ( önceden derleme (AOT) ve yorumlama ) bir birleşimidir ve her ikisinin de bazı avantaj ve dezavantajlarını birleştirir. Kabaca, JIT derlemesi, derlenmiş kodun hızı ile yorumlama esnekliğini, bir yorumlayıcının ek yükü ve ek derleme ve bağlama yükü (yalnızca yorumlama değil) ile birleştirir. JIT derlemesi bir dinamik derleme biçimidir ve dinamik yeniden derleme ve mikro mimariye özgü hızlandırmalar gibi uyarlanabilir optimizasyona izin verir . Çalışma zamanı sistemi geç bağlanan veri türlerini işleyebildiği ve güvenlik garantilerini uygulayabildiği için, yorumlama ve JIT derlemesi özellikle dinamik programlama dilleri için uygundur .

Tarih

İlk yayınlanan JIT derleyicisi, genellikle 1960 yılında John McCarthy tarafından LISP üzerinde yapılan çalışmaya atfedilir . Onun ufuk açıcı makalesinde , Sembolik ifadelerin özyinelemeli işlevleri ve makine tarafından hesaplanması, Kısım I , çalışma zamanı sırasında çevrilen işlevlerden bahseder, böylece derleyici çıktısını delikli kartlara kaydedin (bu daha doğru bir şekilde " Derle ve git sistemi " olarak bilinse de ). Bir başka erken örnek, 1968'de metin editörü QED'de kalıp eşleştirme için düzenli ifadelerin ilk uygulamalarından birini veren Ken Thompson'a aitti . Hız için Thompson , Uyumlu Zaman Paylaşım Sistemindeki IBM 7094 koduna JITing yoluyla düzenli ifade eşleştirmesi uyguladı . Yorumdan derlenmiş kod türetmeye yönelik etkili bir tekniğe , 1970 yılında James G. Mitchell tarafından öncülük edilmiş ve deneysel dil LC² için uygulanmıştır .

Smalltalk (c. 1983), JIT derlemelerinin yeni yönlerine öncülük etti. Örneğin, istek üzerine makine koduna çeviri yapıldı ve sonuç daha sonra kullanılmak üzere önbelleğe alındı. Bellek azaldığında, sistem bu kodun bir kısmını silecek ve gerektiğinde yeniden üretecektir. Sun'ın Öz dili bu teknikleri kapsamlı bir şekilde geliştirdi ve bir noktada dünyanın en hızlı Smalltalk sistemiydi; optimize edilmiş C'nin yarı hızına kadar ancak tamamen nesne yönelimli bir dil ile elde edilir.

Self, Sun tarafından terk edildi, ancak araştırma Java diline girdi. "Just-in-time derleme" "üretim dönemi ödünç edildi terim Tam zamanında " ve 1993 Şu JITing gelen terimi kullanarak James Gosling ile, Java tarafından popüler çoğu uygulamaları tarafından kullanılan Java Virtual Machine olarak, HotSpot bu araştırma temeli üzerine kuruludur ve kapsamlı bir şekilde kullanır.

HP projesi Dynamo, 'bytecode' formatının ve makine kodu formatının aynı olduğu deneysel bir JIT derleyicisiydi; sistem PA-6000 makine kodunu PA-8000 makine koduna dönüştürdü. Sezgisel olmayan bir şekilde, bu, örneğin, daha iyi önbellek kullanımı için satır içi kod ve dinamik kitaplıklara yapılan çağrıların optimizasyonu ve geleneksel olan diğer birçok çalışma zamanı optimizasyonu gibi makine kodu düzeyinde optimizasyonlara izin verildiğinden, bazı durumlarda %30'luk hızlanmalarla sonuçlandı. derleyiciler deneyemez.

Kasım 2020'de PHP 8.0, bir JIT derleyicisini tanıttı.

Tasarım

Bayt koduyla derlenmiş bir sistemde kaynak kod , bayt kodu olarak bilinen bir ara temsile çevrilir . Bayt kodu herhangi bir bilgisayar için makine kodu değildir ve bilgisayar mimarileri arasında taşınabilir olabilir . Bayt kodu daha sonra bir sanal makine tarafından yorumlanabilir veya çalıştırılabilir . JIT derleyicisi birçok bölümdeki (veya tam, nadiren) bayt kodlarını okur ve programın daha hızlı çalışabilmesi için bunları dinamik olarak makine kodunda derler. Bu, dosya başına, işlev başına veya hatta herhangi bir rastgele kod parçası üzerinde yapılabilir; kod, yürütülmek üzereyken derlenebilir (dolayısıyla "tam zamanında" adı verilir) ve daha sonra yeniden derlenmeye gerek kalmadan önbelleğe alınabilir ve yeniden kullanılabilir.

Buna karşılık, geleneksel yorumlanmış bir sanal makine , genellikle çok daha düşük performansla, bayt kodunu basitçe yorumlayacaktır. Hatta bazı tercümanlar , daha da kötü performansla, ilk önce bayt koduna derleme adımı olmadan kaynak kodunu bile yorumlayabilirler. Statik olarak derlenmiş kod veya yerel kod , dağıtımdan önce derlenir. Bir dinamik derleme ortamı derleyici yürütülürken kullanılabilecek bir sistemdir. JIT tekniklerini kullanmanın ortak bir amacı, bayt kodu yorumlamanın avantajlarını korurken statik derlemenin performansına ulaşmak veya bu performansın üzerine çıkmaktır: Orijinal kaynak kodunu ayrıştırmanın ve temel optimizasyonu gerçekleştirmenin "ağır yükünün" çoğu, genellikle derleme zamanında ele alınır, dağıtımdan önce: bayt kodundan makine koduna derleme, kaynaktan derlemeden çok daha hızlıdır. Dağıtılan bayt kodu, yerel kodun aksine taşınabilirdir. Çalışma zamanı, yorumlanmış bayt kodu gibi derleme üzerinde denetime sahip olduğundan, güvenli bir sanal alanda çalışabilir. Bayt kodundan makine koduna derleyicilerin yazılması daha kolaydır, çünkü taşınabilir bayt kodu derleyicisi işin çoğunu zaten yapmıştır.

JIT kodu genellikle yorumlayıcılardan çok daha iyi performans sunar. Ayrıca, birçok optimizasyon yalnızca çalışma zamanında mümkün olduğundan, bazı durumlarda statik derlemeden daha iyi performans sunabilir:

  1. Derleme, hedeflenen CPU'ya ve uygulamanın çalıştığı işletim sistemi modeline göre optimize edilebilir. Örneğin, JIT , CPU'nun bunları desteklediğini algıladığında SSE2 vektör CPU talimatlarını seçebilir . Statik bir derleyici ile bu düzeyde bir optimizasyon özgüllüğü elde etmek için, amaçlanan her platform/mimari için bir ikili dosya derlemeli veya tek bir ikili dosya içinde kodun bölümlerinin birden çok sürümünü içermelidir.
  2. Sistem, programın bulunduğu ortamda gerçekte nasıl çalıştığına dair istatistikler toplayabilir ve optimum performans için yeniden düzenleyebilir ve yeniden derleyebilir. Ancak bazı statik derleyiciler de girdi olarak profil bilgilerini alabilir.
  3. Sistem, dinamik bağlantının avantajlarını kaybetmeden ve statik derleyiciler ve bağlayıcılara özgü genel giderler olmadan global kod optimizasyonlarını (örneğin kitaplık işlevlerinin satır içine alınması) yapabilir. Spesifik olarak, genel satır içi değiştirmeler yaparken, statik bir derleme işlemi, çalışma zamanı kontrollerine ihtiyaç duyabilir ve nesnenin gerçek sınıfı satır içi yöntemi geçersiz kılarsa sanal bir çağrının gerçekleşmesini sağlayabilir ve dizi erişimlerinde sınır koşulu kontrollerinin işlenmesi gerekebilir. döngüler içinde. Çoğu durumda tam zamanında derleme ile bu işlem döngülerin dışına taşınabilir ve genellikle büyük hız artışları sağlar.
  4. Bu, statik olarak derlenmiş çöp toplanan dillerle mümkün olsa da, bir bayt kodu sistemi, daha iyi önbellek kullanımı için yürütülen kodu daha kolay yeniden düzenleyebilir.

Bir JIT'in çalışma zamanında yerel bir ikili görüntüyü oluşturması ve yürütmesi gerektiğinden, gerçek makine kodu JIT'leri, verilerin çalışma zamanında yürütülmesine izin veren platformlar gerektirir ve bu tür JIT'lerin Harvard mimarisi tabanlı bir makinede kullanılmasını imkansız hale getirir ; aynısı belirli işletim sistemleri ve sanal makineler için de söylenebilir. Ancak, "JIT" özel bir tip potansiyel olabilir değil daha ziyade o baytkodu en VM sonunda yerli koda bir JIT güçlendirir özellikle ham makine koduna sınırlamalar hakim optimize edilmiş VM bayt kodu, fiziksel makinenin CPU mimarisini hedef ama.

Verim

JIT, bayt kodunu yüklemek ve derlemek için geçen süre nedeniyle bir uygulamanın ilk yürütülmesinde hafif ila fark edilebilir bir gecikmeye neden olur. Bazen bu gecikmeye "başlangıç ​​zaman gecikmesi" veya "ısınma zamanı" denir. Genel olarak, JIT ne kadar çok optimizasyon gerçekleştirirse, üreteceği kod o kadar iyi olur, ancak ilk gecikme de artacaktır. Bu nedenle bir JIT derleyicisi, derleme süresi ile oluşturmayı umduğu kodun kalitesi arasında bir denge kurmalıdır. Başlangıç ​​zamanı, JIT derlemesine ek olarak artırılmış IO-bağlı işlemleri içerebilir: örneğin, Java Sanal Makinesi (JVM) için rt.jar sınıfı veri dosyası 40 MB'dir ve JVM, bu bağlamsal olarak büyük dosyada çok fazla veri aramalıdır. .

Sun'ın HotSpot Java Sanal Makinesi tarafından kullanılan olası bir optimizasyon, yorumlama ile JIT derlemesini birleştirmektir. Uygulama kodu başlangıçta yorumlanır, ancak JVM hangi bayt kodu dizilerinin sıklıkla yürütüldüğünü izler ve donanım üzerinde doğrudan yürütme için bunları makine koduna çevirir. Yalnızca birkaç kez yürütülen bayt kodu için bu, derleme zamanından tasarruf sağlar ve ilk gecikmeyi azaltır; Sıkça yürütülen bayt kodu için, yavaş yorumlamanın ilk aşamasından sonra yüksek hızda çalıştırmak için JIT derlemesi kullanılır. Ek olarak, bir program çoğu zaman kodunun küçük bir kısmını yürütmek için harcadığından, azaltılmış derleme süresi önemlidir. Son olarak, ilk kod yorumlaması sırasında, derlemeden önce yürütme istatistikleri toplanabilir, bu da daha iyi optimizasyon yapılmasına yardımcı olur.

Doğru takas, koşullara bağlı olarak değişebilir. Örneğin, Sun'ın Java Sanal Makinesi'nin iki ana modu vardır: istemci ve sunucu. İstemci modunda, başlangıç ​​süresini azaltmak için minimum derleme ve optimizasyon gerçekleştirilir. Sunucu modunda, başlatma süresinden ödün verilerek uygulama çalıştırıldığında performansı en üst düzeye çıkarmak için kapsamlı derleme ve optimizasyon gerçekleştirilir. Diğer Java tam zamanında derleyicileri, ne zaman derleneceğine karar vermek için bir yöntemin bayt kodu boyutuyla birlikte bir yöntemin yürütülme sayısının bir çalışma zamanı ölçümünü kullandı. Yine bir diğeri, döngülerin tespiti ile birlikte yürütülen çalışma sayısını kullanır. Genel olarak, kısa süreli uygulamalarda hangi yöntemlerin optimize edileceğini doğru bir şekilde tahmin etmek, uzun süreli uygulamalara göre çok daha zordur.

Microsoft'un Yerel Görüntü Üreticisi (Ngen) , ilk gecikmeyi azaltmaya yönelik başka bir yaklaşımdır. Ngen, Ortak Ara Dil görüntüsündeki bayt kodunu makine yerel koduna önceden derler (veya "JIT öncesi") . Sonuç olarak, çalışma zamanı derlemesine gerek yoktur. Visual Studio 2005 ile birlikte gelen .NET Framework 2.0 , kurulumdan hemen sonra tüm Microsoft kitaplığı DLL'lerinde Ngen'i çalıştırır. Ön jitting, başlatma süresini iyileştirmenin bir yolunu sağlar. Bununla birlikte, oluşturduğu kodun kalitesi, JIT'li olan kadar iyi olmayabilir, aynı nedenlerle, kodun profil kılavuzlu optimizasyon olmadan statik olarak derlenmesi, aşırı durumda JIT derlenmiş kodu kadar iyi olamaz: örneğin, satır içi önbelleğe alma.

Ayrıca bir AOT (zamanın ötesinde) derleyicisini bir JIT derleyicisi ( Excelsior JET ) veya yorumlayıcısı ( Java için GNU Derleyicisi ) ile birleştiren Java uygulamaları da vardır .

Güvenlik

JIT derlemesi temel olarak yürütülebilir verileri kullanır ve bu nedenle güvenlik sorunları ve olası açıklardan yararlanmayı beraberinde getirir.

JIT derlemesinin uygulanması, kaynak kodun veya bayt kodunun makine koduna derlenmesi ve yürütülmesinden oluşur. Bu genellikle doğrudan bellekte yapılır: JIT derleyicisi, makine kodunu doğrudan belleğe verir ve diske çıktı olarak göndermek ve ardından her zamanki gibi önceden derlemede olduğu gibi kodu ayrı bir program olarak çağırmak yerine hemen çalıştırır. Modern mimarilerde bu, yürütülebilir alan koruması nedeniyle bir sorunla karşılaşır : aksi takdirde potansiyel bir güvenlik açığı olacağından keyfi bellek yürütülemez. Bu nedenle, bellek yürütülebilir olarak işaretlenmelidir; güvenlik nedeniyle bu , kod belleğe yazıldıktan ve salt okunur olarak işaretlendikten sonra yapılmalıdır , çünkü yazılabilir/yürütülebilir bellek bir güvenlik açığıdır (bkz. W^X ). Örneğin, Firefox'un Javascript için JIT derleyicisi, bu korumayı Firefox 46'lı bir yayın sürümünde tanıttı.

JIT püskürtme , yığın püskürtme için JIT derlemesini kullanan bir bilgisayar güvenlik açıkları sınıfıdır : sonuçta ortaya çıkan bellek yürütülebilirdir, bu da yürütmenin öbek içine taşınabilmesi durumunda bir istismara izin verir.

kullanır

JIT derlemesi bazı programlara uygulanabilir veya belirli kapasiteler, özellikle düzenli ifadeler gibi dinamik kapasiteler için kullanılabilir . Örneğin, bir metin düzenleyici, daha hızlı eşleştirmeye izin vermek için çalışma zamanında sağlanan normal bir ifadeyi makine koduna derleyebilir: bu, kalıp yalnızca çalışma zamanında sağlandığı için önceden yapılamaz. Çeşitli Modern çalışma ortamları çoğu uygulamaları da dahil olmak üzere, yüksek hızlı kod yürütülmesi için JIT derleme güvenmek Java ile birlikte, Microsoft 'ın .NET Framework . Benzer şekilde, birçok düzenli ifade kitaplığı, bayt kodu veya makine kodu için düzenli ifadelerin JIT derlemesini içerir. JIT derlemesi, bazı emülatörlerde, makine kodunu bir CPU mimarisinden diğerine çevirmek için de kullanılır.

JIT derlemesinin yaygın bir uygulaması, önce bayt kodu derlemesi olarak bilinen ( sanal makine kodu) bayt koduna AOT derlemesine sahip olmak ve ardından bayt kodunun yorumlanması yerine JIT derlemesinden makine koduna (dinamik derleme) sahip olmaktır. Bu, derlemeden kaynaklanan gecikme pahasına, yorumlamaya kıyasla çalışma zamanı performansını iyileştirir. JIT derleyicileri, yorumlayıcılarda olduğu gibi sürekli çeviri yapar, ancak derlenmiş kodun önbelleğe alınması, belirli bir çalıştırma sırasında aynı kodun gelecekteki yürütülmesindeki gecikmeyi en aza indirir. Programın yalnızca bir kısmı derlendiğinden, tüm programın yürütmeden önce derlenmesinden önemli ölçüde daha az gecikme olur.

Ayrıca bakınız

Notlar

Referanslar

daha fazla okuma

Dış bağlantılar