51#define WIZARD_BUCKETS 7
54#define TYPE_BUCKETS 53
57#define INSTANCE_BUCKETS 17
60#define OBJECT_FIELD_BUCKETS 29
62#define NOTIFY_GENERIC_OBSERVERS(container, type, callback, ...) ({ \
63 struct ao2_iterator i = ao2_iterator_init(container, 0); \
64 struct type *observer; \
65 ao2_rdlock(container); \
66 while ((observer = ao2_iterator_next(&i))) { \
67 if (observer->callbacks->callback) { \
68 observer->callbacks->callback(__VA_ARGS__); \
70 ao2_cleanup(observer); \
72 ao2_unlock(container); \
73 ao2_iterator_cleanup(&i); \
76#define NOTIFY_GLOBAL_OBSERVERS(container, callback, ...) \
77 NOTIFY_GENERIC_OBSERVERS(container, sorcery_global_observer, callback, __VA_ARGS__)
79#define NOTIFY_INSTANCE_OBSERVERS(container, callback, ...) \
80 NOTIFY_GENERIC_OBSERVERS(container, sorcery_instance_observer, callback, __VA_ARGS__)
82#define NOTIFY_WIZARD_OBSERVERS(container, callback, ...) \
83 NOTIFY_GENERIC_OBSERVERS(container, sorcery_wizard_observer, callback, __VA_ARGS__)
288 int *field = (
int *)(obj +
args[0]);
294 unsigned int *field = (
unsigned int *)(obj +
args[0]);
300 double *field = (
double *)(obj +
args[0]);
312 unsigned int *field = (
unsigned int *)(obj +
args[0]);
313 return !(*
buf =
ast_strdup(*field ?
"true" :
"false")) ? -1 : 0;
318 unsigned int *field = (
unsigned int *)(obj +
args[0]);
330 char *field = (
char *)(obj +
args[0]);
404 ast_sorcery_internal_wizard_hash_fn,
NULL, ast_sorcery_internal_wizard_cmp_fn);
415 sorcery_proxy_hash_fn,
NULL, sorcery_proxy_cmp_fn);
462 ast_verb(5,
"Sorcery registered wizard '%s'\n", interface->
name);
465 interface->
name, interface);
483 ast_verb(5,
"Sorcery unregistered wizard '%s'\n", interface->
name);
610 __PRETTY_FUNCTION__,
file, line, func);
619 goto failure_cleanup;
625 goto failure_cleanup;
632 goto failure_cleanup;
636 goto failure_cleanup;
640 ast_sorcery_object_type_hash_fn,
NULL, ast_sorcery_object_type_cmp_fn);
642 goto failure_cleanup;
646 goto failure_cleanup;
651 goto failure_cleanup;
689 if (object_type->
info) {
702#define INITIAL_WIZARD_VECTOR_SIZE 5
718 if (!object_type->
fields) {
731 sizeof(*object_type->
info) + 2 *
sizeof(object_type->
info->
files[0]));
732 if (!object_type->
info) {
738 sizeof(*object_type->
file) + 2 *
sizeof(object_type->
file->
types[0]));
739 if (!object_type->
file) {
770 if (object_wizard->
wizard) {
821 const char *object_type_name,
const char *module,
const char *wizard_type_name,
851 const char *
type,
const char *module,
const char *
name)
861#define WIZARD_NAME_COMPARE(a, b) (strcmp((a)->wizard->callbacks.name, (b)) == 0)
863#undef WIZARD_NAME_COMPARE
870 const char *object_type_name,
const char *module,
const char *wizard_type_name,
879 object_wizard =
ao2_alloc(
sizeof(*object_wizard)
883 if (!object_wizard) {
890 "Wizard '%s' could not be applied to object type '%s' as it was not found\n",
891 wizard_type_name, object_type_name);
907#define WIZARD_COMPARE(a, b) ((a)->wizard == (b))
912 ast_debug(1,
"Wizard %s already applied to object type %s\n",
913 internal_wizard->callbacks.name, object_type->name);
920 ast_debug(5,
"Calling wizard %s open callback on object type %s\n",
921 wizard_type_name, object_type->name);
922 if (internal_wizard->callbacks.open && !(object_wizard->data = internal_wizard->callbacks.open(
wizard_args))) {
923 ast_log(
LOG_WARNING,
"Wizard '%s' failed to open mapping for object type '%s' with data: %s\n",
930 object_wizard->wizard =
ao2_bump(internal_wizard);
954 object_wizard->data);
960 *wizard_data = object_wizard->data;
968 const char *
type,
const char *module,
const char *
name,
969 const char *
data,
unsigned int caching,
int position)
978 const char *
type,
const char *module,
const char *
name,
1005 char *data = mapping_value;
1006 char *wizard =
strsep(&data,
",");
1007 unsigned int caching = 0;
1084 if (!object_type || object_type->type.item_alloc) {
1088 object_type->type.name = object_type->name;
1090 object_type->type.category =
".?";
1091 object_type->type.item_alloc = alloc;
1092 object_type->type.hidden = hidden;
1096 object_type->apply =
apply;
1097 object_type->file->types[0] = &object_type->type;
1098 object_type->file->types[1] =
NULL;
1122 low_water, high_water);
1136 object_type->copy =
copy;
1147 object_type->diff =
diff;
1162#define MAX_REGEX_ERROR_LEN 128
1167 if (!object_type || !object_type->type.item_alloc || !config_handler
1173 object_field->multiple_handler = sorcery_handler;
1175 if (!(object_field->name_regex =
ast_calloc(1,
sizeof(regex_t)))) {
1179 if ((rc = regcomp(object_field->name_regex,
regex, REG_EXTENDED | REG_NOSUB))) {
1186 ao2_link(object_type->fields, object_field);
1200 if (!strcmp(
type,
"id") || !object_type || !object_type->type.item_alloc) {
1204 if (!sorcery_handler) {
1208 if (!(object_field =
ao2_alloc(
sizeof(*object_field) + argc *
sizeof(object_field->args[0]),
NULL))) {
1213 object_field->handler = sorcery_handler;
1216 va_start(
args, argc);
1217 for (pos = 0; pos < argc; pos++) {
1218 object_field->args[pos] = va_arg(
args,
size_t);
1223 ao2_link(object_type->fields, object_field);
1229 }
else if (argc == 1) {
1230 __aco_option_register(object_type->info,
name,
ACO_EXACT, object_type->file->types, default_val, opt_type, config_handler, flags, no_doc, argc,
1231 object_field->args[0]);
1232 }
else if (argc == 2) {
1233 __aco_option_register(object_type->info,
name,
ACO_EXACT, object_type->file->types, default_val, opt_type, config_handler, flags, no_doc, argc,
1234 object_field->args[0], object_field->args[1]);
1235 }
else if (argc == 3) {
1236 __aco_option_register(object_type->info,
name,
ACO_EXACT, object_type->file->types, default_val, opt_type, config_handler, flags, no_doc, argc,
1237 object_field->args[0], object_field->args[1], object_field->args[2]);
1250 return object_type && object_type->reloadable;
1341 if (!
type->type.item_alloc) {
1348 ast_log(
LOG_NOTICE,
"Type '%s' is not reloadable, maintaining previous values\n",
1487 if (!(object_field->
handler(
object, object_field->
args, &
buf))) {
1574 if (!object_type || !json) {
1592 for (field =
tmp; field; field = field->
next) {
1602 }
else if (object_field->
handler) {
1610 ast_debug(5,
"Skipping field '%s' for object type '%s'\n",
1611 object_field->
name, object_type->name);
1644 if (object_type->transform && (transformed = object_type->transform(objectset))) {
1645 field = transformed;
1650 for (; field; field = field->
next) {
1656 if (!res && object_type->apply) {
1657 res = object_type->apply(
sorcery,
object);
1671 if (original == modified) {
1675 for (field = modified; field; field = field->
next) {
1678 if (!old_value || strcmp(old_value, field->
value)) {
1686 tmp->next = *changes;
1722 details->
object =
object + size;
1738 details->
object =
object + size;
1749 if (!object_type || !object_type->type.item_alloc ||
1750 !(details = object_type->type.item_alloc(
id))) {
1788 }
else if (object_type->copy) {
1789 res = object_type->copy(
object,
copy);
1815 if (original == modified) {
1817 }
else if (!object_type->diff) {
1826 return object_type->diff(original, modified, changes);
1856 void *
object =
NULL;
1858 unsigned int cached = 0;
1879 cached =
wizard->caching;
1883 if (!cached &&
object) {
1900 void *
object =
NULL;
1902 unsigned int cached = 0;
1935 cached =
wizard->caching;
2044 if (
observer->callbacks->created) {
2083 object_wizard = found_wizard;
2087 if (object_wizard) {
2109 return object_wizard ? 0 : -1;
2117 if (
observer->callbacks->updated) {
2171 object_wizard = found_wizard;
2175 if (object_wizard) {
2197 return object_wizard ? 0 : -1;
2205 if (
observer->callbacks->deleted) {
2259 object_wizard = found_wizard;
2263 if (object_wizard) {
2285 return object_wizard ? 0 : -1;
2306 ast_debug(5,
"After calling wizard '%s', object '%s' is %s\n",
2309 res ?
"stale" :
"not stale");
2341 if (!strcmp(field->
name + 1,
name)) {
2342 return field->
value;
2359 for (field = details->
object->
extended; field; previous = field, field = field->
next) {
2360 if (!strcmp(field->name,
name)) {
2362 previous->next = field->next;
2442 const void *object_left = obj;
2443 const void *object_right = arg;
2444 const char *right_key = arg;
2515 const char *field_name)
2524 if (!object_field) {
2528 if (!object_field) {
static int copy(char *infile, char *outfile)
Utility function to copy a file.
Asterisk main include file. File version handling, generic pbx functions.
int ast_register_cleanup(void(*func)(void))
Register a function to be executed before Asterisk gracefully exits.
#define ast_alloca(size)
call __builtin_alloca to ensure we get gcc builtin semantics
#define ast_strdup(str)
A wrapper for strdup()
#define ast_asprintf(ret, fmt,...)
A wrapper for asprintf()
#define ast_calloc(num, len)
A wrapper for calloc()
int ao2_weakproxy_subscribe(void *weakproxy, ao2_weakproxy_notification_cb cb, void *data, int flags)
Request notification when weakproxy points to NULL.
#define ao2_iterator_next(iter)
#define ao2_link(container, obj)
Add an object to a container.
@ AO2_ALLOC_OPT_LOCK_NOLOCK
@ AO2_ALLOC_OPT_LOCK_RWLOCK
@ AO2_ALLOC_OPT_LOCK_MUTEX
#define ao2_callback(c, flags, cb_fn, arg)
ao2_callback() is a generic function that applies cb_fn() to all objects in a container,...
int ao2_container_count(struct ao2_container *c)
Returns the number of elements in a container.
#define AO2_STRING_FIELD_CMP_FN(stype, field)
Creates a compare function for a structure string field.
#define ao2_unlink(container, obj)
Remove an object from a container.
#define ao2_unlink_flags(container, obj, flags)
Remove an object from a container.
#define ao2_link_flags(container, obj, flags)
Add an object to a container.
void(* ao2_destructor_fn)(void *vdoomed)
Typedef for an object destructor.
#define ao2_alloc_with_lockobj(data_size, destructor_fn, lockobj, tag)
Allocate and initialize an object with separate locking.
#define ao2_find(container, arg, flags)
struct ao2_iterator ao2_iterator_init(struct ao2_container *c, int flags) attribute_warn_unused_result
Create an iterator for a container.
#define ao2_t_weakproxy_alloc(data_size, destructor_fn, tag)
#define ao2_weakproxy_find(c, arg, flags, tag)
Perform an ao2_find on a container with ao2_weakproxy objects, returning the real object.
void * __ao2_weakproxy_find(struct ao2_container *c, const void *arg, enum search_flags flags, const char *tag, const char *file, int line, const char *func)
#define ao2_ref(o, delta)
Reference/unreference an object and return the old refcount.
#define ao2_alloc_options(data_size, destructor_fn, options)
#define ao2_bump(obj)
Bump refcount on an AO2 object by one, returning the object.
#define AO2_STRING_FIELD_HASH_FN(stype, field)
Creates a hash function for a structure string field.
void ao2_iterator_destroy(struct ao2_iterator *iter)
Destroy a container iterator.
@ OBJ_SEARCH_PARTIAL_KEY
The arg parameter is a partial search key similar to OBJ_SEARCH_KEY.
@ OBJ_SEARCH_OBJECT
The arg parameter is an object of the same type.
@ OBJ_NOLOCK
Assume that the ao2_container is already locked.
@ OBJ_SEARCH_MASK
Search option field mask.
@ OBJ_SEARCH_KEY
The arg parameter is a search key, but is not an object.
#define ao2_container_alloc_list(ao2_options, container_options, sort_fn, cmp_fn)
Allocate and initialize a list container.
#define ao2_alloc(data_size, destructor_fn)
void * __ao2_alloc(size_t data_size, ao2_destructor_fn destructor_fn, unsigned int options, const char *tag, const char *file, int line, const char *func) attribute_warn_unused_result
#define ao2_container_alloc_hash(ao2_options, container_options, n_buckets, hash_fn, sort_fn, cmp_fn)
Allocate and initialize a hash container with the desired number of buckets.
#define ao2_t_weakproxy_set_object(weakproxy, obj, flags, tag)
static const char config[]
Configuration option-handling.
int(* aco_option_handler)(const struct aco_option *opt, struct ast_variable *var, void *obj)
A callback function for handling a particular option.
int aco_set_defaults(struct aco_type *type, const char *category, void *obj)
Set all default options of obj.
void aco_info_destroy(struct aco_info *info)
Destroy an initialized aco_info struct.
int aco_info_init(struct aco_info *info)
Initialize an aco_info structure.
aco_option_type
The option types.
@ OPT_UINT_T
Type for default option handler for unsigned integers.
@ OPT_CODEC_T
Type for default option handler for format capabilities.
@ OPT_BOOL_T
Type for default option handler for bools (ast_true/ast_false)
@ OPT_CUSTOM_T
Type for a custom (user-defined) option handler.
@ OPT_CHAR_ARRAY_T
Type for default option handler for character array strings.
@ OPT_SOCKADDR_T
Type for default handler for ast_sockaddrs.
@ OPT_YESNO_T
Type for default option handler for bools (ast_true/ast_false)
@ OPT_INT_T
Type for default option handler for signed integers.
@ OPT_DOUBLE_T
Type for default option handler for doubles.
@ OPT_STRINGFIELD_T
Type for default option handler for stringfields.
void *(* aco_type_item_alloc)(const char *category)
Allocate a configurable ao2 object.
int aco_process_var(struct aco_type *type, const char *cat, struct ast_variable *var, void *obj)
Parse a single ast_variable and apply it to an object.
int __aco_option_register(struct aco_info *info, const char *name, enum aco_matchtype match_type, struct aco_type **types, const char *default_val, enum aco_option_type type, aco_option_handler handler, unsigned int flags, unsigned int no_doc, size_t argc,...)
register a config option
static int regex(struct ast_channel *chan, const char *cmd, char *parse, char *buf, size_t len)
static char prefix[MAX_PREFIX]
char * strsep(char **str, const char *delims)
struct ast_config * ast_config_load2(const char *filename, const char *who_asked, struct ast_flags flags)
Load a config file.
const char * ast_variable_find_in_list(const struct ast_variable *list, const char *variable)
Gets the value of a variable from a variable list by name.
#define ast_variable_new(name, value, filename)
#define CONFIG_STATUS_FILEINVALID
struct ast_variable * ast_variables_dup(struct ast_variable *var)
Duplicate variable list.
void ast_config_destroy(struct ast_config *cfg)
Destroys a config.
struct ast_variable * ast_variable_list_append_hint(struct ast_variable **head, struct ast_variable *search_hint, struct ast_variable *new_var)
Appends a variable list to the end of another list.
void ast_variables_destroy(struct ast_variable *var)
Free variable list.
struct ast_variable * ast_variable_browse(const struct ast_config *config, const char *category_name)
Support for logging to various files, console and syslog Configuration in file logger....
#define ast_debug(level,...)
Log a DEBUG message.
#define ast_verb(level,...)
Asterisk JSON abstraction layer.
struct ast_json * ast_json_string_create(const char *value)
Construct a JSON string from value.
void ast_json_unref(struct ast_json *value)
Decrease refcount on value. If refcount reaches zero, value is freed.
struct ast_json * ast_json_object_create(void)
Create a new JSON object.
int ast_json_object_set(struct ast_json *object, const char *key, struct ast_json *value)
Set a field in a JSON object.
Asterisk module definitions.
#define ast_module_unref(mod)
Release a reference to the module.
#define ast_module_running_ref(mod)
Hold a reference to the module if it is running.
static char * ast_sockaddr_stringify(const struct ast_sockaddr *addr)
Wrapper around ast_sockaddr_stringify_fmt() with default format.
struct ast_sorcery_instance_observer observer
static struct ast_sorcery * sorcery
#define INSTANCE_BUCKETS
Number of buckets for instances (should be prime for performance reasons)
const char * ast_sorcery_object_get_extended(const void *object, const char *name)
Get an extended field value from a sorcery object.
static int int_handler_fn(const void *obj, const intptr_t *args, char **buf)
const char * ast_sorcery_object_get_id(const void *object)
Get the unique identifier of a sorcery object.
static int sorcery_observer_notify_delete(void *obj, void *arg, int flags)
Internal callback function which notifies an individual observer that an object has been deleted.
int ast_sorcery_wizard_unregister(const struct ast_sorcery_wizard *interface)
Unregister a sorcery wizard.
static int sorcery_observers_notify_create(void *data)
Internal callback function which notifies observers that an object has been created.
void ast_sorcery_observer_remove(const struct ast_sorcery *sorcery, const char *type, const struct ast_sorcery_observer *callbacks)
Remove an observer from a specific object type.
int ast_sorcery_object_fields_register(struct ast_sorcery *sorcery, const char *type, const char *regex, aco_option_handler config_handler, sorcery_fields_handler sorcery_handler)
Register a regex for multiple fields within an object.
int ast_sorcery_object_set_extended(const void *object, const char *name, const char *value)
Set an extended field value on a sorcery object.
void ast_sorcery_instance_observer_remove(struct ast_sorcery *sorcery, const struct ast_sorcery_instance_observer *callbacks)
Remove an observer from a sorcery instance.
#define WIZARD_NAME_COMPARE(a, b)
enum ast_sorcery_apply_result __ast_sorcery_apply_default(struct ast_sorcery *sorcery, const char *type, const char *module, const char *name, const char *data)
Apply default object wizard mappings.
static int sorcery_observer_notify_update(void *obj, void *arg, int flags)
Internal callback function which notifies an individual observer that an object has been updated.
void ast_sorcery_load(const struct ast_sorcery *sorcery)
Inform any wizards to load persistent objects.
void ast_sorcery_wizard_observer_remove(struct ast_sorcery_wizard *interface, const struct ast_sorcery_wizard_observer *callbacks)
Remove an observer from a sorcery wizard.
static int sorcery_cache_create(void *obj, void *arg, int flags)
Internal function used to create an object in caching wizards.
const char * ast_sorcery_get_module(const struct ast_sorcery *sorcery)
Get the module that has opened the provided sorcery instance.
static int chararray_handler_fn(const void *obj, const intptr_t *args, char **buf)
const char * ast_sorcery_object_get_type(const void *object)
Get the type of a sorcery object.
static int sorcery_observers_notify_delete(void *data)
Internal callback function which notifies observers that an object has been deleted.
#define NOTIFY_GLOBAL_OBSERVERS(container, callback,...)
static void sorcery_destructor(void *obj)
Destructor called when sorcery structure is destroyed.
#define INITIAL_WIZARD_VECTOR_SIZE
#define MAX_REGEX_ERROR_LEN
void ast_sorcery_object_set_copy_handler(struct ast_sorcery *sorcery, const char *type, sorcery_copy_handler copy)
Set the copy handler for an object type.
void ast_sorcery_object_set_has_dynamic_contents(const void *object)
Set the dynamic contents flag on a sorcery object.
static int stringfield_handler_fn(const void *obj, const intptr_t *args, char **buf)
int ast_sorcery_create(const struct ast_sorcery *sorcery, void *object)
Create and potentially persist an object using an available wizard.
static int codec_handler_fn(const void *obj, const intptr_t *args, char **buf)
struct ast_sorcery_object_type * ast_sorcery_get_object_type(const struct ast_sorcery *sorcery, const char *type)
Get the sorcery object type given a type name.
#define WIZARD_BUCKETS
Number of buckets for wizards (should be prime for performance reasons)
int ast_sorcery_diff(const struct ast_sorcery *sorcery, const void *original, const void *modified, struct ast_variable **changes)
Create a changeset of two objects.
void * ast_sorcery_retrieve_by_id(const struct ast_sorcery *sorcery, const char *type, const char *id)
Retrieve an object using its unique identifier.
AST_VECTOR_RW(ast_sorcery_object_wizards, struct ast_sorcery_object_wizard *)
Interface for a sorcery object type wizards.
void ast_sorcery_reload(const struct ast_sorcery *sorcery)
Inform any wizards to reload persistent objects.
int ast_sorcery_get_wizard_mapping_count(struct ast_sorcery *sorcery, const char *type)
Return the number of wizards mapped to an object type.
struct ao2_container * ast_sorcery_retrieve_by_regex(const struct ast_sorcery *sorcery, const char *type, const char *regex)
Retrieve multiple objects using a regular expression on their id.
int __ast_sorcery_wizard_register(const struct ast_sorcery_wizard *interface, struct ast_module *module)
Register a sorcery wizard.
static void sorcery_object_type_destructor(void *obj)
Destructor function for object types.
int ast_sorcery_observer_add(const struct ast_sorcery *sorcery, const char *type, const struct ast_sorcery_observer *callbacks)
Add an observer to a specific object type.
static int sorcery_observer_remove(void *obj, void *arg, int flags)
Internal callback function for removing an observer.
enum ast_sorcery_apply_result __ast_sorcery_insert_wizard_mapping(struct ast_sorcery *sorcery, const char *type, const char *module, const char *name, const char *data, unsigned int caching, int position)
Internal function which creates an object type and inserts a wizard mapping.
static struct ast_threadpool * threadpool
Thread pool for observers.
void ast_sorcery_force_reload(const struct ast_sorcery *sorcery)
Inform any wizards to reload persistent objects, even if no changes determined.
void ast_sorcery_load_object(const struct ast_sorcery *sorcery, const char *type)
Inform any wizards of a specific object type to load persistent objects.
static struct ast_variable * get_single_field_as_var_list(const void *object, struct ast_sorcery_object_field *object_field)
#define WIZARD_COMPARE(a, b)
static struct ast_variable * get_multiple_fields_as_var_list(const void *object, struct ast_sorcery_object_field *object_field)
void * ast_sorcery_generic_alloc(size_t size, ao2_destructor_fn destructor)
Allocate a generic sorcery capable object.
static int sorcery_wizard_load(void *obj, void *arg, int flags)
int ast_sorcery_object_unregister(struct ast_sorcery *sorcery, const char *type)
Unregister an object type.
static int sorcery_generic_observer_remove(void *obj, void *arg, int flags)
Internal callback function for removing a generic observer.
int __ast_sorcery_remove_wizard_mapping(struct ast_sorcery *sorcery, const char *type, const char *module, const char *name)
Internal function removes a wizard mapping.
static void sorcery_proxy_cb(void *weakproxy, void *data)
Hashing function for sorcery types.
static int sorcery_observer_notify_loaded(void *obj, void *arg, int flags)
Internal callback function which notifies an individual observer that an object type has been loaded.
int ast_sorcery_object_id_compare(void *obj, void *arg, int flags)
ao2 object comparator based on sorcery id.
static int yesno_handler_fn(const void *obj, const intptr_t *args, char **buf)
static int bool_handler_fn(const void *obj, const intptr_t *args, char **buf)
static int sorcery_extended_fields_handler(const void *obj, struct ast_variable **fields)
unsigned int ast_sorcery_object_has_dynamic_contents(const void *object)
Get whether an object contains dynamic contents or not.
void ast_sorcery_ref(struct ast_sorcery *sorcery)
Increase the reference count of a sorcery structure.
static int uint_handler_fn(const void *obj, const intptr_t *args, char **buf)
int __ast_sorcery_object_field_register(struct ast_sorcery *sorcery, const char *type, const char *name, const char *default_val, enum aco_option_type opt_type, aco_option_handler config_handler, sorcery_field_handler sorcery_handler, sorcery_fields_handler multiple_handler, unsigned int flags, unsigned int no_doc, unsigned int alias, size_t argc,...)
Register a field within an object.
int ast_sorcery_wizard_observer_add(struct ast_sorcery_wizard *interface, const struct ast_sorcery_wizard_observer *callbacks)
Add an observer to a sorcery wizard.
static void sorcery_object_destructor(void *object)
int __ast_sorcery_object_register(struct ast_sorcery *sorcery, const char *type, unsigned int hidden, unsigned int reloadable, aco_type_item_alloc alloc, sorcery_transform_handler transform, sorcery_apply_handler apply)
Register an object type.
static int sorcery_wizard_create(const struct ast_sorcery_object_wizard *object_wizard, const struct sorcery_details *details)
Internal function which returns if the wizard has created the object.
int ast_sorcery_changeset_create(const struct ast_variable *original, const struct ast_variable *modified, struct ast_variable **changes)
Create a changeset given two object sets.
#define NOTIFY_INSTANCE_OBSERVERS(container, callback,...)
static int sorcery_reloadable(const struct ast_sorcery *sorcery, const char *type)
Retrieves whether or not the type is reloadable.
static int sorcery_object_load(void *obj, void *arg, int flags)
static struct ao2_container * wizards
Registered sorcery wizards.
enum ast_sorcery_apply_result __ast_sorcery_apply_config(struct ast_sorcery *sorcery, const char *name, const char *module)
Apply configured wizard mappings.
int ast_sorcery_is_object_field_registered(const struct ast_sorcery_object_type *object_type, const char *field_name)
Determine if a particular object field has been registered with sorcery.
static struct ao2_container * instances
Registered sorcery instances.
static int sockaddr_handler_fn(const void *obj, const intptr_t *args, char **buf)
void * ast_sorcery_alloc(const struct ast_sorcery *sorcery, const char *type, const char *id)
Allocate an object.
int ast_sorcery_object_id_sort(const void *obj, const void *arg, int flags)
ao2 object sorter based on sorcery id.
const struct timeval ast_sorcery_object_get_created(const void *object)
Get when the sorcery object was created.
void * ast_sorcery_lockable_alloc(size_t size, ao2_destructor_fn destructor, void *lockobj)
Allocate a generic sorcery capable object with locking.
#define OBJECT_FIELD_BUCKETS
Number of buckets for object fields (should be prime for performance reasons)
struct ao2_container * observers
Registered global observers.
static int sorcery_observer_notify_create(void *obj, void *arg, int flags)
Internal callback function which notifies an individual observer that an object has been created.
int ast_sorcery_update(const struct ast_sorcery *sorcery, void *object)
Update an object.
static int sorcery_extended_config_handler(const struct aco_option *opt, struct ast_variable *var, void *obj)
int ast_sorcery_objectset_apply(const struct ast_sorcery *sorcery, void *object, struct ast_variable *objectset)
Apply an object set (KVP list) to an object.
int ast_sorcery_get_wizard_mapping(struct ast_sorcery *sorcery, const char *type, int index, struct ast_sorcery_wizard **wizard, void **data)
By index, return a wizard mapped to an object type.
static int sorcery_wizard_update(const struct ast_sorcery_object_wizard *object_wizard, const struct sorcery_details *details)
Internal function which returns if a wizard has updated the object.
void ast_sorcery_force_reload_object(const struct ast_sorcery *sorcery, const char *type)
Inform any wizards of a specific object type to reload persistent objects even if no changes determin...
static void sorcery_observer_invocation_destroy(void *obj)
Destructor for observer invocation.
static struct sorcery_observer_invocation * sorcery_observer_invocation_alloc(struct ast_sorcery_object_type *object_type, void *object)
Allocator function for observer invocation.
enum ast_sorcery_apply_result __ast_sorcery_apply_wizard_mapping(struct ast_sorcery *sorcery, const char *type, const char *module, const char *name, const char *data, unsigned int caching)
Internal function which creates an object type and adds a wizard mapping.
int __ast_sorcery_object_type_remove_wizard(struct ast_sorcery *sorcery, const char *object_type_name, const char *module, const char *wizard_type_name, const char *wizard_args)
Remove an object wizard mapping.
static sorcery_field_handler sorcery_field_default_handler(enum aco_option_type type)
void ast_sorcery_global_observer_remove(const struct ast_sorcery_global_observer *callbacks)
Remove a global observer from sorcery.
static int sorcery_wizard_delete(const struct ast_sorcery_object_wizard *object_wizard, const struct sorcery_details *details)
Internal function which returns if a wizard has deleted the object.
struct ast_json * ast_sorcery_objectset_json_create(const struct ast_sorcery *sorcery, const void *object)
Create an object set in JSON format for an object.
static void sorcery_cleanup(void)
Hashing and comparison functions for sorcery wizards.
int ast_sorcery_global_observer_add(const struct ast_sorcery_global_observer *callbacks)
Add a global observer to sorcery.
void ast_sorcery_reload_object(const struct ast_sorcery *sorcery, const char *type)
Inform any wizards of a specific object type to reload persistent objects.
static int sorcery_observers_notify_update(void *data)
Internal callback function which notifies observers that an object has been updated.
#define NOTIFY_WIZARD_OBSERVERS(container, callback,...)
struct ast_variable * ast_sorcery_objectset_create2(const struct ast_sorcery *sorcery, const void *object, enum ast_sorcery_field_handler_flags flags)
Create an object set (KVP list) for an object.
int ast_sorcery_is_stale(const struct ast_sorcery *sorcery, void *object)
Determine if a sorcery object is stale with respect to its backing datastore.
int ast_sorcery_instance_observer_add(struct ast_sorcery *sorcery, const struct ast_sorcery_instance_observer *callbacks)
Add an observer to a sorcery instance.
#define TYPE_BUCKETS
Number of buckets for types (should be prime for performance reasons)
int ast_sorcery_object_id_hash(const void *obj, int flags)
ao2 object hasher based on sorcery id.
struct ast_sorcery * __ast_sorcery_open(const char *module_name, const char *file, int line, const char *func)
static int sorcery_observers_notify_loaded(void *data)
Internal callback function which notifies observers that an object type has been loaded.
static int is_registered_cb(void *obj, void *arg, int flags)
void * ast_sorcery_retrieve_by_fields(const struct ast_sorcery *sorcery, const char *type, unsigned int flags, struct ast_variable *fields)
Retrieve an object or multiple objects using specific fields.
static void sorcery_object_field_destructor(void *obj)
static int double_handler_fn(const void *obj, const intptr_t *args, char **buf)
int ast_sorcery_object_set_congestion_levels(struct ast_sorcery *sorcery, const char *type, long low_water, long high_water)
Set the high and low alert water marks of the sorcery object type.
struct ast_sorcery * ast_sorcery_retrieve_by_module_name(const char *module_name)
Search function for sorcery instances.
int ast_sorcery_delete(const struct ast_sorcery *sorcery, void *object)
Delete an object.
void * ast_sorcery_copy(const struct ast_sorcery *sorcery, const void *object)
Create a copy of an object.
struct ao2_container * ast_sorcery_retrieve_by_prefix(const struct ast_sorcery *sorcery, const char *type, const char *prefix, const size_t prefix_len)
Retrieve multiple objects whose id begins with the specified prefix.
int ast_sorcery_init(void)
Compare function for sorcery instances.
static struct ast_sorcery_object_type * sorcery_object_type_alloc(const char *type, const char *module)
Internal function which allocates an object type structure.
static void sorcery_object_wizard_destructor(void *obj)
Object wizard destructor.
enum ast_sorcery_apply_result __ast_sorcery_object_type_insert_wizard(struct ast_sorcery *sorcery, const char *object_type_name, const char *module, const char *wizard_type_name, const char *wizard_args, enum ast_sorcery_wizard_apply_flags flags, int position, struct ast_sorcery_wizard **wizard, void **wizard_data)
Insert an additional object wizard mapping at a specific position in the wizard list returning wizard...
static void sorcery_internal_wizard_destructor(void *obj)
void ast_sorcery_object_set_diff_handler(struct ast_sorcery *sorcery, const char *type, sorcery_diff_handler diff)
Set the diff handler for an object type.
Sorcery Data Access Layer API.
#define ast_sorcery_objectset_create(sorcery, object)
Create an object set (KVP list) for an object.
struct ast_variable *(* sorcery_transform_handler)(struct ast_variable *set)
A callback function for performing a transformation on an object set.
@ AST_RETRIEVE_FLAG_MULTIPLE
Return all matching objects.
int(* sorcery_fields_handler)(const void *obj, struct ast_variable **fields)
A callback function for translating multiple values into an ast_variable list.
int(* sorcery_apply_handler)(const struct ast_sorcery *sorcery, void *obj)
A callback function for when an object set is successfully applied to an object.
int(* sorcery_diff_handler)(const void *original, const void *modified, struct ast_variable **changes)
A callback function for generating a changeset between two objects.
int(* sorcery_copy_handler)(const void *src, void *dst)
A callback function for copying the contents of one object to another.
@ AST_SORCERY_WIZARD_POSITION_LAST
ast_sorcery_field_handler_flags
Field handler flags.
@ AST_HANDLER_PREFER_STRING
Try both handlers, string first.
@ AST_HANDLER_PREFER_LIST
Try both handlers, list first.
@ AST_HANDLER_ONLY_LIST
Use list handler only.
@ AST_HANDLER_ONLY_STRING
Use string handler only.
int(* sorcery_field_handler)(const void *obj, const intptr_t *args, char **buf)
A callback function for translating a value into a string.
#define MAX_OBJECT_FIELD
Maximum length of an object field name.
#define MAX_OBJECT_TYPE
Maximum size of an object type.
ast_sorcery_wizard_apply_flags
Wizard Apply Flags.
@ AST_SORCERY_WIZARD_APPLY_NONE
@ AST_SORCERY_WIZARD_APPLY_ALLOW_DUPLICATE
@ AST_SORCERY_WIZARD_APPLY_READONLY
@ AST_SORCERY_WIZARD_APPLY_CACHING
@ AST_SORCERY_APPLY_SUCCESS
@ AST_SORCERY_APPLY_NO_CONFIGURATION
@ AST_SORCERY_APPLY_DUPLICATE
@ AST_SORCERY_APPLY_DEFAULT_UNNECESSARY
const char * ast_string_field
String manipulation functions.
#define S_OR(a, b)
returns the equivalent of logic or for strings: first one if not empty, otherwise second one.
static force_inline int attribute_pure ast_str_hash(const char *str)
Compute a hash value on a string.
static force_inline int attribute_pure ast_strlen_zero(const char *s)
#define ast_str_alloca(init_len)
void ast_copy_string(char *dst, const char *src, size_t size)
Size-limited null-terminating string copy.
The representation of a single configuration file to be processed.
struct aco_type * types[]
struct aco_file * files[]
Type information about a category-level configurable object.
When we need to walk through a container, we use an ao2_iterator to keep track of the current positio...
Structure used to handle boolean flags.
Abstract JSON element (object, array, string, int, ...).
Socket address structure.
Interface for the global sorcery observer.
Interface for the sorcery instance observer.
Structure for an internal wizard instance.
struct ao2_container * observers
Observers.
struct ast_sorcery_wizard callbacks
Wizard interface itself.
Structure which contains details about a sorcery object.
struct ast_sorcery_object * object
Pointer to internal sorcery object information.
Structure for registered object field.
regex_t * name_regex
The compiled name regex if name is a regex.
sorcery_field_handler handler
Callback function for translation of a single value.
sorcery_fields_handler multiple_handler
Callback function for translation of multiple values.
intptr_t args[]
Position of the field.
char name[MAX_OBJECT_FIELD]
Name of the field.
Structure for registered object type observer.
const struct ast_sorcery_observer * callbacks
Pointer to the observer implementation.
Structure for registered object type.
sorcery_copy_handler copy
Optional object copy callback.
struct aco_file * file
Configuration framework file information.
struct ast_sorcery_object_wizards wizards
Wizard instances.
sorcery_transform_handler transform
Optional transformation callback.
struct ao2_container * fields
Object fields.
char name[MAX_OBJECT_TYPE]
Unique name of the object type.
sorcery_diff_handler diff
Optional object diff callback.
sorcery_apply_handler apply
Optional object set apply callback.
struct ao2_container * observers
Observers.
struct ast_taskprocessor * serializer
Serializer for observers.
struct aco_type type
Type details.
unsigned int reloadable
Specifies if object type is reloadable or not.
struct aco_info * info
Configuration framework general information.
Structure for a wizard instance which operates on objects.
unsigned int caching
Wizard is acting as an object cache.
struct ast_sorcery_internal_wizard * wizard
Wizard interface itself.
void * data
Unique data for the wizard.
unsigned int allow_duplicates
Wizard allows others of the same type.
char wizard_args[0]
Wizard arguments.
unsigned int read_only
Wizard is read_only.
Structure for internal sorcery object information.
unsigned int has_dynamic_contents
Whether this object has dynamic contents or not.
struct timeval created
Time that the object was created.
ao2_destructor_fn destructor
Optional object destructor.
struct ast_variable * extended
Extended object fields.
char type[MAX_OBJECT_TYPE]
Type of object.
char * id
Unique identifier of this object.
Interface for a sorcery object type observer.
Interface for the sorcery wizard observer.
Interface for a sorcery wizard.
void(* close)(void *data)
Callback for closing a wizard.
void(* retrieve_multiple)(const struct ast_sorcery *sorcery, void *data, const char *type, struct ao2_container *objects, const struct ast_variable *fields)
Optional callback for retrieving multiple objects using some optional field criteria.
struct ast_module * module
Pointer to the Asterisk module this wizard is implemented by.
void *(* retrieve_fields)(const struct ast_sorcery *sorcery, void *data, const char *type, const struct ast_variable *fields)
Optional callback for retrieving an object using fields.
const char * name
Name of the wizard.
void(* load)(void *data, const struct ast_sorcery *sorcery, const char *type)
Optional callback for loading persistent objects.
void *(* retrieve_id)(const struct ast_sorcery *sorcery, void *data, const char *type, const char *id)
Callback for retrieving an object using an id.
int(* create)(const struct ast_sorcery *sorcery, void *data, void *object)
Callback for creating an object.
int(* delete)(const struct ast_sorcery *sorcery, void *data, void *object)
Callback for deleting an object.
int(* is_stale)(const struct ast_sorcery *sorcery, void *data, void *object)
Callback for whether or not the wizard believes the object is stale.
void(* retrieve_prefix)(const struct ast_sorcery *sorcery, void *data, const char *type, struct ao2_container *objects, const char *prefix, const size_t prefix_len)
Optional callback for retrieving multiple objects by matching their id with a prefix.
void(* force_reload)(void *data, const struct ast_sorcery *sorcery, const char *type)
Optional callback for forcing a reload to occur, even if wizard has determined no changes.
void(* retrieve_regex)(const struct ast_sorcery *sorcery, void *data, const char *type, struct ao2_container *objects, const char *regex)
Callback for retrieving multiple objects using a regex on their id.
int(* update)(const struct ast_sorcery *sorcery, void *data, void *object)
Callback for updating an object.
void(* reload)(void *data, const struct ast_sorcery *sorcery, const char *type)
Optional callback for reloading persistent objects.
Full structure for sorcery.
char * module_name
Pointer to module_name in the associated sorcery_proxy.
struct ao2_container * observers
Observers.
struct ao2_container * types
Container for known object types.
Support for dynamic strings.
A ast_taskprocessor structure is a singleton by name.
An opaque threadpool structure.
Structure for variables, used for configurations and for channel variables.
struct ast_variable * next
Structure used when calling create, update, or delete.
void * obj
Pointer to the object itself.
const struct ast_sorcery * sorcery
Pointer to the sorcery instance.
A global observer wrapper.
const struct ast_sorcery_global_observer * callbacks
An instance observer wrapper.
const struct ast_sorcery_instance_observer * callbacks
Structure for passing load/reload details.
unsigned int force
Whether this is forced or not.
const char * type
Type of object being loaded.
unsigned int reload
Whether this is a reload or not.
const struct ast_sorcery * sorcery
Sorcery structure in use.
Structure used for observer invocations.
void * object
Pointer to the object.
struct ast_sorcery_object_type * object_type
Pointer to the object type.
Proxy object for sorcery.
char module_name[0]
The name of the module owning this sorcery instance.
A wizard observer wrapper.
const struct ast_sorcery_wizard_observer * callbacks
An API for managing task processing threads that can be shared across modules.
void * ast_taskprocessor_unreference(struct ast_taskprocessor *tps)
Unreference the specified taskprocessor and its reference count will decrement.
int ast_taskprocessor_push(struct ast_taskprocessor *tps, int(*task_exe)(void *datap), void *datap) attribute_warn_unused_result
Push a task into the specified taskprocessor queue and signal the taskprocessor thread.
void ast_taskprocessor_build_name(char *buf, unsigned int size, const char *format,...)
Build a taskprocessor name with a sequence number on the end.
int ast_taskprocessor_alert_set_levels(struct ast_taskprocessor *tps, long low_water, long high_water)
Set the high and low alert water marks of the given taskprocessor queue.
#define AST_TASKPROCESSOR_MAX_NAME
Suggested maximum taskprocessor name length (less null terminator).
void ast_threadpool_shutdown(struct ast_threadpool *pool)
Shut down a threadpool and destroy it.
struct ast_threadpool * ast_threadpool_create(const char *name, struct ast_threadpool_listener *listener, const struct ast_threadpool_options *options)
Create a new threadpool.
#define AST_THREADPOOL_OPTIONS_VERSION
struct ast_taskprocessor * ast_threadpool_serializer(const char *name, struct ast_threadpool *pool)
Serialized execution of tasks within a ast_threadpool.
struct timeval ast_tvnow(void)
Returns current timeval. Meant to replace calls to gettimeofday().
#define RAII_VAR(vartype, varname, initval, dtor)
Declare a variable that will call a destructor function when it goes out of scope.
char * ast_uuid_generate_str(char *buf, size_t size)
Generate a UUID string.
Vector container support.
#define AST_VECTOR_REMOVE_ORDERED(vec, idx)
Remove an element from a vector by index while maintaining order.
#define AST_VECTOR_SIZE(vec)
Get the number of elements in a vector.
#define AST_VECTOR_INSERT_AT(vec, idx, elem)
Insert an element at a specific position in a vector, growing the vector if needed.
#define AST_VECTOR_RW_WRLOCK(vec)
Obtain write lock on vector.
#define AST_VECTOR_REMOVE_CMP_ORDERED(vec, value, cmp, cleanup)
Remove an element from a vector that matches the given comparison while maintaining order.
#define AST_VECTOR_RW_UNLOCK(vec)
Unlock vector.
#define AST_VECTOR_GET_CMP(vec, value, cmp)
Get an element from a vector that matches the given comparison.
#define AST_VECTOR_RW_FREE(vec)
Deallocates this locked vector.
#define AST_VECTOR_CALLBACK(vec, callback, default_value,...)
Execute a callback on every element in a vector returning the first matched.
#define AST_VECTOR_RW_RDLOCK(vec)
Obtain read lock on vector.
#define AST_VECTOR_CALLBACK_VOID(vec, callback,...)
Execute a callback on every element in a vector disregarding callback return.
#define AST_VECTOR_GET(vec, idx)
Get an element from a vector.
#define AST_VECTOR_RW_INIT(vec, size)
Initialize a vector with a read/write lock.