Как я могу найти только исполняемые файлы в определенной директории в Linux?

157

Как я могу найти только исполняемые файлы в определенной директории в Linux?

ХайЮань Чжан
источник
Вот что-то вроде BASH-скрипта, это неплохо, вот что я могу сказать :) stackoverflow.com/a/20209457/2067125
AjayKumarBasuthkar,
Как насчет использования стандартной fileкоманды ?
Прорыв
5
Для тех, кто хочет сделать это на Mac (протестировано на OS X 10.9.5): ls -l | egrep '^[^d]..x..x..x.*$' выше приведен список всех исполняемых файлов (для всех / пользователя и группы) в текущем каталоге. Примечание . Этот -executableпараметр не работает на Mac, поэтому возможен обходной путь, описанный выше.
techfoobar
Также актуально: Unix найти: поиск исполняемых файлов
Slothworks
1
@techfoobar: Вопрос неоднозначный: это файлы, которые содержат исполняемый код, или файлы, которые имеют разрешение на выполнение? Но даже если мы предположим, что разрешение на исполняемый файл - это то, что нужно (как кажется большинству ответов), вопрос не говорит о том, что исполняемый мир . Ваше решение найдет файлы (а также fifo, сокеты, символические ссылки и т. Д.), Которые имеют разрешение на мировое выполнение, но не 750 ( -rwxr-x---), который по-прежнему исполняем для некоторых пользователей.
G-Man

Ответы:

157

Проверка наличия исполняемых файлов может быть выполнена с -perm(не рекомендуется) или -executable(рекомендуется, так как это учитывает ACL). Чтобы использовать -executableопцию:

find <dir> -executable

если вы хотите найти только исполняемые файлы, а не каталоги с возможностью поиска, объедините их с -type f:

find <dir> -executable -type f
knittl
источник
23
Шебанг не означает, что они исполняемые. он говорит нам только, какой интерпретатор использовать. и по определению linux «исполняемые файлы» - это файлы с установленным битом исполняемого файла (x)
knittl
2
Какая версия find поддерживает этот тип для -type? Человек находит списки b, c, d, p, f, l, s и D в моей системе.
InnaM
2
То же самое здесь, моя находка тоже не имеет -type x.
Davr
7
Если у вас есть старая версия find (вероятно, до 4.3.8), в которой отсутствует -executable, используйте find. -perm / u = x, g = x, o = x.
Людвиг Вайнцерль
8
find: invalid predicate -executable'на RHEL
SSH это
33

Используйте -permопцию поиска . Это найдет файлы в текущем каталоге, которые могут быть выполнены их владельцем, членами группы или другими:

find . -perm /u=x,g=x,o=x

Редактировать:

Я просто нашел другой вариант, который присутствует по крайней мере в GNU find 4.4.0:

find . -executable

Это должно работать даже лучше, потому что списки ACL также рассматриваются.

InnaM
источник
2
Это работает только на более новой версии find. Один , который поставляется по умолчанию с CentOS дает ошибку find: invalid mode / и = х, г = х, о = x'`
Davr
12
Затем вы должны попробовать версию "-perm +", которая в GNU find устарела: find. +111 "
innaM 10.09.09
Похоже, -perm /111может быть самая портативная версия.
Скотт
12

Я знаю, что в этом вопросе конкретно упоминается Linux, но, поскольку это первый результат в Google, я просто хотел добавить ответ, который искал (например, если вы - как и я - в данный момент - вынуждены вашим работодателем использовать не GNU) Система Linux).

Протестировано на macOS 10.12.5

find . -perm +111 -type f
friederbluemle
источник
1
Работает в RHEL 5 тоже.
Хосе Томас Тосино
Это единственный вариант, на котором я мог работать на OS X 10.14, спасибо
Джастин,
3

У меня есть другой подход, в случае, если вы действительно хотите что-то сделать с исполняемыми файлами - и не обязательно фактически заставлять find фильтровать себя:

for i in `find -type f`; do [ -x $i ] && echo "$i is executable"; done

Я предпочитаю это, потому что это не зависит от -executableконкретной платформы; и он не полагается на то, -permчто является немного загадочным, немного специфичным для платформы, и, как написано выше, требует, чтобы файл был исполняемым для всех (не только для вас).

Это -type fважно, потому что каталоги * nix должны быть исполняемыми, чтобы их можно было обойти, и чем больше в команде запросов find, тем эффективнее будет ваша команда.

Во всяком случае, просто предлагая другой подход, поскольку * nix - это страна миллиардов подходов.

