diff options
Diffstat (limited to 'src/process.c')
-rw-r--r-- | src/process.c | 162 |
1 files changed, 108 insertions, 54 deletions
diff --git a/src/process.c b/src/process.c index c5eb321..ec64589 100644 --- a/src/process.c +++ b/src/process.c | |||
@@ -21,12 +21,26 @@ struct spool_list | |||
21 | struct spool_list *next; | 21 | struct spool_list *next; |
22 | struct spool spool; | 22 | struct spool spool; |
23 | }; | 23 | }; |
24 | 24 | ||
25 | static struct spool_list *spool_list; | 25 | static struct spool_list *spool_list; |
26 | 26 | ||
27 | int | ||
28 | for_each_spool (int (*fun) (struct spool *, void *), void *data) | ||
29 | { | ||
30 | struct spool_list *sp; | ||
31 | |||
32 | for (sp = spool_list; sp; sp = sp->next) | ||
33 | { | ||
34 | int rc = fun (&sp->spool, data); | ||
35 | if (rc) | ||
36 | return rc; | ||
37 | } | ||
38 | return 0; | ||
39 | } | ||
40 | |||
27 | void | 41 | void |
28 | register_spool (struct spool *spool) | 42 | register_spool (struct spool *spool) |
29 | { | 43 | { |
30 | struct spool_list *sp = grecs_malloc (sizeof *sp); | 44 | struct spool_list *sp = grecs_malloc (sizeof *sp); |
31 | sp->spool = *spool; | 45 | sp->spool = *spool; |
32 | sp->next = spool_list; | 46 | sp->next = spool_list; |
@@ -119,28 +133,92 @@ parse_file_name (const char *name, struct file_info *finfo) | |||
119 | return; | 133 | return; |
120 | } | 134 | } |
121 | } | 135 | } |
122 | abort (); /* should not happen */ | 136 | abort (); /* should not happen */ |
123 | } | 137 | } |
124 | 138 | ||
125 | int | 139 | void |
140 | file_info_cleanup (struct file_info *finfo) | ||
141 | { | ||
142 | free (finfo->name); | ||
143 | memset (finfo, 0, sizeof (*finfo)); | ||
144 | } | ||
145 | |||
146 | static int | ||
126 | match_uid_p (uid_t uid, int uc, uid_t *uv) | 147 | match_uid_p (uid_t uid, int uc, uid_t *uv) |
127 | { | 148 | { |
128 | int i; | 149 | int i; |
129 | if (!uv) | 150 | if (!uv) |
130 | return 1; | 151 | return 1; |
131 | for (i = 0; i < uc; i++) | 152 | for (i = 0; i < uc; i++) |
132 | if (uv[i] == uid) | 153 | if (uv[i] == uid) |
133 | return 1; | 154 | return 1; |
134 | return 0; | 155 | return 0; |
135 | } | 156 | } |
136 | 157 | ||
158 | int | ||
159 | spool_cwd_add_new_file (const struct spool *spool, const char *name, | ||
160 | int uc, uid_t *uv) | ||
161 | { | ||
162 | struct stat st; | ||
163 | struct file_info finfo; | ||
164 | |||
165 | if (stat (name, &st)) | ||
166 | { | ||
167 | logmsg (LOG_ERR, _("cannot stat file %s/%s: %s"), | ||
168 | spool->source_dir, name, strerror (errno)); | ||
169 | return -1; | ||
170 | } | ||
171 | |||
172 | if (!S_ISREG (st.st_mode)) | ||
173 | { | ||
174 | logmsg (LOG_NOTICE, _("not a regular file: %s/%s"), | ||
175 | spool->source_dir, name); | ||
176 | return -1; | ||
177 | } | ||
178 | |||
179 | if (!match_uid_p (st.st_uid, uc, uv)) | ||
180 | { | ||
181 | if (debug_level) | ||
182 | logmsg (LOG_DEBUG, _("ignoring file: %s/%s"), | ||
183 | spool->source_dir, name); | ||
184 | return -1; | ||
185 | } | ||
186 | |||
187 | finfo.sb = st; | ||
188 | parse_file_name (name, &finfo); | ||
189 | |||
190 | if (debug_level) | ||
191 | logmsg (LOG_DEBUG, _("found file %s: %s, stem: %.*s"), name, | ||
192 | file_type_str (finfo.type), finfo.root_len, finfo.name); | ||
193 | |||
194 | register_file (&finfo, spool); | ||
195 | return 0; | ||
196 | } | ||
197 | |||
198 | int | ||
199 | spool_add_new_file (const struct spool *spool, const char *name, | ||
200 | int uc, uid_t *uv) | ||
201 | { | ||
202 | if (debug_level) | ||
203 | logmsg (LOG_DEBUG, "%s -> %s, adding %s", spool->source_dir, | ||
204 | mu_url_to_string (spool->dest_url), name); | ||
205 | |||
206 | if (chdir (spool->source_dir)) | ||
207 | { | ||
208 | logmsg (LOG_ERR, _("cannot chdir to %s: %s"), spool->source_dir, | ||
209 | strerror (errno)); | ||
210 | return -1; | ||
211 | } | ||
212 | return spool_cwd_add_new_file (spool, name, uc, uv); | ||
213 | } | ||
214 | |||
137 | /* Scan upload directory from the DPAIR and register all files found | 215 | /* Scan upload directory from the DPAIR and register all files found |
138 | there, forming triplets when possible */ | 216 | there, forming triplets when possible */ |
139 | void | 217 | void |
140 | scan_spool_unlocked (const struct spool *spool, int uc, uid_t *uv) | 218 | scan_spool_unlocked (struct spool *spool, int uc, uid_t *uv) |
141 | { | 219 | { |
142 | DIR *dir; | 220 | DIR *dir; |
143 | struct dirent *ent; | 221 | struct dirent *ent; |
144 | 222 | ||
145 | if (debug_level) | 223 | if (debug_level) |
146 | logmsg (LOG_DEBUG, "%s -> %s", spool->source_dir, | 224 | logmsg (LOG_DEBUG, "%s -> %s", spool->source_dir, |
@@ -163,73 +241,28 @@ scan_spool_unlocked (const struct spool *spool, int uc, uid_t *uv) | |||
163 | 241 | ||
164 | timer_start ("spool"); | 242 | timer_start ("spool"); |
165 | /* FIXME: prefix spool tag with something */ | 243 | /* FIXME: prefix spool tag with something */ |
166 | timer_start (spool->tag); | 244 | timer_start (spool->tag); |
167 | while ((ent = readdir (dir))) | 245 | while ((ent = readdir (dir))) |
168 | { | 246 | { |
169 | struct stat st; | ||
170 | struct file_info finfo; | ||
171 | |||
172 | if (strcmp (ent->d_name, ".") == 0 || strcmp (ent->d_name, "..") == 0) | 247 | if (strcmp (ent->d_name, ".") == 0 || strcmp (ent->d_name, "..") == 0) |
173 | continue; | 248 | continue; |
174 | 249 | spool_cwd_add_new_file (spool, ent->d_name, uc, uv); | |
175 | if (stat (ent->d_name, &st)) | ||
176 | { | ||
177 | logmsg (LOG_ERR, _("cannot stat file %s/%s: %s"), | ||
178 | spool->source_dir, ent->d_name, | ||
179 | strerror (errno)); | ||
180 | continue; | ||
181 | } | ||
182 | |||
183 | if (!S_ISREG (st.st_mode)) | ||
184 | { | ||
185 | logmsg (LOG_NOTICE, _("not a regular file: %s/%s"), | ||
186 | spool->source_dir, ent->d_name); | ||
187 | continue; | ||
188 | } | ||
189 | |||
190 | if (!match_uid_p (st.st_uid, uc, uv)) | ||
191 | { | ||
192 | if (debug_level) | ||
193 | logmsg (LOG_DEBUG, _("ignoring file: %s/%s"), | ||
194 | spool->source_dir, ent->d_name); | ||
195 | continue; | ||
196 | } | ||
197 | |||
198 | finfo.sb = st; | ||
199 | parse_file_name (ent->d_name, &finfo); | ||
200 | |||
201 | if (debug_level) | ||
202 | logmsg (LOG_DEBUG, _("found file %s: %s, stem: %.*s"), ent->d_name, | ||
203 | file_type_str (finfo.type), finfo.root_len, finfo.name); | ||
204 | |||
205 | register_file (&finfo, spool); | ||
206 | } | 250 | } |
207 | 251 | ||
208 | closedir (dir); | 252 | closedir (dir); |
209 | 253 | ||
210 | if (count_collected_triplets () > 0) | 254 | if (count_collected_triplets () > 0) |
211 | { | 255 | spool_commit_triplets (spool); |
212 | int i; | 256 | |
213 | |||
214 | for (i = 0; i < dictionary_count; i++) | ||
215 | { | ||
216 | if (dictionary_init (spool->dictionary[i])) | ||
217 | { | ||
218 | logmsg (LOG_ERR, _("failed to initialize dictionary %d"), i); | ||
219 | return; | ||
220 | } | ||
221 | } | ||
222 | enumerate_triplets (spool); | ||
223 | } | ||
224 | timer_stop (spool->tag); | 257 | timer_stop (spool->tag); |
225 | timer_stop ("spool"); | 258 | timer_stop ("spool"); |
226 | } | 259 | } |
227 | 260 | ||
228 | int | 261 | int |
229 | scan_spool (const struct spool *spool, int uc, uid_t *uv) | 262 | scan_spool (struct spool *spool, int uc, uid_t *uv) |
230 | { | 263 | { |
231 | char *lockfile = wydawca_lockname (spool->tag); | 264 | char *lockfile = wydawca_lockname (spool->tag); |
232 | int rc = wydawca_lock (lockfile); | 265 | int rc = wydawca_lock (lockfile); |
233 | switch (rc) | 266 | switch (rc) |
234 | { | 267 | { |
235 | case LOCK_OK: | 268 | case LOCK_OK: |
@@ -246,18 +279,39 @@ scan_spool (const struct spool *spool, int uc, uid_t *uv) | |||
246 | break; | 279 | break; |
247 | } | 280 | } |
248 | free (lockfile); | 281 | free (lockfile); |
249 | return rc; | 282 | return rc; |
250 | } | 283 | } |
251 | 284 | ||
252 | static void | 285 | int |
253 | close_dictionaries (struct spool *spool) | 286 | spool_open_dictionaries (struct spool *spool) |
287 | { | ||
288 | if (!spool->dict_inited) | ||
289 | { | ||
290 | int i; | ||
291 | |||
292 | for (i = 0; i < dictionary_count; i++) | ||
293 | { | ||
294 | if (dictionary_init (spool->dictionary[i])) | ||
295 | { | ||
296 | logmsg (LOG_ERR, _("failed to initialize dictionary %d"), i); | ||
297 | return -1; | ||