Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
freebsd
GitHub Repository: freebsd/freebsd-src
Path: blob/main/contrib/blocklist/bin/state.c
105315 views
1
/* $NetBSD: state.c,v 1.3 2025/10/25 18:43:51 christos Exp $ */
2
3
/*-
4
* Copyright (c) 2015 The NetBSD Foundation, Inc.
5
* All rights reserved.
6
*
7
* This code is derived from software contributed to The NetBSD Foundation
8
* by Christos Zoulas.
9
*
10
* Redistribution and use in source and binary forms, with or without
11
* modification, are permitted provided that the following conditions
12
* are met:
13
* 1. Redistributions of source code must retain the above copyright
14
* notice, this list of conditions and the following disclaimer.
15
* 2. Redistributions in binary form must reproduce the above copyright
16
* notice, this list of conditions and the following disclaimer in the
17
* documentation and/or other materials provided with the distribution.
18
*
19
* THIS SOFTWARE IS PROVIDED BY THE NETBSD FOUNDATION, INC. AND CONTRIBUTORS
20
* ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED
21
* TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
22
* PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE FOUNDATION OR CONTRIBUTORS
23
* BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
24
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
25
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
26
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
27
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
28
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
29
* POSSIBILITY OF SUCH DAMAGE.
30
*/
31
#ifdef HAVE_CONFIG_H
32
#include "config.h"
33
#endif
34
35
#ifdef HAVE_SYS_CDEFS_H
36
#include <sys/cdefs.h>
37
#endif
38
__RCSID("$NetBSD: state.c,v 1.3 2025/10/25 18:43:51 christos Exp $");
39
40
#include <sys/types.h>
41
#include <sys/socket.h>
42
#include <stdio.h>
43
#include <string.h>
44
#include <errno.h>
45
#include <fcntl.h>
46
#include <syslog.h>
47
#include <netinet/in.h>
48
49
#include "bl.h"
50
#include "internal.h"
51
#include "conf.h"
52
#include "support.h"
53
#include "state.h"
54
55
static HASHINFO openinfo = {
56
4096, /* bsize */
57
32, /* ffactor */
58
256, /* nelem */
59
8 * 1024 * 1024,/* cachesize */
60
NULL, /* hash() */
61
0 /* lorder */
62
};
63
64
int
65
state_close(DB *db)
66
{
67
if (db == NULL)
68
return -1;
69
if ((*db->close)(db) == -1) {
70
(*lfun)(LOG_ERR, "%s: can't close db (%m)", __func__);
71
return -1;
72
}
73
return 0;
74
}
75
76
DB *
77
state_open(const char *dbname, int flags, mode_t perm)
78
{
79
DB *db;
80
81
#ifdef __APPLE__
82
flags &= O_CREAT|O_EXCL|O_EXLOCK|O_NONBLOCK|O_RDONLY|
83
O_RDWR|O_SHLOCK|O_TRUNC;
84
#endif
85
db = dbopen(dbname, flags, perm, DB_HASH, &openinfo);
86
if (db == NULL) {
87
if (errno == ENOENT && (flags & O_CREAT) == 0)
88
return NULL;
89
(*lfun)(LOG_ERR, "%s: can't open `%s' (%m)", __func__, dbname);
90
}
91
return db;
92
}
93
94
static int
95
state_sizecheck(const DBT *t)
96
{
97
if (sizeof(struct conf) == t->size)
98
return 0;
99
(*lfun)(LOG_ERR, "Key size mismatch %zu != %zu", sizeof(struct conf),
100
t->size);
101
return -1;
102
}
103
104
static void
105
dumpkey(const struct conf *k)
106
{
107
char buf[10240];
108
blhexdump(buf, sizeof(buf), __func__, k, sizeof(*k));
109
(*lfun)(LOG_DEBUG, "%s", buf);
110
(*lfun)(LOG_DEBUG, "%s: %s", __func__,
111
conf_print(buf, sizeof(buf), "", "", k));
112
113
}
114
115
int
116
state_del(DB *db, const struct conf *c)
117
{
118
int rv;
119
DBT k;
120
121
if (db == NULL)
122
return -1;
123
124
k.data = __UNCONST(c);
125
k.size = sizeof(*c);
126
127
switch (rv = (*db->del)(db, &k, 0)) {
128
case 0:
129
case 1:
130
if (debug > 1) {
131
(*lfun)(LOG_DEBUG, "%s: returns %d", __func__, rv);
132
(*db->sync)(db, 0);
133
}
134
return rv;
135
default:
136
(*lfun)(LOG_ERR, "%s: failed (%m)", __func__);
137
return -1;
138
}
139
}
140
141
int
142
state_get(DB *db, const struct conf *c, struct dbinfo *dbi)
143
{
144
int rv;
145
DBT k, v;
146
147
if (db == NULL)
148
return -1;
149
150
k.data = __UNCONST(c);
151
k.size = sizeof(*c);
152
153
switch (rv = (*db->get)(db, &k, &v, 0)) {
154
case 0:
155
case 1:
156
if (rv)
157
memset(dbi, 0, sizeof(*dbi));
158
else
159
memcpy(dbi, v.data, sizeof(*dbi));
160
if (debug > 1)
161
(*lfun)(LOG_DEBUG, "%s: returns %d", __func__, rv);
162
return 0;
163
default:
164
(*lfun)(LOG_ERR, "%s: failed (%m)", __func__);
165
return -1;
166
}
167
}
168
169
int
170
state_put(DB *db, const struct conf *c, const struct dbinfo *dbi)
171
{
172
int rv;
173
DBT k, v;
174
175
if (db == NULL)
176
return -1;
177
178
k.data = __UNCONST(c);
179
k.size = sizeof(*c);
180
v.data = __UNCONST(dbi);
181
v.size = sizeof(*dbi);
182
183
switch (rv = (*db->put)(db, &k, &v, 0)) {
184
case 0:
185
if (debug > 1) {
186
(*lfun)(LOG_DEBUG, "%s: returns %d", __func__, rv);
187
(*db->sync)(db, 0);
188
}
189
return 0;
190
case 1:
191
errno = EEXIST;
192
/*FALLTHROUGH*/
193
default:
194
(*lfun)(LOG_ERR, "%s: failed (%m)", __func__);
195
return -1;
196
}
197
}
198
199
int
200
state_iterate(DB *db, struct conf *c, struct dbinfo *dbi, unsigned int first)
201
{
202
int rv;
203
DBT k, v;
204
205
if (db == NULL) {
206
(*lfun)(LOG_ERR, "%s: called with no database file", __func__);
207
return -1;
208
}
209
210
first = first ? R_FIRST : R_NEXT;
211
212
switch (rv = (*db->seq)(db, &k, &v, first)) {
213
case 0:
214
if (state_sizecheck(&k) == -1)
215
return -1;
216
memcpy(c, k.data, sizeof(*c));
217
if (debug > 2)
218
dumpkey(c);
219
memcpy(dbi, v.data, sizeof(*dbi));
220
if (debug > 1)
221
(*lfun)(LOG_DEBUG, "%s: returns %d", __func__, rv);
222
return 1;
223
case 1:
224
if (debug > 1)
225
(*lfun)(LOG_DEBUG, "%s: returns %d", __func__, rv);
226
return 0;
227
default:
228
(*lfun)(LOG_ERR, "%s: failed (%m)", __func__);
229
return -1;
230
}
231
}
232
233
int
234
state_sync(DB *db)
235
{
236
return (*db->sync)(db, 0);
237
}
238
239