build: ensure make-prime-list doesn't access out of bounds memory
[platform/upstream/coreutils.git] / src / shred.c
1 /* shred.c - overwrite files and devices to make it harder to recover data
2
3    Copyright (C) 1999-2013 Free Software Foundation, Inc.
4    Copyright (C) 1997, 1998, 1999 Colin Plumb.
5
6    This program is free software: you can redistribute it and/or modify
7    it under the terms of the GNU General Public License as published by
8    the Free Software Foundation, either version 3 of the License, or
9    (at your option) any later version.
10
11    This program is distributed in the hope that it will be useful,
12    but WITHOUT ANY WARRANTY; without even the implied warranty of
13    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
14    GNU General Public License for more details.
15
16    You should have received a copy of the GNU General Public License
17    along with this program.  If not, see <http://www.gnu.org/licenses/>.
18
19    Written by Colin Plumb.  */
20
21 /*
22  * Do a more secure overwrite of given files or devices, to make it harder
23  * for even very expensive hardware probing to recover the data.
24  *
25  * Although this process is also known as "wiping", I prefer the longer
26  * name both because I think it is more evocative of what is happening and
27  * because a longer name conveys a more appropriate sense of deliberateness.
28  *
29  * For the theory behind this, see "Secure Deletion of Data from Magnetic
30  * and Solid-State Memory", on line at
31  * http://www.cs.auckland.ac.nz/~pgut001/pubs/secure_del.html
32  *
33  * Just for the record, reversing one or two passes of disk overwrite
34  * is not terribly difficult with hardware help.  Hook up a good-quality
35  * digitizing oscilloscope to the output of the head preamplifier and copy
36  * the high-res digitized data to a computer for some off-line analysis.
37  * Read the "current" data and average all the pulses together to get an
38  * "average" pulse on the disk.  Subtract this average pulse from all of
39  * the actual pulses and you can clearly see the "echo" of the previous
40  * data on the disk.
41  *
42  * Real hard drives have to balance the cost of the media, the head,
43  * and the read circuitry.  They use better-quality media than absolutely
44  * necessary to limit the cost of the read circuitry.  By throwing that
45  * assumption out, and the assumption that you want the data processed
46  * as fast as the hard drive can spin, you can do better.
47  *
48  * If asked to wipe a file, this also unlinks it, renaming it to in a
49  * clever way to try to leave no trace of the original filename.
50  *
51  * This was inspired by a desire to improve on some code titled:
52  * Wipe V1.0-- Overwrite and delete files.  S. 2/3/96
53  * but I've rewritten everything here so completely that no trace of
54  * the original remains.
55  *
56  * Thanks to:
57  * Bob Jenkins, for his good RNG work and patience with the FSF copyright
58  * paperwork.
59  * Jim Meyering, for his work merging this into the GNU fileutils while
60  * still letting me feel a sense of ownership and pride.  Getting me to
61  * tolerate the GNU brace style was quite a feat of diplomacy.
62  * Paul Eggert, for lots of useful discussion and code.  I disagree with
63  * an awful lot of his suggestions, but they're disagreements worth having.
64  *
65  * Things to think about:
66  * - Security: Is there any risk to the race
67  *   between overwriting and unlinking a file?  Will it do anything
68  *   drastically bad if told to attack a named pipe or socket?
69  */
70
71 /* The official name of this program (e.g., no 'g' prefix).  */
72 #define PROGRAM_NAME "shred"
73
74 #define AUTHORS proper_name ("Colin Plumb")
75
76 #include <config.h>
77
78 #include <getopt.h>
79 #include <stdio.h>
80 #include <assert.h>
81 #include <setjmp.h>
82 #include <sys/types.h>
83
84 #include "system.h"
85 #include "xstrtol.h"
86 #include "error.h"
87 #include "fcntl--.h"
88 #include "human.h"
89 #include "quotearg.h"           /* For quotearg_colon */
90 #include "randint.h"
91 #include "randread.h"
92 #include "stat-size.h"
93
94 /* Default number of times to overwrite.  */
95 enum { DEFAULT_PASSES = 3 };
96
97 /* How many seconds to wait before checking whether to output another
98    verbose output line.  */
99 enum { VERBOSE_UPDATE = 5 };
100
101 /* Sector size and corresponding mask, for recovering after write failures.
102    The size must be a power of 2.  */
103 enum { SECTOR_SIZE = 512 };
104 enum { SECTOR_MASK = SECTOR_SIZE - 1 };
105 verify (0 < SECTOR_SIZE && (SECTOR_SIZE & SECTOR_MASK) == 0);
106
107 struct Options
108 {
109   bool force;           /* -f flag: chmod files if necessary */
110   size_t n_iterations;  /* -n flag: Number of iterations */
111   off_t size;           /* -s flag: size of file */
112   bool remove_file;     /* -u flag: remove file after shredding */
113   bool verbose;         /* -v flag: Print progress */
114   bool exact;           /* -x flag: Do not round up file size */
115   bool zero_fill;       /* -z flag: Add a final zero pass */
116 };
117
118 /* For long options that have no equivalent short option, use a
119    non-character as a pseudo short option, starting with CHAR_MAX + 1.  */
120 enum
121 {
122   RANDOM_SOURCE_OPTION = CHAR_MAX + 1
123 };
124
125 static struct option const long_opts[] =
126 {
127   {"exact", no_argument, NULL, 'x'},
128   {"force", no_argument, NULL, 'f'},
129   {"iterations", required_argument, NULL, 'n'},
130   {"size", required_argument, NULL, 's'},
131   {"random-source", required_argument, NULL, RANDOM_SOURCE_OPTION},
132   {"remove", no_argument, NULL, 'u'},
133   {"verbose", no_argument, NULL, 'v'},
134   {"zero", no_argument, NULL, 'z'},
135   {GETOPT_HELP_OPTION_DECL},
136   {GETOPT_VERSION_OPTION_DECL},
137   {NULL, 0, NULL, 0}
138 };
139
140 void
141 usage (int status)
142 {
143   if (status != EXIT_SUCCESS)
144     emit_try_help ();
145   else
146     {
147       printf (_("Usage: %s [OPTION]... FILE...\n"), program_name);
148       fputs (_("\
149 Overwrite the specified FILE(s) repeatedly, in order to make it harder\n\
150 for even very expensive hardware probing to recover the data.\n\
151 "), stdout);
152
153       emit_mandatory_arg_note ();
154
155       printf (_("\
156   -f, --force    change permissions to allow writing if necessary\n\
157   -n, --iterations=N  overwrite N times instead of the default (%d)\n\
158       --random-source=FILE  get random bytes from FILE\n\
159   -s, --size=N   shred this many bytes (suffixes like K, M, G accepted)\n\
160 "), DEFAULT_PASSES);
161       fputs (_("\
162   -u, --remove   truncate and remove file after overwriting\n\
163   -v, --verbose  show progress\n\
164   -x, --exact    do not round file sizes up to the next full block;\n\
165                    this is the default for non-regular files\n\
166   -z, --zero     add a final overwrite with zeros to hide shredding\n\
167 "), stdout);
168       fputs (HELP_OPTION_DESCRIPTION, stdout);
169       fputs (VERSION_OPTION_DESCRIPTION, stdout);
170       fputs (_("\
171 \n\
172 If FILE is -, shred standard output.\n\
173 \n\
174 Delete FILE(s) if --remove (-u) is specified.  The default is not to remove\n\
175 the files because it is common to operate on device files like /dev/hda,\n\
176 and those files usually should not be removed.  When operating on regular\n\
177 files, most people use the --remove option.\n\
178 \n\
179 "), stdout);
180       fputs (_("\
181 CAUTION: Note that shred relies on a very important assumption:\n\
182 that the file system overwrites data in place.  This is the traditional\n\
183 way to do things, but many modern file system designs do not satisfy this\n\
184 assumption.  The following are examples of file systems on which shred is\n\
185 not effective, or is not guaranteed to be effective in all file system modes:\n\
186 \n\
187 "), stdout);
188       fputs (_("\
189 * log-structured or journaled file systems, such as those supplied with\n\
190 AIX and Solaris (and JFS, ReiserFS, XFS, Ext3, etc.)\n\
191 \n\
192 * file systems that write redundant data and carry on even if some writes\n\
193 fail, such as RAID-based file systems\n\
194 \n\
195 * file systems that make snapshots, such as Network Appliance's NFS server\n\
196 \n\
197 "), stdout);
198       fputs (_("\
199 * file systems that cache in temporary locations, such as NFS\n\
200 version 3 clients\n\
201 \n\
202 * compressed file systems\n\
203 \n\
204 "), stdout);
205       fputs (_("\
206 In the case of ext3 file systems, the above disclaimer applies\n\
207 (and shred is thus of limited effectiveness) only in data=journal mode,\n\
208 which journals file data in addition to just metadata.  In both the\n\
209 data=ordered (default) and data=writeback modes, shred works as usual.\n\
210 Ext3 journaling modes can be changed by adding the data=something option\n\
211 to the mount options for a particular file system in the /etc/fstab file,\n\
212 as documented in the mount man page (man mount).\n\
213 \n\
214 "), stdout);
215       fputs (_("\
216 In addition, file system backups and remote mirrors may contain copies\n\
217 of the file that cannot be removed, and that will allow a shredded file\n\
218 to be recovered later.\n\
219 "), stdout);
220       emit_ancillary_info ();
221     }
222   exit (status);
223 }
224
225
226 /*
227  * Fill a buffer with a fixed pattern.
228  *
229  * The buffer must be at least 3 bytes long, even if
230  * size is less.  Larger sizes are filled exactly.
231  */
232 static void
233 fillpattern (int type, unsigned char *r, size_t size)
234 {
235   size_t i;
236   unsigned int bits = type & 0xfff;
237
238   bits |= bits << 12;
239   r[0] = (bits >> 4) & 255;
240   r[1] = (bits >> 8) & 255;
241   r[2] = bits & 255;
242   for (i = 3; i < size / 2; i *= 2)
243     memcpy (r + i, r, i);
244   if (i < size)
245     memcpy (r + i, r, size - i);
246
247   /* Invert the first bit of every sector. */
248   if (type & 0x1000)
249     for (i = 0; i < size; i += SECTOR_SIZE)
250       r[i] ^= 0x80;
251 }
252
253 /*
254  * Generate a 6-character (+ nul) pass name string
255  * FIXME: allow translation of "random".
256  */
257 #define PASS_NAME_SIZE 7
258 static void
259 passname (unsigned char const *data, char name[PASS_NAME_SIZE])
260 {
261   if (data)
262     sprintf (name, "%02x%02x%02x", data[0], data[1], data[2]);
263   else
264     memcpy (name, "random", PASS_NAME_SIZE);
265 }
266
267 /* Return true when it's ok to ignore an fsync or fdatasync
268    failure that set errno to ERRNO_VAL.  */
269 static bool
270 ignorable_sync_errno (int errno_val)
271 {
272   return (errno_val == EINVAL
273           || errno_val == EBADF
274           /* HP-UX does this */
275           || errno_val == EISDIR);
276 }
277
278 /* Request that all data for FD be transferred to the corresponding
279    storage device.  QNAME is the file name (quoted for colons).
280    Report any errors found.  Return 0 on success, -1
281    (setting errno) on failure.  It is not an error if fdatasync and/or
282    fsync is not supported for this file, or if the file is not a
283    writable file descriptor.  */
284 static int
285 dosync (int fd, char const *qname)
286 {
287   int err;
288
289 #if HAVE_FDATASYNC
290   if (fdatasync (fd) == 0)
291     return 0;
292   err = errno;
293   if ( ! ignorable_sync_errno (err))
294     {
295       error (0, err, _("%s: fdatasync failed"), qname);
296       errno = err;
297       return -1;
298     }
299 #endif
300
301   if (fsync (fd) == 0)
302     return 0;
303   err = errno;
304   if ( ! ignorable_sync_errno (err))
305     {
306       error (0, err, _("%s: fsync failed"), qname);
307       errno = err;
308       return -1;
309     }
310
311   sync ();
312   return 0;
313 }
314
315 /* Turn on or off direct I/O mode for file descriptor FD, if possible.
316    Try to turn it on if ENABLE is true.  Otherwise, try to turn it off.  */
317 static void
318 direct_mode (int fd, bool enable)
319 {
320   if (O_DIRECT)
321     {
322       int fd_flags = fcntl (fd, F_GETFL);
323       if (0 < fd_flags)
324         {
325           int new_flags = (enable
326                            ? (fd_flags | O_DIRECT)
327                            : (fd_flags & ~O_DIRECT));
328           if (new_flags != fd_flags)
329             fcntl (fd, F_SETFL, new_flags);
330         }
331     }
332
333 #if HAVE_DIRECTIO && defined DIRECTIO_ON && defined DIRECTIO_OFF
334   /* This is Solaris-specific.  See the following for details:
335      http://docs.sun.com/db/doc/816-0213/6m6ne37so?q=directio&a=view  */
336   directio (fd, enable ? DIRECTIO_ON : DIRECTIO_OFF);
337 #endif
338 }
339
340 /*
341  * Do pass number k of n, writing "size" bytes of the given pattern "type"
342  * to the file descriptor fd.   Qname, k and n are passed in only for verbose
343  * progress message purposes.  If n == 0, no progress messages are printed.
344  *
345  * If *sizep == -1, the size is unknown, and it will be filled in as soon
346  * as writing fails.
347  *
348  * Return 1 on write error, -1 on other error, 0 on success.
349  */
350 static int
351 dopass (int fd, char const *qname, off_t *sizep, int type,
352         struct randread_source *s, unsigned long int k, unsigned long int n)
353 {
354   off_t size = *sizep;
355   off_t offset;                 /* Current file posiiton */
356   time_t thresh IF_LINT ( = 0); /* Time to maybe print next status update */
357   time_t now = 0;               /* Current time */
358   size_t lim;                   /* Amount of data to try writing */
359   size_t soff;                  /* Offset into buffer for next write */
360   ssize_t ssize;                /* Return value from write */
361
362   /* Fill pattern buffer.  Aligning it to a 32-bit boundary speeds up randread
363      in some cases.  */
364   typedef uint32_t fill_pattern_buffer[3 * 1024];
365   union
366   {
367     fill_pattern_buffer buffer;
368     char c[sizeof (fill_pattern_buffer)];
369     unsigned char u[sizeof (fill_pattern_buffer)];
370   } r;
371
372   off_t sizeof_r = sizeof r;
373   char pass_string[PASS_NAME_SIZE];     /* Name of current pass */
374   bool write_error = false;
375   bool first_write = true;
376
377   /* Printable previous offset into the file */
378   char previous_offset_buf[LONGEST_HUMAN_READABLE + 1];
379   char const *previous_human_offset IF_LINT ( = 0);
380
381   if (lseek (fd, 0, SEEK_SET) == -1)
382     {
383       error (0, errno, _("%s: cannot rewind"), qname);
384       return -1;
385     }
386
387   /* Constant fill patterns need only be set up once. */
388   if (type >= 0)
389     {
390       lim = (0 <= size && size < sizeof_r ? size : sizeof_r);
391       fillpattern (type, r.u, lim);
392       passname (r.u, pass_string);
393     }
394   else
395     {
396       passname (0, pass_string);
397     }
398
399   /* Set position if first status update */
400   if (n)
401     {
402       error (0, 0, _("%s: pass %lu/%lu (%s)..."), qname, k, n, pass_string);
403       thresh = time (NULL) + VERBOSE_UPDATE;
404       previous_human_offset = "";
405     }
406
407   offset = 0;
408   while (true)
409     {
410       /* How much to write this time? */
411       lim = sizeof r;
412       if (0 <= size && size - offset < sizeof_r)
413         {
414           if (size < offset)
415             break;
416           lim = size - offset;
417           if (!lim)
418             break;
419         }
420       if (type < 0)
421         randread (s, &r, lim);
422       /* Loop to retry partial writes. */
423       for (soff = 0; soff < lim; soff += ssize, first_write = false)
424         {
425           ssize = write (fd, r.c + soff, lim - soff);
426           if (ssize <= 0)
427             {
428               if (size < 0 && (ssize == 0 || errno == ENOSPC))
429                 {
430                   /* Ah, we have found the end of the file */
431                   *sizep = size = offset + soff;
432                   break;
433                 }
434               else
435                 {
436                   int errnum = errno;
437                   char buf[INT_BUFSIZE_BOUND (uintmax_t)];
438
439                   /* If the first write of the first pass for a given file
440                      has just failed with EINVAL, turn off direct mode I/O
441                      and try again.  This works around a bug in Linux kernel
442                      2.4 whereby opening with O_DIRECT would succeed for some
443                      file system types (e.g., ext3), but any attempt to
444                      access a file through the resulting descriptor would
445                      fail with EINVAL.  */
446                   if (k == 1 && first_write && errno == EINVAL)
447                     {
448                       direct_mode (fd, false);
449                       ssize = 0;
450                       continue;
451                     }
452                   error (0, errnum, _("%s: error writing at offset %s"),
453                          qname, umaxtostr (offset + soff, buf));
454
455                   /* 'shred' is often used on bad media, before throwing it
456                      out.  Thus, it shouldn't give up on bad blocks.  This
457                      code works because lim is always a multiple of
458                      SECTOR_SIZE, except at the end.  */
459                   verify (sizeof r % SECTOR_SIZE == 0);
460                   if (errnum == EIO && 0 <= size && (soff | SECTOR_MASK) < lim)
461                     {
462                       size_t soff1 = (soff | SECTOR_MASK) + 1;
463                       if (lseek (fd, offset + soff1, SEEK_SET) != -1)
464                         {
465                           /* Arrange to skip this block. */
466                           ssize = soff1 - soff;
467                           write_error = true;
468                           continue;
469                         }
470                       error (0, errno, _("%s: lseek failed"), qname);
471                     }
472                   return -1;
473                 }
474             }
475         }
476
477       /* Okay, we have written "soff" bytes. */
478
479       if (offset > OFF_T_MAX - (off_t) soff)
480         {
481           error (0, 0, _("%s: file too large"), qname);
482           return -1;
483         }
484
485       offset += soff;
486
487       bool done = offset == size;
488
489       /* Time to print progress? */
490       if (n && ((done && *previous_human_offset)
491                 || thresh <= (now = time (NULL))))
492         {
493           char offset_buf[LONGEST_HUMAN_READABLE + 1];
494           char size_buf[LONGEST_HUMAN_READABLE + 1];
495           int human_progress_opts = (human_autoscale | human_SI
496                                      | human_base_1024 | human_B);
497           char const *human_offset
498             = human_readable (offset, offset_buf,
499                               human_floor | human_progress_opts, 1, 1);
500
501           if (done || !STREQ (previous_human_offset, human_offset))
502             {
503               if (size < 0)
504                 error (0, 0, _("%s: pass %lu/%lu (%s)...%s"),
505                        qname, k, n, pass_string, human_offset);
506               else
507                 {
508                   uintmax_t off = offset;
509                   int percent = (size == 0
510                                  ? 100
511                                  : (off <= TYPE_MAXIMUM (uintmax_t) / 100
512                                     ? off * 100 / size
513                                     : off / (size / 100)));
514                   char const *human_size
515                     = human_readable (size, size_buf,
516                                       human_ceiling | human_progress_opts,
517                                       1, 1);
518                   if (done)
519                     human_offset = human_size;
520                   error (0, 0, _("%s: pass %lu/%lu (%s)...%s/%s %d%%"),
521                          qname, k, n, pass_string, human_offset, human_size,
522                          percent);
523                 }
524
525               strcpy (previous_offset_buf, human_offset);
526               previous_human_offset = previous_offset_buf;
527               thresh = now + VERBOSE_UPDATE;
528
529               /*
530                * Force periodic syncs to keep displayed progress accurate
531                * FIXME: Should these be present even if -v is not enabled,
532                * to keep the buffer cache from filling with dirty pages?
533                * It's a common problem with programs that do lots of writes,
534                * like mkfs.
535                */
536               if (dosync (fd, qname) != 0)
537                 {
538                   if (errno != EIO)
539                     return -1;
540                   write_error = true;
541                 }
542             }
543         }
544     }
545
546   /* Force what we just wrote to hit the media. */
547   if (dosync (fd, qname) != 0)
548     {
549       if (errno != EIO)
550         return -1;
551       write_error = true;
552     }
553
554   return write_error;
555 }
556
557 /*
558  * The passes start and end with a random pass, and the passes in between
559  * are done in random order.  The idea is to deprive someone trying to
560  * reverse the process of knowledge of the overwrite patterns, so they
561  * have the additional step of figuring out what was done to the disk
562  * before they can try to reverse or cancel it.
563  *
564  * First, all possible 1-bit patterns.  There are two of them.
565  * Then, all possible 2-bit patterns.  There are four, but the two
566  * which are also 1-bit patterns can be omitted.
567  * Then, all possible 3-bit patterns.  Likewise, 8-2 = 6.
568  * Then, all possible 4-bit patterns.  16-4 = 12.
569  *
570  * The basic passes are:
571  * 1-bit: 0x000, 0xFFF
572  * 2-bit: 0x555, 0xAAA
573  * 3-bit: 0x249, 0x492, 0x924, 0x6DB, 0xB6D, 0xDB6 (+ 1-bit)
574  *        100100100100         110110110110
575  *           9   2   4            D   B   6
576  * 4-bit: 0x111, 0x222, 0x333, 0x444, 0x666, 0x777,
577  *        0x888, 0x999, 0xBBB, 0xCCC, 0xDDD, 0xEEE (+ 1-bit, 2-bit)
578  * Adding three random passes at the beginning, middle and end
579  * produces the default 25-pass structure.
580  *
581  * The next extension would be to 5-bit and 6-bit patterns.
582  * There are 30 uncovered 5-bit patterns and 64-8-2 = 46 uncovered
583  * 6-bit patterns, so they would increase the time required
584  * significantly.  4-bit patterns are enough for most purposes.
585  *
586  * The main gotcha is that this would require a trickier encoding,
587  * since lcm(2,3,4) = 12 bits is easy to fit into an int, but
588  * lcm(2,3,4,5) = 60 bits is not.
589  *
590  * One extension that is included is to complement the first bit in each
591  * 512-byte block, to alter the phase of the encoded data in the more
592  * complex encodings.  This doesn't apply to MFM, so the 1-bit patterns
593  * are considered part of the 3-bit ones and the 2-bit patterns are
594  * considered part of the 4-bit patterns.
595  *
596  *
597  * How does the generalization to variable numbers of passes work?
598  *
599  * Here's how...
600  * Have an ordered list of groups of passes.  Each group is a set.
601  * Take as many groups as will fit, plus a random subset of the
602  * last partial group, and place them into the passes list.
603  * Then shuffle the passes list into random order and use that.
604  *
605  * One extra detail: if we can't include a large enough fraction of the
606  * last group to be interesting, then just substitute random passes.
607  *
608  * If you want more passes than the entire list of groups can
609  * provide, just start repeating from the beginning of the list.
610  */
611 static int const
612   patterns[] =
613 {
614   -2,                           /* 2 random passes */
615   2, 0x000, 0xFFF,              /* 1-bit */
616   2, 0x555, 0xAAA,              /* 2-bit */
617   -1,                           /* 1 random pass */
618   6, 0x249, 0x492, 0x6DB, 0x924, 0xB6D, 0xDB6,  /* 3-bit */
619   12, 0x111, 0x222, 0x333, 0x444, 0x666, 0x777,
620   0x888, 0x999, 0xBBB, 0xCCC, 0xDDD, 0xEEE,     /* 4-bit */
621   -1,                           /* 1 random pass */
622         /* The following patterns have the frst bit per block flipped */
623   8, 0x1000, 0x1249, 0x1492, 0x16DB, 0x1924, 0x1B6D, 0x1DB6, 0x1FFF,
624   14, 0x1111, 0x1222, 0x1333, 0x1444, 0x1555, 0x1666, 0x1777,
625   0x1888, 0x1999, 0x1AAA, 0x1BBB, 0x1CCC, 0x1DDD, 0x1EEE,
626   -1,                           /* 1 random pass */
627   0                             /* End */
628 };
629
630 /*
631  * Generate a random wiping pass pattern with num passes.
632  * This is a two-stage process.  First, the passes to include
633  * are chosen, and then they are shuffled into the desired
634  * order.
635  */
636 static void
637 genpattern (int *dest, size_t num, struct randint_source *s)
638 {
639   size_t randpasses;
640   int const *p;
641   int *d;
642   size_t n;
643   size_t accum, top, swap;
644   int k;
645
646   if (!num)
647     return;
648
649   /* Stage 1: choose the passes to use */
650   p = patterns;
651   randpasses = 0;
652   d = dest;                     /* Destination for generated pass list */
653   n = num;                      /* Passes remaining to fill */
654
655   while (true)
656     {
657       k = *p++;                 /* Block descriptor word */
658       if (!k)
659         {                       /* Loop back to the beginning */
660           p = patterns;
661         }
662       else if (k < 0)
663         {                       /* -k random passes */
664           k = -k;
665           if ((size_t) k >= n)
666             {
667               randpasses += n;
668               break;
669             }
670           randpasses += k;
671           n -= k;
672         }
673       else if ((size_t) k <= n)
674         {                       /* Full block of patterns */
675           memcpy (d, p, k * sizeof (int));
676           p += k;
677           d += k;
678           n -= k;
679         }
680       else if (n < 2 || 3 * n < (size_t) k)
681         {                       /* Finish with random */
682           randpasses += n;
683           break;
684         }
685       else
686         {                       /* Pad out with k of the n available */
687           do
688             {
689               if (n == (size_t) k || randint_choose (s, k) < n)
690                 {
691                   *d++ = *p;
692                   n--;
693                 }
694               p++;
695             }
696           while (n);
697           break;
698         }
699     }
700   top = num - randpasses;       /* Top of initialized data */
701   /* assert (d == dest+top); */
702
703   /*
704    * We now have fixed patterns in the dest buffer up to
705    * "top", and we need to scramble them, with "randpasses"
706    * random passes evenly spaced among them.
707    *
708    * We want one at the beginning, one at the end, and
709    * evenly spaced in between.  To do this, we basically
710    * use Bresenham's line draw (a.k.a DDA) algorithm
711    * to draw a line with slope (randpasses-1)/(num-1).
712    * (We use a positive accumulator and count down to
713    * do this.)
714    *
715    * So for each desired output value, we do the following:
716    * - If it should be a random pass, copy the pass type
717    *   to top++, out of the way of the other passes, and
718    *   set the current pass to -1 (random).
719    * - If it should be a normal pattern pass, choose an
720    *   entry at random between here and top-1 (inclusive)
721    *   and swap the current entry with that one.
722    */
723   randpasses--;                 /* To speed up later math */
724   accum = randpasses;           /* Bresenham DDA accumulator */
725   for (n = 0; n < num; n++)
726     {
727       if (accum <= randpasses)
728         {
729           accum += num - 1;
730           dest[top++] = dest[n];
731           dest[n] = -1;
732         }
733       else
734         {
735           swap = n + randint_choose (s, top - n);
736           k = dest[n];
737           dest[n] = dest[swap];
738           dest[swap] = k;
739         }
740       accum -= randpasses;
741     }
742   /* assert (top == num); */
743 }
744
745 /*
746  * The core routine to actually do the work.  This overwrites the first
747  * size bytes of the given fd.  Return true if successful.
748  */
749 static bool
750 do_wipefd (int fd, char const *qname, struct randint_source *s,
751            struct Options const *flags)
752 {
753   size_t i;
754   struct stat st;
755   off_t size;                   /* Size to write, size to read */
756   unsigned long int n;          /* Number of passes for printing purposes */
757   int *passarray;
758   bool ok = true;
759   struct randread_source *rs;
760
761   n = 0;                /* dopass takes n -- 0 to mean "don't print progress" */
762   if (flags->verbose)
763     n = flags->n_iterations + flags->zero_fill;
764
765   if (fstat (fd, &st))
766     {
767       error (0, errno, _("%s: fstat failed"), qname);
768       return false;
769     }
770
771   /* If we know that we can't possibly shred the file, give up now.
772      Otherwise, we may go into an infinite loop writing data before we
773      find that we can't rewind the device.  */
774   if ((S_ISCHR (st.st_mode) && isatty (fd))
775       || S_ISFIFO (st.st_mode)
776       || S_ISSOCK (st.st_mode))
777     {
778       error (0, 0, _("%s: invalid file type"), qname);
779       return false;
780     }
781
782   direct_mode (fd, true);
783
784   /* Allocate pass array */
785   passarray = xnmalloc (flags->n_iterations, sizeof *passarray);
786
787   size = flags->size;
788   if (size == -1)
789     {
790       /* Accept a length of zero only if it's a regular file.
791          For any other type of file, try to get the size another way.  */
792       if (S_ISREG (st.st_mode))
793         {
794           size = st.st_size;
795           if (size < 0)
796             {
797               error (0, 0, _("%s: file has negative size"), qname);
798               return false;
799             }
800         }
801       else
802         {
803           size = lseek (fd, 0, SEEK_END);
804           if (size <= 0)
805             {
806               /* We are unable to determine the length, up front.
807                  Let dopass do that as part of its first iteration.  */
808               size = -1;
809             }
810         }
811
812       /* Allow 'rounding up' only for regular files.  */
813       if (0 <= size && !(flags->exact) && S_ISREG (st.st_mode))
814         {
815           size += ST_BLKSIZE (st) - 1 - (size - 1) % ST_BLKSIZE (st);
816
817           /* If in rounding up, we've just overflowed, use the maximum.  */
818           if (size < 0)
819             size = TYPE_MAXIMUM (off_t);
820         }
821     }
822
823   /* Schedule the passes in random order. */
824   genpattern (passarray, flags->n_iterations, s);
825
826   rs = randint_get_source (s);
827
828   /* Do the work */
829   for (i = 0; i < flags->n_iterations; i++)
830     {
831       int err = dopass (fd, qname, &size, passarray[i], rs, i + 1, n);
832       if (err)
833         {
834           if (err < 0)
835             {
836               memset (passarray, 0, flags->n_iterations * sizeof (int));
837               free (passarray);
838               return false;
839             }
840           ok = false;
841         }
842     }
843
844   memset (passarray, 0, flags->n_iterations * sizeof (int));
845   free (passarray);
846
847   if (flags->zero_fill)
848     {
849       int err = dopass (fd, qname, &size, 0, rs, flags->n_iterations + 1, n);
850       if (err)
851         {
852           if (err < 0)
853             return false;
854           ok = false;
855         }
856     }
857
858   /* Okay, now deallocate the data.  The effect of ftruncate on
859      non-regular files is unspecified, so don't worry about any
860      errors reported for them.  */
861   if (flags->remove_file && ftruncate (fd, 0) != 0
862       && S_ISREG (st.st_mode))
863     {
864       error (0, errno, _("%s: error truncating"), qname);
865       return false;
866     }
867
868   return ok;
869 }
870
871 /* A wrapper with a little more checking for fds on the command line */
872 static bool
873 wipefd (int fd, char const *qname, struct randint_source *s,
874         struct Options const *flags)
875 {
876   int fd_flags = fcntl (fd, F_GETFL);
877
878   if (fd_flags < 0)
879     {
880       error (0, errno, _("%s: fcntl failed"), qname);
881       return false;
882     }
883   if (fd_flags & O_APPEND)
884     {
885       error (0, 0, _("%s: cannot shred append-only file descriptor"), qname);
886       return false;
887     }
888   return do_wipefd (fd, qname, s, flags);
889 }
890
891 /* --- Name-wiping code --- */
892
893 /* Characters allowed in a file name - a safe universal set.  */
894 static char const nameset[] =
895 "0123456789abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ_.";
896
897 /* Increment NAME (with LEN bytes).  NAME must be a big-endian base N
898    number with the digits taken from nameset.  Return true if successful.
899    Otherwise, (because NAME already has the greatest possible value)
900    return false.  */
901
902 static bool
903 incname (char *name, size_t len)
904 {
905   while (len--)
906     {
907       char const *p = strchr (nameset, name[len]);
908
909       /* Given that NAME is composed of bytes from NAMESET,
910          P will never be NULL here.  */
911       assert (p);
912
913       /* If this character has a successor, use it.  */
914       if (p[1])
915         {
916           name[len] = p[1];
917           return true;
918         }
919
920       /* Otherwise, set this digit to 0 and increment the prefix.  */
921       name[len] = nameset[0];
922     }
923
924   return false;
925 }
926
927 /*
928  * Repeatedly rename a file with shorter and shorter names,
929  * to obliterate all traces of the file name on any system that
930  * adds a trailing delimiter to on-disk file names and reuses
931  * the same directory slot.  Finally, unlink it.
932  * The passed-in filename is modified in place to the new filename.
933  * (Which is unlinked if this function succeeds, but is still present if
934  * it fails for some reason.)
935  *
936  * The main loop is written carefully to not get stuck if all possible
937  * names of a given length are occupied.  It counts down the length from
938  * the original to 0.  While the length is non-zero, it tries to find an
939  * unused file name of the given length.  It continues until either the
940  * name is available and the rename succeeds, or it runs out of names
941  * to try (incname wraps and returns 1).  Finally, it unlinks the file.
942  *
943  * The unlink is Unix-specific, as ANSI-standard remove has more
944  * portability problems with C libraries making it "safe".  rename
945  * is ANSI-standard.
946  *
947  * To force the directory data out, we try to open the directory and
948  * invoke fdatasync and/or fsync on it.  This is non-standard, so don't
949  * insist that it works: just fall back to a global sync in that case.
950  * This is fairly significantly Unix-specific.  Of course, on any
951  * file system with synchronous metadata updates, this is unnecessary.
952  */
953 static bool
954 wipename (char *oldname, char const *qoldname, struct Options const *flags)
955 {
956   char *newname = xstrdup (oldname);
957   char *base = last_component (newname);
958   size_t len = base_len (base);
959   char *dir = dir_name (newname);
960   char *qdir = xstrdup (quotearg_colon (dir));
961   bool first = true;
962   bool ok = true;
963
964   int dir_fd = open (dir, O_RDONLY | O_DIRECTORY | O_NOCTTY | O_NONBLOCK);
965
966   if (flags->verbose)
967     error (0, 0, _("%s: removing"), qoldname);
968
969   while (len)
970     {
971       memset (base, nameset[0], len);
972       base[len] = 0;
973       do
974         {
975           struct stat st;
976           if (lstat (newname, &st) < 0)
977             {
978               if (rename (oldname, newname) == 0)
979                 {
980                   if (0 <= dir_fd && dosync (dir_fd, qdir) != 0)
981                     ok = false;
982                   if (flags->verbose)
983                     {
984                       /*
985                        * People seem to understand this better than talking
986                        * about renaming oldname.  newname doesn't need
987                        * quoting because we picked it.  oldname needs to
988                        * be quoted only the first time.
989                        */
990                       char const *old = (first ? qoldname : oldname);
991                       error (0, 0, _("%s: renamed to %s"), old, newname);
992                       first = false;
993                     }
994                   memcpy (oldname + (base - newname), base, len + 1);
995                   break;
996                 }
997               else
998                 {
999                   /* The rename failed: give up on this length.  */
1000                   break;
1001                 }
1002             }
1003           else
1004             {
1005               /* newname exists, so increment BASE so we use another */
1006             }
1007         }
1008       while (incname (base, len));
1009       len--;
1010     }
1011   if (unlink (oldname) != 0)
1012     {
1013       error (0, errno, _("%s: failed to remove"), qoldname);
1014       ok = false;
1015     }
1016   else if (flags->verbose)
1017     error (0, 0, _("%s: removed"), qoldname);
1018   if (0 <= dir_fd)
1019     {
1020       if (dosync (dir_fd, qdir) != 0)
1021         ok = false;
1022       if (close (dir_fd) != 0)
1023         {
1024           error (0, errno, _("%s: failed to close"), qdir);
1025           ok = false;
1026         }
1027     }
1028   free (newname);
1029   free (dir);
1030   free (qdir);
1031   return ok;
1032 }
1033
1034 /*
1035  * Finally, the function that actually takes a filename and grinds
1036  * it into hamburger.
1037  *
1038  * FIXME
1039  * Detail to note: since we do not restore errno to EACCES after
1040  * a failed chmod, we end up printing the error code from the chmod.
1041  * This is actually the error that stopped us from proceeding, so
1042  * it's arguably the right one, and in practice it'll be either EACCES
1043  * again or EPERM, which both give similar error messages.
1044  * Does anyone disagree?
1045  */
1046 static bool
1047 wipefile (char *name, char const *qname,
1048           struct randint_source *s, struct Options const *flags)
1049 {
1050   bool ok;
1051   int fd;
1052
1053   fd = open (name, O_WRONLY | O_NOCTTY | O_BINARY);
1054   if (fd < 0
1055       && (errno == EACCES && flags->force)
1056       && chmod (name, S_IWUSR) == 0)
1057     fd = open (name, O_WRONLY | O_NOCTTY | O_BINARY);
1058   if (fd < 0)
1059     {
1060       error (0, errno, _("%s: failed to open for writing"), qname);
1061       return false;
1062     }
1063
1064   ok = do_wipefd (fd, qname, s, flags);
1065   if (close (fd) != 0)
1066     {
1067       error (0, errno, _("%s: failed to close"), qname);
1068       ok = false;
1069     }
1070   if (ok && flags->remove_file)
1071     ok = wipename (name, qname, flags);
1072   return ok;
1073 }
1074
1075
1076 /* Buffers for random data.  */
1077 static struct randint_source *randint_source;
1078
1079 /* Just on general principles, wipe buffers containing information
1080    that may be related to the possibly-pseudorandom values used during
1081    shredding.  */
1082 static void
1083 clear_random_data (void)
1084 {
1085   randint_all_free (randint_source);
1086 }
1087
1088
1089 int
1090 main (int argc, char **argv)
1091 {
1092   bool ok = true;
1093   struct Options flags = { 0, };
1094   char **file;
1095   int n_files;
1096   int c;
1097   int i;
1098   char const *random_source = NULL;
1099
1100   initialize_main (&argc, &argv);
1101   set_program_name (argv[0]);
1102   setlocale (LC_ALL, "");
1103   bindtextdomain (PACKAGE, LOCALEDIR);
1104   textdomain (PACKAGE);
1105
1106   atexit (close_stdout);
1107
1108   flags.n_iterations = DEFAULT_PASSES;
1109   flags.size = -1;
1110
1111   while ((c = getopt_long (argc, argv, "fn:s:uvxz", long_opts, NULL)) != -1)
1112     {
1113       switch (c)
1114         {
1115         case 'f':
1116           flags.force = true;
1117           break;
1118
1119         case 'n':
1120           {
1121             uintmax_t tmp;
1122             if (xstrtoumax (optarg, NULL, 10, &tmp, NULL) != LONGINT_OK
1123                 || MIN (UINT32_MAX, SIZE_MAX / sizeof (int)) < tmp)
1124               {
1125                 error (EXIT_FAILURE, 0, _("%s: invalid number of passes"),
1126                        quotearg_colon (optarg));
1127               }
1128             flags.n_iterations = tmp;
1129           }
1130           break;
1131
1132         case RANDOM_SOURCE_OPTION:
1133           if (random_source && !STREQ (random_source, optarg))
1134             error (EXIT_FAILURE, 0, _("multiple random sources specified"));
1135           random_source = optarg;
1136           break;
1137
1138         case 'u':
1139           flags.remove_file = true;
1140           break;
1141
1142         case 's':
1143           {
1144             uintmax_t tmp;
1145             if (xstrtoumax (optarg, NULL, 0, &tmp, "cbBkKMGTPEZY0")
1146                 != LONGINT_OK)
1147               {
1148                 error (EXIT_FAILURE, 0, _("%s: invalid file size"),
1149                        quotearg_colon (optarg));
1150               }
1151             flags.size = tmp;
1152           }
1153           break;
1154
1155         case 'v':
1156           flags.verbose = true;
1157           break;
1158
1159         case 'x':
1160           flags.exact = true;
1161           break;
1162
1163         case 'z':
1164           flags.zero_fill = true;
1165           break;
1166
1167         case_GETOPT_HELP_CHAR;
1168
1169         case_GETOPT_VERSION_CHAR (PROGRAM_NAME, AUTHORS);
1170
1171         default:
1172           usage (EXIT_FAILURE);
1173         }
1174     }
1175
1176   file = argv + optind;
1177   n_files = argc - optind;
1178
1179   if (n_files == 0)
1180     {
1181       error (0, 0, _("missing file operand"));
1182       usage (EXIT_FAILURE);
1183     }
1184
1185   randint_source = randint_all_new (random_source, SIZE_MAX);
1186   if (! randint_source)
1187     error (EXIT_FAILURE, errno, "%s", quotearg_colon (random_source));
1188   atexit (clear_random_data);
1189
1190   for (i = 0; i < n_files; i++)
1191     {
1192       char *qname = xstrdup (quotearg_colon (file[i]));
1193       if (STREQ (file[i], "-"))
1194         {
1195           ok &= wipefd (STDOUT_FILENO, qname, randint_source, &flags);
1196         }
1197       else
1198         {
1199           /* Plain filename - Note that this overwrites *argv! */
1200           ok &= wipefile (file[i], qname, randint_source, &flags);
1201         }
1202       free (qname);
1203     }
1204
1205   exit (ok ? EXIT_SUCCESS : EXIT_FAILURE);
1206 }
1207 /*
1208  * vim:sw=2:sts=2:
1209  */