Mercurial > dovecot > original-hg > dovecot-1.2
annotate src/lib-storage/mail-error.c @ 8642:dd53d40a2f09 HEAD
Permission denied error handling can now suggest missing +w permissions.
author | Timo Sirainen <tss@iki.fi> |
---|---|
date | Fri, 16 Jan 2009 12:45:06 -0500 |
parents | 02ba04b6aa07 |
children | 97a350198a4f |
rev | line source |
---|---|
8590
b9faf4db2a9f
Updated copyright notices to include year 2009.
Timo Sirainen <tss@iki.fi>
parents:
8518
diff
changeset
|
1 /* Copyright (c) 2007-2009 Dovecot authors, see the included COPYING file */ |
5613 | 2 |
3 #include "lib.h" | |
8518
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
4 #include "str.h" |
5613 | 5 #include "mail-error.h" |
6 | |
8518
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
7 #include <sys/stat.h> |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
8 #include <unistd.h> |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
9 #include <pwd.h> |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
10 #include <grp.h> |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
11 |
5613 | 12 bool mail_error_from_errno(enum mail_error *error_r, |
13 const char **error_string_r) | |
14 { | |
15 if (ENOACCESS(errno)) { | |
16 *error_r = MAIL_ERROR_PERM; | |
17 *error_string_r = MAIL_ERRSTR_NO_PERMISSION; | |
18 } else if (ENOSPACE(errno)) { | |
19 *error_r = MAIL_ERROR_NOSPACE; | |
20 *error_string_r = MAIL_ERRSTR_NO_SPACE; | |
21 } else if (ENOTFOUND(errno)) { | |
22 *error_r = MAIL_ERROR_NOTFOUND; | |
23 *error_string_r = errno != ELOOP ? "Not found" : | |
24 "Directory structure is broken"; | |
25 } else { | |
26 return FALSE; | |
27 } | |
28 return TRUE; | |
29 } | |
8518
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
30 |
8642
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
31 static const char * |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
32 mail_error_eacces_msg_full(const char *func, const char *path, bool creating) |
8518
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
33 { |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
34 const char *prev_path = path, *dir = "/", *p; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
35 const struct passwd *pw; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
36 const struct group *group; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
37 string_t *errmsg; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
38 struct stat st; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
39 int ret = -1; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
40 |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
41 errmsg = t_str_new(256); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
42 str_printfa(errmsg, "%s(%s) failed: Permission denied (euid=%s", |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
43 func, path, dec2str(geteuid())); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
44 |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
45 pw = getpwuid(geteuid()); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
46 if (pw != NULL) |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
47 str_printfa(errmsg, "(%s)", pw->pw_name); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
48 |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
49 str_printfa(errmsg, " egid=%s", dec2str(getegid())); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
50 group = getgrgid(getegid()); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
51 if (group != NULL) |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
52 str_printfa(errmsg, "(%s)", group->gr_name); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
53 |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
54 while ((p = strrchr(prev_path, '/')) != NULL) { |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
55 dir = t_strdup_until(prev_path, p); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
56 ret = stat(dir, &st); |
8642
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
57 if (ret == 0) |
8518
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
58 break; |
8642
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
59 if (errno == EACCES) { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
60 /* see if we have access to parent directory */ |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
61 } else if (errno == ENOENT && creating) { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
62 /* probably mkdir_parents() failed here, find the first |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
63 parent directory we couldn't create */ |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
64 } else { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
65 /* some other error, can't handle it */ |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
66 str_printfa(errmsg, " stat(%s) failed: %m", dir); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
67 break; |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
68 } |
8518
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
69 prev_path = dir; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
70 dir = "/"; |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
71 } |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
72 |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
73 if (ret == 0) { |
8642
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
74 /* dir is the first parent directory we can stat() */ |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
75 if (access(dir, X_OK) < 0) { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
76 if (errno == EACCES) |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
77 str_printfa(errmsg, " missing +x perm: %s", dir); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
78 else |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
79 str_printfa(errmsg, " access(%s, x) failed: %m", dir); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
80 } else if (prev_path == path && access(path, R_OK) < 0) { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
81 if (errno == EACCES) |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
82 str_printfa(errmsg, " missing +r perm: %s", path); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
83 else |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
84 str_printfa(errmsg, " access(%s, r) failed: %m", path); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
85 } else if (creating && access(dir, W_OK) < 0) { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
86 if (errno == EACCES) |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
87 str_printfa(errmsg, " missing +w perm: %s", dir); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
88 else |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
89 str_printfa(errmsg, " access(%s, w) failed: %m", dir); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
90 } else |
8641
02ba04b6aa07
Fix to previous commit to actually compile..
Timo Sirainen <tss@iki.fi>
parents:
8640
diff
changeset
|
91 str_printfa(errmsg, " UNIX perms seem ok, ACL problem?"); |
8518
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
92 } |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
93 str_append_c(errmsg, ')'); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
94 return str_c(errmsg); |
1e42b631f037
Improved "Permission denied" error handling. It'll now show also the uid/gid name.
Timo Sirainen <tss@iki.fi>
parents:
7086
diff
changeset
|
95 } |
8642
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
96 |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
97 const char *mail_error_eacces_msg(const char *func, const char *path) |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
98 { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
99 return mail_error_eacces_msg_full(func, path, FALSE); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
100 } |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
101 |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
102 const char *mail_error_create_eacces_msg(const char *func, const char *path) |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
103 { |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
104 return mail_error_eacces_msg_full(func, path, TRUE); |
dd53d40a2f09
Permission denied error handling can now suggest missing +w permissions.
Timo Sirainen <tss@iki.fi>
parents:
8641
diff
changeset
|
105 } |