Skip to article frontmatterSkip to article content
Site not loading correctly?

This may be due to an incorrect BASE_URL configuration. See the MyST Documentation for reference.

Regla 0x4007h: Prohibición de rutas absolutas hardcodeadas en llamadas de archivo

Archivos y E/S (0x40XX)

Universidad Nacional de Río Negro

0x4007h: Prohibición de rutas absolutas hardcodeadas en llamadas de archivo

Enunciado normativo

NO DEBE incluirse una ruta absoluta literal (por ejemplo /home/..., /tmp/... o C:\\...) en una llamada a fopen. La ruta DEBE ser relativa al directorio de ejecución o provenir de un argumento de la línea de comandos o de una variable de entorno.

La regla tampoco permite “arreglar” la ruta para tu máquina: exige que el programa no dependa de una ubicación física concreta.

¿Por qué existe esta regla?

El problema

En C, el nombre de un archivo es una cadena cuyo significado depende del sistema operativo: ISO/IEC 9899:2011 §7.21.3 lo trata como una cadena multibyte y deja la interpretación de la ruta a la implementación. Una ruta absoluta codificada en el fuente funciona solo en la máquina y la cuenta donde se escribió.

El problema es doble. Por portabilidad, el programa deja de funcionar en otra computadora, en otro sistema operativo o incluso en el mismo equipo si cambia el usuario. Por seguridad y reproducibilidad, una ruta absoluta revela la estructura del entorno y, si el archivo se abre con permisos amplios, puede sobrescribir datos ajenos al proyecto. Además, en trabajos grupales cada integrante tiene su propio directorio de inicio, de modo que el código se rompe en cuanto se comparte.

La solución idiomática es recibir la ruta como parámetro. main puede declarar int main(int argc, char *argv[]) (§5.1.2.2.1) y tomar argv[1]; las bibliotecas y funciones reciben la ruta por parámetro, como ya hacen fopen y las funciones de esta categoría.

Consecuencias de violarla

Tipo de consecuenciaEfecto concreto
No portabilidadEl programa falla en cualquier máquina distinta a la de origen.
No reproducibilidadLas pruebas dependen del estado del sistema de archivos local.
SeguridadUna ruta fija con permisos de escritura puede dañar archivos ajenos.
Trabajo en equipoLa entrega no compila ni corre en el entorno del corrector.

Fundamento en el estándar y en la cátedra

ISO/IEC 9899:2011 §7.21.3 define que los nombres de archivo son cadenas multibyte cuya validez y formato son dependientes de la implementación; §5.1.2.2.1 define los parámetros de main como el mecanismo portátil para recibir datos del entorno de ejecución. La cátedra prohíbe las rutas absolutas porque las entregas se corrigen en un entorno distinto del de desarrollo.

Alcance y excepciones

Aplica a cualquier cadena que se pase a fopen, freopen, remove o rename. No alcanza a rutas construidas dinámicamente a partir de argumentos, variables de entorno o del directorio actual, aunque en esos casos hay que validar el resultado.

Excepción razonable: un recurso de prueba dentro del repositorio puede referirse con una ruta relativa al directorio de compilación, siempre que no dependa del usuario ni del equipo.

Ejemplos exhaustivos

❌ Contraejemplo 1 — Ruta absoluta de la máquina del autor

FILE *f = fopen("/home/usuario/tp/datos.csv", "r");

Por qué falla: la ruta solo existe en la cuenta usuario de esa computadora. En el equipo del corrector no existe y fopen retorna NULL; el programa no tiene forma de abrir los datos.

❌ Contraejemplo 2 — Ruta absoluta de Windows y separador específico

FILE *f = fopen("C:\\Users\\Ana\\datos.csv", "r");

Por qué falla: además de ser absoluta, usa la convención de rutas de Windows. En Linux, C:\Users\Ana\datos.csv es un nombre de archivo relativo extraño, no una ruta válida.

✅ Ejemplo conforme 1 — Ruta relativa al directorio de trabajo

FILE *f = fopen("datos.csv", "r");
if (f == NULL) {
    perror("datos.csv");
    return -1;
}

El programa asume que el archivo está en el directorio desde el que se ejecuta, una convención independiente de la máquina. El fallo se diagnostica con la ruta efectivamente intentada.

✅ Ejemplo conforme 2 — Ruta recibida por la línea de comandos

int main(int argc, char *argv[])
{
    if (argc != 2) {
        fprintf(stderr, "uso: %s ARCHIVO\n", argv[0]);
        return 1;
    }
    FILE *f = fopen(argv[1], "r");
    if (f == NULL) {
        perror(argv[1]);
        return 1;
    }
    /* ... */
    fclose(f);
    return 0;
}

La ruta la decide quien ejecuta el programa, no el código fuente; el programa se adapta a cualquier entorno y el mensaje de error nombra el archivo real.

⚠️ Casos límite

Cómo detectarla

HerramientaComandoSeñal
gaffgaff check archivo.cRegla 0x4007h: literal de ruta absoluta en fopen/freopen.
grepgrep -n '"/' archivo.cCadenas que comienzan con / dentro de la llamada.
Revisión manualTodo fopen con cadena literal debe evaluarse como ruta relativa.

Checklist de autocontrol

Reglas relacionadas