İçeriğe geç
academia.sh

Ders 09 / 22

Önyükleme Süreci

Ürün yazılımından ilk sürece ve hedeflere uzanan devir zinciri kurulur; bir birimi yeniden başlatmanın kaç birimi durdurup başlattığı ve açılışta başarısız olan birimin kaç birimi hiç başlatmadığı sayılır.

İçindekiler

Önceki ders tek bir birimi ölçtü: kendi başına çöken, politikasına göre dirilen ya da diriltilmeyen bir birim. O ölçümde birim yalnızdı. Kurgu sunucuda ise birimler birinci derste kurulan grafiğin düğümleridir ve grafik hâlâ oradadır. Bir birimi yeniden başlatmak yalnız onu ilgilendirmez.

Bu ders grafiğin zaman içinde nasıl işletildiğine bakar. Makine açıldığında bu grafik baştan sona bir kez yürütülür; bir birim elle yeniden başlatıldığında grafiğin bir parçası yeniden yürütülür. İki durumda da yöneticinin bastığı satır sayısı ile gerçekte olan iş birbirinden farklıdır. Ölçülen şey, yeniden başlatma komutunun çıktısından çıkarılan tanının kaç kez yanlış olduğudur.

Ürün Yazılımından İlk Sürece

Bir makinenin açılması tek bir olay değil, bir devir zinciridir. Her halka kendinden sonrakini belleğe alır, denetimi ona bırakır ve sahneden çekilir. Halkaların hiçbiri kendinden öncekini denetleyemez; bu yüzden zincirin başındaki bir hata sonundaki araçlarla görülemez.

İlk halka ürün yazılımıdır. Anakart üzerindeki kalıcı bellekte durur, güç verildiğinde çalışır, donanımı sayar ve sınar, sonra önceden belirlenmiş bir sırayla açılış aygıtlarına bakar. Bulduğu ilk uygun aygıttaki kodu belleğe alıp çalıştırır. Ürün yazılımının aygıt sırası bir yapılandırma değeridir ve bu değer işletim sisteminin içinden görünmez.

İkinci halka önyükleyicidir. Görevi bir çekirdek seçmek, onu diskten belleğe okumak, yanına geçici bir kök dosya sistemi almak ve çekirdeğe geçirilecek parametreleri hazırlamaktır. Önyükleyicinin kendisi de birden çok parçadan oluşabilir; ilk parça çok küçüktür, yalnız ikinci parçayı okuyacak kadar yer kaplar. Önyükleyicinin ayrıntısı bir sonraki dersin konusudur.

Üçüncü halka çekirdektir. Belleğe alınır, kendini açar, aygıtları tanır ve yanında getirilen geçici kök dosya sistemini kullanarak asıl kök dosya sistemini takar. Geçici kök gereklidir, çünkü asıl kökü takmak için gereken sürücüler çoğu zaman o kökün içindedir; sıralama sorununu çözen şey bu ara katmandır. Kök takıldıktan sonra çekirdek son işini yapar ve ilk süreci çalıştırır. İlk süreç, süreç ağacının kökündeki tek süreçtir; sistemin sonuna kadar yaşar ve öldüğünde sistem durur.

Dördüncü halka ilk süreçtir ve çoğu sistemde bu süreç servis yöneticisidir. Yönetici birim dosyalarını okur, grafiği kurar ve varsayılan hedefe ulaşmak için gereken birimleri etkinleştirir. Devir zinciri burada biter, birim grafiği burada başlar.

Zincirin tanı açısından önemli özelliği, her halkanın kendi kanıtını başka bir yere yazmasıdır. Ürün yazılımının bulguları ekranda kalır ve hiçbir dosyaya düşmez. Önyükleyicinin ilettiği hata yalnız o an görünür. Çekirdeğin açılış iletileri bellekte bir halka tampona yazılır ve kök dosya sistemi takılana kadar hiçbir yere kaydedilemez; tampon dolarsa en eski iletiler üzerine yazılır. Kalıcı kayıt ancak kök takıldıktan ve günlük birimi çalıştıktan sonra başlar. Bu yüzden zincirin ilk üç halkasında olan bir arıza, sistem açılmadığı sürece hiçbir dosyada iz bırakmaz. Günlüklerin nasıl toplandığı ve nasıl döndürüldüğü bir sonraki konunun sorusudur; buradaki nokta yalnız şu: kanıtın var olması, kaydedilmiş olmasını gerektirir.

