12
12
#include "settings-parser.h"
13
13
#include "auth-master.h"
14
14
#include "master-service.h"
15
#include "mountpoint-list.h"
15
16
#include "mail-storage-settings.h"
16
17
#include "mail-storage-private.h"
17
18
#include "mail-namespace.h"
26
27
static void mail_user_deinit_base(struct mail_user *user)
28
29
mail_namespaces_deinit(&user->namespaces);
29
pool_unref(&user->pool);
30
if (user->mountpoints != NULL)
31
mountpoint_list_deinit(&user->mountpoints);
32
34
struct mail_user *mail_user_alloc(const char *username,
48
50
user->set_info = set_info;
49
51
user->unexpanded_set = settings_dup(set_info, set, pool);
50
52
user->set = settings_dup(set_info, set, pool);
53
user->service = master_service_get_name(master_service);
52
55
/* check settings so that the duplicated structure will again
53
56
contain the parsed fields */
94
97
const struct mail_storage_settings *mail_set;
95
98
const char *home, *key, *value;
97
if (user->_home == NULL &&
98
settings_vars_have_key(user->set_info, user->set,
99
'h', "home", &key, &value) &&
100
mail_user_get_home(user, &home) <= 0) {
101
need_home_dir = user->_home == NULL &&
102
settings_vars_have_key(user->set_info, user->set,
103
'h', "home", &key, &value);
105
/* expand mail_home setting before calling mail_user_get_home() */
106
settings_var_expand(user->set_info, user->set,
107
user->pool, mail_user_var_expand_table(user));
109
if (need_home_dir && mail_user_get_home(user, &home) <= 0) {
101
110
*error_r = t_strdup_printf(
102
111
"userdb didn't return a home directory, "
103
112
"but %s used it (%%h): %s", key, value);
107
settings_var_expand(user->set_info, user->set,
108
user->pool, mail_user_var_expand_table(user));
109
116
if (mail_user_expand_plugins_envs(user, error_r) < 0)
136
143
i_assert(user->refcount > 0);
139
if (--user->refcount == 0)
140
user->v.deinit(user);
146
if (user->refcount > 1) {
151
/* call deinit() with refcount=1, otherwise we may assert-crash in
152
mail_user_ref() that is called by some deinit() handler. */
153
user->v.deinit(user);
154
i_assert(user->refcount == 1);
155
pool_unref(&user->pool);
143
158
struct mail_user *mail_user_find(struct mail_user *user, const char *name)
154
void mail_user_set_vars(struct mail_user *user, uid_t uid, const char *service,
169
void mail_user_set_vars(struct mail_user *user, const char *service,
155
170
const struct ip_addr *local_ip,
156
171
const struct ip_addr *remote_ip)
173
i_assert(service != NULL);
159
175
user->service = p_strdup(user->pool, service);
160
176
if (local_ip != NULL && local_ip->family != 0) {
161
177
user->local_ip = p_new(user->pool, struct ip_addr, 1);
202
219
p_strdup(user->pool, net_ip2addr(user->remote_ip));
203
220
tab[7].value = my_pid;
204
221
tab[8].value = p_strdup(user->pool, dec2str(user->uid));
222
tab[9].value = p_strdup(user->pool, dec2str(user->gid));
206
224
user->var_expand_table = tab;
207
225
return user->var_expand_table;
254
int mail_user_get_home(struct mail_user *user, const char **home_r)
272
static int mail_user_userdb_lookup_home(struct mail_user *user)
256
274
struct auth_user_info info;
257
275
struct auth_user_reply reply;
259
277
const char *username, *const *fields;
280
i_assert(!user->home_looked_up);
262
282
memset(&info, 0, sizeof(info));
263
info.service = "lib-storage";
283
info.service = user->service;
264
284
if (user->local_ip != NULL)
265
285
info.local_ip = *user->local_ip;
266
286
if (user->remote_ip != NULL)
267
287
info.remote_ip = *user->remote_ip;
269
if (user->home_looked_up) {
270
*home_r = user->_home;
271
return user->_home != NULL ? 1 : 0;
275
289
if (mail_user_auth_master_conn == NULL)
279
293
ret = auth_master_user_lookup(mail_user_auth_master_conn,
280
294
user->username, &info, userdb_pool,
281
295
&username, &fields);
283
297
auth_user_fields_parse(fields, userdb_pool, &reply);
284
user->_home = ret == 0 ? NULL :
285
p_strdup(user->pool, reply.home);
286
user->home_looked_up = TRUE;
287
ret = user->_home != NULL ? 1 : 0;
288
*home_r = user->_home;
298
user->_home = p_strdup(user->pool, reply.home);
290
300
pool_unref(&userdb_pool);
304
int mail_user_get_home(struct mail_user *user, const char **home_r)
308
if (user->home_looked_up) {
309
*home_r = user->_home;
310
return user->_home != NULL ? 1 : 0;
313
ret = mail_user_userdb_lookup_home(user);
317
if (ret > 0 && user->_home == NULL && *user->set->mail_home != '\0') {
318
/* no home in userdb, fallback to mail_home setting */
319
user->_home = user->set->mail_home;
321
user->home_looked_up = TRUE;
323
*home_r = user->_home;
324
return user->_home != NULL ? 1 : 0;
294
327
bool mail_user_is_plugin_loaded(struct mail_user *user, struct module *module)
296
329
const char *const *plugins;
330
363
const char *home, *path = *pathp;
332
if (mail_user_get_home(user, &home) < 0)
366
/* no need to expand home */
370
if (mail_user_get_home(user, &home) <= 0)
335
373
path = home_expand_tilde(path, home);
356
394
return t_strconcat(net_ip2addr(user->remote_ip), "/",
357
395
str_tabescape(user->username), NULL);
398
bool mail_user_is_path_mounted(struct mail_user *user, const char *path,
399
const char **error_r)
401
struct mountpoint_list_rec *rec;
402
const char *mounts_path;
406
if (user->mountpoints == NULL) {
407
mounts_path = t_strdup_printf("%s/"MOUNTPOINT_LIST_FNAME,
408
user->set->base_dir);
409
user->mountpoints = mountpoint_list_init_readonly(mounts_path);
411
(void)mountpoint_list_refresh(user->mountpoints);
413
rec = mountpoint_list_find(user->mountpoints, path);
414
if (rec == NULL || strcmp(rec->state, MOUNTPOINT_STATE_IGNORE) == 0) {
415
/* we don't have any knowledge of this path's mountpoint.
419
/* record exists for this mountpoint. see if it's mounted */
420
if (mountpoint_list_update_mounted(user->mountpoints) == 0 &&
422
*error_r = t_strdup_printf("Mountpoint %s isn't mounted. "
423
"Mount it or remove it with doveadm mount remove",