Sortie de gfast-copy et de fast-copy sur www.open-source-projects.net

11
28
oct.
2017
C et C++

Icône de gfast-copy

Copier un unique (gros) fichier d’une source vers une destination donnée n’est pas une tâche pour laquelle les systèmes sont toujours optimisés.

Selon la philosophie UNIX, un programme doit accomplir une unique tâche précise et l’accomplir du mieux possible. C’est ce qui a donné naissance à gfast-copy et à fast-copy. Ces programmes font une chose banale mais le font bien.

J’ai développé ces deux programmes car je copie souvent de gros fichiers (vidéos, images ISO, grosses archives, etc.) de « droite à gauche » et de « gauche à droite ». Et je trouvais que les systèmes d’exploitation copiaient trop lentement, parce qu’ils faisaient parallèlement autre chose, alors j’ai décidé de déléguer cette tâche à un binaire.

J’ai lu dans les manuels GNU qu’un programme qui dispose d’une interface graphique doit pouvoir accomplir la même tâche dans un (pseudo) terminal, alors j’ai écrit deux petits programmes en langage C : gfast-copy (Graphical Fast Copy) et fast-copy (Fast Copy).

gfast-copy (Graphical Fast Copy).

gfast-copy dispose d’une interface graphique simple :
Capture d’écran de gfast-copy

Tout en haut, se trouve une barre de menu. Puis, alignés verticalement, viennent :

  • un bouton étiqueté Source avec une icône qui vous permet de choisir le fichier à copier ;
  • à côté, se trouve un bouton interrupteur affichant une simple icône permettant d’effacer le fichier source ou pas après la copie ;
  • un bouton étiqueté Destination avec une icône vous permettant de choisir le l’emplacement et le nom du fichier de sortie (vous pouvez écraser un fichier).
  • à côté se trouve un bouton permettant de lancer la copie ;
  • et, en bas, une barre de progression affichant la progression rapide de la copie.

fast-copy (Fast Copy)

fast-copy est un outil en ligne de commande permettant de faire la même chose que gfast-copy mais depuis un terminal et, du coup, plus rapidement.
Capture d’écran de fast-copy

Ce programme permet aussi:

  • d’écraser la destination ;
  • d’effacer le fichier source après la copie ;
  • d’utiliser les appels système au lieu des flux (comportement par défaut).
$ fast-copy -h
fast-copy - a fast chunk file copy program.

Usage : fast-copy -r input-file -w output-file [-o] [-s] [-e] [-h]
    -r Read from file (required).
    -w Write to file  (required).
    -o Overwrite destination file (optional).
    -e Erase source file (optional).
    -s Use syscalls instead of streams (optional only UNIX).
    -h Print this help message.

- Copyright (©) 2017 Brüggemann Eddie <mrcyberfighter@gmail.com> GPLv3.

Algorithme de copie.

  1. Le programme cherche d’abord la taille optimale de tampon :
    • soit en regardant si la constante BUFSIZ est définie et si elle est assez grande,
    • sinon, la taille du tampon est mise à 8192 octets,
    • si le programme utilise les appels système, il va regarder la taille optimale du tampon dans le système de fichiers ;
  2. le programme définit un tampon de la taille optimale ;
  3. le programme va copier dans une boucle très rapide la source vers la destination affichant une barre de progression ;
  4. une fois la copie effectuée avec succès le programme va mettre à jour le système de fichiers ;
  5. si vous le désirez le programme va supprimer le fichier source.

Compatibilité et portages

Les programmes ne requièrent que GTK+ en version supérieure ou égale à 3.14 (fast-copy et ne font qu’un petit usage de GLib et de Gio).

Les programmes existent pour plusieurs systèmes d’exploitation :

GNU/Linux

  • un paquetage *.deb ;
  • un paquetage *.rpm ;
  • un tarball basé sur les autotools.

Windows

  • un fichier *.exe auto‐extractible ne comprenant que gfast-copy ;
  • le tarball permet de compiler avec MSYS2 et Cygwin (les dernières versions en date d’aujourd’hui).

macOS (Sierra 10.12)

Le tarball permet de compiler les programmes et vous crée une icône dans le dossier /Applications.

Note : Vous pourrez télécharger GTK 3 grâce à brew et suivre les instructions d’installation.

Notes de l’auteur

