Per quale processo è `/ proc / self /`?


40

https://www.centos.org/docs/5/html/5.2/Deployment_Guide/s3-proc-self.html afferma

La /proc/self/directory è un collegamento al processo attualmente in esecuzione.

Esistono sempre più processi in esecuzione contemporaneamente, quindi quale processo è "il processo attualmente in esecuzione"?

"Il processo attualmente in esecuzione" ha qualcosa a che fare con quale processo è attualmente in esecuzione sulla CPU, considerando il cambio di contesto?

"Il processo attualmente in esecuzione" non ha nulla a che fare con i processi in primo piano e in background?


15
Il processo che valuta /proc/self, ovviamente.
Charles Duffy,

8
A quale persona ci riferiamo io e me ?
Jeffrey Bosboom,

Risposte:


64

Questo non ha nulla a che fare con i processi di primo piano e di sfondo; ha a che fare solo con il processo attualmente in esecuzione. Quando il kernel deve rispondere alla domanda "Cosa indica /proc/self?", Seleziona semplicemente il pid attualmente pianificato , ovvero il processo attualmente in esecuzione (sulla CPU logica corrente). L'effetto è che /proc/selfindica sempre il pid del programma richiedente; se corri

ls -l /proc/self

vedrai lsil pid, se scrivi codice che usa /proc/selfquel codice vedrà il suo pid, ecc.


13
Questo è "accurato" in un certo senso, ma non significativo per qualcuno che non capisce il concetto di "corrente" del kernel. Una risposta migliore sarebbe che è il processo che effettua la chiamata di sistema con /proc/selfcome parte del percorso in uno dei suoi argomenti.
R ..

1
@R .. questo è ciò che evidenzia la risposta di ilkkachu , sentiti libero di votare quella - l'ho fatto.
Stephen Kitt,

37

Quello che accede al symlink (chiama readlink () su di esso, o open () su un percorso attraverso di esso). Al momento sarebbe in esecuzione sulla CPU, ma non è rilevante. Un sistema multiprocessore potrebbe avere contemporaneamente più processi sulla CPU.

I processi in primo piano e in background sono principalmente un costrutto di shell, e non esiste nemmeno un processo di primo piano univoco, poiché tutte le sessioni di shell sul sistema ne avranno uno.


27

La formulazione avrebbe potuto essere migliore, ma anche in questo caso qualsiasi formulazione che si tenta di comporre per esprimere l'idea di auto-riferimento sarà confusa. Il nome della directory è più descrittivo secondo me.

Fondamentalmente, /proc/self/rappresenta il processo che sta leggendo /proc/self/. Quindi, se provi ad aprire /proc/self/da un programma C, allora rappresenta quel programma. Se provi a farlo dalla shell, allora è la shell ecc.

Ma cosa succede se si dispone di una CPU quad core in grado di eseguire 4 processi contemporaneamente, per davvero, non multitasking?

Quindi ogni processo vedrà un diverso /proc/self/per davvero senza essere in grado di vedere gli altri /proc/self/.

Come funziona?

Bene, /proc/self/non è davvero una cartella. È un driver di dispositivo che si presenta come una cartella se si tenta di accedervi. Questo perché implementa l'API necessaria per le cartelle. La /proc/self/directory non è l'unica cosa che fa questo. Prendi in considerazione le cartelle condivise montate da server remoti o il montaggio di chiavette USB o dropbox. Funzionano tutti implementando lo stesso set di API che li fa comportare come cartelle.

Quando un processo tenta di accedere /proc/self/al driver del dispositivo genererà il suo contenuto in modo dinamico leggendo i dati da quel processo. Quindi i file in /proc/self/non esistono davvero. È un po 'come uno specchio che si riflette sul processo che cerca di guardarlo.

È davvero un driver di dispositivo? Sembra che tu stia semplificando troppo le cose!

Sì, lo è davvero. Se vuoi essere pedante è un modulo del kernel. Ma se dai un'occhiata ai post di usenet sui vari canali degli sviluppatori Linux, la maggior parte degli sviluppatori del kernel usa "driver del dispositivo" e "modulo del kernel" in modo intercambiabile. Scrivevo driver di dispositivo, err ... moduli del kernel, per Linux. Se vuoi scrivere la tua interfaccia /proc/, ad esempio vuoi un /proc/unix.stackexchange/filesystem che restituisca post da questo sito web, puoi leggere come farlo nel venerabile libro "Linux Device Driver" pubblicato da O'Reilly. È persino disponibile come copia elettronica online.


6
/proc/selfnon è un driver di dispositivo, ma fa invece parte di un file system esposto nel kernel chiamato procfs.
Chris Down,

1
@ChrisDown: Sì, ma è implementato come un modulo del kernel - che è la versione di Linux del driver del dispositivo - c'è persino un esempio di implementazione di un /procdriver basato nel venerabile libro "Driver di dispositivo Linux". Dovrei saperlo, ne ho implementato uno al college. Probabilmente avrei potuto usare il termine "modulo kernel" invece, ma "driver del dispositivo" è ciò che la maggior parte delle persone ha familiarità e non voglio dare l'impressione fuorviante che ci sia una differenza significativa tra "modulo kernel" e "driver dispositivo" a parte la terminologia.
slebetman,

7
@slebetman bene, procfs non è un modulo in sé, può solo essere integrato, mai costruito come modulo. Se vuoi dividere i capelli, il
taglio

