programm kopieren



  • Hello,

    ich möchte eine Programmdatei, z.b. a.out, öffnen, jedes Zeichen auslesen und
    in eine andere Programmdatei kopieren.

    fp1=fopen("a.out","rb");
    fp2=fopen("a.out2","wb");
    
    while (c=fgetc(fp1)!=EOF) {
    fprintf(fp2,"%c", c);
    }
    

    das gibt dann nen Speicherzugriffsfehler.
    Meine Kopie des Programms hat dann auch etliche Bytes weniger als die ursprüngliche Datei.
    Was muss man beim kopieren von programmen beachten, bzw. wie muss man sie öffnen,
    um sie 1 zu 1 auszulesen?

    thx 👍

    b4sh0r



  • Das öffnen stimmt soweit schon, wobei du hier vielleicht auf abfangen solltest ob es tatsächlich geklappt hat.
    Ansonsten würde im mal mit fwrite die Daten in die Datei schreiben...



  • fwrite() bringt auch nix. Was könnte ich noch probieren?



  • dann guck mal, wann der Fehler auftritt und welche Bytes kopiert werden (Textdatei kopieren).



  • mit fgetc erreichst du nicht. Mach mal das hier:

    #define MAX_LENGTH 4096
    
    #include <stdio.h>
    #include <stdlib.h>
    #include <stdarg.h>
    #include <string.h>
    
    static void fehl_meldung(const char *fmt, va_list az)
    {
        char puffer[MAX_LENGTH];
        vsprintf(puffer, fmt, az);
        fprintf(stderr, "%s\n", puffer);
    }
    
    /*---------------------- global error routine -----------------------*/
    void error_call(const char *fmt, ...)
    {
        va_list az;
    
        va_start(az, fmt);
        fehl_meldung(fmt,az);
    
        va_end(az);
    }
    
    int copyfile(const char* source, const char* destiny)
    {
      FILE* src, *dty;
      unsigned int read=0;
      char buffer[MAX_LENGTH];
    
      if((src=fopen(source, "rb")) == NULL)
        return -1;
      if((dty=fopen(destiny, "wb")) == NULL) {
        fclose(src);
        return -2;
      }
    
      while( (read = fread(buffer,1,MAX_LENGTH, src)) > 0 ) {
        if(read != fwrite(buffer, 1, read, dty)) {
          fclose(dty);
          fclose(src);
          error_call("Not all data could be copied into %s. Proc. aborted.", destiny);
          return -3;
          }
      }
    
      fclose(dty);
      fclose(src);
      return 0;
    }
    

    /bin/bash0R schrieb:

    fwrite() bringt auch nix. Was könnte ich noch probieren?

    man muss nur fwrite richtig benutzen. man: fwrite(3)



  • /bin/bash0R schrieb:

    fp1=fopen("a.out","rb");
    fp2=fopen("a.out2","wb");
    
    while (c=fgetc(fp1)!=EOF) {
    fprintf(fp2,"%c", c);
    }
    

    das gibt dann nen Speicherzugriffsfehler.

    Ich denke es ist eine gute Idee, wenn du dich nochmal etwas näher damit befasst, wie Ausdrücke ausgewertet werden.

    while (c=fgetc(fp1)!=EOF)
    

    Hier passiert nämlich nicht das, was du vielleicht erwartest. Zuerst wird der Ausdruck

    fgetc(fp1)!=EOF
    

    ausgewertet. Dieser wird dann c zugewiesen. Ich denke, du wolltest eher sowas

    while ((c=fgetc(fp1))!=EOF)
    

    fgetc gibt afaik int zurück, das solltest du ebenfalls beachten. Ich kenn zwar den Typ von c nicht, hört sich aber stark nach char an.



  • @groovemaster
    ups, das ist mir schon bewusst, das war schlicht weg ein Leichtsinnsfehler von
    mir. danke für dein scharfes adlerauge 😉

    jetzt möchte ich ein programm mit 9006 byte lesen

    while ((fread(buffer+i,1,1,fp)) > 0)
    ...
    

    und dann in eine andere datei schreiben

    while ( recv(sockfd, &c, 1, 0) ) {
             fwrite(&c,1,1,fp);
             len++;
          }
    

    Mein kopiertes Programm hat jetzt allerdings 9014 bytes!
    Woran kann das denn liegen 😕

    tHx



  • /bin/bash0R schrieb:

    while ((fread(buffer+i,1,1,fp)) > 0)
    

    😃 Man muss es ja nicht übertreiben, hier ist die zusätzliche Klammerung redundant.

    Zum Problem, ich nehme mal an, deine Dateien sind immer noch im Binärmodus geöffnet?
    Wenn ja, zähle mal die Schleifendurchläufe beim Lesen und Schreiben. Sind diese ungleich, solltest du an deiner Vorgehensweise noch etwas arbeiten. Ansonsten wäre das Resultat irgenwie seltsam. Schreibst du nach dem recv() noch irgendwelche Daten in die Datei?



  • ich kriegs einfach nicht zum laufen.
    zum kopieren von einfachen ascii dateien gehts. Sobald ich aber ein programm übertragen will, bekomme ich immer mehr bytes übertragen als das ursprüngliche file groß ist. Das kopierte programm lässt sich dann natürlich nicht ausführen.
    ich poste mal den ganzen code, vielleicht könnt ihr da mehr sehen als ich.

    #include <stdio.h>
    #include <string.h>
    #include <ctype.h>
    #include <sys/socket.h>
    #include <sys/types.h>
    #include <netinet/in.h>
    #include <arpa/inet.h>
    
    #define CLS printf("\033[H\033[2J")
    #define CKB while(getchar()!='\n')
    #define PORT 4666
    #define BUF_SIZE 1024
    #define SA struct sockaddr *
    
    //declarations
    int send_file(void);
    int recv_file(void);
    
    //functions
    int send_file(void)
    {
            FILE *fp;
            char file[128], ip[16], *buffer, c;
            int sockfd, i=0, block=0;
            struct sockaddr_in target;
    
            printf("\n\tf1le, u like t0 s3nd: ");
            scanf("%s", file);
            CKB;
    
            printf("\n\tip-addr 0f th3 t4rget syst3m: ");
            scanf("%s", ip);
            CKB;
    
            if ( (sockfd=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP)) == -1 ) {
                    printf("socket() error\n");
                    return 2;
            }
    
            target.sin_family=AF_INET;
            target.sin_port=htons(PORT);
            target.sin_addr.s_addr=inet_addr(ip);
    
            printf("\tconnect... ");
    
            if ( connect(sockfd,(SA)&target, sizeof(target)) == -1 ) {
                    printf("connect() error\n");
                    return 3;
            }
    
            printf(" OK\n\tn0w, s3nd 7he f1le...\n");
    
            if ( (buffer=(char *)malloc(sizeof(char)*BUF_SIZE)) == NULL ) {
                    printf("\ncouldn´t allocate 1024byte\n");
                    return 4;
            }
    
            if ( (fp=fopen(file,"rb")) == NULL ) {
                    printf("open file failed\n");
                    return 1;
            }
    
            while ((fread(buffer+i,1,1,fp)) > 0) {
    
                    printf("%d, %c\n", i+1, buffer[i]);
    
                    if (i == 1023) {
                            if ( send(sockfd,buffer,BUF_SIZE,0) != 1024 ) {
                                    printf("send() error\n");
                                    return 5;
                            }
                    block++;
                    i=0;
                    }
                    i++;
            }
    
            if ( send(sockfd,buffer,i,0) != i ) {
                            printf("send() error\n");
                            return 5;
            }
    
            printf("\t%d bytes were send to %s \n", i+block*1024, ip);
            printf("-------------------------------------------\n");
    
    fclose(fp);
    close(sockfd);
    
    return 0;
    }
    
    int recv_file(void)
    {
            int s, sockfd, len, tmp, opt=1;
            char c, file[128];
            struct sockaddr_in me, client;
            FILE *fp;
    
            printf("\n\tf1lename t0 wr1te d4t4 1n: ");
            scanf("%s", file);
            CKB;
    
            printf("\n\tw4it1ng f0r d4ta...\n");
    
            if ( (fp=fopen(file,"wb")) == NULL ) {
                    printf("couldn´t open file %s", file);
                    return 1;
            }
    
            if ( (s=socket(AF_INET,SOCK_STREAM,IPPROTO_TCP)) == -1 ) {
                    printf("socket() error\n");
                    return 2;
            }
    
            me.sin_family=AF_INET;
            me.sin_port=htons(PORT);
            me.sin_addr.s_addr=htonl(INADDR_ANY);
    
            if(setsockopt(s, SOL_SOCKET, SO_REUSEADDR, (char *)&opt, sizeof(opt)) == -1) {
         perror("(setsockopt) ");
         return 3;
            }
    
            if ( bind(s,(SA)&me, sizeof(me)) == -1 ) {
                    printf("bind() error\n");
                    return 4;
            }
    
            if ( listen(s,5) == -1 ) {
                    printf ("listen() error\n");
                    return 5;
            }
    
            len=sizeof(client);
            if ( (sockfd=accept(s,(struct sockaddr*)&client,&len)) == -1 ) {
                    printf ("accept() error\n");
                    return 6;
            }
    
            len=0;
    
            while ( recv(sockfd, &c, 1, 0) ) {
                    printf("%c\n", c);
                    fwrite(&c,1,1,fp);
                    len++;
            }
    
            printf("\n\t%d bytes received\n", len);
            printf("\td4t4 s4v3d 1n %s\n", file);
            printf("-------------------------------------------\n");
    
            fclose(fp);
            close(s);
            close(client);
    
    return 0;
    }
    
    int main(int argc, char *arvg[])
    {
            char choice, ret;
    
            CLS;
    
            while (1) {
    
                    printf("\n\t\tkerm1t ;-)\tby b4sh0r\n\n");
    
                    printf("\t(0) --> exit \n");
                    printf("\t(1) --> send a file \n");
                    printf("\t(2) --> recv a file \n\n\t>");
    
                    scanf("%c", &choice);
                    CKB;
    
                    switch (choice) {
    
                    case '0' :  printf("bye...\n"); return 0;
    
                    case '1' :  ret=send_file(); if (ret!=0) return ret;
                            break;
    
                    case '2' :  ret=recv_file(); if (ret!=0) return ret;
                            break;
    
                    default  :
                                            perror("not a valid option, a******, so cu\n");
                            return 1;
    
                    }
            }
    
    return 0;
    }
    

    tHx

    b4sh0r



  • /bin/bash0R schrieb:

    while ((fread(buffer+i,1,1,fp)) > 0) {
    
                    printf("%d, %c\n", i+1, buffer[i]);
    
                    if (i == 1023) {
                            if ( send(sockfd,buffer,BUF_SIZE,0) != 1024 ) {
                                    printf("send() error\n");
                                    return 5;
                            }
                    block++;
                    i=0;
                    }
                    i++;
            }
    

    Ich hab mir nicht alles angeschaut, aber in dieser Schleife gibts ein Problem. Wenn du in den if-Zweig kommst, sendest du ja einen Block an Daten mittels send(). Überleg mal, welchen Wert i beim nächsten Schleifendurchlauf hat, und welchen i haben müsste.



  • @groovemaster
    klingt logisch, ich erhöhe nach dem senden eines blockes den zeichenzähler i, ohne ein zeichen einzulesen, d. h. ich schicke bei jedem block später 1 byte zuviel.
    Werd das gleich mal testen, wenn ich zu hause bin.

    THX 👍


Anmelden zum Antworten