Mercurial > dovecot > original-hg > dovecot-1.2
annotate src/lib-dict/dict-file.c @ 8388:4a608f96609b HEAD
dict-file: Minor optimization when writing the file.
author | Timo Sirainen <tss@iki.fi> |
---|---|
date | Wed, 05 Nov 2008 20:03:05 +0200 |
parents | 54ff30d93cab |
children | 8f083c8482e1 |
rev | line source |
---|---|
8300
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
1 /* Copyright (c) 2008 Dovecot authors, see the included COPYING file */ |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
2 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
3 #include "lib.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
4 #include "array.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
5 #include "hash.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
6 #include "file-dotlock.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
7 #include "nfs-workarounds.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
8 #include "istream.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
9 #include "ostream.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
10 #include "dict-private.h" |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
11 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
12 #include <stdlib.h> |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
13 #include <unistd.h> |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
14 #include <fcntl.h> |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
15 #include <sys/stat.h> |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
16 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
17 struct file_dict { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
18 struct dict dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
19 pool_t hash_pool; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
20 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
21 char *path; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
22 struct hash_table *hash; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
23 int fd; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
24 }; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
25 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
26 struct file_dict_iterate_context { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
27 struct dict_iterate_context ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
28 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
29 struct hash_iterate_context *iter; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
30 char *path; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
31 unsigned int path_len; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
32 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
33 enum dict_iterate_flags flags; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
34 unsigned int failed:1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
35 }; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
36 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
37 enum file_dict_change_type { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
38 FILE_DICT_CHANGE_TYPE_SET, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
39 FILE_DICT_CHANGE_TYPE_UNSET, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
40 FILE_DICT_CHANGE_TYPE_INC |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
41 }; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
42 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
43 struct file_dict_change { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
44 enum file_dict_change_type type; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
45 const char *key; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
46 union { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
47 const char *str; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
48 long long diff; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
49 } value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
50 }; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
51 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
52 struct file_dict_transaction_context { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
53 struct dict_transaction_context ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
54 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
55 pool_t pool; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
56 ARRAY_DEFINE(changes, struct file_dict_change); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
57 }; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
58 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
59 static struct dotlock_settings file_dict_dotlock_settings = { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
60 MEMBER(temp_prefix) NULL, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
61 MEMBER(lock_suffix) NULL, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
62 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
63 MEMBER(timeout) 30, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
64 MEMBER(stale_timeout) 5 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
65 }; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
66 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
67 static struct dict *file_dict_init(struct dict *driver, const char *uri, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
68 enum dict_data_type value_type ATTR_UNUSED, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
69 const char *username ATTR_UNUSED) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
70 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
71 struct file_dict *dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
72 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
73 dict = i_new(struct file_dict, 1); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
74 dict->dict = *driver; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
75 dict->path = i_strdup(uri); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
76 dict->hash_pool = pool_alloconly_create("file dict", 1024); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
77 dict->hash = hash_create(default_pool, dict->hash_pool, 0, str_hash, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
78 (hash_cmp_callback_t *)strcmp); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
79 dict->fd = -1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
80 return &dict->dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
81 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
82 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
83 static void file_dict_deinit(struct dict *_dict) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
84 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
85 struct file_dict *dict = (struct file_dict *)_dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
86 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
87 hash_destroy(&dict->hash); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
88 pool_unref(&dict->hash_pool); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
89 i_free(dict->path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
90 i_free(dict); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
91 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
92 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
93 static bool file_dict_need_refresh(struct file_dict *dict) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
94 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
95 struct stat st1, st2; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
96 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
97 if (dict->fd == -1) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
98 return TRUE; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
99 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
100 nfs_flush_file_handle_cache(dict->path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
101 if (nfs_safe_stat(dict->path, &st1) < 0) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
102 i_error("stat(%s) failed: %m", dict->path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
103 return FALSE; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
104 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
105 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
106 if (fstat(dict->fd, &st2) < 0) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
107 if (errno != ESTALE) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
108 i_error("fstat(%s) failed: %m", dict->path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
109 return TRUE; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
110 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
111 if (st1.st_ino != st2.st_ino || |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
112 !CMP_DEV_T(st1.st_dev, st2.st_dev)) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
113 /* file changed */ |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
114 return TRUE; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
115 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
116 return FALSE; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
117 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
118 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
119 static int file_dict_refresh(struct file_dict *dict) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
120 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
121 struct istream *input; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
122 char *key, *value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
123 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
124 if (!file_dict_need_refresh(dict)) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
125 return 0; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
126 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
127 if (dict->fd != -1) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
128 if (close(dict->fd) < 0) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
129 i_error("close(%s) failed: %m", dict->path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
130 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
131 dict->fd = open(dict->path, O_RDONLY); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
132 if (dict->fd == -1) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
133 if (errno == ENOENT) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
134 return 0; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
135 i_error("open(%s) failed: %m", dict->path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
136 return -1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
137 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
138 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
139 hash_clear(dict->hash, TRUE); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
140 p_clear(dict->hash_pool); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
141 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
142 input = i_stream_create_fd(dict->fd, (size_t)-1, FALSE); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
143 while ((key = i_stream_read_next_line(input)) != NULL && |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
144 (value = i_stream_read_next_line(input)) != NULL) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
145 key = p_strdup(dict->hash_pool, key); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
146 value = p_strdup(dict->hash_pool, value); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
147 hash_insert(dict->hash, key, value); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
148 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
149 i_stream_destroy(&input); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
150 return 0; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
151 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
152 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
153 static int file_dict_lookup(struct dict *_dict, pool_t pool, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
154 const char *key, const char **value_r) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
155 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
156 struct file_dict *dict = (struct file_dict *)_dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
157 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
158 if (file_dict_refresh(dict) < 0) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
159 return -1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
160 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
161 *value_r = p_strdup(pool, hash_lookup(dict->hash, key)); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
162 return *value_r == NULL ? 0 : 1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
163 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
164 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
165 static struct dict_iterate_context * |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
166 file_dict_iterate_init(struct dict *_dict, const char *path, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
167 enum dict_iterate_flags flags) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
168 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
169 struct file_dict_iterate_context *ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
170 struct file_dict *dict = (struct file_dict *)_dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
171 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
172 ctx = i_new(struct file_dict_iterate_context, 1); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
173 ctx->path = i_strdup(path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
174 ctx->path_len = strlen(path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
175 ctx->flags = flags; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
176 ctx->iter = hash_iterate_init(dict->hash); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
177 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
178 if (file_dict_refresh(dict) < 0) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
179 ctx->failed = TRUE; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
180 return &ctx->ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
181 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
182 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
183 static int file_dict_iterate(struct dict_iterate_context *_ctx, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
184 const char **key_r, const char **value_r) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
185 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
186 struct file_dict_iterate_context *ctx = |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
187 (struct file_dict_iterate_context *)_ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
188 void *key, *value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
189 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
190 while (hash_iterate(ctx->iter, &key, &value)) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
191 if (strncmp(ctx->path, key, ctx->path_len) != 0) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
192 continue; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
193 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
194 if ((ctx->flags & DICT_ITERATE_FLAG_RECURSE) == 0 && |
8359 | 195 strchr((char *)key + ctx->path_len, '/') != NULL) |
8300
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
196 continue; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
197 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
198 *key_r = key; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
199 *value_r = value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
200 return 1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
201 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
202 return ctx->failed ? -1 : 0; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
203 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
204 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
205 static void file_dict_iterate_deinit(struct dict_iterate_context *_ctx) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
206 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
207 struct file_dict_iterate_context *ctx = |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
208 (struct file_dict_iterate_context *)_ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
209 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
210 hash_iterate_deinit(&ctx->iter); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
211 i_free(ctx->path); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
212 i_free(ctx); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
213 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
214 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
215 static struct dict_transaction_context * |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
216 file_dict_transaction_init(struct dict *_dict) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
217 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
218 struct file_dict_transaction_context *ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
219 pool_t pool; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
220 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
221 pool = pool_alloconly_create("file dict transaction", 1024); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
222 ctx = p_new(pool, struct file_dict_transaction_context, 1); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
223 ctx->ctx.dict = _dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
224 ctx->pool = pool; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
225 p_array_init(&ctx->changes, pool, 32); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
226 return &ctx->ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
227 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
228 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
229 static void file_dict_apply_changes(struct file_dict_transaction_context *ctx) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
230 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
231 struct file_dict *dict = (struct file_dict *)ctx->ctx.dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
232 const char *tmp; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
233 char *key, *value, *old_value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
234 void *orig_key, *orig_value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
235 const struct file_dict_change *changes; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
236 unsigned int i, count, new_len; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
237 long long diff; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
238 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
239 changes = array_get(&ctx->changes, &count); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
240 for (i = 0; i < count; i++) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
241 if (hash_lookup_full(dict->hash, changes[i].key, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
242 &orig_key, &orig_value)) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
243 key = orig_key; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
244 old_value = orig_value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
245 } else { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
246 key = NULL; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
247 old_value = NULL; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
248 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
249 value = NULL; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
250 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
251 switch (changes[i].type) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
252 case FILE_DICT_CHANGE_TYPE_INC: |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
253 diff = old_value == NULL ? 0 : |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
254 strtoll(old_value, NULL, 10); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
255 diff += changes[i].value.diff; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
256 tmp = t_strdup_printf("%lld", diff); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
257 new_len = strlen(tmp); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
258 if (new_len > strlen(old_value)) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
259 value = p_strdup(dict->hash_pool, tmp); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
260 else { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
261 memcpy(old_value, tmp, new_len + 1); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
262 value = old_value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
263 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
264 /* fall through */ |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
265 case FILE_DICT_CHANGE_TYPE_SET: |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
266 if (key == NULL) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
267 key = p_strdup(dict->hash_pool, changes[i].key); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
268 if (value == NULL) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
269 value = p_strdup(dict->hash_pool, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
270 changes[i].value.str); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
271 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
272 hash_update(dict->hash, key, value); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
273 break; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
274 case FILE_DICT_CHANGE_TYPE_UNSET: |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
275 if (old_value != NULL) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
276 hash_remove(dict->hash, key); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
277 break; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
278 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
279 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
280 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
281 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
282 static int file_dict_write_changes(struct file_dict_transaction_context *ctx) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
283 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
284 struct file_dict *dict = (struct file_dict *)ctx->ctx.dict; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
285 struct dotlock *dotlock; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
286 struct hash_iterate_context *iter; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
287 struct ostream *output; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
288 void *key, *value; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
289 int fd; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
290 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
291 fd = file_dotlock_open(&file_dict_dotlock_settings, dict->path, 0, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
292 &dotlock); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
293 if (fd == -1) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
294 i_error("file dict commit: file_dotlock_open() failed: %m"); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
295 return -1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
296 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
297 /* refresh once more now that we're locked */ |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
298 if (file_dict_refresh(dict) < 0) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
299 file_dotlock_delete(&dotlock); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
300 return -1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
301 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
302 file_dict_apply_changes(ctx); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
303 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
304 output = o_stream_create_fd(fd, 0, FALSE); |
8388
4a608f96609b
dict-file: Minor optimization when writing the file.
Timo Sirainen <tss@iki.fi>
parents:
8359
diff
changeset
|
305 o_stream_cork(output); |
8300
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
306 iter = hash_iterate_init(dict->hash); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
307 while (hash_iterate(iter, &key, &value)) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
308 o_stream_send_str(output, key); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
309 o_stream_send(output, "\n", 1); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
310 o_stream_send_str(output, value); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
311 o_stream_send(output, "\n", 1); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
312 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
313 hash_iterate_deinit(&iter); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
314 o_stream_destroy(&output); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
315 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
316 if (file_dotlock_replace(&dotlock, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
317 DOTLOCK_REPLACE_FLAG_DONT_CLOSE_FD) < 0) { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
318 (void)close(fd); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
319 return -1; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
320 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
321 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
322 if (dict->fd != -1) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
323 (void)close(dict->fd); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
324 dict->fd = fd; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
325 return 0; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
326 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
327 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
328 static int file_dict_transaction_commit(struct dict_transaction_context *_ctx) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
329 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
330 struct file_dict_transaction_context *ctx = |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
331 (struct file_dict_transaction_context *)_ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
332 int ret; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
333 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
334 ret = file_dict_write_changes(ctx); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
335 pool_unref(&ctx->pool); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
336 return ret; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
337 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
338 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
339 static void file_dict_transaction_rollback(struct dict_transaction_context *_ctx) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
340 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
341 struct file_dict_transaction_context *ctx = |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
342 (struct file_dict_transaction_context *)_ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
343 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
344 pool_unref(&ctx->pool); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
345 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
346 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
347 static void file_dict_set(struct dict_transaction_context *_ctx, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
348 const char *key, const char *value) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
349 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
350 struct file_dict_transaction_context *ctx = |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
351 (struct file_dict_transaction_context *)_ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
352 struct file_dict_change *change; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
353 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
354 change = array_append_space(&ctx->changes); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
355 change->type = FILE_DICT_CHANGE_TYPE_SET; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
356 change->key = p_strdup(ctx->pool, key); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
357 change->value.str = p_strdup(ctx->pool, value); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
358 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
359 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
360 static void file_dict_unset(struct dict_transaction_context *_ctx, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
361 const char *key) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
362 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
363 struct file_dict_transaction_context *ctx = |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
364 (struct file_dict_transaction_context *)_ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
365 struct file_dict_change *change; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
366 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
367 change = array_append_space(&ctx->changes); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
368 change->type = FILE_DICT_CHANGE_TYPE_UNSET; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
369 change->key = p_strdup(ctx->pool, key); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
370 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
371 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
372 static void |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
373 file_dict_atomic_inc(struct dict_transaction_context *_ctx, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
374 const char *key, long long diff) |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
375 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
376 struct file_dict_transaction_context *ctx = |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
377 (struct file_dict_transaction_context *)_ctx; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
378 struct file_dict_change *change; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
379 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
380 change = array_append_space(&ctx->changes); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
381 change->type = FILE_DICT_CHANGE_TYPE_INC; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
382 change->key = p_strdup(ctx->pool, key); |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
383 change->value.diff = diff; |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
384 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
385 |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
386 struct dict dict_driver_file = { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
387 MEMBER(name) "file", |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
388 { |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
389 file_dict_init, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
390 file_dict_deinit, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
391 file_dict_lookup, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
392 file_dict_iterate_init, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
393 file_dict_iterate, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
394 file_dict_iterate_deinit, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
395 file_dict_transaction_init, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
396 file_dict_transaction_commit, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
397 file_dict_transaction_rollback, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
398 file_dict_set, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
399 file_dict_unset, |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
400 file_dict_atomic_inc |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
401 } |
9d963e3bbe65
Added a simple flat file dict backend.
Timo Sirainen <tss@iki.fi>
parents:
diff
changeset
|
402 }; |