Search code examples
chexfwritefseekhex-editors

I'm losing binary data when using fseek in c


I wrote a function that is responsible for moving to a binary file and editing its bytes

int replace(FILE *binaryFile, long offset, unsigned char *replaced, int length) {
    if (binaryFile != NULL) {
        for (int i = 0; i < length; i++) {
            fseek(binaryFile, offset + i, SEEK_SET);
            fwrite(&replaced[i], sizeof(*replaced), 1, binaryFile);
        }
        fclose(binaryFile);
        return 0;
    }
    else return -1;
}

When I use this function, I encounter a strange problem
All data in the file is filled with NULL bytes
And only one of the addresses in the file changes

Example:

FILE* fp = fopen("target.bin", "wb");

replace(fp, 0x57d8b0, "\x1E\xFF\x2F\xE1", 4);
replace(fp, 0x57c770, "\x01\x00\xA0\xE3\x1E\xFF\x2F\xE1", 8);

Result:

0x57c770: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
...
0x57d8a0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
0x57d8b0: 1e ff 2f e1

Correct result:

0x57c770: 01 00 A0 E3 1E FF 2F E1 ...
...
0x57d8a0: 9c c4 0a ea 70 d2 68 00 44 d4 68 00 10 d1 68 00
0x57d8b0: 1e ff 2f e1 18 b0 8d e2 02 8b 2d ed 18 d0 4d e2

Please help me to solve the function problem or other problems.


Solution

  • wb is not correct. It clobbers the file.

    From here,

    Mode Meaning Explanation If already exists If does not exist
    "r" read Open a file for reading read from start failure to open
    "w" write Create a file for writing destroy contents create new
    "a" append Append to a file write to end create new
    "r+" read extended Open a file for read/write read from start error
    "w+" write extended Create a file for read/write destroy contents create new
    "a+" append extended Open a file for read/write write to end create new

    You want r+b.


    Also, you close the file handle in replace, which is premature. This should be done outside of replace, after you're done with the handle.


    As an aside, you shouldn't be doing a number of seeks and writes of length one equal to length; you should be doing one seek and one write of length length.