10

Qualunque sia il processo che accede /proc/selfo i file / cartelle in essi contenuti.

Prova cat /proc/self/cmdline. Otterrai, sorpresa sorpresa, cat /proc/self/cmdline(in realtà, invece di uno spazio, ci sarà un carattere nullo tra il te il /) perché sarà il processo del gatto ad accedere a questo pseudofilo.

Quando lo fai ls -l /proc/self, vedrai il pid del processo stesso. O che ne dici ls -l /proc/self/exe; punterà all'eseguibile ls.

Oppure prova questo, per cambiare:

$ cp /proc/self/cmdline /tmp/cmd
$ hexdump -C /tmp/cmd
00000000  63 70 00 2f 70 72 6f 63  2f 73 65 6c 66 2f 63 6d  |cp./proc/self/cm|
00000010  64 6c 69 6e 65 00 2f 74  6d 70 2f 63 6d 64 00     |dline./tmp/cmd.|
0000001f

o anche

$ hexdump -C /proc/self/cmdline 
00000000  68 65 78 64 75 6d 70 00  2d 43 00 2f 70 72 6f 63  |hexdump.-C./proc|
00000010  2f 73 65 6c 66 2f 63 6d  64 6c 69 6e 65 00        |/self/cmdline.|
0000001e

Come ho detto, è qualsiasi processo acceda /proc/selfai file o alle cartelle in essi contenuti.


2

/ proc / self è lo zucchero sintattico. È una scorciatoia per contatenare / proc / e il risultato di getpid () syscall (accessibile in bash come metavariabile $$). Può diventare confuso, tuttavia, nel caso degli script di shell, poiché molte delle dichiarazioni invocano altri processi, completi dei propri PID ... PID che si riferiscono, più spesso, a processi morti. Ritenere:

root@vps01:~# ls -l /proc/self/fd
total 0
lrwx------ 1 root root 64 Jan  1 01:51 0 -> /dev/pts/0
lrwx------ 1 root root 64 Jan  1 01:51 1 -> /dev/pts/0
lrwx------ 1 root root 64 Jan  1 01:51 2 -> /dev/pts/0
lr-x------ 1 root root 64 Jan  1 01:51 3 -> /proc/26562/fd
root@vps01:~# echo $$
593

'/ bin / ls' valuterà il percorso della directory, risolvendolo come / proc / 26563, poiché quello è il PID del processo - il processo / bin / ls appena creato - che legge il contenuto della directory. Ma quando il processo successivo nella pipeline, nel caso di script di shell, o quando ritorna il prompt, nel caso di una shell interattiva, il percorso non esiste più e l'output delle informazioni si riferisce a un processo inesistente.

Ciò si applica solo ai comandi esterni (quelli che sono file di programma eseguibili effettivi, invece di essere integrati nella shell stessa). Quindi, otterrai risultati diversi se, ad esempio, usi il globbing del nome file per ottenere un elenco dei contenuti della directory, anziché passare il nome del percorso al processo esterno / bin / ls:

root@vps01:~# ls /proc/self/fd
0  1  2  3
root@vps01:~/specs# echo /proc/self/fd/*
/proc/self/fd/0 /proc/self/fd/1 /proc/self/fd/2 /proc/self/fd/255 /proc/self/fd/3

Nella prima riga, la shell ha generato un nuovo processo, '/ bin / ls', tramite la syscall exec (), passando "/ proc / self / fd" come argv [1]. '/ bin / ls', a sua volta, apriva la directory / proc / self / fd e leggeva, quindi stampava, il suo contenuto mentre scorreva su di essi.

La seconda riga, tuttavia, usa glob () dietro le quinte per espandere l'elenco dei nomi dei file; questi vengono passati come una matrice di stringhe da eco. (Di solito implementato come comando interno, ma spesso c'è anche un binario / bin / echo ... ma quella parte è in realtà irrilevante, poiché l'eco ha a che fare solo con stringhe che non si alimenta mai a nessuna scala relativa ai nomi dei percorsi.)

Ora, considera il seguente caso:

root@vps01:~# cd /proc/self/fd
root@vps01:~# ls
0  1  2  255

Qui, la shell, il processo genitore di / bin / ls, ha reso una sottodirectory di / proc / self la sua directory corrente . Pertanto, i percorsi relativi vengono valutati dal suo punto di vista. La mia ipotesi migliore è che ciò sia correlato alla semantica dei file POSIX in cui è possibile creare più collegamenti fisici a un file, inclusi eventuali descrittori di file aperti. Quindi questa volta, / bin / ls si comporta in modo simile a echo / proc / $$ / fd / *.


-2

Quando la shell invoca programmi come ls in processi separati, / proc / self apparirà come un link simbolico a nnnnn , dove nnnnn è l'ID di processo del processo ls. Per quanto ne so, le shell comunemente usate non hanno incorporato per la lettura di collegamenti simbolici, ma Perl ha:

perl -e 'print "/ proc / self link:", readlink ("/ proc / self"), "- pid $$ \ n";'

Quindi / proc / self si comporta come un collegamento simbolico, ma il filesystem procfs lo rende "magicamente" consapevole del processo.

Utilizzando il nostro sito, riconosci di aver letto e compreso le nostre Informativa sui cookie e Informativa sulla privacy.
Licensed under cc by-sa 3.0 with attribution required.