Hedefler ve Katmanlar

Önyükleme, birim grafiğinin bir kez baştan yürütülmesidir. Yönetici varsayılan hedefi alır, o hedefin gerektirdiği ve istediği birimleri bulur, onların gerektirdiklerini bulur ve grafiği geriye doğru açar. Sonuçta ortaya bir katman yapısı çıkar: aralarında kenar bulunmayan birimler aynı katmandadır ve aynı anda başlatılabilir.

Katman sayısı önyükleme süresinin alt sınırını belirler. Altı birim art arda başlatılsaydı altı birimlik bir bekleme olurdu; katmanlara ayrıldığında bekleme katman sayısı kadardır. Bu, birinci derste “yönetici neden grafiğe ihtiyaç duyar” sorusunun cevabıydı.

Servis yöneticileri açılışın ne kadar sürdüğünü ve hangi birimin ne kadar beklettiğini basan bir çözümleme komutu sunar. Bu komutun çıktısı sık yanlış okunur ve yanlış okumanın kaynağı yine grafiktir: bir birimin karşısında yazan süre, o birimin kendi işinin süresi değil, başlatma isteğinin verilmesiyle hazır sayılması arasındaki süredir. Gerektirdiği birimleri bekleyerek geçen zaman da bu sürenin içindedir. Sıralamada en üstte görünen birim çoğu zaman en yavaş birim değil, en derin katmandaki birimdir. Bu çıktıya dayanarak birim eniyilemeye kalkışan operatör, yanlış birimi eniyiler. Önyükleme süresinin gerçek sayıları donanıma ve yapılandırmaya bağlıdır ve burada yazılmaz; yazılabilecek olan, sıralamanın neyi sıraladığıdır.

SV32 — varsayılan hedef altı birimin altısını da ister. SV33 — bir birim, gerektirdiği bütün birimler başlamadan başlamaz. SV34 — aynı katmandaki birimler aynı anda başlar ve birbirini beklemez. SV35 — sıralama kenarları katman hesabına girmez; yalnız gerektirme kenarları girer. SV36 — bir birimi yeniden başlatmak, onu gerektiren bütün birimleri durdurup yeniden başlatır. SV37 — yeniden başlatma komutu tek satır basar ve yalnız adı verilen birimi anar. SV38 — açılışta başarısız olan bir birim, kendisini gerektiren birimlerin hiç başlamamasına yol açar. SV39 — açılış özeti başarısız birim sayısını yalnız gerçekten denenip başarısız olanlar üzerinden verir; hiç denenmeyen birimler bu sayıya girmez. SV40 — grafik önyükleme boyunca değişmez.

Bu varsayımların ölçüden önce yazılmasının nedeni, hepsinin çıktıda görünmemesidir. Yönetici katmanları da, atlanan birimleri de biliyor; bastığı satırlarda bunların hiçbiri yok.

Komutun Bastığı Satır

Yeniden başlatma komutu başarılı olduğunda hiçbir şey basmaz; başarısızlıkta tek satırlık bir hata basar. Açılıştan sonra sistemin bütününü soran komut da tek sözcükle cevap verir. Aşağıdaki dökümler çalıştırılmamıştır; çıktının hangi bilgiyi taşıdığını göstermek için yazılmıştır:

$ systemctl restart veri-alma.service
$ systemctl is-system-running
degraded
$ systemctl --failed
  UNIT               LOAD    ACTIVE  SUB     DESCRIPTION
* veri-alma.service  loaded  failed  failed  Veri alma birimi

1 loaded units listed.

Birinci komut sessizce döndü ve bu sessizlik “yalnız istenen oldu” diye okunur. İkinci komut sistemin bütünü hakkında tek sözcük verir ve o sözcük hangi birimin bozuk olduğunu söylemez. Üçüncü komut başarısız birimleri listeler; son satır sayıyı yazar. Üç çıktının hiçbiri, o bir birime bağlı dört birimin de durmuş olduğunu söylemez. Bağlı birimler “başarısız” değildir, “etkin değil” durumundadır ve bu listeye girmezler. Aradaki fark bir durum sözcüğü farkıdır ve tanıyı tersine çevirir.

