Czy istnieje sposób na uzyskanie współczynnika trafień / braków pamięci podręcznej dla urządzeń blokowych w systemie Linux?

21

Czy w Linuksie można zobaczyć, ile żądań odczytu i zapisu z przestrzeni użytkownika powoduje trafienia do pamięci podręcznej i opuszcza urządzenia blokujące?

Kyle Brandt
źródło

Odpowiedzi:

9

Możesz opracować własny skrypt SystemTap . Musisz uwzględnić następujące dwa podsystemy:

  • VFS: reprezentuje wszystkie żądania I / O przed pamięcią podręczną bufora (tj. Absolutnie każde żądanie I / O); przejrzyj sondy „vfs.read”, „vfs.write” i „kernel.function („ vfs_ * ”)”; musisz odfiltrować urządzenia blokowe, które chcesz monitorować, według ich odpowiednich głównych + mniejszych liczb.
  • Blok: reprezentuje wszystkie żądania We / Wy wysłane do urządzeń blokowych przed harmonogramem We / Wy (który również łączy + zmienia kolejność żądań We / Wy); tutaj wiemy, które żądania zostały pominięte przez pamięć podręczną bufora; przejrzyj sondę „ioblock.request”.

Opracowanie SystemTap zajmuje trochę czasu. Jeśli jesteś umiarkowanym programistą i masz dobrą wiedzę na temat Linuksa, powinieneś to zrobić za 3-4 dni. Tak, nauka zajmuje dużo czasu, ale będziesz bardzo zadowolony z rezultatów - SystemTap daje Ci możliwość (bezpiecznego) umieszczenia sond w prawie dowolnym miejscu jądra Linux.

Zauważ, że twoje jądro musi obsługiwać ładowanie i rozładowywanie modułów jądra. Większość obecnych jąder obsługuje to. Będziesz także musiał zainstalować symbole debugowania dla swojego jądra. W moim systemie Ubuntu było to tak proste, jak pobranie kilkuset MB pliku .deb, który skompilował dla mnie zespół programistów jądra Ubuntu. Jest to wyjaśnione na przykład na stronie Wiki SystemtapOnUbuntu .

PS Podejdź do SystemTap tylko wtedy, gdy nie masz innego rozwiązania, ponieważ jest to zupełnie nowa struktura, której musisz się nauczyć, a to kosztuje czas / pieniądze, a czasem frustrację.

famzah
źródło
1
+1 ładne i czyste wyjaśnienie. dziękuję, ja również kasę systemtap.
risyasin
Skrypt SystemTap do tego znajduje się na ich wiki.
Michael Hampton
8

Poszedłem naprzód i napisałem do tego scenariusz. Jest jedna na wiki systemtap, ale wydaje się, że nie jest poprawna. W podstawowych testach wydaje się to dość dokładne, ale YMMV.

#! /usr/bin/env stap
global total_bytes, disk_bytes, counter

probe vfs.read.return {
  if (bytes_read>0) {
    if (devname=="N/A") {
    } else {
      total_bytes += bytes_read
    }
  }
}
probe ioblock.request
{
    if (rw == 0 && size > 0)
    {
        if (devname=="N/A") { 
        } else {
          disk_bytes += size
        }
    }

}

# print VFS hits and misses every 5 second, plus the hit rate in %
probe timer.s(5) {
    if (counter%15 == 0) {
        printf ("\n%18s %18s %10s %10s\n", 
            "Cache Reads (KB)", "Disk Reads (KB)", "Miss Rate", "Hit Rate")
    }
    cache_bytes = total_bytes - disk_bytes
    if (cache_bytes < 0)
      cache_bytes = 0
    counter++
    hitrate =  10000 * cache_bytes / (cache_bytes+disk_bytes)
    missrate = 10000 * disk_bytes / (cache_bytes+disk_bytes)
    printf ("%18d %18d %6d.%02d%% %6d.%02d%%\n",
        cache_bytes/1024, disk_bytes/1024,
        missrate/100, missrate%100, hitrate/100, hitrate%100)
    total_bytes = 0
    disk_bytes = 0
}
Dave Wright
źródło
Niesamowite! Dodałem małą średnią statystykę użycia pamięci podręcznej do wydrukowania po zamknięciu: pastie.org/1845683
entropo
Mam skopiuj / wklej kod, aby go uruchomić, po wystąpieniu następującego błędu, semantic error: unable to find member 'bi_size' for struct bio (alternatives: bi_next bi_bdev bi_flags bi_rw bi_iter bi_phys_segments bi_seg_front_size bi_seg_back_size bi_remaining bi_end_io bi_private bi_ioc bi_css bi_integrity bi_vcnt bi_max_vecs bi_cnt bi_io_vec bi_pool bi_inline_vecs): operator '->' at /usr/share/systemtap/tapset/linux/ioblock.stp:113:20 source: size = $bio->bi_size ^ Pass 2: analysis failed. [man error::pass2]czy możesz pomóc?
Fopa Léon Constantin,
2

