Eu tentei marcar tarde para uma pergunta semelhante à minha em stackoverflow ( Localizar nomes de arquivo não-UTF8 no sistema de arquivos do Linux ) para obter mais respostas, sem sorte até agora, então aqui vai novamente ...
Eu tenho o mesmo problema que o OP no link acima e o convmv é uma ótima ferramenta para consertar o próprio sistema de arquivos. Minha pergunta é, portanto, acadêmica, mas acho insatisfatório (na verdade, não posso acreditar) que 'encontrar' não é capaz de encontrar caracteres ascii não padrão.
Existe alguém por aí que saiba qual combinação de opções usar para encontrar nomes de arquivos que contenham caracteres não padrão no que parece ser um FS unicode, no meu caso os caracteres parecem ser 8bits ascii em vez de unicode, o arquivos vêm de uma máquina Windows (iso-8859-1) e eu regularmente preciso buscá-los. Eu adoraria ver como find e / ou grep podem fazer o mesmo que convmv.
Arquivos de amostra:
> ls
Abc�def ÉÈéèáà-rest everest éverest
> ls -b
Abc1def ÉÈéèáà-rest everest éverest
O primeiro arquivo vem do Windows (ou simulado com touch $(printf "Abc\xA9def")
).
> find . -regex '.*[^a-zA-Z./].*'
./ÉÈéèáà-rest
> ls | egrep '[^a-zA-Z]'
ÉÈéèáà-rest
Faltando quase todos eles (o hífen salvou esse arquivo, pode ser visto com grep colorido). O que quer que esteja acontecendo aqui não é o que eu esperaria: nem encontrar nem grep é capaz de levar uma letra acentuada como estando fora do intervalo fornecido [^ a-zA-Z ./].
> find . -regex '.*é.*'
./éverest
./ÉÈéèáà-rest
> ls | egrep 'é'
ÉÈéèáà-rest
éverest
> ls | egrep '[é]'
ÉÈéèáà-rest
éverest
> find . -regex '.*[é].*'
./éverest
./ÉÈéèáà-rest
Bizarramente, ambos são capazes de captar um acento padrão quando fornecidos (inclusive no intervalo). Qualquer tentativa de encontrar ou grep com \ xA9, \ 0251 ou \ o251 falhará (sem correspondência).
> ls | fgrep e
Abc�def
ÉÈéèáà-rest
everest
éverest
A procura por um caracter não controverso mostra todos os arquivos com o grep, como eu esperava.
> find . -regex '.*e.*'
./éverest
./ÉÈéèáà-rest
./everest
> find . -name '*e*'
./éverest
./ÉÈéèáà-rest
./everest
encontrar, no entanto, é muito discriminatório: mesmo procurando um caractere normal, parece-me que elimina nomes de arquivos que contêm caracteres fora do intervalo de caracteres aceitáveis para o esquema de codificação de nomes do sistema de arquivos.
Tanto quanto eu estou preocupado se o arquivo está no sistema de arquivos, então encontrar deve encontrá-lo, certo? Mas talvez haja um recurso que eu não conheça?
Qualquer ideia seria muito apreciada.