É possível obter o nome do arquivo de um descritor de arquivo (Linux) em C?
c
linux
file
file-descriptor
adk
fonte
fonte
Respostas:
Você pode usar
readlink
em/proc/self/fd/NNN
onde NNN é o descritor de arquivo. Isso fornecerá o nome do arquivo como estava quando foi aberto - entretanto, se o arquivo foi movido ou excluído desde então, ele pode não ser mais preciso (embora o Linux possa rastrear renomeações em alguns casos). Para verificar,stat
o nome do arquivo dado efstat
o fd que você tem, e certifique-sest_dev
est_ino
são os mesmos.Obviamente, nem todos os descritores de arquivo se referem a arquivos e, para eles, você verá algumas strings de texto estranhas, como
pipe:[1538488]
. Como todos os nomes de arquivos reais serão caminhos absolutos, você pode determinar quais são facilmente. Além disso, como outros notaram, os arquivos podem ter vários links físicos apontando para eles - isso só informará aquele com o qual foi aberto. Se você quiser encontrar todos os nomes de um determinado arquivo, terá apenas que percorrer todo o sistema de arquivos.fonte
fd
seria essa referência), o número do inode não pode ser reutilizado. Qualquer software que faça uso de um número de inode depois de fechar o arquivo ou antes de abri-lo está inerentemente sujeito a condições de corrida.setuid()
truques, é possível/proc/self/fd
que seu processo não fique acessível. Veja: permalink.gmane.org/gmane.linux.kernel/1302546Tive esse problema no Mac OS X. Não temos um
/proc
sistema de arquivos virtual, então a solução aceita não funciona.Em vez disso, temos um
F_GETPATH
comando parafcntl
:Portanto, para obter o arquivo associado a um descritor de arquivo, você pode usar este snippet:
Como nunca me lembro onde
MAXPATHLEN
está definido, pensei quePATH_MAX
syslimits seria bom.fonte
getsockname
.No Windows, com GetFileInformationByHandleEx , passando FileNameInfo , você pode recuperar o nome do arquivo.
fonte
Como Tyler aponta, não há como fazer o que você precisa "direta e confiável", uma vez que um determinado FD pode corresponder a 0 nomes de arquivo (em vários casos) ou> 1 (vários "links físicos" é como a última situação é geralmente descrita ) Se você ainda precisa da funcionalidade com todas as limitações (na velocidade E na possibilidade de obter 0, 2, ... resultados em vez de 1), veja como você pode fazer isso: primeiro, fstat o FD - isso lhe diz , no resultado
struct stat
, em qual dispositivo o arquivo reside, quantos links físicos ele possui, se é um arquivo especial, etc. Isso já pode responder à sua pergunta - por exemplo, se 0 links físicos você SABER que de fato não há nenhum nome de arquivo correspondente no disco.Se as estatísticas te dão esperança, então você tem que "andar na árvore" de diretórios no dispositivo relevante até encontrar todos os links físicos (ou apenas o primeiro, se você não precisar de mais de um e qualquer um servirá ) Para esse propósito, você usa readdir (e opendir & c, é claro) abrindo subdiretórios recursivamente até encontrar em um,
struct dirent
portanto, recebeu o mesmo número de inode que você tinha no originalstruct stat
(nesse momento, se você quiser todo o caminho, em vez de apenas o nome, você precisará percorrer a cadeia de diretórios para trás para reconstruí-la).Se esta abordagem geral for aceitável, mas você precisar de um código C mais detalhado, informe-nos, não será difícil escrever (embora eu prefira não escrevê-lo se for inútil, ou seja, você não pode suportar o desempenho inevitavelmente lento ou o possibilidade de obter! = 1 resultado para os fins de sua aplicação ;-).
fonte
Antes de descartar isso como impossível, sugiro que você examine o código-fonte do comando lsof .
Pode haver restrições, mas lsof parece capaz de determinar o descritor e o nome do arquivo. Essas informações existem no sistema de arquivos / proc, portanto, deve ser possível obtê-las em seu programa.
fonte
Você pode usar fstat () para obter o inode do arquivo por struct stat. Então, usando readdir () você pode comparar o inode que você encontrou com aqueles que existem (struct dirent) em um diretório (assumindo que você conhece o diretório, caso contrário, você terá que pesquisar todo o sistema de arquivos) e encontrar o nome do arquivo correspondente. Desagradável?
fonte
Impossível. Um descritor de arquivo pode ter vários nomes no sistema de arquivos ou pode não ter nenhum nome.
Edit: Supondo que você esteja falando sobre um sistema POSIX simples e antigo, sem APIs específicas do sistema operacional, já que você não especificou um sistema operacional.
fonte