2010-01-22 6 views
1

C'est le code que j'ai, mais le fichier est un peu plus petit et n'exécute pas:Comment copier le code binaire d'un exécutable dans un nouveau fichier sans utiliser de commande de copie système?

int WriteFileContentsToNewFile(string inFilename, string outFilename) 
{ 
    ifstream infile(inFilename.c_str(), ios::binary); 
    ofstream outfile(outFilename.c_str(), ios::binary); 

    string line; 
    // Initial read 
    infile >> line; 
    outfile << line; 
    // Read the rest 
    while(infile) 
    { 
     infile >> line; 
     outfile << line; 
    } 

    infile.close(); 
    outfile.close(); 

    return 0; 
} 

Qu'est-ce que je fais mal? Y at-il une meilleure façon de lire dans le binaire d'un fichier exécutable et immédiatement l'écrire à un autre nom? Des exemples de code?

Je dois le faire sans copie système pour simuler l'écriture sur disque.

+4

Vous utilisez des E/S formatées. Jetez un oeil à 'read' et' write' dans 'fstream'. – AraK

+0

Merci AraK, le formatage me gâchait. J'ai utilisé le code exact de http://www.cplusplus.com/reference/iostream/ostream/write/ et cela a fonctionné exactement comme je le voulais. –

Répondre

4

Une façon est d'utiliser le flux introducteur pour un streambuf:

int WriteFileContentsToNewFile(string inFilename, string outFilename) 
{ 
    ifstream infile(inFilename.c_str(), ios::binary); 
    ofstream outfile(outFilename.c_str(), ios::binary); 

    outfile << infile.rdbuf(); 
} 
+0

+1 avec un nit: Je * pense * que, pour être sûr qu'il n'y a pas d'interférence de la facette codecvt, 'std :: locale :: classic()' devrait être 'imbue()' -ed sur les flux aussi. –

+0

Ceci est un concept intéressant. Je vais essayer celui-ci un peu plus tard car il y a moins de lignes de code que celle avec laquelle j'ai fini par aller. Quelqu'un peut-il vérifier que cela fait le travail? –

+0

@ Éric Malenfant: Oui, si le reste du code changeait les paramètres régionaux globaux, ce serait probablement une bonne chose à faire. –

2

Le flux operator>>() effectue une entrée formatée même si vous ouvrez le flux en mode binaire. L'entrée formatée s'attend à voir des chaînes de caractères imprimables séparées par des espaces, mais ce n'est pas ce que contiennent les fichiers binaires comme les exécutables. Vous devez lire le fichier avec la fonction read() du flux et l'écrire avec la fonction write() du flux de sortie.

0

Du haut de ma tête: (pas de vérification d'erreur)

EDIT: Changement pour corriger bug feof.

int WriteFileContentsToNewFile(string inFilename, string outFilename) 
{ 
    FILE* in = fopen(inFilename.c_str(),"rb"); 
    FILE* out = fopen(outFilename.c_str(),"wb"); 
    char buf[4096]; //1024 is a habit of mine. 4096 is most likely your blocksize. it could also be 2<<13 instead. 
    int len; 
    while((len = fread(buf,1,1024,in)) > 0) 
    { 
    fwrite(buf,1,len,out); 
    } 
    fclose(in); 
    fclose(out); 
} 
+1

Que faire si vous avez plus de 1024 octets dans le fichier? L'exemple que j'ai utilisé vérifie la longueur du fichier dans lequel il est lu. –

+1

Cela a un bug évident. N'utilisez jamais 'feof (stream)' comme condition d'une boucle. Il est possible de le faire fonctionner correctement, mais pas facilement, et nécessite au moins une autre sortie de la boucle pour fonctionner correctement. La même chose vaut pour l'équivalent en utilisant iostreams. –

+0

@Brian T Hannan: un fichier plus long ne causera pas de problème - il essaye de répéter la boucle jusqu'à ce qu'il atteigne la fin du fichier. Travailler en morceaux de 1 Ko peut être un peu lent, mais un code comme celui-ci peut fonctionner correctement. –

0

(unix) la commande système cp copies non seulement le contenu du fichier, mais aussi des copies (certaines) des autorisations de fichiers, qui comprennent le bit d'exécution.

Assurez-vous que votre copie définit également le bit d'exécution sur le fichier de sortie selon le cas.

Questions connexes