BIRIM = {
    "veri-alma": {"gerektirir": [], "yeniden": "her zaman"},
    "kuyruk":    {"gerektirir": ["veri-alma"], "yeniden": "her zaman"},
    "isleme":    {"gerektirir": ["kuyruk"], "yeniden": "arizada"},
    "rapor":     {"gerektirir": ["isleme"], "yeniden": "hayir"},
    "olcum":     {"gerektirir": ["veri-alma"], "yeniden": "her zaman"},
    "yedek":     {"gerektirir": [], "yeniden": "hayir"},
}


def bagimli_olanlar(birim, birimler=None):
    birimler = BIRIM if birimler is None else birimler
    dogrudan = [a for a, v in birimler.items() if birim in v["gerektirir"]]
    hepsi = set(dogrudan)
    for d in dogrudan:
        hepsi |= bagimli_olanlar(d, birimler)
    return hepsi


def yeniden_baslatma_zinciri(birim):
    """Bir birimi yeniden baslatmak kac birimi daha durdurup baslatir."""
    etkilenen = bagimli_olanlar(birim)
    return {"birim": birim, "etkilenen": len(etkilenen),
            "etkilenen_ad": sorted(etkilenen)}


def katman(birim):
    """Onyuklemede birimin kacinci dalgada baslayabilecegi."""
    g = BIRIM[birim]["gerektirir"]
    return 0 if not g else 1 + max(katman(x) for x in g)


def onyukleme(basarisiz):
    """Bir birim acilista basarisiz olursa hangi birimler hic baslamaz."""
    atlanan = bagimli_olanlar(basarisiz)
    baslayan = [b for b in BIRIM if b != basarisiz and b not in atlanan]
    return {"baslayan": len(baslayan), "atlanan": len(atlanan), "bildirilen": 1}


print("birim      katman  arac ciktisi  kahin(duran ve basayan)  tani dogru mu")
yanlis = 0
for b in BIRIM:
    z = yeniden_baslatma_zinciri(b)
    kahin = 1 + z["etkilenen"]
    dogru = kahin == 1
    yanlis += 0 if dogru else 1
    print(f"  {b:10s} {katman(b):6d} {'1 birim':>13s}  {kahin:23d}"
          f"  {'evet' if dogru else 'HAYIR'}")
print("  yanlis tani:", yanlis, "/ 6 | gizlenen birim:",
      sum(len(bagimli_olanlar(b)) for b in BIRIM))
print("  veri-alma zinciri:", yeniden_baslatma_zinciri("veri-alma"))
print()
print("acilista basarisiz  baslayan  hic baslamayan  bildirilen hata")
for b in BIRIM:
    o = onyukleme(b)
    print(f"  {b:18s} {o['baslayan']:8d}  {o['atlanan']:14d}  {o['bildirilen']:15d}")
birim      katman  arac ciktisi  kahin(duran ve basayan)  tani dogru mu
  veri-alma       0       1 birim                        5  HAYIR
  kuyruk          1       1 birim                        3  HAYIR
  isleme          2       1 birim                        2  HAYIR
  rapor           3       1 birim                        1  evet
  olcum           1       1 birim                        1  evet
  yedek           0       1 birim                        1  evet
  yanlis tani: 3 / 6 | gizlenen birim: 7
  veri-alma zinciri: {'birim': 'veri-alma', 'etkilenen': 4, 'etkilenen_ad': ['isleme', 'kuyruk', 'olcum', 'rapor']}

acilista basarisiz  baslayan  hic baslamayan  bildirilen hata
  veri-alma                 1               4                1
  kuyruk                    3               2                1
  isleme                    4               1                1
  rapor                     5               0                1
  olcum                     5               0                1
  yedek                     5               0                1

Üç Sayı

Kâhin: veri-alma biriminin yeniden başlatılması 4 birimi daha durdurup başlatır — isleme, kuyruk, olcum ve rapor. Kendisiyle birlikte kesinti gören birim sayısı 5. Altı birim üzerinde toplam 7 birim gizlice etkileniyor. Araç çıktısı: komut her birim için tek satır basıyor ve o satırda yalnız 1 birim anılıyor. Yanlış tanı: altı birimin 3’ünde “yalnız bu birim etkilendi” tanısı yanlış; veri-alma için sayı beş kat, kuyruk için üç kat, isleme için iki kat eksik.

