Path: utzoo!mnetor!uunet!lll-winken!lll-lcc!lll-tis!ames!think!bloom-beacon!gatech!mcnc!uvaarpa!umd5!mimsy!chris From: chris@mimsy.UUCP (Chris Torek) Newsgroups: comp.unix.wizards Subject: Re: Holey files, Batman! Message-ID: <10705@mimsy.UUCP> Date: 18 Mar 88 15:16:30 GMT References: <143@aoa.UUCP> <9978@steinmetz.steinmetz.UUCP> Organization: U of Maryland, Dept. of Computer Science, Coll. Pk., MD 20742 Lines: 56 In article <9978@steinmetz.steinmetz.UUCP> davidsen@steinmetz.steinmetz.UUCP (William E. Davidsen Jr) writes: >The problem comes in copying [sparse or `holey' files] to a backup device >and reloading them. I know of no program to do this, although it would be >easy to have the reload program write a sparse file if blocks of zeros >were encountered. 4BSD dump and restore know about holes. Curiously, `restore' makes the assumption that the last block of a file is never a hole. This was true until the introduction of the `truncate' system call, because there was no way to shorten a file, and the only way to create a file with holes was fd = open(...); lseek(fd, (long)way_out, 0); write(fd, "", 1); which did allocate at least one block (or fragment) containing only zero bytes. Now, however, it is possible to create a file containing ONLY holes; a program that does this is appended. >Is there a problem with this? No, althought it might be slow. `restore' works with an image of the original inode, and only replaces holes with holes; it does not test each block. >That is, is there a way to tell a sparse file from a file with a lot of zeros? There are two ways. One is to look at the inode (bypass the file system). The other is to count the number of blocks used (easy in 4.2/4.3BSD, hard in others). But all normal file system operations are obliged to treat them the same. /* create a file that is entirely hole */ #include #include struct stat st; main(){ int fd = creat("t.hole", 0666); if (fd < 0) perror("t.hole"), exit(1); (void) lseek(fd, 65536L, 0); (void) write(fd, "", 1); (void) fstat(fd, &st); (void) printf("t.hole has %ld blocks\n", st.st_blocks); (void) ftruncate(fd, 32768L); (void) fstat(fd, &st); (void) printf("t.hole now has %ld blocks\n", st.st_blocks); exit(0); } -- In-Real-Life: Chris Torek, Univ of MD Comp Sci Dept (+1 301 454 7163) Domain: chris@mimsy.umd.edu Path: uunet!mimsy!chris