I'm working on a problem to create my own C version of unix ar. Right now I'm trying to create the header and write it to the file.
Initially, I used a stat struct and printed the contents using an fprintf. However, when I try to use the ar command on a file printed with such a method, it does not work. I was told that the better solution would be to use an fwrite to write the struct directly to the file. So I'm now trying to implement that.
I've tried to populate then fwrite my ar_hdr struct with the stat info, however when I write to the file, I get garbage.
Update 2: using just an fprintf based upon @fvu's recommendations. Last item on fprintf is the constant ARFMAG from ar.h which I believe is the same as printing the two characters.
void header(char *archive, char *read_file){
struct stat sb;
FILE *fp;
if (stat(read_file, &sb) == -1)
fail('s');
fp = fopen(archive, "a");
if (!fp)
fail('f');
fprintf(fp, "%-16s%-12ld%-6ld%-6ld%-8d%-10lld%s", read_file, (long)sb.st_mtimespec.tv_sec,
(long)sb.st_uid, (long)sb.st_gid, sb.st_mode, (long long)sb.st_size, ARFMAG);
fclose(fp);
}
The test output of my program is now something like this:
!<arch>
b.txt 1359332639 502 20 33188 28 `
Appending B. shortb long b
d.txt 1359332655 502 20 33188 28 `
Appending D. shortb long b
c.txt 1359332646 502 20 33188 17 `
COpy this.
When I try the unix command: ar -tv myfile.a
result is: Inappropriate file type or format
If I use nano to look at test.a this is the result
!<arch>
^@b.txt 1359332639 502 20 100644 28 `
Appending B. shortb long b
d.txt 1359332655 502 20 100644 28 `
Appending D. shortb long b
c.txt 1359332646 502 20 100644 17 `
COpy this shit.
There's a weird shift@ symbol before the first header. Here's my code to write the overall file header, any hints would be appreciated.
char title[] = ARMAG; //constant defined in ar.h
//open or create the output file
sf = open(argv[2], O_WRONLY | O_CREAT | O_APPEND, perms);
if (sf == -1)
fail('o'); //open fail
title_num = write(sf, title, sizeof(title));
Adding results from od -x file | head -n 2:
0000000 3c21 7261 6863 0a3e 2e62 7874 2074 2020
0000020 2020 2020 2020 2020 3331 3935 3333 3632