error-handling awk race-condition gawk

error handling - ¿Puede awk omitir archivos que no existen, sin carreras?



error-handling race-condition (6)

¿Hay alguna manera de hacer que awk (gawk) ignore u omita archivos perdidos? Es decir, archivos pasados ​​en la línea de comandos que ya no existen en el sistema de archivos (por ejemplo, archivos que aparecen / desaparecen rápidamente en / proc / [1-9] *).

Por defecto, un archivo faltante es un error fatal :-(

Me gustaría poder hacer el equivalente a algo como esto:

BEGIN { MISSING_FILES_ARE_FATAL = 0 } # <- Wishful thinking! { count++ } END { print count }

Un script de envoltura no puede verificar que los archivos existan antes de que se ejecute awk, ya que pueden desaparecer entre el momento en que se comprueban y awk y luego intenta abrirlos, es decir, es una condición de carrera. (También es una condición de carrera verificar-y-luego-abrir dentro de awk, aunque el tiempo es más estricto)


Bueno, puede consultar con el sistema de llamada en los contenidos de ARGV , luego procesarlos a través de getline .

if (system("test -r " ARGV[1]) == 0) while ( (getline aline < ARGV[1]) >0 ) # process ARGV[1] via `aline` instead of $0

...

Luego procese ARGV [2], etc. HTH


En la mejor de las tradiciones, responderé a su pregunta con un programa Perl.

#!/usr/bin/perl -w for my $file (@ARGV) { open my $fh, $file or next; while(<$fh>) { ...do your thing here... } }

(No es extraño, pero es la única solución sin una condición de carrera).


Incluso pegando un perl o shell wrapper alrededor de su script awk, creo que todavía habrá una condición de carrera. Por ejemplo, usando el fragmento de shell de ADEpt por lo demás fino:

[ -r "$filename" ] && awk -f ... $filename

no hay nada que impida que el proceso se salga entre el -r y el tiempo en que awk intenta abrir el archivo ...

La única respuesta que se me ocurre es usar LD_PRELOAD para reemplazar la llamada abierta del sistema por awk, de modo que si falta el archivo, se abre un descriptor de archivo de lectura en / dev / null.

Aquello podría funcionar...


Oh, lo siento. Ignora mi respuesta anterior. Aquí hay otra sugerencia:

cat /proc/[1-9]* 2>/dev/null | awk ....

Cat se tragará todos los archivos, faltan y existen por igual, el error de gato se abandonará al olvido (el archivo faltante es un error no fatal para cat), y el awk podrá procesar el resultado.


Me parece que una característica "MISSING_FILES_ARE_FATAL = 0" será parte de la próxima versión de gawk. Vea el archivo ChangeLog del actual código fuente estable de gawk:

--- snip ---

Vie 22 Ago 14:43:49 2008 Arnold D. Robbins

* io.c (nextfile): Users Strong In The Ways Of The Source can use non-existant files on the command line without it being a fatal error.

--- snip ---

http://cvs.savannah.gnu.org/viewvc/gawk-stable/ChangeLog?revision=1.87&root=gawk&view=markup

Hermann


GAWK 4 tiene BEGINFILE en el que puede probar ERRNO y hacer un siguiente nextfile si ERRNO no está vacío (lo que indica que el archivo no se pudo abrir).