Please find below a patch (revision 2, 2005-01-29) for dirvish-expire which chmods the tree before attempting rm. This was requested by MichaelTibbetts on DirvishUsers.
I don't know if we should redirect the chmod error stream to /dev/null or not. I guess this would be portable across Unix systems and shells? (something like "2> /dev/null").
Also, I've used the -R and the "X" features of GNU chmod. I don't know if this is portable and/or supported by chmods other than the GNU/Linux flavour. (I use the "X" flag to make sure we give ourselves the permission to list the directories we traverse.)
--- /usr/sbin/dirvish-expire.orig 2004-09-08 23:21:43.000000000 +0200
+++ /usr/sbin/dirvish-expire 2004-09-08 23:22:07.000000000 +0200
@@ -171,14 +171,52 @@
$$Options{'no-run'} and next;
- system("rm -rf $$expire{path}/tree");
+ $exit = system("chmod u+rwX $$expire{path}/tree && find $$expire{path}/tree -type d -exec chmod u+rwX \\{\\} \\;");
+ check_exitcode("Failed to chmod $$expire{path}/tree and subdirectories", "chmod/find", $exit);
+
+ $exit = system("rm -rf $$expire{path}/tree");
+ check_exitcode("Failed to delete $$expire{path}/tree", "rm", $exit);
+
$$Options{tree} and next;
- system("rm -rf $$expire{path}");
+ $exit = system("chmod u+rwX $$expire{path} && find $$expire{path} -type d -exec chmod u+rwX \\{\\} \\;");
+ check_exitcode("Failed to chmod $$expire{path} and subdirectories", "chmod/find", $exit);
+
+ $exit = system("rm -rf $$expire{path}");
+ check_exitcode("Failed to delete $$expire{path}", "rm", $exit);
}
exit 0;
+sub check_exitcode
+{
+ my ($action, $command, $exit) = @_;
+ my $msg = "WARNING: $action. $command ";
+
+ # Code based on the documentation for the system() call in Programming Perl,2nd ed.
+ $exit &= 0xffff;
+
+ if ($exit == 0) {
+ return 1;
+ } elsif ($exit == 0xff00) {
+ $msg .= " failed: $!";
+ } elsif ($exit > 0x80) {
+ $exit >>= 8;
+ $msg .= "exited with status $exit.";
+ } else {
+ $msg .= "failed with ";
+ if ($exit & 0x80) {
+ $exit &= ~0x80;
+ $msg .= "coredump from ";
+ }
+ $msg .= "signal $exit.";
+ }
+
+ print STDERR "$msg\n";
+
+ return 0;
+}
+
sub check_expire
{
my ($summary, $expire_time) = @_;Revision 2 - 2005-01-29 - Fixed bug: backup files were being made u+rwX when a backup image was expired. This made hardlinked images non-hardlinkable with future backups leading to increased disk space usage. The fix consists in only changing permissions on directories: this is sufficient to fulfill the aim of the patch and does not affect hardlinking since you can't hardlink directories anyway.
