Take the 2-minute tour ×
Super User is a question and answer site for computer enthusiasts and power users. It's 100% free, no registration required.

I have to replace on a linux webserver, the first 128 bytes of some binary files.

The files have a size of ~ 5Gb and I just have to rewrite the header bytes. What would be the best aproach to do this using linux native commands or even PHP?

share|improve this question

2 Answers 2

up vote 10 down vote accepted

Simply open the file in "append" or similar mode, seek to position 0, then write your data.


"Linux native commands": the syscalls (or their libc wrappers) are as close as you can get.

#include <fcntl.h>
#include <unistd.h>

void main() {
    char buf[128] = "this and that";
    int fd = open("file", O_WRONLY);
    lseek(fd, 0, SEEK_SET);
    write(fd, &buf, sizeof(buf));
    close(fd);
}

PHP:

<?php
$buf = "this and that";
$fh = fopen("file", "a" "r+");
fseek($fh, 0);
fwrite($fh, $buf);
fclose($fh);
share|improve this answer
1  
It would have been nice if I could test the php solution, but as it is, doesn't work (If you have opened the file in append (a or a+) mode, any data you write to the file will always be appended, regardless of the file position, and the result of calling fseek() will be undefined. ) –  Mark Mar 20 '12 at 12:15
1  
@Xander: That is an ... interesting design decision from PHP's side. Try opening the file as c or r+, then. (Is this actually documented anywhere?) –  grawity Mar 20 '12 at 13:39
1  
Ah, I found it under fseek(). Sigh. –  grawity Mar 20 '12 at 13:47
1  
@Xander: I suggest encoding them with Base64 (PHP has base64_encode and base64_decode for that) and sending them over POST. Don't forget proper authentication! –  André Paramés Mar 20 '12 at 17:29
1  
@grawity That's not PHP's fault, "a" is equivalent to opening with O_APPEND, and is documented in the equivalent C functions (both open and fopen) –  Random832 Mar 20 '12 at 19:34

The dd is a simple approach.

dd if=128bytefile of=videofiletofix.mkv bs=128 count=1 conv=notrunc

So this will take the first 128 bytes of a file called 128bytefile and overwrite the first 128 bytes of a file called videofiletofix.mkv.

The bs parameter says to copy 128 bytes at a time, and the count parameter says to copy one such 128 byte block. The conv=notrunc parameter is important — without it, dd will truncate the output file to the length of the copied data (here, 128 bytes), which is most definitely not what you want.

share|improve this answer
    
nice solution Paul, thanks for your help. I would rise a point but I'm too new around and the system does not allow :) –  Mark Mar 20 '12 at 12:07
    
This is how I'd do it, excellent answer. –  Rob Mar 20 '12 at 14:17
1  
@Xander: You can do something like dd if=localfile bs=128 count=1 | ssh server 'dd of=videofile conv=notrunc'. However, why not just copy the 128-byte file to the server first? –  Ilmari Karonen Mar 20 '12 at 14:46
    
@Xander: You could always download dd for Windows and use it to extract the first 128 bytes. (Just use the same command as in the answer, but with a non-existent file as the target.) –  Ilmari Karonen Mar 20 '12 at 15:00
    
@Xander: 1. Anything that can transfer binary files is fine. 2. Use the dd command given in the answer. Just to be safe, you may want to make a backup copy of the target file first, at least until you're sure you've got the hang of it. –  Ilmari Karonen Mar 20 '12 at 15:23

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.