bash - programa - hacer ejecutable archivo sh
Unix find: búsqueda de archivos ejecutables (9)
Bueno, la respuesta fácil sería: "los archivos ejecutables están en los directorios que figuran en la variable PATH", pero eso realmente no encontraría los ejecutables y podría perder muchos ejecutables de todos modos.
No sé mucho sobre mac pero creo que "mdfind ''kMDItemContentType = public.unix-executable''" podría perderse cosas como scripts interpretados
Si está bien que encuentre archivos con los bits ejecutables establecidos (independientemente de si son realmente ejecutables), entonces está bien hacerlo
find . -type f -perm +111 -print
donde se admite la opción "-executable" hará que un filtro adicional mire acl y otros artefactos de permisos, pero técnicamente no es muy diferente de "-pemr +111".
Tal vez en el futuro find sea compatible con "-magic" y te permitirá buscar de forma explícita archivos con una id. Mágica específica ... pero tendrías que especificar para corregir todos los formatos ejecutables magic id.
No conozco una salida técnicamente correcta y fácil en Unix.
¿Qué tipo de parámetro / indicador puedo usar con el comando Unix find
para buscar ejecutables?
En las versiones de GNU de find puedes usar -executable
:
find . -type f -executable -print
Para las versiones BSD de find, puede usar -perm
con +
y una máscara octal:
find . -type f -perm +111 -print
En este contexto, "+" significa "cualquiera de estos bits está establecido" y 111 es los bits de ejecución.
Tenga en cuenta que esto no es idéntico al predicado -executable
en GNU find. En particular, -executable
pruebas -executable
que el archivo puede ser ejecutado por el usuario actual, mientras que -perm +111
solo prueba si se han establecido permisos de ejecución.
Las versiones anteriores de GNU encuentran también soporte para la sintaxis -perm +111
, pero desde 4.5.12 esta sintaxis ya no es compatible. En cambio, puede usar -perm /111
para obtener este comportamiento.
Es TAN ridículo que esto no sea súper fácil ... menos aún casi imposible . Manos arriba, difiero a Apple / Spotlight ...
mdfind ''kMDItemContentType=public.unix-executable''
¡Al menos funciona!
Esto funcionó para mí y pensé en compartir ...
find ./ -type f -name "*" -not -name "*.o" -exec sh -c ''
case "$(head -n 1 "$1")" in
?ELF*) exit 0;;
MZ*) exit 0;;
#!*/ocamlrun*)exit0;;
esac
exit 1
'' sh {} /; -print
Para tener otra posibilidad 1 de encontrar los archivos que son ejecutables por el usuario actual:
find . -type f -exec test -x {} /; -print
(el comando de prueba aquí es el que se encuentra en PATH, muy probablemente /usr/bin/test
, no en el built-in).
1 ¡ Solo use esto si el -executable
de find
-executable
no está disponible! esto es sutilmente diferente de la solución -perm +111
.
Puede usar el -executable
prueba -executable
:
-executable
Matches files which are executable and directories which are
searchable (in a file name resolution sense).
Tuve el mismo problema, y la respuesta estaba en el código fuente de dmenu : la utilidad stest creada para ese fin. Puede compilar los archivos ''stest.c'' y ''arg.h'' y debería funcionar. Hay una página man para el uso, que puse allí por conveniencia:
STEST(1) General Commands Manual STEST(1)
NAME
stest - filter a list of files by properties
SYNOPSIS
stest [-abcdefghlpqrsuwx] [-n file] [-o file]
[file...]
DESCRIPTION
stest takes a list of files and filters by the
files'' properties, analogous to test(1). Files
which pass all tests are printed to stdout. If no
files are given, stest reads files from stdin.
OPTIONS
-a Test hidden files.
-b Test that files are block specials.
-c Test that files are character specials.
-d Test that files are directories.
-e Test that files exist.
-f Test that files are regular files.
-g Test that files have their set-group-ID
flag set.
-h Test that files are symbolic links.
-l Test the contents of a directory given as
an argument.
-n file
Test that files are newer than file.
-o file
Test that files are older than file.
-p Test that files are named pipes.
-q No files are printed, only the exit status
is returned.
-r Test that files are readable.
-s Test that files are not empty.
-u Test that files have their set-user-ID flag
set.
-v Invert the sense of tests, only failing
files pass.
-w Test that files are writable.
-x Test that files are executable.
EXIT STATUS
0 At least one file passed all tests.
1 No files passed all tests.
2 An error occurred.
SEE ALSO
dmenu(1), test(1)
dmenu-4.6 STEST(1)
Consejo del sombrero a gniourf_gniourf por aclarar un error fundamental.
Esta respuesta intenta proporcionar una visión general de las respuestas existentes y discutir sus sutilezas y méritos relativos , así como también proporcionar información básica , especialmente con respecto a la portabilidad .
Encontrar archivos que sean ejecutables puede referirse a dos casos de uso distintos :
- centrado en el usuario : encuentre archivos ejecutables por el usuario actual .
- centrado en archivos: busca archivos que tienen (uno o más) bits de permisos ejecutables establecidos .
Tenga en cuenta que, en cualquier caso , puede tener sentido utilizar find -L ...
lugar de simplemente find ...
para encontrar también enlaces simbólicos a ejecutables .
Tenga en cuenta que el caso más simple centrado en archivos, buscar ejecutables con el bit de permisos ejecutables establecido para TODOS los tres principales de seguridad (usuario, grupo, otro), generalmente , pero no necesariamente dará los mismos resultados que el escenario centrado en el usuario, y es importante para entender la diferencia.
-executable
usuario ( -executable
)
La respuesta aceptada recomienda recomendable:
-executable
, SI elfind
GNU está disponible.- El
find
GNU viene con la mayoría de las distribuciones de Linux- Por el contrario, las plataformas basadas en BSD, incluido macOS, vienen con BSD find, que es menos potente.
- Tal como lo exige el escenario,
-executable
coincidir solo los archivos que el usuario actual puede ejecutar (hay casos-executable
[1] ).
- El
La alternativa de
find
BSD ofrecida por la respuesta aceptada (-perm +111
) responde a una pregunta de archivo diferente y céntrica (como lo dice la respuesta misma).- Usar solo
-perm
para responder al usuario -pregunta céntrica es imposible , porque lo que se necesita es relacionar la identidad del usuario y del grupo del archivo con la del usuario actual , mientras que-perm
solo puede probar los permisos del archivo .
Al usar solo las características defind
POSIX , la pregunta no puede responderse sin la participación de utilidades externas. Por lo tanto, el mejor
-perm
puede hacer (por sí mismo) es una aproximación de-executable
. Quizás una aproximación más cercana que-perm +111
es-perm -111
, para encontrar archivos que tengan el bit ejecutable establecido para TODOS los principales de seguridad (usuario, grupo, otro) - esto me parece el típico escenario del mundo real. Como beneficio adicional, también es compatible con POSIX (usefind -L
para incluir enlaces simbólicos, ver más abajo para una explicación):find . -type f -perm -111 # or: find . -type f -perm -a=x
- Usar solo
La respuesta de gniourf_gniourf proporciona un equivalente verdadero y portátil de
-executable
, utilizando-exec test -x {} /;
, aunque a expensas del rendimiento .Combinando
-exec test -x {} /;
con-perm +111
(es decir, archivos con al menos un conjunto de bits ejecutables) puede ayudar a que el rendimiento en eseexec
no sea invocado para cada archivo (el siguiente usa el equivalente POSIX-compatible de BSD find-perm +111
/ GNU find-perm /111
; ver más abajo para una explicación):find . -type f /( -perm -u=x -o -perm -g=x -o -perm -o=x /) -exec test -x {} /; -print
Archivo-céntrico ( -perm
)
- Para responder a las preguntas centradas en archivos , es suficiente usar el primario de
-perm
compatible con-perm
(conocido como prueba en la terminología de búsqueda de GNU).-
-perm
te permite probar cualquier permiso de archivo, no solo ejecutable. - Los permisos se especifican como modos octales o simbólicos . Los modos octales son números octales (por ejemplo,
111
), mientras que los modos simbólicos son cadenas (por ejemplo,a=x
). - Los modos simbólicos identifican los principales de seguridad como
u
(usuario),g
(grupo) yo
(otro), oa
para referirse a los tres. Los permisos se expresan comox
para ejecutable, por ejemplo, y se asignan a los principales que usan operadores=
,+
y-
; para una discusión completa, incluyendo modos octales, vea la especificación POSIX para la utilidadchmod
. - En el contexto de
find
:- Prefijar un modo con
-
(por ejemplo,-ug=x
) significa: archivos de coincidencia que tienen todos los permisos especificados (pero los archivos coincidentes pueden tener permisos adicionales). - Tener prefijo NO (por ejemplo,
755
) significa: archivos de coincidencia que tienen este conjunto completo y exacto de permisos. - Advertencia : Tanto GNU find como BSD find implementan un prefijo adicional no estándar con -ANY-of-the-specified-permission-bits-set logic , pero lo hacen con sintaxis incompatible :
- BSD encuentra:
+
- GNU encontrar:
/
[2]
- BSD encuentra:
- Por lo tanto, evite estas extensiones, si su código debe ser portátil .
- Prefijar un modo con
-
- Los siguientes ejemplos demuestran respuestas portátiles a varias preguntas centradas en archivos.
Ejemplos de comandos centrados en archivos
Nota:
- Los siguientes ejemplos cumplen con POSIX , lo que significa que deben funcionar en cualquier implementación compatible con POSIX, incluidos GNU find y BSD find; específicamente, esto requiere:
- NO utiliza prefijos de modo no estándar
+
o/
. - Usando las formas POSIX de los primarios del operador lógico :
-
!
para NOT (GNU find y BSD find también permiten-not
); nota que/!
se usa en los ejemplos para proteger!
de las expansiones de la historia del proyectil -
-a
para AND (GNU find y BSD find también allow-and
) -
-o
para OR (GNU find y BSD find también allow-or
)
-
- NO utiliza prefijos de modo no estándar
- Los ejemplos usan modos simbólicos , porque son más fáciles de leer y recordar.
- Con el prefijo de modo
-
, los operadores=
y+
se pueden usar indistintamente (p. Ej.,-u=x
es equivalente a-u+x
- a menos que aplique-x
más tarde, pero no tiene sentido hacerlo). - Use
,
para unir modos parciales; Y la lógica está implícita; por ejemplo,-u=x,g=x
significa que deben establecerse tanto el usuario como el bit ejecutable del grupo. - Los modos no pueden expresar coincidencias negativas en el sentido de "coincidencia solo si este bit NO está establecido"; debes usar una expresión de
-perm
separada con el NOT primario-perm
.
- Con el prefijo de modo
- Tenga en cuenta que las primarias de búsqueda (como
-print
o-perm
, también conocidas como acciones y pruebas en GNU find) están implícitamente unidas con-a
(AND lógico), y que-o
y posiblemente paréntesis (escapado como/(
y/)
para el shell) son necesarios para implementar la lógica OR. -
find -L ...
lugar de solofind ...
se usa para hacer coincidir los enlaces simbólicos con los ejecutables-
-L
instruye a encontrar para evaluar los objetivos de los enlaces simbólicos en lugar de los enlaces simbólicos en sí mismos; por lo tanto, sin-L
,-type f
ignoraría los enlaces simbólicos por completo.
-
# Match files that have ALL executable bits set - for ALL 3 security
# principals (u (user), g (group), o (others)) and are therefore executable
# by *anyone*.
# This is the typical case, and applies to executables in _system_ locations
# (e.g., /bin) and user-installed executables in _shared_ locations
# (e.g., /usr/local/bin), for instance.
find -L . -type f -perm -a=x # -a=x is the same as -ugo=x
# The POSIX-compliant equivalent of `-perm +111` from the accepted answer:
# Match files that have ANY executable bit set.
# Note the need to group the permission tests using parentheses.
find -L . -type f /( -perm -u=x -o -perm -g=x -o -perm -o=x /)
# A somewhat contrived example to demonstrate the use of a multi-principial
# mode (comma-separated clauses) and negation:
# Match files that have _both_ the user and group executable bit set, while
# also _not_ having the other executable bit set.
find -L . -type f -perm -u=x,g=x /! -perm -o=x
[1] Descripción de -executable
de man find
como de GNU find 4.4.2:
Coincide con los archivos que son ejecutables y los directorios que se pueden buscar (en un sentido de resolución de nombre de archivo). Esto tiene en cuenta las listas de control de acceso y otros artefactos de permisos que la prueba de esperma ignora. Esta prueba hace uso de la llamada al sistema de acceso (2), por lo que los servidores NFS que hacen mapeo UID (o eliminación de raíz) pueden engañar, ya que muchos sistemas implementan el acceso (2) en el kernel del cliente y no pueden usar la información de asignación de UID que se guarda en el servidor. Debido a que esta prueba se basa únicamente en el resultado de la llamada al sistema de acceso (2), no hay garantía de que un archivo para el cual esta prueba tenga éxito pueda ejecutarse realmente.
[2] Las versiones de GNU find anteriores a la 4.5.12 también permitían el prefijo +
, pero esto se desaprobó primero y finalmente se eliminó, porque combinar +
con rendimientos de modos simbólicos probablemente produzca resultados inesperados debido a que se interpreta como una máscara de permisos exacta . Si (a) se ejecuta en una versión anterior a la 4.5.12 y (b) se restringe solo a modos octales , puede salirse con la suya usando +
con tanto GNU find como BSD find, pero no es una buena idea.
find . -executable -type f
realmente no garantiza que el archivo sea ejecutable, encontrará archivos con el bit de ejecución establecido. Si lo haces
chmod a+x image.jpg
el hallazgo anterior pensará que image.jpg es un ejecutable incluso si es realmente una imagen jpeg con el bit de ejecución establecido.
Por lo general, trabajo alrededor del problema con esto:
find . -type f -executable -exec file {} /; | grep -wE "executable|shared object|ELF|script|a/.out|ASCII text"
Si desea que el hallazgo realmente imprima información de domo sobre archivos ejecutables, puede hacer algo como esto:
find . -type f -executable -printf "%i.%D %s %m %U %G %C@ %p" 2>/dev/null |while read LINE
do
NAME=$(awk ''{print $NF}'' <<< $LINE)
file -b $NAME |grep -qEw "executable|shared object|ELF|script|a/.out|ASCII text" && echo $LINE
done
En el ejemplo anterior, la ruta de acceso completa del archivo está en el último campo y debe reflejar dónde la busca con awk "NAME = $ (awk ''{print $ NF}'' <<< $ LINE)" si el nombre del archivo estaba en otro lugar la cadena de salida de búsqueda que necesita para reemplazar "NF" con la posición numérica correcta. Si su separador no está en el espacio, también debe decirle a awk cuál es su separador.