Марк МакКенна
источник
(0) Что вы предпочитаете, тайное и правильное или интуитивное и ошибочное? Я предпочитаю правильно. (1)  ответ InnaM в , показывая find -perm, находит файлы , которые имеют любое разрешение на выполнение бит. (2) Напротив, этот ответ находит только файлы, для которых текущий пользователь имеет разрешение на выполнение. Конечно, это может быть тем, чего хочет ОП, но неясно. … (Продолжение)
Скотт
(Продолжение)… (3) Для ясности, вы можете захотеть перейти `…`на… $(…)увидеть это , это и это . (4) Но не делай for i in $(find …); do …; это терпит неудачу на именах файлов, которые содержат пробел (ы). Вместо этого делай find … -exec …. (5) И, когда вы работаете с переменными оболочки, всегда заключайте их в кавычки (в двойных кавычках), если у вас нет веских причин не делать этого, и вы уверены, что знаете, что делаете.
Скотт
@ Scott Хорошо, я исправлен :) Я прочитал -permаргумент как требующий все три, а не один из них. Кроме того, спасибо за вклад в защиту аргументов оболочки, это все, о чем я не знал.
Марк МакКенна
@MarkMcKenna у вас есть опечатка: for i in найти. -тип f ; do [ -x $i ] && echo "$i is executable"; done; вам не хватает части <dir>, которую я использую точку (.)
Деви
2

Файл, помеченный как исполняемый, не обязательно должен быть исполняемым или загружаемым файлом или объектом.

Вот что я использую:

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
AjayKumarBasuthkar
источник
2
Что это делает?
DerMike
@DerMike, это один из способов найти исполняемый файл в текущем каталоге, включая файлы .so, даже если файл не помечен как исполняемый файл, который он может обнаружить.
AjayKumarBasuthkar
Ну, я имею в виду, как это сделать?
DerMike
Он читает из заголовка файла для обнаружения, каждый бинарный файл или файл сценария имеет заголовок.
AjayKumarBasuthkar
Насколько я знаю, -name "*"это никак не влияет find- он обычно находит все файлы, которые не были удалены тестами.
G-Man
1

Как поклонник одного лайнера ...

find /usr/bin -executable -type f -print0 | xargs file | grep ASCII

Использование 'xargs' для получения вывода команды find (использование print0 для обеспечения правильной обработки имен файлов с пробелами). Теперь у нас есть список исполняемых файлов, и мы предоставляем их один за другим в качестве параметра команды file. Затем grep для термина ASCII, чтобы игнорировать двоичные файлы. Пожалуйста, замените -executable в команде find тем, какой стиль вы предпочитаете (см. Предыдущие ответы) или что работает в вашей 'NIX OS

Я требовал, чтобы выше было найти файлы с eval в сценариях, принадлежащих root, поэтому создал следующее, чтобы помочь найти слабые места для повышения привилегий, когда пользователь root запускает сценарии с небезопасными параметрами ...

echo -n "+ Identifying script files owned by root that execute and have an eval in them..."
find /  -not \( -path /proc -prune \)  -type f -executable -user root -exec grep -l eval {} \; -exec file {} \; | grep ASCII| cut -d ':' -f1 > $outputDir"/root_owned_scripts_with_eval.out" 2>/dev/null &
Ричард Браганса
источник
Это не сработает, если скрипт содержит не-ASCII символы. fileсообщает кодировку, поэтому сценарий Python может быть сообщен как a /usr/bin/python script, UTF-8 Unicode text executable. find ... | xargs file -b | grep -v '^ELF'может работать лучше, чтобы обнаружить недвоичные файлы.
ксеноид
0

~/.bashrcСегодня вечером я создал функцию для поиска исполняемых файлов не по системному пути и не по каталогам:

# Quickly locate executables not in the path
xlocate () {
    locate -0r "$1" | xargs -0 -I{} bash -c '[[ -x "$1" ]] && [[ ! -d "$1" ]] \
        &&  echo "executable: $1"'  _  {}
} # xlocate ()

Преимущество состоит в том, что он будет искать три дистрибутива Linux и установку Windows менее чем за секунду, где findкоманда занимает 15 минут.

Например:

$ time xlocate llocate
executable: /bin/ntfsfallocate
executable: /home/rick/restore/mnt/e/bin/llocate
executable: /mnt/clone/bin/ntfsfallocate
executable: /mnt/clone/home/rick/restore/mnt/e/bin/llocate
executable: /mnt/clone/usr/bin/fallocate
executable: /mnt/e/bin/llocate
executable: /mnt/old/bin/ntfsfallocate
executable: /mnt/old/usr/bin/fallocate
executable: /usr/bin/fallocate

real    0m0.504s
user    0m0.487s
sys     0m0.018s

Или для всего каталога и всех его подпрограмм:

$ time xlocate /mnt/e/usr/local/bin/ | wc -l
65

real    0m0.741s
user    0m0.705s
sys     0m0.032s
WinEunuuchs2Unix
источник