Q. What is 'holes' in files?
A. (By Andrew Gierth andrewg@microlise.co.uk)
The issue of 'holes' in files is thus:
Suppose a program creates a new file, seeks to a large offset, and then
writes 1 byte.
The file now consumes only 1 block of disk space, but appears to be large
(both in the byte size returned by stat(), and to a program that reads it
sequentially). The space that was never written to reads back as all
zeros, but consumes no space. This is referred to as a 'sparse file'.
The most common situation that causes these is use of the dbm package,
which takes advantage of this ability.
"Suppose a program creates a new file, seeks to a large offset, and
then writes 1 byte."
Once created, treat the sparse files as normal ones.
And i just wrote a simple program, hoping it would help.
/*
* Simple Demo to show how to create a sparse file(containing 'holes')
* and then copy a file to it.
*/
#define RFILE "foo"
#define WFILE "bar"
#define BUFSIZ 8096
#define MODE 0644
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include <unistd.h>
#include <stdio.h>
#include <stdlib.h>
int main(void)
{
int rfd, wfd, n;
struct stat rstat;
char buf[BUFSIZ];
if ((rfd = open(RFILE, O_RDONLY)) < 0) {
perror("open error");
exit(1);
}
/* Create the sparse file with the same size of RFILE */
if ((wfd = creat(WFILE, MODE)) < 0) {
perror("creat error");
exit(1);
}
if (fstat(rfd, &rstat) < 0) {
perror("fstat error");
exit(1);
}
if (lseek(wfd, rstat.st_size - 1, SEEK_SET) < 0) {
perror("lseek error");
exit(1);
}
if (write(wfd, "/0", 1) != 1) {
perror("write error");
exit(1);
}
/* Now copy RFILE to WFILE; nothing special */
if (lseek(wfd, 0, SEEK_SET) < 0) {
perror("lseek error");
exit(1);
}
while ((n = read(rfd, buf, BUFSIZ)) > 0) {
if (write(wfd, buf, n) != n) {
perror("write error");
exit(1);
}
}
if (n < 0) {
perror("read error");
exit(1);
}
return 0;
}