Как найти файлы формата dos в файловой системе linux

Я хотел бы узнать, какие из моих файлов в каталоге являются текстовыми файлами dos (в отличие от текстовых файлов unix).

что я пробовал:

find . -name "*.php" | xargs grep ^M -l

это не дает мне надежных результатов... поэтому я ищу лучшую альтернативу.

какие-то предложения, идеи?

спасибо

уточнение

в дополнение к тому, что я сказал выше, проблема в том, что у меня есть куча файлов dos без ^M символы в них (отсюда моя заметка о надежности).

способ, которым я в настоящее время определяю, является ли файл dos или нет, через Vim, где внизу он говорит:

"filename.php" [dos] [noeol]

6 ответов


Не уверен, что вы подразумеваете под "не надежным", но вы можете попробовать:

find . -name '*.php' -print0 | xargs -0 grep -l '^M$'

это использует более зверские-имена-с-места-в-них-фрэндли options и только находит возврат каретки непосредственно перед концом строки.

имейте в виду, что ^M один CTRLM персонажа, а не два символы.

а также что он будет перечислять файлы, где даже один строка находится в режиме DOS, что, вероятно, вы все равно хотите, так как это были бы файлы UNIX, искалеченные редактором, отличным от UNIX.


на основе вашего обновления, что vim сообщает ваши файлы в формате DOS:

если vim и сообщить об этом в формате DOS, затем каждый строка заканчивается CRLF. Так работает ВИМ. Если даже один в строке нет CR, тогда это считается форматом UNIX и ^M в буфере отображаются символы. Если это все формат DOS,^M символы не отображаются:

Vim будет искать окончания строк dos и unix, но Vim имеет встроенное предпочтение для формата unix.

- Если все строки в файле заканчиваются CRLF, будет применен формат файла dos, что означает, что каждый CRLF удаляется при чтении строк в буфер, а опция буфера " ff " будет dos.
- Если одна или несколько строк заканчиваются только с LF будет применен формат файла unix, что означает, что каждый LF удаляется (но каждый CR будет присутствовать в буфере и будет отображаться как ^M), а опция буфера " ff " будет unix.

если вы действительно хотите знать, что в файле, не полагайтесь на слишком умный инструмент, такой как vim: -)

использование:

od -xcb input_file_name | less

и проверьте окончание строки самостоятельно.


Как насчет:

find . -name "*.php" | xargs file | grep "CRLF"

Я не думаю, что это надежно, чтобы попытаться использовать ^M чтобы попытаться найти файлы.


Это очень похоже на ваше оригинальное решение; поэтому, возможно, вам легче запомнить:

find . -name "*.php" | xargs grep "\r" -l

мысли:

в VIM, чтобы удалить ^M вы вводите:

 %s:/^M//g

где ^ - клавиша Ctrl, А M-клавиша ENTER. Но я никогда не мог вспомнить ключи для ввода, чтобы напечатать эту последовательность, поэтому я всегда удалял их с помощью:

 %s:/\r//g

таким образом, мой вывод заключается в том, что \r и ^M эквивалентны, с первым будучи легче запомнить типу.


Мне повезло с

find . -name "*.php" -exec grep -Pl "\r" {} \;

GNU find

find . -type f -iname "*.php"  -exec file "{}" + | grep CRLF

Я не знаю, что вы хотите сделать после того, как найдете эти файлы DOS php, но если вы хотите преобразовать их в формат unix, то

find . -type f -iname "*.php"  -exec dos2unix "{}" +;

хватит. Нет необходимости специально проверять, являются ли они файлами DOS или нет.


Если вы предпочитаете vim, чтобы сообщить вам, какие файлы находятся в этом формате, вы можете использовать следующий скрипт:

"use this script to check which files are in dos format according to vim
"use: in the folder that you want to check
"create a file, say res.txt
"> vim -u NONE --noplugins res.txt
"> in vim: source this_script.vim

python << EOF
import os
import vim

cur_buf =  vim.current.buffer

IGNORE_START = ''.split()
IGNORE_END = '.pyc .swp .png ~'.split()

IGNORE_DIRS = '.hg .git dd_ .bzr'.split()

for dirpath, dirnames, fnames in os.walk(os.curdir):
  for dirn in dirnames:
    for diri in IGNORE_DIRS:
      if dirn.endswith(diri):
        dirnames.remove(dirn)
        break
  for fname in fnames:
    skip = False
    for fstart in IGNORE_START:
      if fname.startswith(fstart):
        skip = True
    for fend in IGNORE_END:
      if fname.endswith(fend):
        skip = True
    if skip is True:
      continue
    fname = os.path.join(dirpath, fname)
    vim.command('view {}'.format(fname))
    curr_ff = vim.eval('&ff')
    if vim.current.buffer != cur_buf:
      vim.command('bw!')
    if curr_ff == 'dos':
      cur_buf.append('{} {}'.format(curr_ff, fname))
EOF

ваш vim должен быть скомпилирован с python (python используется для цикла над файлами в папке, вероятно, есть более простой способ сделать это, но я действительно не знаю этого....