2 Unix SMB/CIFS implementation.
3 Implementation of reliable cleanup events
4 Copyright (C) Ralph Boehme 2016
6 This program is free software; you can redistribute it and/or modify
7 it under the terms of the GNU General Public License as published by
8 the Free Software Foundation; either version 3 of the License, or
9 (at your option) any later version.
11 This program is distributed in the hope that it will be useful,
12 but WITHOUT ANY WARRANTY; without even the implied warranty of
13 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 GNU General Public License for more details.
16 You should have received a copy of the GNU General Public License
17 along with this program. If not, see <http://www.gnu.org/licenses/>.
20 #include "cleanupdb.h"
30 static struct tdb_wrap *cleanup_db(void)
32 static struct tdb_wrap *db;
34 int tdbflags = TDB_INCOMPATIBLE_HASH | TDB_CLEAR_IF_FIRST |
41 db_path = lock_path("smbd_cleanupd.tdb");
42 if (db_path == NULL) {
46 db = tdb_wrap_open(NULL, db_path, 0, tdbflags,
47 O_CREAT | O_RDWR, 0644);
49 DBG_ERR("Failed to open smbd_cleanupd.tdb\n");
56 bool cleanupdb_store_child(const pid_t pid, const bool unclean)
59 struct cleanup_key key = { .pid = pid };
60 struct cleanup_rec rec = { .unclean = unclean };
61 TDB_DATA tdbkey = { .dptr = (uint8_t *)&key, .dsize = sizeof(key) };
62 TDB_DATA tdbdata = { .dptr = (uint8_t *)&rec, .dsize = sizeof(rec) };
70 result = tdb_store(db->tdb, tdbkey, tdbdata, TDB_REPLACE);
72 DBG_ERR("tdb_store failed for pid %d\n", (int)pid);
79 bool cleanupdb_delete_child(const pid_t pid)
82 struct cleanup_key key = { .pid = pid };
83 TDB_DATA tdbkey = { .dptr = (uint8_t *)&key, .dsize = sizeof(key) };
91 result = tdb_delete(db->tdb, tdbkey);
93 DBG_ERR("tdb_delete failed for pid %d\n", (int)pid);
100 struct cleanup_read_state {
101 int (*fn)(const pid_t pid, const bool cleanup, void *private_data);
105 static int cleanup_traverse_fn(struct tdb_context *tdb,
106 TDB_DATA key, TDB_DATA value,
109 struct cleanup_read_state *state =
110 (struct cleanup_read_state *)private_data;
111 struct cleanup_key ckey;
112 struct cleanup_rec rec;
115 if (key.dsize != sizeof(struct cleanup_key)) {
116 DBG_ERR("Found invalid key length %zu in cleanup.tdb\n",
120 memcpy(&ckey, key.dptr, sizeof(struct cleanup_key));
122 if (value.dsize != sizeof(struct cleanup_rec)) {
123 DBG_ERR("Found invalid value length %zu in cleanup.tdb\n",
127 memcpy(&rec, value.dptr, sizeof(struct cleanup_rec));
129 result = state->fn(ckey.pid, rec.unclean, state->private_data);
137 int cleanupdb_traverse_read(int (*fn)(const pid_t pid,
143 struct cleanup_read_state state;
151 state = (struct cleanup_read_state) {
153 .private_data = private_data
156 result = tdb_traverse_read(db->tdb, cleanup_traverse_fn, &state);
158 DBG_ERR("tdb_traverse_read failed\n");