/ proc / slabinfo to dobry początek, ale nie daje ci dość informacji, których szukasz (nie daj się zwieść procentom trafień / braków w systemach z włączoną wieloma rdzeniami i statystykami; to coś innego). O ile mi wiadomo, nie ma sposobu na wyciągnięcie tej konkretnej informacji z jądra, chociaż napisanie odrobiny kodu nie powinno być trudne.

Edycja: http://www.kernel.org/doc/man-pages/online/pages/man5/slabinfo.5.html

BMDan
źródło
1

Teraz jest narzędzie cachestat z pakietu perf-tools .

Autor wymienia także niektóre (prawdopodobnie bardziej brutalne) alternatywy, z których ludzie korzystają:

A) Zbadaj wskaźnik brakujących pamięci podręcznej strony za pomocą iostat (1) do monitorowania odczytów dysku i załóż, że są to błędy pamięci podręcznej, a nie na przykład O_DIRECT. Zresztą wskaźnik pominięć jest zwykle ważniejszy niż stosunek, ponieważ pomyłki są proporcjonalne do bólu aplikacji. Użyj również free (1), aby zobaczyć rozmiary pamięci podręcznej.

B) Upuść pamięć podręczną strony (echo 1> / proc / sys / vm / drop_caches) i zmierz, o ile wydajność się pogarsza! Uwielbiam stosowanie negatywnego eksperymentu, ale jest to oczywiście bolesny sposób, aby rzucić nieco światła na użycie pamięci podręcznej.

C) Użyj sar (1) i przestudiuj drobne i poważne usterki. Nie wydaje mi się, żeby to działało (np. Zwykłe I / O).

D) Użyj skryptu SystemTap cache-hit-rate.stp, który jest numerem dwa w wyszukiwaniu w Internecie współczynnika trafień w pamięci podręcznej stron systemu Linux. Instrumentuje dostęp do pamięci podręcznej wysoko na stosie, w interfejsie VFS, dzięki czemu można odczytać dane z dowolnego systemu plików lub urządzenia pamięci masowej. Pomyłki w pamięci podręcznej są mierzone przez ich dyskowe operacje we / wy. Pomija to również niektóre rodzaje obciążeń (niektóre są wymienione w „Lekcjach” na tej stronie), a współczynniki wywołań „stawki”.

lemonsqueeze
źródło
1

Jeśli interesuje Cię współczynnik trafień / chybień we / wy konkretnego procesu, prostym, ale bardzo skutecznym podejściem jest odczytanie /proc/<pid>/iopliku.

Tutaj znajdziesz 4 kluczowe wartości:

  • rchar: całkowita liczba odczytanych bajtów z punktu widzenia aplikacji (tj. bez różnicy między odczytem spełnionym z pamięci fizycznej, a nie z pamięci podręcznej)
  • wchar: jak wyżej, ale o bajtach zapisanych
  • read_bytes: bajty naprawdę odczytane z podsystemu pamięci masowej
  • write_bytes: bajty naprawdę zapisane w podsystemie pamięci masowej

Powiedz, że proces ma następujące wartości:

rchar: 1000000
read_bytes: 200000

Współczynnik pominięcia pamięci podręcznej odczytu (w bajtach) wynosi 100*200000/1000000 = 20%, a współczynnik trafień wynosi100-20 = 80%

Istnieje jednak pewien haczyk: rcharwartość obejmuje coś jako tty IO, więc dla procesów, które dużo czytają / piszą z / do potoku, powyższe obliczenia zostaną wypaczone, zgłaszając wyższy współczynnik trafień niż efektywny.

Shodanshok
źródło