The FreeRADIUS server $Id: 15bac2a4c627c01d1aa2047687b3418955ac7f00 $
Loading...
Searching...
No Matches
rlm_cache.h
Go to the documentation of this file.
1#pragma once
2/*
3 * This program is free software; you can redistribute it and/or modify
4 * it under the terms of the GNU General Public License as published by
5 * the Free Software Foundation; either version 2 of the License, or (at
6 * your option) any later version.
7 *
8 * This program is distributed in the hope that it will be useful,
9 * but WITHOUT ANY WARRANTY; without even the implied warranty of
10 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 * GNU General Public License for more details.
12 *
13 * You should have received a copy of the GNU General Public License
14 * along with this program; if not, write to the Free Software
15 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
16 */
17
18/*
19 * $Id: 7915bb91ec36f02cb9e12c7cc4809c282a3c33b1 $
20 * @file rlm_cache.h
21 * @brief Cache values and merge them back into future requests.
22 *
23 * @copyright 2014 The FreeRADIUS server project
24 * @copyright 2014 Arran Cudbard-Bell (a.cudbardb@freeradius.org)
25 */
26RCSIDH(cache_h, "$Id: 7915bb91ec36f02cb9e12c7cc4809c282a3c33b1 $")
27
28#include <freeradius-devel/server/base.h>
29#include <freeradius-devel/server/dl_module.h>
30#include <freeradius-devel/server/map.h>
31#include <freeradius-devel/protocol/freeradius/freeradius.internal.h>
32
34
35typedef void rlm_cache_handle_t;
36
37#define MAX_ATTRMAP 128
38
39typedef enum {
40 CACHE_RECONNECT = -2, //!< Handle needs to be reconnected
41 CACHE_ERROR = -1, //!< Fatal error
42 CACHE_OK = 0, //!< Cache entry found/updated
43 CACHE_MISS = 1 //!< Cache entry notfound
45
46/** Configuration for the rlm_cache module
47 *
48 * This is separate from the #rlm_cache_t struct, to limit driver's visibility of
49 * rlm_cache instance data.
50 */
51typedef struct {
52 fr_time_delta_t ttl; //!< How long an entry is valid for.
53 uint32_t max_entries; //!< Maximum entries allowed.
54 int32_t epoch; //!< Time after which entries are considered valid.
55 bool stats; //!< Generate statistics.
57
58/*
59 * Define a structure for our module configuration.
60 *
61 * These variables do not need to be in a structure, but it's
62 * a lot cleaner to do so, and a pointer to the structure can
63 * be used as the instance handle.
64 */
65typedef struct {
66 rlm_cache_config_t config; //!< Must come first because of icky hacks.
67
68 module_instance_t *driver_submodule; //!< Driver's instance data.
69 rlm_cache_driver_t const *driver; //!< Driver's exported interface.
71
72typedef struct {
73 fr_value_box_t key; //!< Key used to identify entry.
74 long long int hits; //!< How many times the entry has been retrieved.
75 fr_unix_time_t created; //!< When the entry was created.
76 fr_unix_time_t expires; //!< When the entry expires.
77
78 map_list_t maps; //!< Head of the maps list.
80
81/** Allocate a new cache entry
82 *
83 */
84typedef rlm_cache_entry_t *(*cache_entry_alloc_t)(rlm_cache_config_t const *config, void *instance, request_t *request);
85
86/** Free a cache entry
87 *
88 * @note This callback is optional, but the driver assume responsibility for freeing the
89 * cache_entry_t on #cache_entry_expire_t.
90 *
91 * If the driver does not need to keep a local copy of the cache entry, it should provide
92 * a callback to free the memory previously allocated for the cache entry by
93 * #cache_entry_find_t or by rlm_cache.
94 *
95 * @param c entry to free.
96 */
98
99/** Retrieve an entry from the cache
100 *
101 * If a cache entry is found, but the cache entry needs to be deserialized, the driver
102 * is expected to allocate an appropriately sized #rlm_cache_entry_t, perform the deserialisation,
103 * and write a pointer to the new entry to out, returning #CACHE_OK.
104 *
105 * If the #rlm_cache_handle_t is inviable, the driver should return #CACHE_RECONNECT, to have
106 * it reinitialised/reconnected.
107 *
108 * @param[out] out Where to write a pointer to the retrieved entry (if there was one).
109 * @param[in] config for this instance of the rlm_cache module.
110 * @param[in] instance Driver specific instance data.
111 * @param[in] request The current request.
112 * @param[in] handle the driver gave us when we called #cache_acquire_t, or NULL if no
113 * #cache_acquire_t callback was provided.
114 * @param[in] key to use to lookup cache entry
115 * @return
116 * - #CACHE_RECONNECT - If handle needs to be reinitialised/reconnected.
117 * - #CACHE_ERROR - If the lookup couldn't be completed.
118 * - #CACHE_OK - Lookup was successful.
119 * - #CACHE_MISS - No cached entry was found.
120 */
122 void *instance, request_t *request, void *handle,
123 fr_value_box_t const *key);
124
125/** Insert an entry into the cache
126 *
127 * Serialize (if necessary) the entry passed to us, and write it to the cache with
128 * the key c->key.
129 *
130 * The cache entry should not be freed by the driver, irrespective of success or failure.
131 * If the entry needs to be freed after insertion because a local copy should not be kept,
132 * the driver should provide a #cache_entry_free_t callback.
133 *
134 * If the #rlm_cache_handle_t is inviable, the driver should return #CACHE_RECONNECT, to have
135 * it reinitialised/reconnected.
136 *
137 * @note This callback is not optional.
138 *
139 * @note This callback *must* overwrite existing cache entries on insert.
140 *
141 * @param config for this instance of the rlm_cache module.
142 * @param instance Driver specific instance data.
143 * @param request The current request.
144 * @param handle the driver gave us when we called #cache_acquire_t, or NULL if no
145 * #cache_acquire_t callback was provided.
146 * @param c to insert.
147 * @return
148 * - #CACHE_RECONNECT - If handle needs to be reinitialised/reconnected.
149 * - #CACHE_ERROR - If the insert couldn't be completed.
150 * - #CACHE_OK - If the insert was successful.
151 */
153 request_t *request, void *handle,
154 rlm_cache_entry_t const *c);
155
156/** Remove an entry from the cache
157 *
158 * @note This callback is not optional.
159 *
160 * @param[in] config for this instance of the rlm_cache module.
161 * @param[in] instance Driver specific instance data.
162 * @param[in] request The current request.
163 * @param[in] handle the driver gave us when we called #cache_acquire_t, or NULL if no
164 * #cache_acquire_t callback was provided.
165 * @param[in] key of entry to expire.
166 * @return
167 * - #CACHE_RECONNECT - If handle needs to be reinitialised/reconnected.
168 * - #CACHE_ERROR - If the entry couldn't be expired.
169 * - #CACHE_OK - If the entry was expired.
170 * - #CACHE_MISS - If the entry didn't exist, so couldn't be expired.
171 */
173 request_t *request, void *handle,
174 fr_value_box_t const *key);
175
176/** Update the ttl of an entry in the cache
177 *
178 * @note This callback optional. If it's not specified the cache code will expire and
179 * recreate the entry with a new TTL.
180 *
181 * If the #rlm_cache_handle_t is inviable, the driver should return #CACHE_RECONNECT, to have
182 * it reinitialised/reconnected.
183 *
184 * @param[in] config for this instance of the rlm_cache module.
185 * @param[in] instance Driver specific instance data.
186 * @param[in] request The current request.
187 * @param[in] handle the driver gave us when we called #cache_acquire_t, or NULL if no
188 * #cache_acquire_t callback was provided.
189 * @param[in] c to update the TTL of. c->ttl will have been set to the new value.
190 * @return
191 * - #CACHE_RECONNECT - If handle needs to be reinitialised/reconnected.
192 * - #CACHE_ERROR - If the entry TTL couldn't be updated.
193 * - #CACHE_OK - If the entry's TTL was updated.
194 */
196 request_t *request, void *handle,
198
199/** Get the number of entries in the cache
200 *
201 * @note This callback is optional. Though max_entries will not be enforced if it is not provided.
202 *
203 * @param[in] config for this instance of the rlm_cache module.
204 * @param[in] instance Driver specific instance data.
205 * @param[in] request The current request.
206 * @param handle the driver gave us when we called #cache_acquire_t, or NULL if no
207 * #cache_acquire_t callback was provided.
208 * @return number of entries in the cache.
209 */
210typedef uint64_t (*cache_entry_count_t)(rlm_cache_config_t const *config, void *instance,
211 request_t *request, void *handle);
212
213/** Acquire a handle to access the cache
214 *
215 * @note This callback is optional. If it's not provided the handle argument to other callbacks
216 * will be NULL.
217 *
218 * @param[out] handle Where to write pointer to handle to access the cache with.
219 * @param[in] config for this instance of the rlm_cache module.
220 * @param[in] instance Driver specific instance data.
221 * @param[in] request The current request.
222 * @return
223 * - 0 on success.
224 * - -1 on failure.
225 */
226typedef int (*cache_acquire_t)(void **handle, rlm_cache_config_t const *config, void *instance,
227 request_t *request);
228
229/** Release a previously acquired handle
230 *
231 * @note This callback is optional.
232 *
233 * @param[in] config for this instance of the rlm_cache module.
234 * @param[in] instance Driver specific instance data.
235 * @param[in] request The current request.
236 * @param[in] handle to release.
237 */
238typedef void (*cache_release_t)(rlm_cache_config_t const *config, void *instance, request_t *request,
239 rlm_cache_handle_t *handle);
240
241/** Reconnect a previously acquired handle
242 *
243 * @note This callback is optional.
244 *
245 * @param[in,out] handle to reinitialise/reconnect.
246 * @param[in] config for this instance of the rlm_cache module.
247 * @param[in] instance Driver specific instance data.
248 * @param[in] request The current request.
249
250 * @return
251 * - 0 on success.
252 * - -1 on failure.
253 */
255 void *instance, request_t *request);
256
258 module_t common; //!< Common fields for all loadable modules.
259
260 cache_entry_alloc_t alloc; //!< (optional) Allocate a new entry.
261 cache_entry_free_t free; //!< (optional) Free memory used by an entry.
262
263 cache_entry_find_t find; //!< Retrieve an existing cache entry.
264 cache_entry_insert_t insert; //!< Add a new entry.
265 cache_entry_expire_t expire; //!< Remove an old entry.
266 cache_entry_set_ttl_t set_ttl; //!< (Optional) Update the TTL of an entry.
267 cache_entry_count_t count; //!< (Optional) Number of entries currently in
268 //!< the cache.
269
270 cache_acquire_t acquire; //!< (optional) Acquire exclusive access to a resource
271 //!< used to retrieve the cache entry.
272 cache_release_t release; //!< (optional) Release access to resource acquired
273 //!< with acquire callback.
274 cache_reconnect_t reconnect; //!< (optional) Re-initialise resource.
275
276 call_env_parse_pair_t key_parse; //!< (optional) custom key parser. Allows the driver
277 ///< to have complete control over how the key is
278 ///< parsed. If not provided, the default key parser
279 ///< will be used. data will be set to the submodule's
280 ///< instance data, NOT the #rlm_cache_t.
281};
#define RCSIDH(h, id)
Definition build.h:484
int(* call_env_parse_pair_t)(TALLOC_CTX *ctx, void *out, tmpl_rules_t const *t_rules, CONF_ITEM *ci, call_env_ctx_t const *cec, call_env_parser_t const *rule)
Callback for performing custom parsing of a CONF_PAIR.
Definition call_env.h:146
unsigned int uint32_t
static const conf_parser_t config[]
Definition base.c:183
uint32_t max_entries
Maximum entries allowed.
Definition rlm_cache.h:53
cache_entry_find_t find
Retrieve an existing cache entry.
Definition rlm_cache.h:263
int32_t epoch
Time after which entries are considered valid.
Definition rlm_cache.h:54
cache_entry_insert_t insert
Add a new entry.
Definition rlm_cache.h:264
module_instance_t * driver_submodule
Driver's instance data.
Definition rlm_cache.h:68
cache_status_t(* cache_entry_set_ttl_t)(rlm_cache_config_t const *config, void *instance, request_t *request, void *handle, rlm_cache_entry_t *c)
Update the ttl of an entry in the cache.
Definition rlm_cache.h:195
fr_time_delta_t ttl
How long an entry is valid for.
Definition rlm_cache.h:52
cache_entry_expire_t expire
Remove an old entry.
Definition rlm_cache.h:265
cache_status_t(* cache_entry_insert_t)(rlm_cache_config_t const *config, void *instance, request_t *request, void *handle, rlm_cache_entry_t const *c)
Insert an entry into the cache.
Definition rlm_cache.h:152
cache_entry_set_ttl_t set_ttl
(Optional) Update the TTL of an entry.
Definition rlm_cache.h:266
bool stats
Generate statistics.
Definition rlm_cache.h:55
cache_entry_alloc_t alloc
(optional) Allocate a new entry.
Definition rlm_cache.h:260
fr_value_box_t key
Key used to identify entry.
Definition rlm_cache.h:73
map_list_t maps
Head of the maps list.
Definition rlm_cache.h:78
uint64_t(* cache_entry_count_t)(rlm_cache_config_t const *config, void *instance, request_t *request, void *handle)
Get the number of entries in the cache.
Definition rlm_cache.h:210
fr_unix_time_t created
When the entry was created.
Definition rlm_cache.h:75
rlm_cache_config_t config
Must come first because of icky hacks.
Definition rlm_cache.h:66
void(* cache_entry_free_t)(rlm_cache_entry_t *c)
Free a cache entry.
Definition rlm_cache.h:97
int(* cache_reconnect_t)(rlm_cache_handle_t **handle, rlm_cache_config_t const *config, void *instance, request_t *request)
Reconnect a previously acquired handle.
Definition rlm_cache.h:254
rlm_cache_driver_t const * driver
Driver's exported interface.
Definition rlm_cache.h:69
long long int hits
How many times the entry has been retrieved.
Definition rlm_cache.h:74
cache_release_t release
(optional) Release access to resource acquired with acquire callback.
Definition rlm_cache.h:272
cache_entry_free_t free
(optional) Free memory used by an entry.
Definition rlm_cache.h:261
void(* cache_release_t)(rlm_cache_config_t const *config, void *instance, request_t *request, rlm_cache_handle_t *handle)
Release a previously acquired handle.
Definition rlm_cache.h:238
cache_entry_count_t count
(Optional) Number of entries currently in the cache.
Definition rlm_cache.h:267
int(* cache_acquire_t)(void **handle, rlm_cache_config_t const *config, void *instance, request_t *request)
Acquire a handle to access the cache.
Definition rlm_cache.h:226
rlm_cache_entry_t *(* cache_entry_alloc_t)(rlm_cache_config_t const *config, void *instance, request_t *request)
Allocate a new cache entry.
Definition rlm_cache.h:84
module_t common
Common fields for all loadable modules.
Definition rlm_cache.h:258
cache_status_t
Definition rlm_cache.h:39
@ CACHE_ERROR
Fatal error.
Definition rlm_cache.h:41
@ CACHE_RECONNECT
Handle needs to be reconnected.
Definition rlm_cache.h:40
@ CACHE_OK
Cache entry found/updated.
Definition rlm_cache.h:42
@ CACHE_MISS
Cache entry notfound.
Definition rlm_cache.h:43
cache_reconnect_t reconnect
(optional) Re-initialise resource.
Definition rlm_cache.h:274
call_env_parse_pair_t key_parse
(optional) custom key parser.
Definition rlm_cache.h:276
void rlm_cache_handle_t
Definition rlm_cache.h:35
fr_unix_time_t expires
When the entry expires.
Definition rlm_cache.h:76
cache_status_t(* cache_entry_find_t)(rlm_cache_entry_t **out, rlm_cache_config_t const *config, void *instance, request_t *request, void *handle, fr_value_box_t const *key)
Retrieve an entry from the cache.
Definition rlm_cache.h:121
cache_acquire_t acquire
(optional) Acquire exclusive access to a resource used to retrieve the cache entry.
Definition rlm_cache.h:270
cache_status_t(* cache_entry_expire_t)(rlm_cache_config_t const *config, void *instance, request_t *request, void *handle, fr_value_box_t const *key)
Remove an entry from the cache.
Definition rlm_cache.h:172
Configuration for the rlm_cache module.
Definition rlm_cache.h:51
Definition rlm_cache.h:72
Module instance data.
Definition module.h:265
Struct exported by a rlm_* module.
Definition module.h:195
A time delta, a difference in time measured in nanoseconds.
Definition time.h:80
"Unix" time.
Definition time.h:95
static size_t char ** out
Definition value.h:997