2010-10-21 12 views
7

Tengo el siguiente código . Solo una parte se muestra aquí y estoy comprobando si es del tipo de archivo.¿Cómo saber si un archivo es un enlace?

struct stat *buf /* just to show the type buf is*/ 

switch (buf.st_mode & S_IFMT) { 
    case S_IFBLK: printf(" block device\n");   break; 
    case S_IFCHR: printf(" character device\n");  break; 
    case S_IFDIR: printf(" directory\n");    break; 
    case S_IFIFO: printf(" FIFO/pipe\n");    break; 
    case S_IFLNK: printf(" symlink\n");     break; 
    case S_IFREG: printf(" regular file\n");   break; 
    case S_IFSOCK: printf(" socket\n");     break; 
    default:  printf(" unknown?\n");    break; 
} 

El problema: valor de st_mode obtenido cuando hago un printf("\nMode: %d\n",buf.st_mode); el resultado es 33188.

Probé mi programa con un tipo de archivo normal y un enlace simbólico. En ambos casos, la salida fue "archivo regular", es decir, el caso del enlace simbólico está fallando y no entiendo por qué?

+0

La pregunta es un poco confusa. ¿Estás probando un enlace simbólico y el programa dice que es un archivo común? ¿Cuál es el valor de buf.st_mode? –

+0

@Gintautas: editado. –

+4

Necesita 'lstat()'. 'stat()' sigue a los enlaces simbólicos y verifica los archivos a los que apuntan. –

Respuesta

14

Desde la página stat (2) hombre:

stat() Estadísticas del archivo apuntada por camino y rellena buf.

lstat() es idéntico a stat(), excepto que si la ruta es un enlace simbólico, entonces el enlace en sí mismo es stat-ed, no el archivo al que se refiere.

En otras palabras, la llamada stat seguirán el enlace simbólico al archivo de destino y recuperar la información para que . Intente utilizar lstat en su lugar, le dará la información para el enlace .


Si hace lo siguiente:

touch junkfile 
ln -s junkfile junklink 

continuación, compilar y ejecutar el programa siguiente:

#include <stdio.h> 
#include <sys/types.h> 
#include <sys/stat.h> 
#include <unistd.h> 

int main (void) { 
    struct stat buf; 
    int x; 

    x = stat ("junklink", &buf); 
    if (S_ISLNK(buf.st_mode)) printf (" stat says link\n"); 
    if (S_ISREG(buf.st_mode)) printf (" stat says file\n"); 

    x = lstat ("junklink", &buf); 
    if (S_ISLNK(buf.st_mode)) printf ("lstat says link\n"); 
    if (S_ISREG(buf.st_mode)) printf ("lstat says file\n"); 

    return 0; 
} 

se obtiene:

stat says file 
lstat says link 

como se esperaba.

Cuestiones relacionadas