Ortak tanımın üçüncü okuması buradadır: bir birimi yeniden başlatmak dördünü daha durduruyor ve zincir çıktıda görünmez. Yanlış tanının yönü hep aynı, hep eksik sayma. Bu yön işletimde belirli bir hataya karşılık gelir: kısa bir bakım için veri-alma yeniden başlatılır, rapor üretimi de aynı anda kesilir, kesintinin nedeni raporun kendi günlüğünde görünmez ve arıza başka yerde aranır.

Katman sütunu ikinci bir şey söylüyor. veri-alma ve yedek sıfırıncı katmanda, kuyruk ve olcum birinci, isleme ikinci, rapor üçüncü katmanda. Grafiğin derinliği dört. Yeniden başlatmanın etkilediği birim sayısıyla katman derinliği aynı şey değil: olcum birinci katmanda olduğu hâlde hiçbir birimi etkilemiyor, çünkü onu gerektiren kimse yok. Derinlik ile etki birbirinden bağımsız iki ölçüdür ve ikisini karıştırmak, grafiğin dibindeki birimleri gereksizce tehlikeli saymaya yol açar.

Açılışta Başarısız Olan Birim

İkinci tablo aynı grafiği önyükleme yönünde okuyor. veri-alma açılışta başlatılamazsa yalnız 1 birim başlar, 4 birim hiç denenmez ve açılış özeti 1 başarısız birim bildirir. Bildirilen sayı doğrudur — gerçekten bir birim başarısız oldu — ama sistemin durumunu anlatmaz. Dört birim başarısız olmadı; hiç denenmedi, ve denenmedikleri için haklarında hiçbir kayıt üretilmedi.

Bu, kursun üçüncü iddiasının bu dersteki biçimi: kanıt kendiliğinden yok oluyor. Bir birim çalışıp hata verseydi geriye bir hata kaydı kalırdı. Hiç başlatılmayan birim hiçbir şey yazmaz. Açılıştan sonra bakan operatörün elinde tek bir başarısızlık bildirimi ve sessiz dört birim vardır; sessizlik, sağlıkla aynı biçimde görünür.

Doğru okuma yolu, açılış özetindeki sayıya değil, beklenen birim kümesiyle başlayan birim kümesinin farkına bakmaktır. Bu fark grafikten hesaplanır ve hiçbir komut tek başına basmaz. Tablonun son üç satırı da bunu doğruluyor: rapor, olcum ve yedek başarısız olduğunda hiçbir birim atlanmıyor ve bildirilen sayı bir kez doğru oluyor. Aynı bildirim, aynı biçim, farklı anlam.

Kapanış Aynı Grafiğin Ters Yönüdür

Açılış grafiği ileri yönde yürütüyorsa kapanış aynı grafiği geri yönde yürütür. Önce en üstteki birimler durdurulur, sonra onların gerektirdikleri. Sıra tersine çevrilmezse veri yazan bir birim, altındaki depolama birimi çoktan sökülmüşken kapanmaya çalışır.

Kapanışın kendi zaman sınırı vardır ve bu sınır bir tanı kaynağıdır. Yönetici bir birime durma isteği gönderir, belirli bir süre bekler, birim durmazsa zorlayan sinyali gönderir. Süreç yönetimi konusunda kurulan ayrım burada da geçerlidir: istek ile zorlama farklı şeylerdir ve ikisi arasındaki pencere, birimin verisini diske yazmak için elindeki tek süredir. Sınır kısa tutulduğunda kapanış hızlanır ve yarım yazılmış dosyalar üretir; uzun tutulduğunda tek bir takılmış birim bütün makinenin kapanmasını dakikalarca bekletir. Bu, ayakta kalma ile görünürlük takasının kapanış tarafındaki karşılığıdır.

Kurtarma Hedefleri ve Bir Sonraki Halka

