¿Cree rápidamente un archivo grande en un sistema Linux?

¿Cómo puedo crear rápidamente un archivo grande en un sistema Linux ( Red Hat Linux )? dd hará el trabajo, pero leer desde /dev/zero y escribir en el disco puede llevar mucho tiempo si necesita un archivo de varios cientos de GB para probar … Si necesita hacer eso repetidamente, el tiempo realmente sum.

No me importa el contenido del archivo, solo quiero que se cree rápidamente. ¿Cómo puede hacerse esto?

Usar un archivo disperso no funcionará para esto. Necesito que se le asigne espacio al disco.

    dd es una buena solución, pero es lenta para este propósito. En Linux, tenemos fallocate .

    Por ejemplo:

     fallocate -l 10G gentoo_root.img 

    Esta es una pregunta común, especialmente en el entorno actual de entornos virtuales. Lamentablemente, la respuesta no es tan directa como uno podría suponer.

    dd es la primera opción obvia, pero dd es esencialmente una copia y eso te obliga a escribir cada bloque de datos (por lo tanto, inicializando el contenido del archivo) … Y esa inicialización es lo que ocupa tanto tiempo de E / S. (¿Quiere hacer que tome más tiempo? Utilice / dev / random en lugar de / dev / zero ! Luego usará CPU así como tiempo de E / S!) Al final, dd es una opción pobre (aunque esencialmente el valor predeterminado utilizado por la VM “crear” GUIs). P.ej:

     dd if=/dev/zero of=./gentoo_root.img bs=4k iflag=fullblock,count_bytes count=10G 

    truncar es otra opción, y probablemente sea la más rápida … Pero eso se debe a que crea un “archivo disperso”. Esencialmente, un archivo disperso es una sección de disco que tiene muchos de los mismos datos, y el sistema de archivos subyacente “engaña” al no almacenar realmente todos los datos, sino simplemente “pretender” que todo está allí. Por lo tanto, cuando utiliza truncar para crear una unidad de 20 GB para su máquina virtual, el sistema de archivos no asigna 20 GB, pero hace trampa y dice que hay 20 GB de ceros, aunque solo una pista en el disco puede realmente (realmente) estar en uso. P.ej:

      truncate -s 10G gentoo_root.img 

    fallocate es la elección final, y la mejor , para su uso con la asignación de disco VM, porque esencialmente “reserva” (o “asigna” todo el espacio que está buscando, pero no se molesta en escribir nada. Cuando utiliza fallocate para crear un espacio de disco virtual de 20 GB, realmente obtiene un archivo de 20 GB (no un “archivo disperso”, y no se habrá tomado la molestia de escribirle nada, lo que significa que prácticamente cualquier cosa podría estar en allí – ¡algo así como un disco nuevo!) Por ejemplo:

     fallocate -l 10G gentoo_root.img 

    Linux y todos los sistemas de archivos

    xfs_mkfile 10240m 10Gigfile

    Linux y algunos sistemas de archivos (ext4, xfs, btrfs y ocfs2)

    fallocate -l 10G 10Gigfile

    OS X, Solaris, SunOS y probablemente otros UNIXes

    mkfile 10240m 10Gigfile

    HP-UX

    prealloc 10Gigfile 10737418240

    Explicación

    Pruebe mkfile myfile como una alternativa de dd . Con la opción -n , se observa el tamaño, pero los bloques de disco no se asignan hasta que se escriben datos en ellos. Sin la opción -n , el espacio está lleno de cero, lo que significa escribir en el disco, lo que significa tomarse el tiempo.

    mkfile se deriva de SunOS y no está disponible en todas partes. La mayoría de los sistemas Linux tienen xfs_mkfile que funciona exactamente de la misma manera, y no solo en los sistemas de archivos XFS a pesar del nombre. Está incluido en xfsprogs (para Debian / Ubuntu) o paquetes con nombres similares.

    La mayoría de los sistemas Linux también tienen fallocate , que solo funciona en ciertos sistemas de archivos (como btrfs, ext4, ocfs2 y xfs), pero es el más rápido, ya que asigna todo el espacio de archivos (crea archivos no holey) pero no inicializa cualquiera de eso.

     truncate -s 10M output.file 

    creará un archivo de 10 M de forma instantánea (M representa 1024 * 1024 bytes, MB representa 1000 * 1000 – lo mismo con K, KB, G, GB …)

    EDITAR: como muchos han señalado, esto no asignará físicamente el archivo en su dispositivo. Con esto, puedes crear un archivo grande arbitrario, independientemente del espacio disponible en el dispositivo

    Por lo tanto, al hacer esto, se pospondrá la asignación física hasta que se acceda al archivo. Si mapea este archivo en la memoria, es posible que no tenga el rendimiento esperado.

    Pero esto sigue siendo un comando útil para saber

    Donde buscar es el tamaño del archivo que desea en bytes – 1.

     dd if=/dev/zero of=filename bs=1 count=1 seek=1048575 

    Ejemplos donde seek es el tamaño del archivo que desea en bytes

     #kilobytes dd if=/dev/zero of=filename bs=1 count=0 seek=200K #megabytes dd if=/dev/zero of=filename bs=1 count=0 seek=200M #gigabytes dd if=/dev/zero of=filename bs=1 count=0 seek=200G #terabytes dd if=/dev/zero of=filename bs=1 count=0 seek=200T 

    De la página de dd:

    BLOCKS y BYTES pueden ir seguidos de los siguientes sufijos multiplicativos: c = 1, w = 2, b = 512, kB = 1000, K = 1024, MB = 1000 * 1000, M = 1024 * 1024, GB = 1000 * 1000 * 1000, G = 1024 * 1024 * 1024, y así sucesivamente para T, P, E, Z, Y.

    No sé mucho sobre Linux, pero aquí está el código C que escribí para falsificar enormes archivos en DC Share hace muchos años.

     #include < stdio.h > #include < stdlib.h > int main() { int i; FILE *fp; fp=fopen("bigfakefile.txt","w"); for(i=0;i< (1024*1024);i++) { fseek(fp,(1024*1024),SEEK_CUR); fprintf(fp,"C"); } } 

    para hacer un archivo 1G:

     dd if=/dev/zero of=filename bs=1G count=1 

    Puede usar el comando “yes” también. La syntax es bastante simple:

     #yes >> myfile 

    Presione “Ctrl + C” para detener esto, de lo contrario se comerá todo su espacio disponible.

    Para limpiar este archivo, ejecuta:

     #>myfile 

    limpiará este archivo.

    No creo que vayas a obtener mucho más rápido que dd. El cuello de botella es el disco; Escribir cientos de GB de datos va a llevar mucho tiempo, sin importar cómo lo hagas.

    Pero esta es una posibilidad que podría funcionar para su aplicación. Si no le importan los contenidos del archivo, ¿qué le parece crear un archivo “virtual” cuyos contenidos son el resultado dynamic de un progtwig? En lugar de abrir () el archivo, use popen () para abrir un conducto a un progtwig externo. El progtwig externo genera datos cada vez que es necesario. Una vez que la tubería está abierta, actúa como un archivo normal en el que el progtwig que abrió la tubería puede fseek (), rebobinar (), etc. Tendrás que usar pclose () en lugar de close () cuando estés hecho con la tubería.

    Si su aplicación necesita que el archivo tenga un determinado tamaño, le corresponderá al progtwig externo realizar un seguimiento de dónde se encuentra en el “archivo” y enviar un eof cuando se haya alcanzado el “final”.

    Un enfoque: si puede garantizar que las aplicaciones no relacionadas no utilizarán los archivos de manera conflictiva, simplemente cree un conjunto de archivos de diferentes tamaños en un directorio específico y luego cree enlaces a ellos cuando sea necesario.

    Por ejemplo, tiene un grupo de archivos llamado:

    • / home / bigfiles / 512M-A
    • / home / bigfiles / 512M-B
    • / home / bigfiles / 1024M-A
    • / home / bigfiles / 1024M-B

    Luego, si tiene una aplicación que necesita un archivo 1G llamado / home / oracle / logfile, ejecute un ” ln /home/bigfiles/1024M-A /home/oracle/logfile “.

    Si está en un sistema de archivos separado, tendrá que usar un enlace simbólico.

    Los archivos A / B / etc se pueden usar para garantizar que no haya un uso conflictivo entre aplicaciones no relacionadas.

    La operación de enlace es lo más rápida que puedes obtener.

    El GPL mkfile es solo un contenedor de script (ba) sh alrededor de dd; El archivo mk de BSD simplemente configura un buffer con un valor distinto de cero y lo escribe repetidamente. No esperaría que el primero supere a dd. Esto último podría limitar dd if = / dev / zero ligeramente, ya que omite las lecturas, pero cualquier cosa que lo haga significativamente mejor probablemente solo esté creando un archivo disperso.

    En ausencia de una llamada al sistema que realmente asigna espacio para un archivo sin escribir datos (y Linux y BSD carecen de esto, probablemente Solaris también), puede obtener una pequeña mejora en el rendimiento al usar ftrunc (2) / truncar (1) para extender el archivo al tamaño deseado, mmap el archivo en la memoria, luego escriba datos distintos de cero en los primeros bytes de cada bloque de disco (use fgetconf para encontrar el tamaño del bloque del disco).

    Este es el más rápido que pude hacer (que no es rápido) con las siguientes limitaciones:

    • El objective del archivo grande es llenar un disco, por lo que no puede ser comprimible.
    • Usando el sistema de archivos ext3. (fallocate no disponible)

    Esta es la esencia de esto … `

     // include stdlib.h, stdio.h, and stdint.h int32_t buf[256]; // Block size. for (int i = 0; i < 256; ++i) { buf[i] = rand(); // random to be non-compressible. } FILE* file = fopen("/file/on/your/system", "wb"); int blocksToWrite = 1024 * 1024; // 1 GB for (int i = 0; i < blocksToWrite; ++i) { fwrite(buf, sizeof(int32_t), 256, file); } 

    `

    En nuestro caso, esto es para un sistema embebido de Linux y esto funciona bastante bien, pero preferiría algo más rápido.

    FYI el comando "dd if = / dev / urandom of = outputfile bs = 1024 count = XX" fue tan lento que no se pudo usar.

    Plug desvergonzado: OTFFS proporciona un sistema de archivos que proporciona archivos arbitrariamente grandes (bueno, casi. Exabytes es el límite actual) del contenido generado. Es solo Linux, C simple y en principios alfa.

    Ver https://github.com/s5k6/otffs .