|
1 // Copyright (C) 1999,2000 Bruce Guenter <bruceg@em.ca> |
|
2 // |
|
3 // This program is free software; you can redistribute it and/or modify |
|
4 // it under the terms of the GNU General Public License as published by |
|
5 // the Free Software Foundation; either version 2 of the License, or |
|
6 // (at your option) any later version. |
|
7 // |
|
8 // This program is distributed in the hope that it will be useful, |
|
9 // but WITHOUT ANY WARRANTY; without even the implied warranty of |
|
10 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
|
11 // GNU General Public License for more details. |
|
12 // |
|
13 // You should have received a copy of the GNU General Public License |
|
14 // along with this program; if not, write to the Free Software |
|
15 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA |
|
16 |
|
17 #include <config.h> |
|
18 #include "maildir.h" |
|
19 #include <unistd.h> |
|
20 #include <string.h> |
|
21 #include "ac/dirent.h" |
|
22 #include "stat_fns.h" |
|
23 #include "mystring/mystring.h" |
|
24 |
|
25 static inline int rmdir(const mystring& n) |
|
26 { |
|
27 return rmdir(n.c_str()); |
|
28 } |
|
29 |
|
30 int mkdirp(const mystring& dirname, mode_t mode) |
|
31 { |
|
32 if(is_dir(dirname.c_str())) |
|
33 return 0; |
|
34 int i = dirname.find_last('/'); |
|
35 if(i > 0) { |
|
36 if(mkdirp(dirname.left(i), 0755)) |
|
37 return -1; |
|
38 } |
|
39 return mkdir(dirname.c_str(), mode); |
|
40 } |
|
41 |
|
42 bool make_maildir(const mystring& dirname) |
|
43 { |
|
44 if(mkdirp(dirname, 0700)) |
|
45 return false; |
|
46 mystring curdir = dirname + "/cur"; |
|
47 if(mkdir(curdir.c_str(), 0755)) { |
|
48 rmdir(dirname); |
|
49 return false; |
|
50 } |
|
51 mystring newdir = dirname + "/new"; |
|
52 if(mkdir(newdir.c_str(), 0755)) { |
|
53 rmdir(curdir); |
|
54 rmdir(dirname); |
|
55 return false; |
|
56 } |
|
57 mystring tmpdir = dirname + "/tmp"; |
|
58 if(mkdir(tmpdir.c_str(), 0755)) { |
|
59 rmdir(newdir); |
|
60 rmdir(curdir); |
|
61 rmdir(dirname); |
|
62 return false; |
|
63 } |
|
64 return true; |
|
65 } |
|
66 |
|
67 bool delete_directory(const mystring& dirname) |
|
68 { |
|
69 DIR* dir = opendir(dirname.c_str()); |
|
70 if(!dir) |
|
71 return false; |
|
72 while(dirent* entry = readdir(dir)) { |
|
73 const char* name = entry->d_name; |
|
74 if(name[0] == '.' && |
|
75 (NAMLEN(entry) == 1 || |
|
76 (name[1] == '.' && NAMLEN(entry) == 2))) |
|
77 continue; |
|
78 mystring fullname = dirname + "/"; |
|
79 fullname += mystring(name, NAMLEN(entry)); |
|
80 if(is_dir(fullname.c_str())) { |
|
81 if(!delete_directory(fullname)) { |
|
82 closedir(dir); |
|
83 return false; |
|
84 } |
|
85 } |
|
86 else if(unlink(fullname.c_str())) { |
|
87 closedir(dir); |
|
88 return false; |
|
89 } |
|
90 } |
|
91 closedir(dir); |
|
92 return !rmdir(dirname); |
|
93 } |