Varsayılan hedef tek seçenek değildir. Sistem yöneticileri için iki küçük hedef daha vardır: biri yalnız kök dosya sistemini takıp tek bir kabuk verir, diğeri ondan da azını yapar ve neredeyse hiçbir birimi başlatmaz. Bu hedeflere geçmenin iki yolu var. Sistem çalışıyorken yöneticiye hedef değiştirmesi söylenebilir; sistem hiç açılmıyorsa tek yol, önyükleme parametresiyle hedefi baştan belirlemektir.

İkinci yol bu konunun sınırını gösteriyor. Bu derse kadar anlatılan her şey, ilk süreç ayağa kalktıktan sonrası içindi. İlk süreç hiç ayağa kalkmıyorsa ne birim listesi vardır ne durum sorgusu; elde yalnız önyükleyicinin sunduğu düzenleme satırı kalır. Zincirin sonundaki araçlarla zincirin başındaki hata görülemez.

İkinci Tohum

Bu dersin sayıları tohumlu bir üreteçten değil, sabit birim grafiğinden geliyor. Ölçünün grafiğe bağlı olup olmadığını görmek için aynı hesap, tohumlu üreteçle kurulan yirmişer rastgele altı birimlik grafik üzerinde iki tohumla tekrarlandı. Gizlenen birim toplamı 20260218 ile 124, 20260219 ile 132; yanlış tanı sayısı 120 birim üzerinden 64 ve 68. Büyüklük düzeni korunuyor ve oran her iki tohumda da yarının biraz üstünde: rastgele bir grafikte bir birimi yeniden başlatmanın başka birimleri etkilemesi kural, istisna değil. Tek tek sayılar kurguya bağlıdır; komut çıktısının etkilenen birim sayısını taşımaması kurguya bağlı değildir.

Rastgele grafiklerin oranı sabit birim grafiğinden yüksek çıkıyor: kurgu sunucuda altı birimin üçünde yanlış tanı varken rastgele grafiklerde yüz yirmi birimin altmış dördünde ve altmış sekizinde var. Fark, kurgu sunucunun grafiğinin ince bir zincir olmasından geliyor; kenar yoğunluğu arttıkça etkilenen birim sayısı da artıyor. Gerçek bir sunucuda birim sayısı yüzlerle ölçülür ve grafik burada çizilenden çok daha yoğundur. Ölçünün gerçek sistemdeki karşılığı bu yüzden daha kötü olmayı bekler, daha iyi olmayı değil.

Özet

  • Önyükleme bir devir zinciridir: ürün yazılımı, önyükleyici, çekirdek ve geçici kök, sonra ilk süreç. Her halka kendinden sonrakini yükler ve çekilir; sonraki halka öncekini denetleyemez.
  • İlk süreç çoğu sistemde servis yöneticisidir; varsayılan hedeften geriye doğru grafiği açar ve birimleri katman katman başlatır.
  • Kurgu sunucuda grafiğin derinliği dört katmandır; derinlik ile etki farklı ölçülerdir.
  • veri-alma yeniden başlatıldığında 4 birim daha durup başlıyor, kesinti gören birim sayısı 5, komut çıktısı 1 birim diyor; altı birimin 3’ünde tanı yanlış.
  • Açılışta veri-alma başarısız olursa 4 birim hiç denenmez ve özet yalnız 1 başarısızlık bildirir; denenmeyen birim hiçbir kayıt bırakmaz.
  • Doğru okuma, özetteki sayıya değil beklenen küme ile başlayan küme arasındaki farka bakmaktır.

Sonraki Adım

Devir zincirinin dört halkasından üçü bu derste birim grafiğine bağlandı. Geriye ikinci halka kaldı: önyükleyici. Hangi çekirdeğin yükleneceğini, yanında hangi geçici kökün geleceğini ve çekirdeğe hangi parametrelerin geçirileceğini o belirler. Sonraki ders önyükleyici yapılandırmasının nasıl okunacağını, bir parametre değişikliğinin gerçekten etkili olup olmadığının nasıl sınanacağını ve yapılandırmayı bozan işlemlerin neden geri alınamaz olduğunu ele alır. Aynı derste yirmi dört parametre değişikliğinin kaçının gerçekten iş gördüğü sayılır; üretici komutun cevabı yirmi dördü de.

İlerlemeni kaydetmek ve not almak için Giriş yap

Notlarım

Not almak için giriş yapmalısın.

Aramak için yazmaya başlayın.

↑↓ Esc gezin · aç · kapat