N’utilisez ces deux programmes que pour copier de gros fichiers. Pour les autres, votre système d’exploitation s’en occupe très bien.

Si vous préférez la rapidité de votre système d’exploitation alors n’utilisez pas ces programmes.

Pourquoi ces programmes ne permettent pas de copier plusieurs fichiers à la fois
(surtout fast-copy) ?

Car il existe des outils pour cela et le récursivité des chemins de fichiers de destination n’est pas une chose facile.

Car, comme je l’ai dit, je les ai développés à des fins personnelles mais je désire les partager.

Note : J’ai sûrement péché d’avoir mis une option pour chaque chemin de fichier, mais regardez la notice, vous trouverez un exemple de « wrapper » de fast-copy très pratique.

Performances

Cela dépend de plusieurs facteurs : le système d’exploitation sur lequel est utilisé le programme, la charge de la machine et, bien sûr, la nature des sources et cibles de l’opération de copie :

  • disque dur interne vers un disque dur interne ;
  • disque dur interne vers un disque dur externe ;
  • disque dur externe vers un disque dur interne.
  • # Benchmark ?

    Posté par . Évalué à 10 (+20/-0).

    Des chiffres pour illustrer à quel point c'est plus rapide qu'une copie classique ?

    • [^] # Re: Benchmark ?

      Posté par (page perso) . Évalué à 10 (+9/-0).

      Par rapport aux commande cp ou dd (de base sous unix) …

      En général, le temps de copie est lié au temps d'accès au support (disque dur, ssd …).

  • # Simple

    Posté par . Évalué à 10 (+10/-0).

    De la gestion d'erreurs ? Du checksum ?? On peut faire pause ? :)

    Merci

  • # ultracopier

    Posté par (page perso) . Évalué à 10 (+10/-0). Dernière modification le 28/10/17 à 11:16.

    Tu connais Ultracopier? ici sur linuxfr

    T'as testé? un avis? ça apporte quoi de plus? approche différente?

  • # pipe viewer

    Posté par (page perso) . Évalué à 10 (+9/-0). Dernière modification le 28/10/17 à 11:38.

    Le programme définit un tampon de la taille optimale.
    Le programme va copier dans une boucle très rapide la source vers la destination affichant une barre de progression.

    Ça ressemble au fonctionnement de pv: https://www.ivarch.com/programs/pv.shtml

    Silmeria ~ % pv /mnt/external/bar.mp4 > bar.mp4
     387MiB 0:00:01 [ 213MiB/s] [================================>] 100%
    

    Si on ne veut pas installer pv, il y a aussi le bon vieux rsync:

    Silmeria ~ % rsync -av --info=progress2 /mnt/external/foo.mp4 .
    sending incremental file list
    foo.mp4
            419.14M 100%  136.74MB/s    0:00:02 (xfr#1, to-chk=0/1)
    
    sent 419.24M bytes  received 35 bytes  119.78M bytes/sec
    total size is 419.14M  speedup is 1.00
    

    Évidemment ne pas comparer les vitesses sur un fichier si petit, il y a aussi des histoire de cache…

  • # pas compris

    Posté par . Évalué à 10 (+22/-0). Dernière modification le 28/10/17 à 13:37.

    J'ai rapidement regardé le code source de fast-copy, et ce que je vois c'est :

    open src
    open dest
    boucle:
      read src
      write dest
      fprintf progress_bar
    fsync
    close dest
    close src
    

    Vu que tu ne fais appel qu'à des fonctions standards, et outre le fait que tu t'affranchis de toutes les vérifications de ce qui pourrait poser des problèmes comme le fait le vénérable cp, pourquoi fast-copy serait-il plus rapide ?

    Si tu ne l'as pas fait je t'invite à aller étudier le code de cp qui est bien documenté:

    https://github.com/coreutils/coreutils/blob/master/src/cp.c
    https://github.com/coreutils/coreutils/blob/master/src/copy.c

    Encore une fois, j'ai regardé ça rapidement: si je suis passé à coté de l'essentiel, merci de me corriger.

    • [^] # Re: pas compris

      Posté par . Évalué à 3 (+0/-0).

      comme le fait le vénérable cp, pourquoi fast-copy serait-il plus rapide ?

      Pour avoir déjà fait le teste, j'imagine que c'est à cause de la taille de buffers. Lire puis écrire des morceaux de 16 Mo est beaucoup plus rapide qu'avec des morceaux de 8 Ko, surtout avec un HD.

      "La première sécurité est la liberté"

      • [^] # Re: pas compris

        Posté par (page perso) . Évalué à 2 (+0/-0).

        Tu as des différences dans des cas que tu peux identifier comme étant spécifiques, ou à peu près toujours ?

        Pour ma part je n'ai pas le souvenir que cp avec un gros fichier soit plus lent que par exemple dd if=src.bin of=dest.bin bs=16M, ou alors vraiment marginalement. Je trouve que le cache fait bien son travail. Avec des disques-durs mécaniques j'ai quasi toujours un peu moins de la moitié du débit théorique. Par exemple sur une zone du disque qui fait 180 Mio/s en lecture, ce type de copie se fait grosso-modo à 80 Mio/s.
        Pas testé sur SSD.

        • [^] # Re: pas compris

          Posté par . Évalué à 3 (+0/-0).

          Mes tests remontent à loin, mais typiquement dd était bien plus rapide que cp, je crois que j'avais surtout vu cela avec un raid 0, pour saturer la bande passante, il fallait des gros buffers.

          "La première sécurité est la liberté"

  • # Perfs inferieures a cp

    Posté par . Évalué à 10 (+10/-1).

    J'ai testé avec un fichier de 9go et c'est legerement plus lent qu'un cp standard sur un ssd (avec un reboot entre les 2 tests pour ne pas biaiser les resultats avec le cache disque).

    Le code de copie est pas tres propre, tout est dans le main() qui fait dans les 700 lignes.

  • # copie efficace vers/de une machine distante

    Posté par (page perso) . Évalué à 2 (+1/-0).

    Un problème plus difficile (et plus intéressant) est celui de la copie de/vers une machine distante. rsync n'utilise qu'une seule connexion TCP, ce qui fait qu'il a souvent du mal à "remplir le réseau" si le débit disponible est important, et que la latence vers le serveur distant est importante aussi. Il y a des outils comme GridFTP qui règlent ce problème en établissant plusieurs connexions TCP, mais ils sont pénibles à déployer et n'ont pas l'interface pratique de rsync…

    Bon, peut-être que la solution transparente et magique viendra de MPTCP…

    • [^] # Re: copie efficace vers/de une machine distante

      Posté par (page perso) . Évalué à 3 (+0/-0).

      rsync n'utilise qu'une seule connexion TCP, ce qui fait qu'il a souvent du mal à "remplir le réseau" si le débit disponible est important, et que la latence vers le serveur distant est importante aussi.

      Tu peux tenter de changer l'algorithme de congestion TCP utilisé. Par exemple, passer à BBR https://www.cyberciti.biz/cloud-computing/increase-your-linux-server-internet-speed-with-tcp-bbr-congestion-control/

      Bon, peut-être que la solution transparente et magique viendra de MPTCP…

      MPTCP n'est intéressant que s'il y a plusieurs chemins. Ce qui n'est pas le cas du décris.

      « Rappelez-vous toujours que si la Gestapo avait les moyens de vous faire parler, les politiciens ont, eux, les moyens de vous faire taire. » Coluche

    • [^] # Re: copie efficace vers/de une machine distante

      Posté par . Évalué à 3 (+2/-0).

      Ce qui ralenti surtout Rsync (sur du Gbits ou supérieur), c'est le chiffrement utilisé.
      En changeant de système de chiffrement, il est accéléré considérablement. Il devient aussi rapide que "scp" (voir plus rapide).
      Attention, il faut que le chiffrement choisi soit disponible sur les 2 pc.

      Source:
      https://gist.github.com/KartikTalwar/4393116

    • [^] # Re: copie efficace vers/de une machine distante

      Posté par (page perso) . Évalué à 4 (+3/-0).

      Pour des volumétries dépassant la centaine de TB, j'utilise fpart + (gnu)parallel + rsync. C'est un combo trés efficace, et pensé dès le départ pour être déployé sur une grille de calcul.

      https://github.com/martymac/fpart

    • [^] # Re: copie efficace vers/de une machine distante

      Posté par . Évalué à 10 (+8/-0).

      En fait la stratégie d'ouvrir plusieurs connexions TCP en parallèle pour remplir le réseau n'est qu'un contournement. Le vrai problème est souvent lié à un problème de taille de fenêtre TCP qui ne monte pas assez haut.

      C'est assez trivial à comprendre. TCP est un protocole qui nécessite l’acquittement des données transmises régulièrement. La quantité de donnée qu'une extrémité peut envoyer avant d'attendre un acquittement de l'autre extrémité s'appelle la fenêtre de réception. Dés que la latence ou la bande passante augmente dans certaine proportions, il faut que la taille de cette fenêtre suive, sinon, l’émetteur passe son temps a attendre l'acquittement des données qu'il vient de transmettre.

      La formule c'est RWIN = BP * RTT.

      Imagine une liaison satellite à 10Gb/s ayant un RTT de 0.5s, il faut que cette fenêtre atteigne 5Gb soit une fenêtre de 625Mo pour que la connexion TCP remplisse le tuyau.

      C'est un exemple extrême, mais même avec des latence type WAN "contintental", disons 10 ms, il faut déjà une fenêtre de 12,5 Mo pour monter à 10Gb/s (1,25 pour 1 Gb/s, etc …)

      Il y a plein de chose qui peuvent "brider" cette fenêtre de transmission, par exemple, un certain nombre de paramètres sur les systèmes hôtes (par exemple sous linux : net.ipv4.tcp_rmem ou tcp_window_scaling). Mais pas seulement, quelque fois le problème est carrément coté applicatif qui n'alloue pas assez de mémoire dans ses buffers interne. Par exemple, il y a un patch bien connu qui existe pour openssh : https://www.psc.edu/hpn-ssh

      L'accélération matérielle TCP de certaines cartes réseau peut aussi interférer.

      A l'origine, le protocole TCP lui-même ne prévoyait qu'une fenêtre maximum de 64ko. Étendue à 1Go en utilisant le mécanisme d'extension de la fenêtre de transmission TCP (TCP window scaling, RFC 1323). Pour approfondir, on peut lire l'excellent billet de Stéphane Bortzmeyer sur la question.

      Faut pas gonfler Gérard Lambert quand il répare sa mobylette.

      • [^] # Re: copie efficace vers/de une machine distante

        Posté par (page perso) . Évalué à 2 (+0/-0).

        La relative lenteur de rsync est principalement dûe au fait qu'il est synchrone :
        1 - vérifier si tel fichier est présent, les attributs, etc
        2 - comparer les données
        3 - transférer ce qui diffère (avec chiffrement, ça peut poser problème sur connexion rapide)
        4 - revenir à l'étape 1

        Avec de nombreux petits fichiers, l'étape 1 consomme pas mal de temps.
        Si les étapes 1 et 2 étaient faites dans un processus séparé, quasi 100% du débit réseau serait utilisé (à condition d'avoir des données à transférer. Si les fichiers diffèrent peu c'est sans importance).

  • # Comparaison rsync

    Posté par . Évalué à 4 (+4/-0). Dernière modification le 29/10/17 à 17:36.

    Quels sont les avantages par rapport à rsync?
    Y'a t il une fonction de reprise en cas de plantage?
    Est ce les fichiers sont vérifiés?

  • # Note de l'auteur.

    Posté par (page perso) . Évalué à 1 (+0/-0).

    En faîtes il n'y pas de chiffre de mesures de performances, car je n'y ai pas penser:

    J'ai construit ces programmes pour palier le manque de vitesse de copie des chunk files (Surtout des films) dans l'environnement de bureau gnome ou de Windows 7.

    C.a.d le (copier ou couper) - coller

    A des fins personnels,

    mais je le mets a disposition de la communauté

    si cela intéresse quelqu'un.

    Car il faut dite que mon système Windows 7 rame quand il s'agit de copier un seule film.

    Et que je suis gagnant avec gnome grâce au wrapper décrit dans la documentation.

    Sans me préoccuper de mesures de performances.

    Vous pouvez modifier mon code comme vous le désirez grâce a ces gens qui milite pour notre liberté face aux multinationales privatives et la licence GPLv3.

    Si il se batte, alors pourquoi pas moi ?

    Merci pour vos commentaires.


    Enfin il faut dire que les performances des 2 programmes dépendent de pas mal de facteurs:

    • l'O.S

    • La charge système.

    • Le uptime

    • Selon la direction (disque externe -> disque interne et vice versa).

    • Etc…

Envoyer un commentaire

Suivre le flux des commentaires

Note : les commentaires appartiennent à ceux qui les ont postés. Nous n'en sommes pas responsables.