Estoy buscando una función de línea de comando o una función c que me permita saber si un archivo está abierto o en uso por algo.
lsof
y fuser
digo esto, pero proporcionan mucha otra información que resulta en tomar hasta 300 ms en algunas situaciones (como cuando uso este código en MAC OS X, estoy desarrollando para Linux y OS X) (tengo un sistema operativo Windows solución que tarda 5 ms, así que estoy tratando de encontrar algo en Unix que también sea muy rápido y solo devuelva verdadero o falso si el archivo está en uso)
Respuesta1
Si está utilizando esto como bloqueo, no funcionará como ninguno de los dos lsof
ni fuser
evitará las condiciones de carrera.
El proceso básico que lsof
hace es rastrear todos los procesos /proc/*/fs
en busca de descriptores de archivos abiertos. Esto llevará tiempo, hagas lo que hagas.
Puede hacerlo usted mismo, pero no es probable que sea más rápido ya que debe verificar todos los procesos abiertos en el sistema.
Si lo que está haciendo requiere tiempo crítico, busque otra forma de hacerlo.
- Si controla el archivo a través de un programa que usted escribió; Utilice un archivo de bloqueo.
- Si está ejecutando algún comando que opera en el archivo, mire y vea qué documentación ofrece ese comando/programa y vea si no puede crear un archivo de bloqueo. De lo contrario, vea si no puede crear un archivo con su PID dentro. Luego puede mirar
/proc/<PID>/fs
para ver si su archivo está actualmente abierto o no. Mirar solo un proceso de descriptores de archivos abiertos será mucho más rápido que mapearlos todos. - De lo contrario, para poder ayudarte necesitaré más información sobre lo que estás haciendo.
Dio más información en un comentario que desea determinar si Firefox se está ejecutando en un sistema determinado. La mejor manera de hacerlo es buscar los archivos de bloqueo de Firefox. Estos se almacenan enubicaciones predeterminadasespecificado en la wiki de Mozilla.
Por ejemplo, en Linux, haga que su programa haga lo siguiente:
- abre el
~/.mozilla/firefox/
directorio. - Enumere todos los directorios, filtrando los directorios que terminan en
.default
. (Creo que todos los perfiles terminan en.default
, si no, simplemente acceda a cada directorio). - En cada directorio anterior, busque la existencia de un archivo llamado
lock
o.parentlock
. Si ve uno o ambos archivos, Firefox está abierto.
Este algoritmo debería ejecutarse más rápido que lo que se hace actualmente en Windows.
Respuesta2
TL;DR
Enuno de tus comentarios, usted afirma:
Bueno, mi situación exacta es: tengo la ruta a un archivo. Está bloqueado si se está ejecutando Firefox. Quiero ver si está bloqueado o no para saber si Firefox se está ejecutando.
Su pregunta original sobre los archivos de bloqueo parece un camino más largo cuando hay formas más fáciles de saber si Firefox se está ejecutando para un usuario determinado e inspeccionar el estado de su proceso.
Estado del proceso de examen
Una forma más sensata de encontrar el PID de un proceso determinado es utilizarpgrepdesde elprocesopaquete. Por ejemplo:
$ pgrep -u $LOGNAME firefox
5671
Luego puede inspeccionar el estado del PID conPD:
$ ps 5671
PID TTY STAT TIME COMMAND
5671 ? Sl 105:47 /usr/lib/firefox/firefox
o simplemente obtener las banderas estatales sin ningún otro problema:
$ ps -ho stat $(pgrep -u $LOGNAME firefox)
Sl
En mi sistema, la frase de arriba siempre tarda solo 1,4 milisegundos en completarse. Su experiencia puede ser diferente.
Códigos de estado de proceso
La sección CÓDIGOS DE ESTADO DE PROCESO de ps(1) detalla lo que significan las distintas banderas estatales. En Ubuntu 14.04, la página de manual dice:
PROCESS STATE CODES
Here are the different values that the s, stat and state output
specifiers (header "STAT" or "S") will display to describe the state of
a process:
D uninterruptible sleep (usually IO)
R running or runnable (on run queue)
S interruptible sleep (waiting for an event to complete)
T stopped, either by a job control signal or because it is
being traced
W paging (not valid since the 2.6.xx kernel)
X dead (should never be seen)
Z defunct ("zombie") process, terminated but not reaped by
its parent
For BSD formats and when the stat keyword is used, additional
characters may be displayed:
< high-priority (not nice to other users)
N low-priority (nice to other users)
L has pages locked into memory (for real-time and custom IO)
s is a session leader
l is multi-threaded (using CLONE_THREAD, like NPTL pthreads
do)
+ is in the foreground process group