Apache HTTPD
mod_socache_dbm.c
Go to the documentation of this file.
1/* Licensed to the Apache Software Foundation (ASF) under one or more
2 * contributor license agreements. See the NOTICE file distributed with
3 * this work for additional information regarding copyright ownership.
4 * The ASF licenses this file to You under the Apache License, Version 2.0
5 * (the "License"); you may not use this file except in compliance with
6 * the License. You may obtain a copy of the License at
7 *
8 * http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#include "httpd.h"
18#include "http_log.h"
19#include "http_request.h"
20#include "http_protocol.h"
21#include "http_config.h"
22#include "mpm_common.h"
23#include "mod_status.h"
24
25#include "apr.h"
26#include "apr_strings.h"
27#include "apr_time.h"
28#define APR_WANT_STRFUNC
29#include "apr_want.h"
30#include "apr_dbm.h"
31
32#if APR_HAVE_UNISTD_H
33#include <unistd.h>
34#endif
35
36#include "ap_socache.h"
37
38#if AP_NEED_SET_MUTEX_PERMS
39#include "unixd.h"
40#endif
41
42/* Use of the context structure must be thread-safe after the initial
43 * create/init; callers must hold the mutex. */
45 const char *data_file;
46 /* Pool must only be used with the mutex held. */
50};
51
55#define DBM_FILE_MODE ( APR_UREAD | APR_UWRITE | APR_GREAD | APR_WREAD )
56
57#define DEFAULT_DBM_PREFIX "socache-dbm-"
58
59/* ### this should use apr_dbm_usednames. */
60#if !defined(DBM_FILE_SUFFIX_DIR) && !defined(DBM_FILE_SUFFIX_PAG)
61#if defined(DBM_SUFFIX)
62#define DBM_FILE_SUFFIX_DIR DBM_SUFFIX
63#define DBM_FILE_SUFFIX_PAG DBM_SUFFIX
64#elif defined(__FreeBSD__) || (defined(DB_LOCK) && defined(DB_SHMEM))
65#define DBM_FILE_SUFFIX_DIR ".db"
66#define DBM_FILE_SUFFIX_PAG ".db"
67#else
68#define DBM_FILE_SUFFIX_DIR ".dir"
69#define DBM_FILE_SUFFIX_PAG ".pag"
70#endif
71#endif
72
74
76 server_rec *s, const unsigned char *id,
77 unsigned int idlen, apr_pool_t *p);
78
80 const char *arg,
81 apr_pool_t *tmp, apr_pool_t *p)
82{
84
85 *context = ctx = apr_pcalloc(p, sizeof *ctx);
86
87 if (arg && *arg) {
88 ctx->data_file = ap_server_root_relative(p, arg);
89 if (!ctx->data_file) {
90 return apr_psprintf(tmp, "Invalid cache file path %s", arg);
91 }
92 }
93
94 apr_pool_create(&ctx->pool, p);
95 apr_pool_tag(ctx->pool, "socache_dbm_instance");
96
97 return NULL;
98}
99
100#if AP_NEED_SET_MUTEX_PERMS
101static int try_chown(apr_pool_t *p, server_rec *s,
102 const char *name, const char *suffix)
103{
104 if (suffix)
106 if (-1 == chown(name, ap_unixd_config.user_id,
107 (gid_t)-1 /* no gid change */ ))
108 {
109 if (errno != ENOENT)
111 "Can't change owner of %s", name);
112 return -1;
113 }
114 return 0;
115}
116#endif
117
118
120 const char *namespace,
121 const struct ap_socache_hints *hints,
123{
124#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
126 const apu_err_t *err;
127#endif
128 apr_dbm_t *dbm;
129 apr_status_t rv;
130
131 /* for the DBM we need the data file */
132 if (ctx->data_file == NULL) {
133 const char *path = apr_pstrcat(p, DEFAULT_DBM_PREFIX, namespace,
134 NULL);
135
136 ctx->data_file = ap_runtime_dir_relative(p, path);
137
138 if (ctx->data_file == NULL) {
140 "could not use default path '%s' for DBM socache",
141 path);
142 return APR_EINVAL;
143 }
144 }
145
146 /* open it once to create it and to make sure it _can_ be created */
147 apr_pool_clear(ctx->pool);
148
149#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
150 if ((rv = apr_dbm_get_driver(&driver, NULL, &err,
151 ctx->pool) != APR_SUCCESS) {
152 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(10277)
153 "Cannot load socache DBM library '%s': %s",
154 err->reason, err->msg);
155 return rv;
156 }
157 if ((rv = apr_dbm_open2(&dbm, driver, ctx->data_file,
159 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00804)
160 "Cannot create socache DBM file `%s'",
161 ctx->data_file);
162 return DECLINED;
163 }
164#else
165 if ((rv = apr_dbm_open(&dbm, ctx->data_file,
167 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00804)
168 "Cannot create socache DBM file `%s'",
169 ctx->data_file);
170 return rv;
171 }
172#endif
174
175 ctx->expiry_interval = (hints && hints->expiry_interval
176 ? hints->expiry_interval : apr_time_from_sec(30));
177
178#if AP_NEED_SET_MUTEX_PERMS
179 /*
180 * We have to make sure the Apache child processes have access to
181 * the DBM file. But because there are brain-dead platforms where we
182 * cannot exactly determine the suffixes we try all possibilities.
183 */
184 if (geteuid() == 0 /* is superuser */) {
185 try_chown(p, s, ctx->data_file, NULL);
186 if (try_chown(p, s, ctx->data_file, DBM_FILE_SUFFIX_DIR))
187 if (try_chown(p, s, ctx->data_file, ".db"))
188 try_chown(p, s, ctx->data_file, ".dir");
189 if (try_chown(p, s, ctx->data_file, DBM_FILE_SUFFIX_PAG))
190 if (try_chown(p, s, ctx->data_file, ".db"))
191 try_chown(p, s, ctx->data_file, ".pag");
192 }
193#endif
195
196 return APR_SUCCESS;
197}
198
200{
201 /* the correct way */
202 unlink(apr_pstrcat(ctx->pool, ctx->data_file, DBM_FILE_SUFFIX_DIR, NULL));
203 unlink(apr_pstrcat(ctx->pool, ctx->data_file, DBM_FILE_SUFFIX_PAG, NULL));
204 /* the additional ways to be sure */
205 unlink(apr_pstrcat(ctx->pool, ctx->data_file, ".dir", NULL));
206 unlink(apr_pstrcat(ctx->pool, ctx->data_file, ".pag", NULL));
207 unlink(apr_pstrcat(ctx->pool, ctx->data_file, ".db", NULL));
208 unlink(ctx->data_file);
209}
210
212 server_rec *s, const unsigned char *id,
213 unsigned int idlen, apr_time_t expiry,
214 unsigned char *ucaData,
215 unsigned int nData, apr_pool_t *pool)
216{
217#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
219 const apu_err_t *err;
220#endif
221 apr_dbm_t *dbm;
224 apr_status_t rv;
225
226 /* be careful: do not try to store too much bytes in a DBM file! */
227#ifdef PAIRMAX
228 if ((idlen + nData) >= PAIRMAX) {
230 "data size too large for DBM socache: %d >= %d",
231 (idlen + nData), PAIRMAX);
232 return APR_ENOSPC;
233 }
234#else
235 if ((idlen + nData) >= 950 /* at least less than approx. 1KB */) {
237 "data size too large for DBM socache: %d >= %d",
238 (idlen + nData), 950);
239 return APR_ENOSPC;
240 }
241#endif
242
243 /* create DBM key */
244 dbmkey.dptr = (char *)id;
245 dbmkey.dsize = idlen;
246
247 /* create DBM value */
248 dbmval.dsize = sizeof(apr_time_t) + nData;
249 dbmval.dptr = (char *)ap_malloc(dbmval.dsize);
250 memcpy((char *)dbmval.dptr, &expiry, sizeof(apr_time_t));
251 memcpy((char *)dbmval.dptr+sizeof(apr_time_t), ucaData, nData);
252
253 /* and store it to the DBM file */
254 apr_pool_clear(ctx->pool);
255
256#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
257 if ((rv = apr_dbm_get_driver(&driver, NULL, &err,
258 ctx->pool) != APR_SUCCESS) {
259 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(10278)
260 "Cannot load socache DBM library '%s' (store): %s",
261 err->reason, err->msg);
262 free(dbmval.dptr);
263 return rv;
264 }
265 if ((rv = apr_dbm_open2(&dbm, driver, ctx->data_file,
267 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00807)
268 "Cannot open socache DBM file `%s' for writing "
269 "(store)",
270 ctx->data_file);
271 free(dbmval.dptr);
272 return rv;
273 }
274#else
275 if ((rv = apr_dbm_open(&dbm, ctx->data_file,
277 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00807)
278 "Cannot open socache DBM file `%s' for writing "
279 "(store)",
280 ctx->data_file);
281 free(dbmval.dptr);
282 return rv;
283 }
284#endif
287 "Cannot store socache object to DBM file `%s'",
288 ctx->data_file);
290 free(dbmval.dptr);
291 return rv;
292 }
294
295 /* free temporary buffers */
296 free(dbmval.dptr);
297
298 /* allow the regular expiring to occur */
300
301 return APR_SUCCESS;
302}
303
305 const unsigned char *id, unsigned int idlen,
306 unsigned char *dest, unsigned int *destlen,
307 apr_pool_t *p)
308{
309#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
311 const apu_err_t *err;
312#endif
313 apr_dbm_t *dbm;
316 unsigned int nData;
317 apr_time_t expiry;
320
321 /* allow the regular expiring to occur */
323
324 /* create DBM key and values */
325 dbmkey.dptr = (char *)id;
326 dbmkey.dsize = idlen;
327
328 /* and fetch it from the DBM file
329 * XXX: Should we open the dbm against r->pool so the cleanup will
330 * do the apr_dbm_close? This would make the code a bit cleaner.
331 */
332 apr_pool_clear(ctx->pool);
333#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
334 if ((rv = apr_dbm_get_driver(&driver, NULL, &err,
335 ctx->pool) != APR_SUCCESS) {
336 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(10279)
337 "Cannot load socache DBM library '%s' (fetch): %s",
338 err->reason, err->msg);
339 return rc;
340 }
341 if ((rv = apr_dbm_open2(&dbm, driver, ctx->data_file,
343 ap_log_error(APLOG_MARK, APLOG_ERR, rc, s, APLOGNO(00809)
344 "Cannot open socache DBM file `%s' for reading "
345 "(fetch)",
346 ctx->data_file);
347 return rc;
348 }
349#else
350 if ((rc = apr_dbm_open(&dbm, ctx->data_file, APR_DBM_RWCREATE,
351 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
352 ap_log_error(APLOG_MARK, APLOG_ERR, rc, s, APLOGNO(00809)
353 "Cannot open socache DBM file `%s' for reading "
354 "(fetch)",
355 ctx->data_file);
356 return rc;
357 }
358#endif
360 if (rc != APR_SUCCESS) {
362 return APR_NOTFOUND;
363 }
364 if (dbmval.dptr == NULL || dbmval.dsize <= sizeof(apr_time_t)) {
366 return APR_EGENERAL;
367 }
368
369 /* parse resulting data */
370 nData = dbmval.dsize-sizeof(apr_time_t);
371 if (nData > *destlen) {
373 return APR_ENOSPC;
374 }
375
376 *destlen = nData;
377 memcpy(&expiry, dbmval.dptr, sizeof(apr_time_t));
378 memcpy(dest, (char *)dbmval.dptr + sizeof(apr_time_t), nData);
379
381
382 /* make sure the stuff is still not expired */
383 now = apr_time_now();
384 if (expiry <= now) {
386 return APR_NOTFOUND;
387 }
388
389 return APR_SUCCESS;
390}
391
393 server_rec *s, const unsigned char *id,
394 unsigned int idlen, apr_pool_t *p)
395{
396#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
398 const apu_err_t *err;
399#endif
400 apr_dbm_t *dbm;
402 apr_status_t rv;
403
404 /* create DBM key and values */
405 dbmkey.dptr = (char *)id;
406 dbmkey.dsize = idlen;
407
408 /* and delete it from the DBM file */
409 apr_pool_clear(ctx->pool);
410
411#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
412 if ((rv = apr_dbm_get_driver(&driver, NULL, &err,
413 ctx->pool) != APR_SUCCESS) {
414 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(10280)
415 "Cannot load socache DBM library '%s' (delete): %s",
416 err->reason, err->msg);
417 return rv;
418 }
419 if ((rv = apr_dbm_open2(&dbm, driver, ctx->data_file,
421 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00810)
422 "Cannot open socache DBM file `%s' for writing "
423 "(delete)",
424 ctx->data_file);
425 return rv;
426 }
427#else
428 if ((rv = apr_dbm_open(&dbm, ctx->data_file, APR_DBM_RWCREATE,
429 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
430 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00810)
431 "Cannot open socache DBM file `%s' for writing "
432 "(delete)",
433 ctx->data_file);
434 return rv;
435 }
436#endif
439
440 return APR_SUCCESS;
441}
442
444{
445#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
447 const apu_err_t *err;
448#endif
449 apr_dbm_t *dbm;
452 apr_time_t expiry;
453 int elts = 0;
454 int deleted = 0;
455 int expired;
457 int keyidx;
458 int i;
460 apr_status_t rv;
461
462 /*
463 * make sure the expiration for still not-accessed
464 * socache entries is done only from time to time
465 */
466 now = apr_time_now();
467
468 if (now < ctx->last_expiry + ctx->expiry_interval) {
469 return;
470 }
471
472 ctx->last_expiry = now;
473
474#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
475 if ((rv = apr_dbm_get_driver(&driver, NULL, &err,
476 ctx->pool) != APR_SUCCESS) {
477 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(10281)
478 "Cannot load socache DBM library '%s' (expire): %s",
479 err->reason, err->msg);
480 return rv;
481 }
482#endif
483
484 /*
485 * Here we have to be very carefully: Not all DBM libraries are
486 * smart enough to allow one to iterate over the elements and at the
487 * same time delete expired ones. Some of them get totally crazy
488 * while others have no problems. So we have to do it the slower but
489 * more safe way: we first iterate over all elements and remember
490 * those which have to be expired. Then in a second pass we delete
491 * all those expired elements. Additionally we reopen the DBM file
492 * to be really safe in state.
493 */
494
495#define KEYMAX 1024
496
497 for (;;) {
498 /* allocate the key array in a memory sub pool */
499 apr_pool_clear(ctx->pool);
500
501 if ((keylist = apr_palloc(ctx->pool, sizeof(dbmkey)*KEYMAX)) == NULL) {
502 break;
503 }
504
505 /* pass 1: scan DBM database */
506 keyidx = 0;
507#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
508 if ((rv = apr_dbm_open2(&dbm, driver, ctx->data_file, APR_DBM_RWCREATE,
509 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
511 "Cannot open socache DBM file `%s' for "
512 "scanning",
513 ctx->data_file);
514 break;
515 }
516#else
517 if ((rv = apr_dbm_open(&dbm, ctx->data_file, APR_DBM_RWCREATE,
518 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
520 "Cannot open socache DBM file `%s' for "
521 "scanning",
522 ctx->data_file);
523 break;
524 }
525#endif
527 while (dbmkey.dptr != NULL) {
528 elts++;
529 expired = FALSE;
531 if (dbmval.dsize <= sizeof(apr_time_t) || dbmval.dptr == NULL)
532 expired = TRUE;
533 else {
534 memcpy(&expiry, dbmval.dptr, sizeof(apr_time_t));
535 if (expiry <= now)
536 expired = TRUE;
537 }
538 if (expired) {
539 if ((keylist[keyidx].dptr = apr_pmemdup(ctx->pool, dbmkey.dptr, dbmkey.dsize)) != NULL) {
540 keylist[keyidx].dsize = dbmkey.dsize;
541 keyidx++;
542 if (keyidx == KEYMAX)
543 break;
544 }
545 }
547 }
549
550 /* pass 2: delete expired elements */
551#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
552 if (apr_dbm_open2(&dbm, driver, ctx->data_file, APR_DBM_RWCREATE,
553 DBM_FILE_MODE, ctx->pool) != APR_SUCCESS) {
555 "Cannot re-open socache DBM file `%s' for "
556 "expiring",
557 ctx->data_file);
558 break;
559 }
560#else
561 if (apr_dbm_open(&dbm, ctx->data_file, APR_DBM_RWCREATE,
562 DBM_FILE_MODE, ctx->pool) != APR_SUCCESS) {
564 "Cannot re-open socache DBM file `%s' for "
565 "expiring",
566 ctx->data_file);
567 break;
568 }
569#endif
570 for (i = 0; i < keyidx; i++) {
572 deleted++;
573 }
575
576 if (keyidx < KEYMAX)
577 break;
578 }
579
581 "DBM socache expiry: "
582 "old: %d, new: %d, removed: %d",
583 elts, elts-deleted, deleted);
584}
585
587 int flags)
588{
589#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
591 const apu_err_t *err;
592#endif
593 apr_dbm_t *dbm;
596 int elts;
597 long size;
598 int avg;
599 apr_status_t rv;
600
601 elts = 0;
602 size = 0;
603
604 apr_pool_clear(ctx->pool);
605#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
606 if ((rv = apr_dbm_get_driver(&driver, NULL, &err,
607 ctx->pool) != APR_SUCCESS) {
608 ap_log_rerror(APLOG_MARK, APLOG_ERR, rv, r, APLOGNO(10282)
609 "Cannot load socache DBM library '%s' (status retrieval): %s",
610 err->reason, err->msg);
611 return;
612 }
613 if ((rv = apr_dbm_open2(&dbm, driver, ctx->data_file, APR_DBM_RWCREATE,
614 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
615 ap_log_rerror(APLOG_MARK, APLOG_ERR, rv, r, APLOGNO(00814)
616 "Cannot open socache DBM file `%s' for status "
617 "retrieval",
618 ctx->data_file);
619 return;
620 }
621#else
622 if ((rv = apr_dbm_open(&dbm, ctx->data_file, APR_DBM_RWCREATE,
623 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
624 ap_log_rerror(APLOG_MARK, APLOG_ERR, rv, r, APLOGNO(00814)
625 "Cannot open socache DBM file `%s' for status "
626 "retrieval",
627 ctx->data_file);
628 return;
629 }
630#endif
631 /*
632 * XXX - Check the return value of apr_dbm_firstkey, apr_dbm_fetch - TBD
633 */
635 for ( ; dbmkey.dptr != NULL; apr_dbm_nextkey(dbm, &dbmkey)) {
637 if (dbmval.dptr == NULL)
638 continue;
639 elts += 1;
640 size += dbmval.dsize;
641 }
643 if (size > 0 && elts > 0)
644 avg = (int)(size / (long)elts);
645 else
646 avg = 0;
647 if (!(flags & AP_STATUS_SHORT)) {
648 ap_rprintf(r, "cache type: <b>DBM</b>, maximum size: <b>unlimited</b><br>");
649 ap_rprintf(r, "current entries: <b>%d</b>, current size: <b>%ld</b> bytes<br>", elts, size);
650 ap_rprintf(r, "average entry size: <b>%d</b> bytes<br>", avg);
651 }
652 else {
653 ap_rputs("CacheType: DBM\n", r);
654 ap_rputs("CacheMaximumSize: unlimited\n", r);
655 ap_rprintf(r, "CacheCurrentEntries: %d\n", elts);
656 ap_rprintf(r, "CacheCurrentSize: %ld\n", size);
657 ap_rprintf(r, "CacheAvgEntrySize: %d\n", avg);
658 }
659}
660
662 server_rec *s, void *userctx,
663 ap_socache_iterator_t *iterator,
665{
666#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
668 const apu_err_t *err;
669#endif
670 apr_dbm_t *dbm;
673 apr_time_t expiry;
674 int expired;
676 apr_status_t rv;
677
678 /*
679 * make sure the expired records are omitted
680 */
681 now = apr_time_now();
682#if APU_MAJOR_VERSION > 1 || (APU_MAJOR_VERSION == 1 && APU_MINOR_VERSION >= 7)
683 if ((rv = apr_dbm_get_driver(&driver, NULL, &err,
684 ctx->pool) != APR_SUCCESS) {
685 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(10283)
686 "Cannot load socache DBM library '%s' (iterating): %s",
687 err->reason, err->msg);
688 return rv;
689 }
690 if ((rv = apr_dbm_open2(&dbm, driver, ctx->data_file, APR_DBM_RWCREATE,
691 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
692 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00815)
693 "Cannot open socache DBM file `%s' for "
694 "iterating", ctx->data_file);
695 return rv;
696 }
697#else
698 if ((rv = apr_dbm_open(&dbm, ctx->data_file, APR_DBM_RWCREATE,
699 DBM_FILE_MODE, ctx->pool)) != APR_SUCCESS) {
700 ap_log_error(APLOG_MARK, APLOG_ERR, rv, s, APLOGNO(00815)
701 "Cannot open socache DBM file `%s' for "
702 "iterating", ctx->data_file);
703 return rv;
704 }
705#endif
707 while (rv == APR_SUCCESS && dbmkey.dptr != NULL) {
708 expired = FALSE;
709 apr_dbm_fetch(dbm, dbmkey, &dbmval);
710 if (dbmval.dsize <= sizeof(apr_time_t) || dbmval.dptr == NULL)
711 expired = TRUE;
712 else {
713 memcpy(&expiry, dbmval.dptr, sizeof(apr_time_t));
714 if (expiry <= now)
715 expired = TRUE;
716 }
717 if (!expired) {
718 rv = iterator(ctx, s, userctx,
719 (unsigned char *)dbmkey.dptr, dbmkey.dsize,
720 (unsigned char *)dbmval.dptr + sizeof(apr_time_t),
721 dbmval.dsize - sizeof(apr_time_t), pool);
723 "dbm `%s' entry iterated", ctx->data_file);
724 if (rv != APR_SUCCESS)
725 return rv;
726 }
727 rv = apr_dbm_nextkey(dbm, &dbmkey);
728 }
730
731 if (rv != APR_SUCCESS && rv != APR_EOF) {
733 "Failure reading first/next socache DBM file `%s' record",
734 ctx->data_file);
735 return rv;
736 }
737 return APR_SUCCESS;
738}
739
752
759
762 NULL, NULL, NULL, NULL, NULL,
764};
Small object cache provider interface.
#define TRUE
Definition abts.h:38
#define FALSE
Definition abts.h:35
APR-UTIL DBM library.
APR Strings library.
APR Time Library.
APR Standard Headers Support.
if(!found)
Definition core.c:2803
char * ap_runtime_dir_relative(apr_pool_t *p, const char *fname)
Definition config.c:1610
#define AP_DECLARE_MODULE(foo)
char * ap_server_root_relative(apr_pool_t *p, const char *fname)
Definition config.c:1594
request_rec int int apr_table_t const char * path
request_rec * r
#define APLOGNO(n)
Definition http_log.h:117
#define APLOG_ERR
Definition http_log.h:67
#define ap_log_error
Definition http_log.h:370
#define APLOG_MARK
Definition http_log.h:283
#define APLOG_DEBUG
Definition http_log.h:71
apr_md5_ctx_t * context
Definition util_md5.h:58
int ap_rprintf(request_rec *r, const char *fmt,...) __attribute__((format(printf
static APR_INLINE int ap_rputs(const char *str, request_rec *r)
apr_status_t ap_register_provider(apr_pool_t *pool, const char *provider_group, const char *provider_name, const char *provider_version, const void *provider)
Definition provider.c:35
void const char * arg
Definition http_vhost.h:63
#define APR_EGENERAL
Definition apr_errno.h:313
#define APR_ENOSPC
Definition apr_errno.h:676
#define APR_EOF
Definition apr_errno.h:461
#define APR_NOTFOUND
Definition apr_errno.h:463
#define APR_EINVAL
Definition apr_errno.h:711
apr_brigade_flush void * ctx
const char const apr_dbd_driver_t ** driver
Definition apr_dbd.h:106
#define APR_DBM_RWCREATE
Definition apr_dbm.h:58
const char apr_ssize_t int flags
Definition apr_encode.h:168
apr_redis_t * rc
Definition apr_redis.h:173
apr_status_t() ap_socache_iterator_t(ap_socache_instance_t *instance, server_rec *s, void *userctx, const unsigned char *id, unsigned int idlen, const unsigned char *data, unsigned int datalen, apr_pool_t *pool)
Definition ap_socache.h:77
#define AP_SOCACHE_PROVIDER_GROUP
Definition ap_socache.h:218
#define AP_SOCACHE_FLAG_NOTMPSAFE
Definition ap_socache.h:46
#define AP_SOCACHE_PROVIDER_VERSION
Definition ap_socache.h:220
#define AP_STATUS_SHORT
Definition mod_status.h:32
#define STANDARD20_MODULE_STUFF
void * ap_malloc(size_t size) __attribute__((malloc))
Definition util.c:3152
apr_size_t size
const char int apr_pool_t * pool
Definition apr_cstr.h:84
#define APR_FROM_OS_ERROR(e)
Definition apr_errno.h:1214
#define APR_SUCCESS
Definition apr_errno.h:225
int apr_status_t
Definition apr_errno.h:44
#define apr_pool_create(newpool, parent)
Definition apr_pools.h:322
#define apr_pcalloc(p, size)
Definition apr_pools.h:465
const char * s
Definition apr_strings.h:95
apr_int32_t apr_int32_t apr_int32_t err
apr_int64_t apr_interval_time_t
Definition apr_time.h:55
apr_int64_t apr_time_t
Definition apr_time.h:45
#define apr_time_from_sec(sec)
Definition apr_time.h:78
Apache Configuration.
Apache Logging library.
HTTP protocol handling.
Apache Request library.
HTTP Daemon routines.
apr_pool_t * p
Definition md_event.c:32
return NULL
Definition mod_so.c:359
for(i=0;i< sconf->loaded_modules->nelts;i++)
Definition mod_so.c:353
int i
Definition mod_so.c:347
static apr_status_t socache_dbm_iterate(ap_socache_instance_t *ctx, server_rec *s, void *userctx, ap_socache_iterator_t *iterator, apr_pool_t *pool)
static apr_status_t socache_dbm_store(ap_socache_instance_t *ctx, server_rec *s, const unsigned char *id, unsigned int idlen, apr_time_t expiry, unsigned char *ucaData, unsigned int nData, apr_pool_t *pool)
static apr_status_t socache_dbm_retrieve(ap_socache_instance_t *ctx, server_rec *s, const unsigned char *id, unsigned int idlen, unsigned char *dest, unsigned int *destlen, apr_pool_t *p)
#define DBM_FILE_MODE
static const ap_socache_provider_t socache_dbm
#define DEFAULT_DBM_PREFIX
static void register_hooks(apr_pool_t *p)
static apr_status_t socache_dbm_init(ap_socache_instance_t *ctx, const char *namespace, const struct ap_socache_hints *hints, server_rec *s, apr_pool_t *p)
#define DBM_FILE_SUFFIX_PAG
static void socache_dbm_destroy(ap_socache_instance_t *ctx, server_rec *s)
static const char * socache_dbm_create(ap_socache_instance_t **context, const char *arg, apr_pool_t *tmp, apr_pool_t *p)
#define DBM_FILE_SUFFIX_DIR
static void socache_dbm_status(ap_socache_instance_t *ctx, request_rec *r, int flags)
static apr_status_t socache_dbm_remove(ap_socache_instance_t *ctx, server_rec *s, const unsigned char *id, unsigned int idlen, apr_pool_t *p)
static void socache_dbm_expire(ap_socache_instance_t *ctx, server_rec *s)
#define KEYMAX
Status Report Extension Module to Apache.
Multi-Processing Modules functions.
#define PAIRMAX
char * name
apr_interval_time_t expiry_interval
char * dptr
Definition apr_dbm.h:50
A structure that represents the current request.
Definition httpd.h:845
A structure to store information for each virtual server.
Definition httpd.h:1322
static apr_time_t now
Definition testtime.c:33
typedef int(WSAAPI *apr_winapi_fpt_WSAPoll)(IN OUT LPWSAPOLLFD fdArray