NAZWA¶
core - plik zrzutu pamięci
OPIS¶
Dla pewnych sygnałów domyślną akcją procesu jest
zakończenie działania i utworzenie
pliku zrzutu pamięci
(core), czyli pliku zawierającego obraz pamięci procesu w czasie,
gdy został on zakończony. Dowolny debugger (np.
gdb(1))
może użyć tego obrazu do zbadania stanu programu w czasie jego
zakończenia. Listę sygnałów powodujących utworzenie
pliku core przez proces można znaleźć w
signal(7).
Proces może ustawić miękki limit zasobów
RLIMIT_CORE,
aby ograniczyć maksymalny rozmiar pliku, który zostanie utworzony po
otrzymaniu sygnału powodującego zrzut pamięci;
szczegółowe informacje można znaleźć w
getrlimit(2).
W następujących wypadkach plik zrzutu pamięci nie będzie
utworzony:
- *
- Proces nie ma uprawnień, aby zapisać plik zrzutu
pamięci (Domyślnie plik ten nazywa się core i jest
tworzony w bieżącym katalogu roboczym procesu. Nazwę
tę można zmienić - patrz niżej). Zapisywanie pliku
zrzutu nie powiedzie się również wtedy, gdy prawa katalogu,
w którym ten plik miałby być utworzony, nie pozwalają
na zapis do niego lub gdy plik o tej samej nazwie istnieje i nie jest
zapisywalny lub nie jest zwykłym plikiem (ale np. katalogiem lub
dowiązaniem symbolicznym).
- *
- Już istnieje (zapisywalny, zwykły) plik o tej
samej nazwie, jaka zostałaby użyta dla pliku zrzutu
pamięci, jednakże plik ten ma więcej niż jedno
dowiązanie twarde.
- *
- System plików, w którym zostałby utworzony
plik zrzutu pamięci, jest pełny, wyczerpał mu się
limit i-węzłów, jest zamontowany w trybie tylko do odczytu
albo użytkownik osiągnął kwotę systemu
plików
- *
- Nie istnieje katalog, w którym miałby być
utworzony plik zrzutu pamięci.
- *
- Limity zasobów RLIMIT_CORE (rozmiar pliku
zrzutu pamięci) lub RLIMIT_FSIZE (rozmiar pliku) dla procesu
są ustawione na zero; patrz getrlimit(2) i dokumentacja
wbudowanego w powłokę polecenia ulimit (lub limit
w powłoce csh(1)).
- *
- Nie są ustawione uprawnienia do odczytu pliku
binarnego uruchomionego przez proces.
- *
- Proces uruchomił program z flagą set-user-ID
(set-group-ID), którego właścicielem jest użytkownik
(grupa) inny niż rzeczywisty użytkownik (grupa) procesu.
(Jednakże patrz w prctl(2) opis operacji
PR_SET_DUMPABLE oraz w proc(5) opis pliku
/proc/sys/fs/suid_dumpable).
Nazwy plików zrzutu pamięci¶
Domyślnie plik zrzutu pamięci nazywa się
core,
jednakże w pliku
/proc/sys/kernel/core_pattern (od wersji 2.6 i
2.4.21 Linuksa) można zdefiniować szablon, który będzie
użyty do nazywania plików zrzutu pamięci. Szablon ten może
zawierać specjalne znaczniki zaczynające się od "%",
które podczas tworzenia pliku zrzutu będą zastąpione
następującymi wartościami:
- %%
- pojedynczy znak %
- %p
- Identyfikator (PID) procesu, który zrzucił
pamięć
- %u
- (numeryczny) identyfikator użytkownika (UID) procesu,
który zrzucił pamięć
- %g
- (numeryczny) identyfikator grupy (GID) procesu, który
zrzucił pamięć
- %s
- numer sygnału powodującego zrzut
pamięci
- %t
- czas zrzutu wyrażony w sekundach od początku
epoki, czyli od 1970-01-01 00:00:00 +0000 (UTC)
- %h
- nazwa komputera (taka sama jak nodename zwracane
przez uname(2))
- %e
- nazwa pliku wykonywalnego (niepoprzedzona pełną
ścieżką do tego pliku)
- %E
- nazwa ścieżki pliku wykonywalnego, z
ukośnikami ("/") zastąpionymi przez wykrzykniki
("!")
- %c
- miękki limit zasobu rozmiaru pliku zrzutu pamięci
procesu zrzucającego pamięć (od Linuksa 2.6.24)
Jeśli szablon kończy się pojedynczym znakiem %, to znak ten
zostanie usunięty z nazwy pliku zrzutu. Podobnie zostaną
usunięte wszelkie kombinacje % ze znakami innymi niż te, wymienione
powyżej. Wszystkie inne znaki szablonu staną się
częścią nazwy pliku zrzutu. Szablon może zawierać
znaki "/", które są interpretowane jako separatory nazw
katalogów. Maksymalna długość wygenerowanej nazwy pliku
wynosi 128 bajtów (64 bajty w wersjach jądra wcześniejszych
niż 2.6.19). Domyślną wartością jest
"core". W celu zachowania wstecznej zgodności, jeśli
/proc/sys/kernel/core_pattern nie zawiera "%p", a
/proc/sys/kernel/core_uses_pid (patrz niżej) ma niezerową
wartość, to .PID będzie dołączony do nazwy pliku
zrzutu.
Od wersji 2.4 Linux dostarcza również bardziej prymitywnej metody
kontrolowania nazwy pliku zrzutu pamięci. Gdy plik
/proc/sys/kernel/core_uses_pid zawiera wartość 0, plik zrzutu
pamięci ma po prostu nazwę
core. Gdy plik ten zawiera
wartość niezerową, plik zrzutu pamięci będzie
zawierał w swojej nazwie ID procesu, w postaci
core.PID.
Przekazywanie zrzutów pamięci potokiem do programu¶
Od wersji 2.6.19 jądra Linux wspiera alternatywną składnię
pliku
/proc/sys/kernel/core_pattern. Jeśli pierwszym znakiem pliki
jest symbol potoku (
|), to wszystko, co po nim występuje, jest
interpretowane jako program do uruchomienia. Zamiast zostać zapisanym na
dysku, zrzut pamięci jest przekazywany na standardowe wejście
programu. Proszę zauważyć, że:
- *
- Program musi być podany używając
ścieżki bezwzględnej (lub ścieżki względnej
w stosunku do korzenia systemu plików, czyli katalogu /) i
musi występować bezpośrednio po znaku "|".
- *
- Proces tworzony do wykonania programu jest wykonywany jako
użytkownik i grupa root.
- *
- Można przekazać do programu argumenty linii
poleceń (od jądra 2.6.24), rozdzielając je spacjami
(aż do wyczerpania limitu całkowitej długości linii
wynoszącego 128 bajtów).
- *
- Argumenty linii poleceń mogą zawierać
dowolne z wymienionych powyżej specyfikatorów %. Na
przykład, aby przekazać identyfikator procesu zrzucającego
pamięć, należy podać %p jako argument.
Kontrolowanie mapowań zapisywanych do pliku zrzutu
pamięci¶
Od wersji 2.6.23 jądra można użyć specyficznego dla Linuksa
pliku
/proc/PID/coredump_filter do kontrolowania, które segmenty
pamięci zostaną zapisane do pliku zrzutu pamięci, w przypadku
gdy pamięć jest zrzucana przez proces o podanym identyfikatorze.
Wartość w tym pliku jest maską bitową typów
mapowań pamięci (patrz
mmap(2)). Jeśli bit jest
ustawiony w masce, to odpowiadające mu mapowanie jest zapisywane w pliku,
w przeciwnym wypadku - nie jest. Bity w masce mają następujące
znaczenia:
- bit 0
- Zrzucanie anonimowych mapowań prywatnych.
- bit 1
- Zrzucanie anonimowych mapowań
współdzielonych.
- bit 2
- Zrzucanie prywatnych mapowań plików.
- bit 3
- Zrzucanie współdzielonych mapowań
plików.
- bit 4 (od Linuksa 2.6.24)
- Zrzucanie nagłówków ELF.
- bit 5 (od Linuksa 2.6.28)
- Zrzucanie prywatnych dużych stron.
- bit 6 (od Linuksa 2.6.28)
- Zrzucanie współdzielonych dużych stron.
Domyślnie ustawione są następujące bity: 0, 1, 4 (jeśli
jest włączona opcja
CONFIG_CORE_DUMP_DEFAULT_ELF_HEADERS
konfiguracji jądra) oraz 5. Wartość pliku jest wyświetlana
jako liczba szesnastkowa (dlatego domyślna wartość jest
wyświetlana jako 33).
Strony wejścia/wyjścia mapowane w pamięci, takie jak frame
buffer, nigdy nie są zrzucane, a wirtualne strony DSO są zawsze
zrzucane, niezależnie od wartości
coredump_filter.
Proces-dziecko utworzony przez
fork(2) dziedziczy wartość
coredump_filter od swojego rodzica; wartość ta jest
także zachowywana podczas
execve(2).
Może być użyteczne ustawienie
coredump_filter w
powłoce przed uruchomieniem programu, na przykład:
$ echo 0x7 > /proc/self/coredump_filter
$ ./some_program
Plik istnieje, jeśli jądro zostało zbudowane z
włączoną opcją konfiguracji
CONFIG_ELF_CORE.
UWAGI¶
Aby uzyskać zrzut pamięci działającego procesu, można
użyć polecenia
gcore programu
gdb(1).
Jeżeli pamięć zrzuca proces wielowątkowy (albo - bardziej
precyzyjnie - proces, który dzieli swą pamięć z innym
procesem utworzonym z flagą
CLONE_VM funkcji
clone(2)), to
identyfikator procesu zawsze będzie dołączony do nazwy pliku
zrzutu, chyba że ów identyfikator procesu już występuje w
nazwie pliku, ponieważ w pliku
/proc/sys/kernel/core_pattern
użyto specyfikatora "%p" (Jest to szczególnie
użyteczne podczas stosowania implementacji LinuxThreads, w której
każdy wątek procesu ma inny PID).
PRZYKŁAD¶
Poniższy program pokazuje użycie składni potoku w pliku
/proc/sys/kernel/core_pattern. Poniższa sesja powłoki
demonstruje użycie tego programu (skompilowanego do pliku o nazwie
core_pattern_pipe_test):
$ cc -o core_pattern_pipe_test core_pattern_pipe_test.c
$ su
Password:
# echo "|$PWD/core_pattern_pipe_test %p UID=%u GID=%g sig=%s" > \
/proc/sys/kernel/core_pattern
# exit
$ sleep 100
^\ # wpisz control+odwrotny ukośnik
Quit (core dumped)
$ cat core.info
argc=5
argc[0]=</home/mtk/core_pattern_pipe_test>
argc[1]=<20575>
argc[2]=<UID=1000>
argc[3]=<GID=100>
argc[4]=<sig=3>
Całkowita liczba bajtów pliku core: 282624
Żródło programu¶
/* core_pattern_pipe_test.c */
#define _GNU_SOURCE
#include <sys/stat.h>
#include <fcntl.h>
#include <limits.h>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#define BUF_SIZE 1024
int
main(int argc, char *argv[])
{
int tot, j;
ssize_t nread;
char buf[BUF_SIZE];
FILE *fp;
char cwd[PATH_MAX];
/* Zmienia bieżący katalog roboczy na katalog procesu,
który generuje zrzut pamięci */
snprintf(cwd, PATH_MAX, "/proc/%s/cwd", argv[1]);
chdir(cwd);
/* Zapisuje wyjście do pliku "core.info" w tym katalogu */
fp = fopen("core.info", "w+");
if (fp == NULL)
exit(EXIT_FAILURE);
/* Wyświetla argumenty linii poleceń przekazane do programu
filtrującego "core_pattern" */
fprintf(fp, "argc=%d\n", argc);
for (j = 0; j < argc; j++)
fprintf(fp, "argc[%d]=<%s>\n", j, argv[j]);
/* Zlicza bajty na standardowym wejściu (daje rozmiar
zrzutu pamięci) */
tot = 0;
while ((nread = read(STDIN_FILENO, buf, BUF_SIZE)) > 0)
tot += nread;
fprintf(fp, "Całkowita liczba bajtów pliku core: %d\n", tot);
exit(EXIT_SUCCESS);
}
ZOBACZ TAKŻE¶
bash(1),
gdb(1),
getrlimit(2),
mmap(2),
prctl(2),
sigaction(2),
elf(5),
proc(5),
pthreads(7),
signal(7)
O STRONIE¶
Angielska wersja tej strony pochodzi z wydania 3.40 projektu Linux
man-pages. Opis projektu oraz informacje dotyczące zgłaszania
błędów można znaleźć pod adresem
http://www.kernel.org/doc/man-pages/.
TŁUMACZENIE¶
Autorem polskiego tłumaczenia niniejszej strony podręcznika man jest
Robert Luberda <robert@debian.org>.
Polskie tłumaczenie jest częścią projektu manpages-pl;
uwagi, pomoc, zgłaszanie błędów na stronie
http://sourceforge.net/projects/manpages-pl/. Jest zgodne z wersją
3.40 oryginału.