
Estoy trabajando con un sistema de compilación que se basa en rutas absolutas para hacer referencia a archivos fuente, etc. Cuando quiero probar la compilación con diferentes cadenas de herramientas, monto el directorio src en VM o chroots. El problema es que la ruta a mi directorio src en mi máquina host es muy compleja (digamos /a/b/c/d/src) y tiene que coincidir con la ruta montada.
Quiero poder montar mi directorio src en algún lugar como /mnt/src, pero siempre termino necesitando crear un enlace simbólico /a/b/c/d/src a /mnt/src, o simplemente tener el punto de montaje en /a/b/c/d/src directamente.
Se siente sucio tener /a/b/c/d en el sistema de archivos y, en general, es posible que ni siquiera tenga permisos para crear archivos en /a/b/c/d (o en cualquiera de los directorios principales). ¿Hay alguna forma de falsificar este camino para apaciguar mi sistema de compilación?
Respuesta1
La mejor solución sería enseñarle a ese sistema de compilación que las rutas de origen y las rutas de instalación no son lo mismo, pero asumiré que no se puede hacer eso.
El método más sencillo sería hacer que la ruta de origen sea algo que pueda reproducirse fácilmente, como por ejemplo /var/tmp/mybuild
. Si el sistema de compilación no es demasiado desagradable, debería ser suficiente hacer de este un enlace simbólico hacia donde se encuentran los archivos. Si el sistema de compilación insiste en canonicalizar enlaces simbólicos, deberías poder engañarlo usando unenlazar montajeen cambio. Con bindfs, no necesita privilegios de root, solo necesita tener permiso de escritura en la ubicación donde desea que aparezcan los archivos.
Si no puede actuar sobre el sistema fuente, un enfoque alternativo esprecargar una biblioteca dinámica que redirige ciertos accesos a archivos. Esto supone que todos los ejecutables que se ejecutarán están vinculados dinámicamente. El código del ejemplo vinculado muestra cómo hacerlo desde un archivo específico; se puede modificar para redirigir todos los archivos cuya ruta comienza con un prefijo determinado. Reemplazar
if (!strcmp(path, FROM)) {
path = TO;
}
…
return ret;
por algo como (no probado)
char *other_path = NULL;
if (!strncmp(path, FROM, strlen(FROM))) {
other_path = malloc(strlen(path) - strlen(FROM) + strlen(TO) + 1);
if (other_path == NULL) return -ENOENT; // return NULL in fopen
memcpy(other_path, TO, strlen(TO));
memcpy(other_path + strlen(TO), path + strlen(FROM), strlen(path) - strlen(FROM) + 1);
path = other_path;
}
…
free(other_path);
return ret;
Respuesta2
Si su objetivo es evitar contaminar "el host" con residuos de compilaciones de prueba, entonces construir dentro de una firejail
superposición persistente debería ser una buena opción. Con ese enfoque, construiría, y tal vez instalaría, como si fuera real, pero los archivos terminan en una superposición en lugar de contaminar el sistema de archivos "real".
Existe el inconveniente de que necesitará ubicar los resultados de la compilación de pruebas dentro de la superposición, pero al mismo tiempo esto tiene la posible ventaja de preservar los resultados de la compilación de pruebas sucesivas, por ejemplo, para compararlos o cualquier otro análisis forense posterior que pueda necesitar. hacer.