¿Cómo puedo convertir un puntero de archivo (FILE * fp) a un descriptor de archivo (int fd)?

174

Tengo un FILE *, devuelto por una llamada a fopen(). Necesito obtener un descriptor de archivo para hacer llamadas como fsync(fd)en él. ¿Cuál es la función para obtener un descriptor de archivo desde un puntero de archivo?

Phil Miller
fuente
O podría abrir el archivo con open (2), y tendría un descriptor de archivo desde el principio
Antoine Pelisse

Respuestas:

214

La función adecuada es int fileno(FILE *stream). Se puede encontrar en <stdio.h>, y es un estándar POSIX pero no un estándar C.

Phil Miller
fuente
44
Estrictamente hablando, no sería necesario mencionar encabezados o bibliotecas si la función fuera parte de la biblioteca estándar de C. Sin embargo, no es estándar, por lo que podría tener sentido mencionar el encabezado al menos.
ANT
20
Para acceder a las funciones en la biblioteca C estándar es necesario incluir encabezados, al menos si su compilador espera prototipos (nunca recuerdo cuál es el comportamiento estándar en ese sentido). Sin encabezados, no se definen nombres al comienzo de un archivo C.
Phil Miller
1
@Novelocrat: No quise decir que no hay necesidad de #includenada. Simplemente quise decir que siempre es fácil encontrar el nombre del encabezado adecuado para una función estándar . Es decir, no es realmente crítico mencionar el nombre exacto del encabezado en la respuesta.
ANT
9
Esta es una buena respuesta, pero vale la pena señalar que esta no es una función c estándar, es una función posix.
Evan Teran
66
No está en el estándar C, porque los descriptores de archivos son una cosa UNIX (en Linux, está abierto (2), no abierto (3)).
no es un usuario
42

Incluso si fileno(FILE *)puede devolver un descriptor de archivo, tenga MUY cuidado de no omitir el búfer de stdio. Si hay datos de búfer (lectura leída o escritura no vaciada), las lecturas / escrituras del descriptor de archivo pueden proporcionarle resultados inesperados.

Para responder una de las preguntas secundarias, para convertir un descriptor de archivo en un puntero de ARCHIVO, use fdopen(3)

Mark Gerolimatos
fuente
1
No creo que esto haya sido útil para las personas que buscan esto específicamente, y esto ya ha sido respondido en la sección de comentarios de la publicación de OP un mes antes de que esto fuera escrito. Esto es más una aclaración lógica en lugar de información real.
kevr
44
Los comentarios que son tan importantes deben plantearse como respuestas. Un gran porcentaje de los comentarios son metacommentaciones sarcásticas e inútiles como la suya ... y esta;)
Mark Gerolimatos