Merge branch 'variadic-enumerators'

This adds several changes to enumerator_t and linked_list_t to improve
portability.  In particular to Apple's ARM64 iOS platform, whose calling
convention for variadic and regular functions are different.  This means
that assigning a non-variadic function to a variadic function pointer,
as we did with our enumerator_t::enumerate() implementations and several
callbacks, will result in crashes as the called function will access the
arguments differently than the caller provided them.

To avoid this issue the enumerator_t interface is now fully variadic.
A new mandatory method is added, venumerate(), that takes a va_list with
the arguments provided while enumerating.  enumerate() is replaced with
a generic implementation that prepares a va_list and calls the
enumerator's venumerate() implementation.  As this allows passing the
arguments of one enumerator to another it avoids the five pointer hack
used by enumerator_create_nested() and enumerator_create_cleaner().
To simplify the implementation of venumerate() a helper macro is provided
that assigns values from a given va_list to local variables.

The signature of the callback passed to enumerator_create_filter() has
also changed significantly.  It's now required to enumerate over the
original enumerator in the callback as this avoids the previous in/out
pointer hack. The arguments to the outer enumerator are provided in a
va_list.

Similar changes to avoid such five pointer hacks affect the signatures
of the callbacks for linked_list_t's invoke_function() and find_first()
methods.  For the latter the return type also changed from status_t to
bool, which is important as SUCCESS is defined as 0, so checks for ==
SUCCESS will now fail.
This commit is contained in:
Tobias Brunner 2017-05-26 13:57:57 +02:00
commit b668bf3f9e
128 changed files with 2912 additions and 1962 deletions

View File

@ -120,48 +120,49 @@ typedef struct {
identification_t *id;
} cert_data_t;
/**
* Destroy CA certificate enumerator data
*/
static void cert_data_destroy(cert_data_t *data)
CALLBACK(cert_data_destroy, void,
cert_data_t *data)
{
data->this->lock->unlock(data->this->lock);
free(data);
}
/**
* Filter function for certificates enumerator
*/
static bool cert_filter(cert_data_t *data, certificate_t **in,
certificate_t **out)
CALLBACK(cert_filter, bool,
cert_data_t *data, enumerator_t *orig, va_list args)
{
certificate_t *cert = *in;
certificate_t *cert, **out;
public_key_t *public;
public = cert->get_public_key(cert);
if (!public)
{
return FALSE;
}
if (data->key != KEY_ANY && public->get_type(public) != data->key)
{
public->destroy(public);
return FALSE;
}
if (data->id && data->id->get_type(data->id) == ID_KEY_ID &&
public->has_fingerprint(public, data->id->get_encoding(data->id)))
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &cert))
{
public = cert->get_public_key(cert);
if (!public)
{
continue;
}
if (data->key != KEY_ANY && public->get_type(public) != data->key)
{
public->destroy(public);
continue;
}
if (data->id && data->id->get_type(data->id) == ID_KEY_ID &&
public->has_fingerprint(public, data->id->get_encoding(data->id)))
{
public->destroy(public);
*out = cert;
return TRUE;
}
public->destroy(public);
if (data->id && !cert->has_subject(cert, data->id))
{
continue;
}
*out = cert;
return TRUE;
}
public->destroy(public);
if (data->id && !cert->has_subject(cert, data->id))
{
return FALSE;
}
*out = cert;
return TRUE;
return FALSE;
}
/**
@ -181,7 +182,7 @@ static enumerator_t *create_trusted_cert_enumerator(private_nm_creds_t *this,
this->lock->read_lock(this->lock);
return enumerator_create_filter(
this->certs->create_enumerator(this->certs),
(void*)cert_filter, data, (void*)cert_data_destroy);
cert_filter, data, cert_data_destroy);
}
METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
@ -235,9 +236,13 @@ typedef struct {
} shared_enumerator_t;
METHOD(enumerator_t, shared_enumerate, bool,
shared_enumerator_t *this, shared_key_t **key, id_match_t *me,
id_match_t *other)
shared_enumerator_t *this, va_list args)
{
shared_key_t **key;
id_match_t *me, *other;
VA_ARGS_VGET(args, key, me, other);
if (this->done)
{
return FALSE;
@ -307,7 +312,8 @@ METHOD(credential_set_t, create_shared_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_shared_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _shared_enumerate,
.destroy = _shared_destroy,
},
.this = this,

View File

@ -65,29 +65,33 @@ METHOD(attribute_handler_t, handle, bool,
return TRUE;
}
/**
* Implementation of create_attribute_enumerator().enumerate() for WINS
*/
static bool enumerate_nbns(enumerator_t *this,
configuration_attribute_type_t *type, chunk_t *data)
METHOD(enumerator_t, enumerate_nbns, bool,
enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
*type = INTERNAL_IP4_NBNS;
*data = chunk_empty;
/* done */
this->enumerate = (void*)return_false;
this->venumerate = (void*)return_false;
return TRUE;
}
/**
* Implementation of create_attribute_enumerator().enumerate() for DNS
*/
static bool enumerate_dns(enumerator_t *this,
configuration_attribute_type_t *type, chunk_t *data)
METHOD(enumerator_t, enumerate_dns, bool,
enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
*type = INTERNAL_IP4_DNS;
*data = chunk_empty;
/* enumerate WINS server as next attribute ... */
this->enumerate = (void*)enumerate_nbns;
this->venumerate = _enumerate_nbns;
return TRUE;
}
@ -100,7 +104,8 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t*,
INIT(enumerator,
/* enumerate DNS attribute first ... */
.enumerate = (void*)enumerate_dns,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_dns,
.destroy = (void*)free,
);
return enumerator;
@ -108,13 +113,20 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t*,
return enumerator_create_empty();
}
/**
* convert plain byte ptrs to handy chunk during enumeration
*/
static bool filter_chunks(void* null, char **in, chunk_t *out)
CALLBACK(filter_chunks, bool,
void *null, enumerator_t *orig, va_list args)
{
*out = chunk_create(*in, 4);
return TRUE;
chunk_t *out;
char *ptr;
VA_ARGS_VGET(args, out);
if (orig->enumerate(orig, &ptr))
{
*out = chunk_create(ptr, 4);
return TRUE;
}
return FALSE;
}
METHOD(nm_handler_t, create_enumerator, enumerator_t*,
@ -134,7 +146,7 @@ METHOD(nm_handler_t, create_enumerator, enumerator_t*,
return enumerator_create_empty();
}
return enumerator_create_filter(list->create_enumerator(list),
(void*)filter_chunks, NULL, NULL);
filter_chunks, NULL, NULL);
}
METHOD(nm_handler_t, reset, void,

View File

@ -101,61 +101,63 @@ static void sad_entry_destroy(sad_entry_t *entry)
}
}
/**
* Find a list entry with given src, dst, (remote) spi and proto values.
*/
static bool sad_entry_match(sad_entry_t * const entry, const host_t * const src,
const host_t * const dst, const uint32_t * const spi,
const uint8_t * const proto)
CALLBACK(sad_entry_match, bool,
sad_entry_t * const entry, va_list args)
{
const host_t *src, *dst;
const uint32_t *spi;
const uint8_t *proto;
VA_ARGS_VGET(args, src, dst, spi, proto);
if (entry->src == NULL || entry->dst == NULL)
{
return FALSE;
}
return src->ip_equals(entry->src, (host_t *)src) &&
dst->ip_equals(entry->dst, (host_t *)dst) &&
entry->spi_rem == *spi && entry->proto == *proto;
}
/**
* Find a list entry with given reqid, spi and proto values.
*/
static bool sad_entry_match_dst(sad_entry_t * const entry,
const uint32_t * const reqid,
const uint32_t * const spi,
const uint8_t * const proto)
CALLBACK(sad_entry_match_dst, bool,
sad_entry_t * const entry, va_list args)
{
const uint32_t *reqid, *spi;
const uint8_t *proto;
VA_ARGS_VGET(args, reqid, spi, proto);
return entry->reqid == *reqid &&
entry->spi_rem == *spi &&
entry->proto == *proto;
}
/**
* Find a list entry with given esa id.
*/
static bool sad_entry_match_esa_id(sad_entry_t * const entry,
const esa_id_type * const esa_id)
CALLBACK(sad_entry_match_esa_id, bool,
sad_entry_t * const entry, va_list args)
{
const esa_id_type *esa_id;
VA_ARGS_VGET(args, esa_id);
return entry->esa_id == *esa_id;
}
/**
* Find a list entry with given reqid and different esa id.
*/
static bool sad_entry_match_other_esa(sad_entry_t * const entry,
const esa_id_type * const esa_id,
const uint32_t * const reqid)
CALLBACK(sad_entry_match_other_esa, bool,
sad_entry_t * const entry, va_list args)
{
const esa_id_type *esa_id;
const uint32_t *reqid;
VA_ARGS_VGET(args, esa_id, reqid);
return entry->reqid == *reqid &&
entry->esa_id != *esa_id;
}
/**
* Compare two SAD entries for equality.
*/
static bool sad_entry_equal(sad_entry_t * const left, sad_entry_t * const right)
CALLBACK(sad_entry_equal, bool,
sad_entry_t * const left, va_list args)
{
sad_entry_t *right;
VA_ARGS_VGET(args, right);
if (left->src == NULL || left->dst == NULL || right->src == NULL ||
right->dst == NULL)
{
@ -175,8 +177,8 @@ METHOD(tkm_kernel_sad_t, insert, bool,
const uint32_t reqid, const host_t * const src, const host_t * const dst,
const uint32_t spi_loc, const uint32_t spi_rem, const uint8_t proto)
{
status_t result;
sad_entry_t *new_entry;
bool found;
INIT(new_entry,
.esa_id = esa_id,
@ -189,10 +191,9 @@ METHOD(tkm_kernel_sad_t, insert, bool,
);
this->mutex->lock(this->mutex);
result = this->data->find_first(this->data,
(linked_list_match_t)sad_entry_equal, NULL,
found = this->data->find_first(this->data, sad_entry_equal, NULL,
new_entry);
if (result == NOT_FOUND)
if (!found)
{
DBG3(DBG_KNL, "inserting SAD entry (esa: %llu, reqid: %u, src: %H, "
"dst: %H, spi_loc: %x, spi_rem: %x,proto: %u)", esa_id, reqid, src,
@ -207,7 +208,7 @@ METHOD(tkm_kernel_sad_t, insert, bool,
free(new_entry);
}
this->mutex->unlock(this->mutex);
return result == NOT_FOUND;
return !found;
}
METHOD(tkm_kernel_sad_t, get_esa_id, esa_id_type,
@ -218,11 +219,10 @@ METHOD(tkm_kernel_sad_t, get_esa_id, esa_id_type,
sad_entry_t *entry = NULL;
this->mutex->lock(this->mutex);
const status_t res = this->data->find_first(this->data,
(linked_list_match_t)sad_entry_match,
(void**)&entry, src, dst, &spi,
&proto);
if (res == SUCCESS && entry)
const bool res = this->data->find_first(this->data, sad_entry_match,
(void**)&entry, src, dst, &spi,
&proto);
if (res && entry)
{
id = entry->esa_id;
DBG3(DBG_KNL, "returning ESA id %llu of SAD entry (src: %H, dst: %H, "
@ -243,13 +243,12 @@ METHOD(tkm_kernel_sad_t, get_other_esa_id, esa_id_type,
esa_id_type id = 0;
sad_entry_t *entry = NULL;
uint32_t reqid;
status_t res;
bool res;
this->mutex->lock(this->mutex);
res = this->data->find_first(this->data,
(linked_list_match_t)sad_entry_match_esa_id,
res = this->data->find_first(this->data, sad_entry_match_esa_id,
(void**)&entry, &esa_id);
if (res == SUCCESS && entry)
if (res && entry)
{
reqid = entry->reqid;
}
@ -260,10 +259,9 @@ METHOD(tkm_kernel_sad_t, get_other_esa_id, esa_id_type,
return id;
}
res = this->data->find_first(this->data,
(linked_list_match_t)sad_entry_match_other_esa,
res = this->data->find_first(this->data, sad_entry_match_other_esa,
(void**)&entry, &esa_id, &reqid);
if (res == SUCCESS && entry)
if (res && entry)
{
id = entry->esa_id;
DBG3(DBG_KNL, "returning ESA id %llu of other SAD entry with reqid %u",
@ -281,10 +279,9 @@ METHOD(tkm_kernel_sad_t, get_dst_host, host_t *,
sad_entry_t *entry = NULL;
this->mutex->lock(this->mutex);
const status_t res = this->data->find_first(this->data,
(linked_list_match_t)sad_entry_match_dst,
(void**)&entry, &reqid, &spi, &proto);
if (res == SUCCESS && entry)
const bool res = this->data->find_first(this->data, sad_entry_match_dst,
(void**)&entry, &reqid, &spi, &proto);
if (res && entry)
{
dst = entry->dst;
DBG3(DBG_KNL, "returning destination host %H of SAD entry (reqid: %u,"

View File

@ -36,13 +36,20 @@ struct private_config_t {
linked_list_t *configs;
};
/**
* filter function for ike configs
*/
static bool ike_filter(void *data, peer_cfg_t **in, ike_cfg_t **out)
CALLBACK(ike_filter, bool,
void *data, enumerator_t *orig, va_list args)
{
*out = (*in)->get_ike_cfg(*in);
return TRUE;
peer_cfg_t *cfg;
ike_cfg_t **out;
VA_ARGS_VGET(args, out);
if (orig->enumerate(orig, &cfg))
{
*out = cfg->get_ike_cfg(cfg);
return TRUE;
}
return FALSE;
}
METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
@ -51,7 +58,7 @@ METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
return enumerator_create_filter(
this->configs->create_enumerator(this->configs),
(void*)ike_filter, NULL, NULL);
ike_filter, NULL, NULL);
}
METHOD(backend_t, create_peer_cfg_enumerator, enumerator_t*,

View File

@ -92,11 +92,12 @@ static void overlay_destroy(overlay_t *this)
free(this);
}
/**
* compare two overlays by path
*/
static bool overlay_equals(overlay_t *this, overlay_t *other)
CALLBACK(overlay_equals, bool,
overlay_t *this, va_list args)
{
overlay_t *other;
VA_ARGS_VGET(args, other);
return streq(this->path, other->path);
}
@ -108,8 +109,8 @@ static bool overlay_remove(private_cowfs_t *this, char *path)
{
overlay_t over, *current;
over.path = path;
if (this->overlays->find_first(this->overlays,
(linked_list_match_t)overlay_equals, (void**)&current, &over) != SUCCESS)
if (!this->overlays->find_first(this->overlays, overlay_equals,
(void**)&current, &over))
{
return FALSE;
}

View File

@ -267,10 +267,12 @@ typedef struct {
} template_enumerator_t;
METHOD(enumerator_t, template_enumerate, bool,
template_enumerator_t *this, char **template)
template_enumerator_t *this, va_list args)
{
struct stat st;
char *rel;
char *rel, **template;
VA_ARGS_VGET(args, template);
while (this->inner->enumerate(this->inner, &rel, NULL, &st))
{
@ -296,7 +298,8 @@ METHOD(dumm_t, create_template_enumerator, enumerator_t*,
template_enumerator_t *enumerator;
INIT(enumerator,
.public = {
.enumerate = (void*)_template_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _template_enumerate,
.destroy = (void*)_template_enumerator_destroy,
},
.inner = enumerator_create_directory(TEMPLATE_DIR),

View File

@ -73,20 +73,28 @@ METHOD(attribute_handler_t, release, void,
}
METHOD(enumerator_t, enumerate_dns6, bool,
enumerator_t *this, configuration_attribute_type_t *type, chunk_t *data)
enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
*type = INTERNAL_IP6_DNS;
*data = chunk_empty;
this->enumerate = (void*)return_false;
this->venumerate = (void*)return_false;
return TRUE;
}
METHOD(enumerator_t, enumerate_dns4, bool,
enumerator_t *this, configuration_attribute_type_t *type, chunk_t *data)
enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
*type = INTERNAL_IP4_DNS;
*data = chunk_empty;
this->enumerate = (void*)_enumerate_dns6;
this->venumerate = _enumerate_dns6;
return TRUE;
}
@ -96,7 +104,8 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t*,
enumerator_t *enumerator;
INIT(enumerator,
.enumerate = (void*)_enumerate_dns4,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_dns4,
.destroy = (void*)free,
);
return enumerator;

View File

@ -215,7 +215,7 @@ failed:
/**
* Bypass a single socket
*/
static bool bypass_single_socket(intptr_t fd, private_charonservice_t *this)
static bool bypass_single_socket(private_charonservice_t *this, int fd)
{
JNIEnv *env;
jmethodID method_id;
@ -242,16 +242,24 @@ failed:
return FALSE;
}
CALLBACK(bypass_single_socket_cb, void,
intptr_t fd, va_list args)
{
private_charonservice_t *this;
VA_ARGS_VGET(args, this);
bypass_single_socket(this, fd);
}
METHOD(charonservice_t, bypass_socket, bool,
private_charonservice_t *this, int fd, int family)
{
if (fd >= 0)
{
this->sockets->insert_last(this->sockets, (void*)(intptr_t)fd);
return bypass_single_socket((intptr_t)fd, this);
return bypass_single_socket(this, fd);
}
this->sockets->invoke_function(this->sockets, (void*)bypass_single_socket,
this);
this->sockets->invoke_function(this->sockets, bypass_single_socket_cb, this);
return TRUE;
}

View File

@ -167,6 +167,15 @@ METHOD(kernel_net_t, get_source_addr, host_t*,
return host_create_from_sockaddr((sockaddr_t*)&addr);
}
CALLBACK(vip_equals, bool,
host_t *vip, va_list args)
{
host_t *host;
VA_ARGS_VGET(args, host);
return host->ip_equals(host, vip);
}
METHOD(kernel_net_t, get_source_addr_old, host_t*,
private_android_net_t *this, host_t *dest, host_t *src)
{
@ -179,8 +188,7 @@ METHOD(kernel_net_t, get_source_addr_old, host_t*,
if (host)
{
this->mutex->lock(this->mutex);
if (this->vips->find_first(this->vips, (void*)host->ip_equals,
NULL, host) == SUCCESS)
if (this->vips->find_first(this->vips, vip_equals, NULL, host))
{
host->destroy(host);
host = NULL;
@ -236,8 +244,8 @@ METHOD(kernel_net_t, del_ip, status_t,
host_t *vip;
this->mutex->lock(this->mutex);
if (this->vips->find_first(this->vips, (void*)virtual_ip->ip_equals,
(void**)&vip, virtual_ip) == SUCCESS)
if (this->vips->find_first(this->vips, vip_equals, (void**)&vip,
virtual_ip))
{
this->vips->remove(this->vips, vip, NULL);
vip->destroy(vip);

View File

@ -237,14 +237,14 @@ typedef struct {
linked_list_t *vips;
} initiator_enumerator_t;
/**
* Enumerator implementation for initiator attributes
*/
static bool initiator_enumerate(initiator_enumerator_t *this,
attribute_handler_t **handler,
configuration_attribute_type_t *type,
chunk_t *value)
METHOD(enumerator_t, initiator_enumerate, bool,
initiator_enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
attribute_handler_t **handler;
chunk_t *value;
VA_ARGS_VGET(args, handler, type, value);
/* enumerate inner attributes using outer handler enumerator */
while (!this->inner || !this->inner->enumerate(this->inner, type, value))
{
@ -261,10 +261,8 @@ static bool initiator_enumerate(initiator_enumerator_t *this,
return TRUE;
}
/**
* Cleanup function of initiator attribute enumerator
*/
static void initiator_destroy(initiator_enumerator_t *this)
METHOD(enumerator_t, initiator_destroy, void,
initiator_enumerator_t *this)
{
this->this->lock->unlock(this->this->lock);
this->outer->destroy(this->outer);
@ -281,8 +279,9 @@ METHOD(attribute_manager_t, create_initiator_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)initiator_enumerate,
.destroy = (void*)initiator_destroy,
.enumerate = enumerator_enumerate_default,
.venumerate = _initiator_enumerate,
.destroy = _initiator_destroy,
},
.this = this,
.ike_sa = ike_sa,

View File

@ -512,10 +512,15 @@ typedef struct {
} lease_enumerator_t;
METHOD(enumerator_t, lease_enumerate, bool,
lease_enumerator_t *this, identification_t **id, host_t **addr, bool *online)
lease_enumerator_t *this, va_list args)
{
u_int *offset;
identification_t **id;
unique_lease_t *lease;
host_t **addr;
u_int *offset;
bool *online;
VA_ARGS_VGET(args, id, addr, online);
DESTROY_IF(this->addr);
this->addr = NULL;
@ -570,7 +575,8 @@ METHOD(mem_pool_t, create_lease_enumerator, enumerator_t*,
this->mutex->lock(this->mutex);
INIT(enumerator,
.public = {
.enumerate = (void*)_lease_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _lease_enumerate,
.destroy = _lease_enumerator_destroy,
},
.pool = this,

View File

@ -207,20 +207,20 @@ static inline void register_logger(private_bus_t *this, debug_t group,
}
}
/**
* Find the log level of the first registered logger that implements log or
* vlog (or both).
*/
static bool find_max_levels(log_entry_t *entry, debug_t *group, level_t *level,
level_t *vlevel)
CALLBACK(find_max_levels, bool,
log_entry_t *entry, va_list args)
{
level_t *level, *vlevel;
debug_t group;
VA_ARGS_VGET(args, group, level, vlevel);
if (entry->logger->log && *level == LEVEL_SILENT)
{
*level = entry->levels[*group];
*level = entry->levels[group];
}
if (entry->logger->vlog && *vlevel == LEVEL_SILENT)
{
*vlevel = entry->levels[*group];
*vlevel = entry->levels[group];
}
return *level > LEVEL_SILENT && *vlevel > LEVEL_SILENT;
}
@ -258,8 +258,8 @@ static inline void unregister_logger(private_bus_t *this, logger_t *logger)
loggers = this->loggers[group];
loggers->remove(loggers, found, NULL);
loggers->find_first(loggers, (linked_list_match_t)find_max_levels,
NULL, &group, &level, &vlevel);
loggers->find_first(loggers, find_max_levels, NULL, group,
&level, &vlevel);
set_level(&this->max_level[group], level);
set_level(&this->max_vlevel[group], vlevel);
}
@ -330,11 +330,12 @@ typedef struct {
va_list args;
} log_data_t;
/**
* logger->log() invocation as a invoke_function callback
*/
static void log_cb(log_entry_t *entry, log_data_t *data)
CALLBACK(log_cb, void,
log_entry_t *entry, va_list args)
{
log_data_t *data;
VA_ARGS_VGET(args, data);
if (entry->logger->log && entry->levels[data->group] >= data->level)
{
entry->logger->log(entry->logger, data->group, data->level,
@ -342,11 +343,12 @@ static void log_cb(log_entry_t *entry, log_data_t *data)
}
}
/**
* logger->vlog() invocation as a invoke_function callback
*/
static void vlog_cb(log_entry_t *entry, log_data_t *data)
CALLBACK(vlog_cb, void,
log_entry_t *entry, va_list args)
{
log_data_t *data;
VA_ARGS_VGET(args, data);
if (entry->logger->vlog && entry->levels[data->group] >= data->level)
{
va_list copy;
@ -405,8 +407,7 @@ METHOD(bus_t, vlog, void,
}
if (len > 0)
{
loggers->invoke_function(loggers, (linked_list_invoke_t)log_cb,
&data);
loggers->invoke_function(loggers, log_cb, &data);
}
if (data.message != buf)
{
@ -422,7 +423,7 @@ METHOD(bus_t, vlog, void,
data.message = format;
va_copy(data.args, args);
loggers->invoke_function(loggers, (linked_list_invoke_t)vlog_cb, &data);
loggers->invoke_function(loggers, vlog_cb, &data);
va_end(data.args);
}

View File

@ -265,20 +265,24 @@ static void peer_enum_destroy(peer_data_t *data)
free(data);
}
/**
* convert enumerator value from match_entry to config
*/
static bool peer_enum_filter(linked_list_t *configs,
match_entry_t **in, peer_cfg_t **out)
CALLBACK(peer_enum_filter, bool,
linked_list_t *configs, enumerator_t *orig, va_list args)
{
*out = (*in)->cfg;
return TRUE;
match_entry_t *entry;
peer_cfg_t **out;
VA_ARGS_VGET(args, out);
if (orig->enumerate(orig, &entry))
{
*out = entry->cfg;
return TRUE;
}
return FALSE;
}
/**
* Clean up temporary config list
*/
static void peer_enum_filter_destroy(linked_list_t *configs)
CALLBACK(peer_enum_filter_destroy, void,
linked_list_t *configs)
{
match_entry_t *entry;
@ -379,8 +383,8 @@ METHOD(backend_manager_t, create_peer_cfg_enumerator, enumerator_t*,
helper->destroy(helper);
return enumerator_create_filter(configs->create_enumerator(configs),
(void*)peer_enum_filter, configs,
(void*)peer_enum_filter_destroy);
peer_enum_filter, configs,
peer_enum_filter_destroy);
}
METHOD(backend_manager_t, get_peer_cfg_by_name, peer_cfg_t*,

View File

@ -165,8 +165,12 @@ METHOD(child_cfg_t, add_proposal, void,
}
}
static bool match_proposal(proposal_t *item, proposal_t *proposal)
CALLBACK(match_proposal, bool,
proposal_t *item, va_list args)
{
proposal_t *proposal;
VA_ARGS_VGET(args, proposal);
return item->equals(item, proposal);
}
@ -185,8 +189,7 @@ METHOD(child_cfg_t, get_proposals, linked_list_t*,
{
current->strip_dh(current, MODP_NONE);
}
if (proposals->find_first(proposals, (linked_list_match_t)match_proposal,
NULL, current) == SUCCESS)
if (proposals->find_first(proposals, match_proposal, NULL, current))
{
current->destroy(current);
continue;

View File

@ -209,9 +209,12 @@ typedef struct {
} child_cfgs_replace_enumerator_t;
METHOD(enumerator_t, child_cfgs_replace_enumerate, bool,
child_cfgs_replace_enumerator_t *this, child_cfg_t **chd, bool *added)
child_cfgs_replace_enumerator_t *this, va_list args)
{
child_cfg_t *child_cfg;
child_cfg_t *child_cfg, **chd;
bool *added;
VA_ARGS_VGET(args, chd, added);
if (!this->wrapped)
{
@ -303,8 +306,9 @@ METHOD(peer_cfg_t, replace_child_cfgs, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_child_cfgs_replace_enumerate,
.destroy = (void*)_child_cfgs_replace_enumerator_destroy,
.enumerate = enumerator_enumerate_default,
.venumerate = _child_cfgs_replace_enumerate,
.destroy = _child_cfgs_replace_enumerator_destroy,
},
.removed = removed,
.added = added,
@ -336,8 +340,11 @@ METHOD(enumerator_t, child_cfg_enumerator_destroy, void,
}
METHOD(enumerator_t, child_cfg_enumerate, bool,
child_cfg_enumerator_t *this, child_cfg_t **chd)
child_cfg_enumerator_t *this, va_list args)
{
child_cfg_t **chd;
VA_ARGS_VGET(args, chd);
return this->wrapped->enumerate(this->wrapped, chd);
}
@ -348,8 +355,9 @@ METHOD(peer_cfg_t, create_child_cfg_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_child_cfg_enumerate,
.destroy = (void*)_child_cfg_enumerator_destroy,
.enumerate = enumerator_enumerate_default,
.venumerate = _child_cfg_enumerate,
.destroy = _child_cfg_enumerator_destroy,
},
.mutex = this->mutex,
.wrapped = this->child_cfgs->create_enumerator(this->child_cfgs),

View File

@ -94,27 +94,31 @@ METHOD(proposal_t, add_algorithm, void,
array_insert(this->transforms, ARRAY_TAIL, &entry);
}
/**
* filter function for peer configs
*/
static bool alg_filter(uintptr_t type, entry_t **in, uint16_t *alg,
void **unused, uint16_t *key_size)
CALLBACK(alg_filter, bool,
uintptr_t type, enumerator_t *orig, va_list args)
{
entry_t *entry = *in;
entry_t *entry;
uint16_t *alg, *key_size;
if (entry->type != type)
VA_ARGS_VGET(args, alg, key_size);
while (orig->enumerate(orig, &entry))
{
return FALSE;
if (entry->type != type)
{
continue;
}
if (alg)
{
*alg = entry->alg;
}
if (key_size)
{
*key_size = entry->key_size;
}
return TRUE;
}
if (alg)
{
*alg = entry->alg;
}
if (key_size)
{
*key_size = entry->key_size;
}
return TRUE;
return FALSE;
}
METHOD(proposal_t, create_enumerator, enumerator_t*,
@ -122,7 +126,7 @@ METHOD(proposal_t, create_enumerator, enumerator_t*,
{
return enumerator_create_filter(
array_create_enumerator(this->transforms),
(void*)alg_filter, (void*)(uintptr_t)type, NULL);
alg_filter, (void*)(uintptr_t)type, NULL);
}
METHOD(proposal_t, get_algorithm, bool,

View File

@ -282,13 +282,14 @@ static void logger_entry_unregister_destroy(logger_entry_t *this)
logger_entry_destroy(this);
}
/**
* Match a logger entry by target and whether it is a file or syslog logger
*/
static bool logger_entry_match(logger_entry_t *this, char *target,
logger_type_t *type)
CALLBACK(logger_entry_match, bool,
logger_entry_t *this, va_list args)
{
return this->type == *type && streq(this->target, target);
logger_type_t type;
char *target;
VA_ARGS_VGET(args, target, type);
return this->type == type && streq(this->target, target);
}
/**
@ -350,8 +351,8 @@ static logger_entry_t *get_logger_entry(char *target, logger_type_t type,
{
logger_entry_t *entry;
if (existing->find_first(existing, (void*)logger_entry_match,
(void**)&entry, target, &type) != SUCCESS)
if (!existing->find_first(existing, logger_entry_match, (void**)&entry,
target, type))
{
INIT(entry,
.target = strdup(target),

View File

@ -190,8 +190,12 @@ struct keyid_enumerator_t {
};
METHOD(enumerator_t, keyid_enumerate, bool,
keyid_enumerator_t *this, chunk_t *chunk)
keyid_enumerator_t *this, va_list args)
{
chunk_t *chunk;
VA_ARGS_VGET(args, chunk);
if (this->pos == NULL)
{
this->pos = this->full.ptr;
@ -224,7 +228,8 @@ METHOD(certreq_payload_t, create_keyid_enumerator, enumerator_t*,
}
INIT(enumerator,
.public = {
.enumerate = (void*)_keyid_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _keyid_enumerate,
.destroy = (void*)free,
},
.full = this->data,

View File

@ -306,8 +306,12 @@ typedef struct {
} spi_enumerator_t;
METHOD(enumerator_t, spis_enumerate, bool,
spi_enumerator_t *this, uint32_t *spi)
spi_enumerator_t *this, va_list args)
{
uint32_t *spi;
VA_ARGS_VGET(args, spi);
if (this->spis.len >= sizeof(*spi))
{
memcpy(spi, this->spis.ptr, sizeof(*spi));
@ -328,7 +332,8 @@ METHOD(delete_payload_t, create_spi_enumerator, enumerator_t*,
}
INIT(e,
.public = {
.enumerate = (void*)_spis_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _spis_enumerate,
.destroy = (void*)free,
},
.spis = this->spis,

View File

@ -270,8 +270,12 @@ typedef struct {
} type_enumerator_t;
METHOD(enumerator_t, enumerate_types, bool,
type_enumerator_t *this, eap_type_t *type, uint32_t *vendor)
type_enumerator_t *this, va_list args)
{
eap_type_t *type;
uint32_t *vendor;
VA_ARGS_VGET(args, type, vendor);
this->offset = extract_type(this->payload, this->offset, type, vendor);
return this->offset;
}
@ -289,7 +293,8 @@ METHOD(eap_payload_t, get_types, enumerator_t*,
{
INIT(enumerator,
.public = {
.enumerate = (void*)_enumerate_types,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_types,
.destroy = (void*)free,
},
.payload = this,

View File

@ -632,21 +632,18 @@ METHOD(kernel_interface_t, enable_udp_decap, bool,
METHOD(kernel_interface_t, is_interface_usable, bool,
private_kernel_interface_t *this, const char *iface)
{
status_t expected;
if (!this->ifaces_filter)
{
return TRUE;
}
expected = this->ifaces_exclude ? NOT_FOUND : SUCCESS;
return this->ifaces_filter->find_first(this->ifaces_filter, (void*)streq,
NULL, iface) == expected;
return this->ifaces_filter->find_first(this->ifaces_filter,
linked_list_match_str, NULL, iface) != this->ifaces_exclude;
}
METHOD(kernel_interface_t, all_interfaces_usable, bool,
private_kernel_interface_t *this)
{
return this->ifaces_filter == NULL;
return !this->ifaces_filter;
}
METHOD(kernel_interface_t, get_address_by_ts, status_t,

View File

@ -182,12 +182,15 @@ METHOD(attribute_handler_t, release, void,
}
METHOD(enumerator_t, enumerate_dns, bool,
enumerator_t *this, configuration_attribute_type_t *type, chunk_t *data)
enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
*type = INTERNAL_IP4_DNS;
*data = chunk_empty;
/* stop enumeration */
this->enumerate = (void*)return_false;
this->venumerate = return_false;
return TRUE;
}
@ -198,7 +201,8 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t *,
enumerator_t *enumerator;
INIT(enumerator,
.enumerate = (void*)_enumerate_dns,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_dns,
.destroy = (void*)free,
);
return enumerator;

View File

@ -75,17 +75,23 @@ typedef struct {
ike_version_t ike;
} enumerator_data_t;
/**
* convert enumerator value from attribute_entry
*/
static bool attr_enum_filter(enumerator_data_t *data, attribute_entry_t **in,
configuration_attribute_type_t *type, void* none, chunk_t *value)
CALLBACK(attr_enum_filter, bool,
enumerator_data_t *data, enumerator_t *orig, va_list args)
{
if ((*in)->ike == IKE_ANY || (*in)->ike == data->ike)
configuration_attribute_type_t *type;
attribute_entry_t *entry;
chunk_t *value;
VA_ARGS_VGET(args, type, value);
while (orig->enumerate(orig, &entry))
{
*type = (*in)->type;
*value = (*in)->value;
return TRUE;
if (entry->ike == IKE_ANY || entry->ike == data->ike)
{
*type = entry->type;
*value = entry->value;
return TRUE;
}
}
return FALSE;
}
@ -112,7 +118,7 @@ METHOD(attribute_provider_t, create_attribute_enumerator, enumerator_t*,
this->lock->read_lock(this->lock);
return enumerator_create_filter(
this->attributes->create_enumerator(this->attributes),
(void*)attr_enum_filter, data, attr_enum_destroy);
attr_enum_filter, data, attr_enum_destroy);
}
return enumerator_create_empty();
}

View File

@ -110,15 +110,12 @@ static bool policy_equals(bypass_policy_t *a, bypass_policy_t *b)
*/
static bool consider_interface(private_bypass_lan_listener_t *this, char *iface)
{
status_t expected;
if (!iface || !this->ifaces_filter)
{
return TRUE;
}
expected = this->ifaces_exclude ? NOT_FOUND : SUCCESS;
return this->ifaces_filter->find_first(this->ifaces_filter, (void*)streq,
NULL, iface) == expected;
return this->ifaces_filter->find_first(this->ifaces_filter,
linked_list_match_str, NULL, iface) != this->ifaces_exclude;
}
/**

View File

@ -151,8 +151,7 @@ METHOD(attribute_provider_t, create_attribute_enumerator, enumerator_t*,
identification_t *id;
host_t *vip;
if (pools->find_first(pools, (linked_list_match_t)streq,
NULL, "dhcp") != SUCCESS)
if (!pools->find_first(pools, linked_list_match_str, NULL, "dhcp"))
{
return NULL;
}

View File

@ -382,8 +382,7 @@ METHOD(dhcp_socket_t, enroll, dhcp_transaction_t*,
while (try <= DHCP_TRIES && discover(this, transaction))
{
if (!this->condvar->timed_wait(this->condvar, this->mutex, 1000 * try) &&
this->request->find_first(this->request, NULL,
(void**)&transaction) == SUCCESS)
this->request->find_first(this->request, NULL, (void**)&transaction))
{
break;
}

View File

@ -114,16 +114,22 @@ METHOD(dhcp_transaction_t, add_attribute, void,
this->attributes->insert_last(this->attributes, entry);
}
/**
* Filter function to map entries to type/data
*/
static bool attribute_filter(void *null, attribute_entry_t **entry,
configuration_attribute_type_t *type,
void **dummy, chunk_t *data)
CALLBACK(attribute_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
*type = (*entry)->type;
*data = (*entry)->data;
return TRUE;
configuration_attribute_type_t *type;
attribute_entry_t *entry;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
if (orig->enumerate(orig, &entry))
{
*type = entry->type;
*data = entry->data;
return TRUE;
}
return FALSE;
}
METHOD(dhcp_transaction_t, create_attribute_enumerator, enumerator_t*,
@ -131,7 +137,7 @@ METHOD(dhcp_transaction_t, create_attribute_enumerator, enumerator_t*,
{
return enumerator_create_filter(
this->attributes->create_enumerator(this->attributes),
(void*)attribute_filter, NULL, NULL);
attribute_filter, NULL, NULL);
}
/**

View File

@ -75,12 +75,15 @@ typedef struct {
} cert_enumerator_t;
METHOD(enumerator_t, cert_enumerator_enumerate, bool,
cert_enumerator_t *this, certificate_t **cert)
cert_enumerator_t *this, va_list args)
{
certificate_t **cert;
dnscert_t *cur_crt;
rr_t *cur_rr;
chunk_t certificate;
VA_ARGS_VGET(args, cert);
/* Get the next supported CERT using the inner enumerator. */
while (this->inner->enumerate(this->inner, &cur_rr))
{
@ -175,7 +178,8 @@ METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_cert_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _cert_enumerator_enumerate,
.destroy = _cert_enumerator_destroy,
},
.inner = response->get_rr_set(response)->create_rr_enumerator(

View File

@ -69,6 +69,15 @@ static bool entry_matches(eap_vendor_type_t *item, eap_vendor_type_t *other)
return item->type == other->type && item->vendor == other->vendor;
}
CALLBACK(entry_matches_cb, bool,
eap_vendor_type_t *item, va_list args)
{
eap_vendor_type_t *other;
VA_ARGS_VGET(args, other);
return entry_matches(item, other);
}
/**
* Load the given EAP method
*/
@ -121,8 +130,7 @@ static void select_method(private_eap_dynamic_t *this)
{
if (inner)
{
if (inner->find_first(inner, (void*)entry_matches,
NULL, entry) != SUCCESS)
if (!inner->find_first(inner, entry_matches_cb, NULL, entry))
{
if (entry->vendor)
{

View File

@ -404,11 +404,13 @@ typedef struct {
attr_t *current;
} attribute_enumerator_t;
METHOD(enumerator_t, attribute_enumerate, bool,
attribute_enumerator_t *this, configuration_attribute_type_t *type,
chunk_t *data)
attribute_enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
if (this->current)
{
destroy_attr(this->current);
@ -446,7 +448,8 @@ METHOD(attribute_provider_t, create_attribute_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_attribute_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _attribute_enumerate,
.destroy = _attribute_destroy,
},
.list = linked_list_create(),

View File

@ -79,10 +79,8 @@ typedef struct {
private_eap_sim_file_triplets_t *this;
} triplet_enumerator_t;
/**
* destroy a triplet enumerator
*/
static void enumerator_destroy(triplet_enumerator_t *e)
METHOD(enumerator_t, enumerator_destroy, void,
triplet_enumerator_t *e)
{
if (e->current)
{
@ -97,13 +95,14 @@ static void enumerator_destroy(triplet_enumerator_t *e)
free(e);
}
/**
* enumerate through triplets
*/
static bool enumerator_enumerate(triplet_enumerator_t *e, identification_t **imsi,
char **rand, char **sres, char **kc)
METHOD(enumerator_t, enumerator_enumerate, bool,
triplet_enumerator_t *e, va_list args)
{
identification_t **imsi;
triplet_t *triplet;
char **rand, **sres, **kc;
VA_ARGS_VGET(args, imsi, rand, sres, kc);
if (e->inner->enumerate(e->inner, &triplet))
{
@ -124,12 +123,15 @@ METHOD(eap_sim_file_triplets_t, create_enumerator, enumerator_t*,
triplet_enumerator_t *enumerator = malloc_thing(triplet_enumerator_t);
this->mutex->lock(this->mutex);
enumerator->public.enumerate = (void*)enumerator_enumerate;
enumerator->public.destroy = (void*)enumerator_destroy;
enumerator->inner = this->triplets->create_enumerator(this->triplets);
enumerator->current = NULL;
enumerator->this = this;
INIT(enumerator,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerator_enumerate,
.destroy = _enumerator_destroy,
},
.inner = this->triplets->create_enumerator(this->triplets),
.this = this,
);
return &enumerator->public;
}

View File

@ -613,17 +613,23 @@ METHOD(listener_t, ike_update, bool,
return TRUE;
}
/**
* Filter to map entries to ts/mark
*/
static bool ts_filter(entry_t *entry, traffic_selector_t **ts,
traffic_selector_t **out, void *dummy, uint32_t *mark,
void *dummy2, bool *reinject)
CALLBACK(ts_filter, bool,
entry_t *entry, enumerator_t *orig, va_list args)
{
*out = *ts;
*mark = entry->mark;
*reinject = entry->reinject;
return TRUE;
traffic_selector_t *ts, **out;
uint32_t *mark;
bool *reinject;
VA_ARGS_VGET(args, out, mark, reinject);
if (orig->enumerate(orig, &ts))
{
*out = ts;
*mark = entry->mark;
*reinject = entry->reinject;
return TRUE;
}
return FALSE;
}
/**
@ -632,7 +638,7 @@ static bool ts_filter(entry_t *entry, traffic_selector_t **ts,
static enumerator_t* create_inner_local(entry_t *entry, rwlock_t *lock)
{
return enumerator_create_filter(array_create_enumerator(entry->lts),
(void*)ts_filter, entry, NULL);
ts_filter, entry, NULL);
}
/**
@ -641,7 +647,7 @@ static enumerator_t* create_inner_local(entry_t *entry, rwlock_t *lock)
static enumerator_t* create_inner_remote(entry_t *entry, rwlock_t *lock)
{
return enumerator_create_filter(array_create_enumerator(entry->rts),
(void*)ts_filter, entry, NULL);
ts_filter, entry, NULL);
}
METHOD(forecast_listener_t, create_enumerator, enumerator_t*,

View File

@ -331,10 +331,12 @@ typedef struct {
} attribute_enumerator_t;
METHOD(enumerator_t, attribute_enumerate, bool,
attribute_enumerator_t *this, ha_message_attribute_t *attr_out,
ha_message_value_t *value)
attribute_enumerator_t *this, va_list args)
{
ha_message_attribute_t attr;
ha_message_attribute_t attr, *attr_out;
ha_message_value_t *value;
VA_ARGS_VGET(args, attr_out, value);
if (this->cleanup)
{
@ -602,7 +604,8 @@ METHOD(ha_message_t, create_attribute_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_attribute_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _attribute_enumerate,
.destroy = _enum_destroy,
},
.buf = chunk_skip(this->buf, 2),

View File

@ -111,8 +111,12 @@ typedef struct {
} shared_enum_t;
METHOD(enumerator_t, shared_enumerate, bool,
shared_enum_t *this, shared_key_t **key, id_match_t *me, id_match_t *other)
shared_enum_t *this, va_list args)
{
shared_key_t **key;
id_match_t *me, *other;
VA_ARGS_VGET(args, key, me, other);
if (this->key)
{
if (me)
@ -151,7 +155,8 @@ METHOD(ha_creds_t, create_shared_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_shared_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _shared_enumerate,
.destroy = (void*)free,
},
.key = this->key,

View File

@ -62,13 +62,16 @@ typedef struct {
} cert_enumerator_t;
METHOD(enumerator_t, cert_enumerator_enumerate, bool,
cert_enumerator_t *this, certificate_t **cert)
cert_enumerator_t *this, va_list args)
{
certificate_t **cert;
ipseckey_t *cur_ipseckey;
public_key_t *public;
rr_t *cur_rr;
chunk_t key;
VA_ARGS_VGET(args, cert);
/* Get the next supported IPSECKEY using the inner enumerator. */
while (this->inner->enumerate(this->inner, &cur_rr))
{
@ -211,7 +214,8 @@ METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_cert_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _cert_enumerator_enumerate,
.destroy = _cert_enumerator_destroy,
},
.inner = rrset->create_rr_enumerator(rrset),

View File

@ -466,9 +466,12 @@ typedef struct {
} addr_enumerator_t;
METHOD(enumerator_t, addr_enumerate, bool,
addr_enumerator_t *this, host_t **host)
addr_enumerator_t *this, va_list args)
{
iface_t *entry;
host_t **host;
VA_ARGS_VGET(args, host);
while (TRUE)
{
@ -523,7 +526,8 @@ METHOD(kernel_net_t, create_address_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_addr_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _addr_enumerate,
.destroy = _addr_destroy,
},
.which = which,

View File

@ -84,12 +84,12 @@ static void exclude_route_destroy(exclude_route_t *this)
free(this);
}
/**
* Find an exclude route entry by destination address
*/
static bool exclude_route_match(exclude_route_t *current,
host_t *dst)
CALLBACK(exclude_route_match, bool,
exclude_route_t *current, va_list args)
{
host_t *dst;
VA_ARGS_VGET(args, dst);
return dst->ip_equals(dst, current->dst);
}
@ -204,12 +204,12 @@ static void policy_entry_destroy(policy_entry_t *this)
free(this);
}
/**
* Compare two policy_entry_t objects
*/
static inline bool policy_entry_equals(policy_entry_t *a,
policy_entry_t *b)
CALLBACK(policy_entry_equals, bool,
policy_entry_t *a, va_list args)
{
policy_entry_t *b;
VA_ARGS_VGET(args, b);
return a->direction == b->direction &&
a->src.proto == b->src.proto &&
a->dst.proto == b->dst.proto &&
@ -297,9 +297,8 @@ static void add_exclude_route(private_kernel_libipsec_ipsec_t *this,
exclude_route_t *exclude;
host_t *gtw;
if (this->excludes->find_first(this->excludes,
(linked_list_match_t)exclude_route_match,
(void**)&exclude, dst) == SUCCESS)
if (this->excludes->find_first(this->excludes, exclude_route_match,
(void**)&exclude, dst))
{
route->exclude = exclude;
exclude->refs++;
@ -524,9 +523,8 @@ METHOD(kernel_ipsec_t, add_policy, status_t,
policy = create_policy_entry(id->src_ts, id->dst_ts, id->dir);
this->mutex->lock(this->mutex);
if (this->policies->find_first(this->policies,
(linked_list_match_t)policy_entry_equals,
(void**)&found, policy) == SUCCESS)
if (this->policies->find_first(this->policies, policy_entry_equals,
(void**)&found, policy))
{
policy_entry_destroy(policy);
policy = found;
@ -567,9 +565,8 @@ METHOD(kernel_ipsec_t, del_policy, status_t,
policy = create_policy_entry(id->src_ts, id->dst_ts, id->dir);
this->mutex->lock(this->mutex);
if (this->policies->find_first(this->policies,
(linked_list_match_t)policy_entry_equals,
(void**)&found, policy) != SUCCESS)
if (!this->policies->find_first(this->policies, policy_entry_equals,
(void**)&found, policy))
{
policy_entry_destroy(policy);
this->mutex->unlock(this->mutex);

View File

@ -542,10 +542,10 @@ static policy_sa_t *policy_sa_create(private_kernel_netlink_ipsec_t *this,
/**
* Destroy a policy_sa(_in)_t object
*/
static void policy_sa_destroy(policy_sa_t *policy, policy_dir_t *dir,
static void policy_sa_destroy(policy_sa_t *policy, policy_dir_t dir,
private_kernel_netlink_ipsec_t *this)
{
if (*dir == POLICY_OUT)
if (dir == POLICY_OUT)
{
policy_sa_out_t *out = (policy_sa_out_t*)policy;
out->src_ts->destroy(out->src_ts);
@ -555,6 +555,16 @@ static void policy_sa_destroy(policy_sa_t *policy, policy_dir_t *dir,
free(policy);
}
CALLBACK(policy_sa_destroy_cb, void,
policy_sa_t *policy, va_list args)
{
private_kernel_netlink_ipsec_t *this;
policy_dir_t dir;
VA_ARGS_VGET(args, dir, this);
policy_sa_destroy(policy, dir, this);
}
typedef struct policy_entry_t policy_entry_t;
/**
@ -599,9 +609,8 @@ static void policy_entry_destroy(private_kernel_netlink_ipsec_t *this,
}
if (policy->used_by)
{
policy->used_by->invoke_function(policy->used_by,
(linked_list_invoke_t)policy_sa_destroy,
&policy->direction, this);
policy->used_by->invoke_function(policy->used_by, policy_sa_destroy_cb,
policy->direction, this);
policy->used_by->destroy(policy->used_by);
}
free(policy);
@ -2768,7 +2777,7 @@ METHOD(kernel_ipsec_t, del_policy, status_t,
ipsec_sa_equals(mapping->sa, &assigned_sa))
{
current->used_by->remove_at(current->used_by, enumerator);
policy_sa_destroy(mapping, &id->dir, this);
policy_sa_destroy(mapping, id->dir, this);
break;
}
if (is_installed)

View File

@ -163,19 +163,21 @@ static void iface_entry_destroy(iface_entry_t *this)
free(this);
}
/**
* find an interface entry by index
*/
static bool iface_entry_by_index(iface_entry_t *this, int *ifindex)
CALLBACK(iface_entry_by_index, bool,
iface_entry_t *this, va_list args)
{
return this->ifindex == *ifindex;
int ifindex;
VA_ARGS_VGET(args, ifindex);
return this->ifindex == ifindex;
}
/**
* find an interface entry by name
*/
static bool iface_entry_by_name(iface_entry_t *this, char *ifname)
CALLBACK(iface_entry_by_name, bool,
iface_entry_t *this, va_list args)
{
char *ifname;
VA_ARGS_VGET(args, ifname);
return streq(this->ifname, ifname);
}
@ -1112,8 +1114,8 @@ static bool is_interface_up_and_usable(private_kernel_netlink_net_t *this,
{
iface_entry_t *iface;
if (this->ifaces->find_first(this->ifaces, (void*)iface_entry_by_index,
(void**)&iface, &index) == SUCCESS)
if (this->ifaces->find_first(this->ifaces, iface_entry_by_index,
(void**)&iface, index))
{
return iface_entry_up_and_usable(iface);
}
@ -1125,9 +1127,13 @@ static bool is_interface_up_and_usable(private_kernel_netlink_net_t *this,
*
* this->lock must be locked when calling this function
*/
static void addr_entry_unregister(addr_entry_t *addr, iface_entry_t *iface,
private_kernel_netlink_net_t *this)
CALLBACK(addr_entry_unregister, void,
addr_entry_t *addr, va_list args)
{
private_kernel_netlink_net_t *this;
iface_entry_t *iface;
VA_ARGS_VGET(args, iface, this);
if (addr->refcount)
{
addr_map_entry_remove(this->vips, addr, iface);
@ -1171,9 +1177,8 @@ static void process_link(private_kernel_netlink_net_t *this,
{
case RTM_NEWLINK:
{
if (this->ifaces->find_first(this->ifaces,
(void*)iface_entry_by_index, (void**)&entry,
&msg->ifi_index) != SUCCESS)
if (!this->ifaces->find_first(this->ifaces, iface_entry_by_index,
(void**)&entry, msg->ifi_index))
{
INIT(entry,
.ifindex = msg->ifi_index,
@ -1217,7 +1222,7 @@ static void process_link(private_kernel_netlink_net_t *this,
* another interface? */
this->ifaces->remove_at(this->ifaces, enumerator);
current->addrs->invoke_function(current->addrs,
(void*)addr_entry_unregister, current, this);
addr_entry_unregister, current, this);
iface_entry_destroy(current);
break;
}
@ -1288,8 +1293,8 @@ static void process_addr(private_kernel_netlink_net_t *this,
}
this->lock->write_lock(this->lock);
if (this->ifaces->find_first(this->ifaces, (void*)iface_entry_by_index,
(void**)&iface, &msg->ifa_index) == SUCCESS)
if (this->ifaces->find_first(this->ifaces, iface_entry_by_index,
(void**)&iface, msg->ifa_index))
{
addr_map_entry_t *entry, lookup = {
.ip = host,
@ -1518,35 +1523,39 @@ typedef struct {
kernel_address_type_t which;
} address_enumerator_t;
/**
* cleanup function for address enumerator
*/
static void address_enumerator_destroy(address_enumerator_t *data)
CALLBACK(address_enumerator_destroy, void,
address_enumerator_t *data)
{
data->this->lock->unlock(data->this->lock);
free(data);
}
/**
* filter for addresses
*/
static bool filter_addresses(address_enumerator_t *data,
addr_entry_t** in, host_t** out)
CALLBACK(filter_addresses, bool,
address_enumerator_t *data, enumerator_t *orig, va_list args)
{
if (!(data->which & ADDR_TYPE_VIRTUAL) && (*in)->refcount)
{ /* skip virtual interfaces added by us */
return FALSE;
addr_entry_t *addr;
host_t **out;
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &addr))
{
if (!(data->which & ADDR_TYPE_VIRTUAL) && addr->refcount)
{ /* skip virtual interfaces added by us */
continue;
}
if (!(data->which & ADDR_TYPE_REGULAR) && !addr->refcount)
{ /* address is regular, but not requested */
continue;
}
if (addr->scope >= RT_SCOPE_LINK)
{ /* skip addresses with a unusable scope */
continue;
}
*out = addr->ip;
return TRUE;
}
if (!(data->which & ADDR_TYPE_REGULAR) && !(*in)->refcount)
{ /* address is regular, but not requested */
return FALSE;
}
if ((*in)->scope >= RT_SCOPE_LINK)
{ /* skip addresses with a unusable scope */
return FALSE;
}
*out = (*in)->ip;
return TRUE;
return FALSE;
}
/**
@ -1556,30 +1565,35 @@ static enumerator_t *create_iface_enumerator(iface_entry_t *iface,
address_enumerator_t *data)
{
return enumerator_create_filter(
iface->addrs->create_enumerator(iface->addrs),
(void*)filter_addresses, data, NULL);
iface->addrs->create_enumerator(iface->addrs),
filter_addresses, data, NULL);
}
/**
* filter for interfaces
*/
static bool filter_interfaces(address_enumerator_t *data, iface_entry_t** in,
iface_entry_t** out)
CALLBACK(filter_interfaces, bool,
address_enumerator_t *data, enumerator_t *orig, va_list args)
{
if (!(data->which & ADDR_TYPE_IGNORED) && !(*in)->usable)
{ /* skip interfaces excluded by config */
return FALSE;
iface_entry_t *iface, **out;
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &iface))
{
if (!(data->which & ADDR_TYPE_IGNORED) && !iface->usable)
{ /* skip interfaces excluded by config */
continue;
}
if (!(data->which & ADDR_TYPE_LOOPBACK) && (iface->flags & IFF_LOOPBACK))
{ /* ignore loopback devices */
continue;
}
if (!(data->which & ADDR_TYPE_DOWN) && !(iface->flags & IFF_UP))
{ /* skip interfaces not up */
continue;
}
*out = iface;
return TRUE;
}
if (!(data->which & ADDR_TYPE_LOOPBACK) && ((*in)->flags & IFF_LOOPBACK))
{ /* ignore loopback devices */
return FALSE;
}
if (!(data->which & ADDR_TYPE_DOWN) && !((*in)->flags & IFF_UP))
{ /* skip interfaces not up */
return FALSE;
}
*out = *in;
return TRUE;
return FALSE;
}
METHOD(kernel_net_t, create_address_enumerator, enumerator_t*,
@ -1596,9 +1610,9 @@ METHOD(kernel_net_t, create_address_enumerator, enumerator_t*,
return enumerator_create_nested(
enumerator_create_filter(
this->ifaces->create_enumerator(this->ifaces),
(void*)filter_interfaces, data, NULL),
filter_interfaces, data, NULL),
(void*)create_iface_enumerator, data,
(void*)address_enumerator_destroy);
address_enumerator_destroy);
}
METHOD(kernel_net_t, get_interface_name, bool,
@ -1661,8 +1675,8 @@ static int get_interface_index(private_kernel_netlink_net_t *this, char* name)
DBG2(DBG_KNL, "getting iface index for %s", name);
this->lock->read_lock(this->lock);
if (this->ifaces->find_first(this->ifaces, (void*)iface_entry_by_name,
(void**)&iface, name) == SUCCESS)
if (this->ifaces->find_first(this->ifaces, iface_entry_by_name,
(void**)&iface, name))
{
ifindex = iface->ifindex;
}
@ -1687,8 +1701,8 @@ static char *get_interface_name_by_index(private_kernel_netlink_net_t *this,
DBG2(DBG_KNL, "getting iface name for index %d", index);
this->lock->read_lock(this->lock);
if (this->ifaces->find_first(this->ifaces, (void*)iface_entry_by_index,
(void**)&iface, &index) == SUCCESS)
if (this->ifaces->find_first(this->ifaces, iface_entry_by_index,
(void**)&iface, index))
{
name = strdup(iface->ifname);
}
@ -1928,7 +1942,7 @@ static host_t *get_route(private_kernel_netlink_net_t *this, host_t *dest,
table = (uintptr_t)route->table;
if (this->rt_exclude->find_first(this->rt_exclude, NULL,
(void**)&table) == SUCCESS)
(void**)&table))
{ /* route is from an excluded routing table */
continue;
}
@ -2165,8 +2179,14 @@ METHOD(enumerator_t, destroy_subnet_enumerator, void,
}
METHOD(enumerator_t, enumerate_subnets, bool,
subnet_enumerator_t *this, host_t **net, uint8_t *mask, char **ifname)
subnet_enumerator_t *this, va_list args)
{
host_t **net;
uint8_t *mask;
char **ifname;
VA_ARGS_VGET(args, net, mask, ifname);
if (!this->current)
{
this->current = this->msg;
@ -2270,7 +2290,8 @@ METHOD(kernel_net_t, create_local_subnet_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_enumerate_subnets,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_subnets,
.destroy = _destroy_subnet_enumerator,
},
.private = this,
@ -2380,11 +2401,11 @@ METHOD(kernel_net_t, add_ip, status_t,
}
/* try to find the target interface, either by config or via src ip */
if (!this->install_virtual_ip_on ||
this->ifaces->find_first(this->ifaces, (void*)iface_entry_by_name,
(void**)&iface, this->install_virtual_ip_on) != SUCCESS)
!this->ifaces->find_first(this->ifaces, iface_entry_by_name,
(void**)&iface, this->install_virtual_ip_on))
{
if (this->ifaces->find_first(this->ifaces, (void*)iface_entry_by_name,
(void**)&iface, iface_name) != SUCCESS)
if (!this->ifaces->find_first(this->ifaces, iface_entry_by_name,
(void**)&iface, iface_name))
{ /* if we don't find the requested interface we just use the first */
this->ifaces->get_first(this->ifaces, (void**)&iface);
}

View File

@ -464,10 +464,10 @@ static policy_sa_t *policy_sa_create(private_kernel_pfkey_ipsec_t *this,
/**
* Destroy a policy_sa(_in)_t object
*/
static void policy_sa_destroy(policy_sa_t *policy, policy_dir_t *dir,
static void policy_sa_destroy(policy_sa_t *policy, policy_dir_t dir,
private_kernel_pfkey_ipsec_t *this)
{
if (*dir == POLICY_OUT)
if (dir == POLICY_OUT)
{
policy_sa_out_t *out = (policy_sa_out_t*)policy;
out->src_ts->destroy(out->src_ts);
@ -477,6 +477,16 @@ static void policy_sa_destroy(policy_sa_t *policy, policy_dir_t *dir,
free(policy);
}
CALLBACK(policy_sa_destroy_cb, void,
policy_sa_t *policy, va_list args)
{
private_kernel_pfkey_ipsec_t *this;
policy_dir_t dir;
VA_ARGS_VGET(args, dir, this);
policy_sa_destroy(policy, dir, this);
}
typedef struct policy_entry_t policy_entry_t;
/**
@ -557,9 +567,8 @@ static void policy_entry_destroy(policy_entry_t *policy,
}
if (policy->used_by)
{
policy->used_by->invoke_function(policy->used_by,
(linked_list_invoke_t)policy_sa_destroy,
&policy->direction, this);
policy->used_by->invoke_function(policy->used_by, policy_sa_destroy_cb,
policy->direction, this);
policy->used_by->destroy(policy->used_by);
}
DESTROY_IF(policy->src.net);
@ -567,12 +576,21 @@ static void policy_entry_destroy(policy_entry_t *policy,
free(policy);
}
/**
* compares two policy_entry_t
*/
static inline bool policy_entry_equals(policy_entry_t *current,
policy_entry_t *policy)
CALLBACK(policy_entry_destroy_cb, void,
policy_entry_t *policy, va_list args)
{
private_kernel_pfkey_ipsec_t *this;
VA_ARGS_VGET(args, this);
policy_entry_destroy(policy, this);
}
CALLBACK(policy_entry_equals, bool,
policy_entry_t *current, va_list args)
{
policy_entry_t *policy;
VA_ARGS_VGET(args, policy);
return current->direction == policy->direction &&
current->src.proto == policy->src.proto &&
current->dst.proto == policy->dst.proto &&
@ -582,13 +600,13 @@ static inline bool policy_entry_equals(policy_entry_t *current,
current->dst.net->equals(current->dst.net, policy->dst.net);
}
/**
* compare the given kernel index with that of a policy
*/
static inline bool policy_entry_match_byindex(policy_entry_t *current,
uint32_t *index)
CALLBACK(policy_entry_match_byindex, bool,
policy_entry_t *current, va_list args)
{
return current->index == *index;
uint32_t index;
VA_ARGS_VGET(args, index);
return current->index == index;
}
/**
@ -1261,9 +1279,8 @@ static void process_acquire(private_kernel_pfkey_ipsec_t *this,
index = response.x_policy->sadb_x_policy_id;
this->mutex->lock(this->mutex);
if (this->policies->find_first(this->policies,
(linked_list_match_t)policy_entry_match_byindex,
(void**)&policy, &index) == SUCCESS &&
if (this->policies->find_first(this->policies, policy_entry_match_byindex,
(void**)&policy, index) &&
policy->used_by->get_first(policy->used_by, (void**)&sa) == SUCCESS)
{
reqid = sa->sa->cfg.reqid;
@ -2554,8 +2571,7 @@ static status_t add_policy_internal(private_kernel_pfkey_ipsec_t *this,
/* we try to find the policy again and update the kernel index */
this->mutex->lock(this->mutex);
if (this->policies->find_first(this->policies, NULL,
(void**)&policy) != SUCCESS)
if (!this->policies->find_first(this->policies, NULL, (void**)&policy))
{
DBG2(DBG_KNL, "unable to update index, the policy is already gone, "
"ignoring");
@ -2606,9 +2622,8 @@ METHOD(kernel_ipsec_t, add_policy, status_t,
/* find a matching policy */
this->mutex->lock(this->mutex);
if (this->policies->find_first(this->policies,
(linked_list_match_t)policy_entry_equals,
(void**)&found, policy) == SUCCESS)
if (this->policies->find_first(this->policies, policy_entry_equals,
(void**)&found, policy))
{ /* use existing policy */
DBG2(DBG_KNL, "policy %R === %R %N already exists, increasing "
"refcount", id->src_ts, id->dst_ts, policy_dir_names, id->dir);
@ -2701,9 +2716,8 @@ METHOD(kernel_ipsec_t, query_policy, status_t,
/* find a matching policy */
this->mutex->lock(this->mutex);
if (this->policies->find_first(this->policies,
(linked_list_match_t)policy_entry_equals,
(void**)&found, policy) != SUCCESS)
if (!this->policies->find_first(this->policies, policy_entry_equals,
(void**)&found, policy))
{
DBG1(DBG_KNL, "querying policy %R === %R %N failed, not found",
id->src_ts, id->dst_ts, policy_dir_names, id->dir);
@ -2814,9 +2828,8 @@ METHOD(kernel_ipsec_t, del_policy, status_t,
/* find a matching policy */
this->mutex->lock(this->mutex);
if (this->policies->find_first(this->policies,
(linked_list_match_t)policy_entry_equals,
(void**)&found, policy) != SUCCESS)
if (!this->policies->find_first(this->policies, policy_entry_equals,
(void**)&found, policy))
{
DBG1(DBG_KNL, "deleting policy %R === %R %N failed, not found",
id->src_ts, id->dst_ts, policy_dir_names, id->dir);
@ -2860,7 +2873,7 @@ METHOD(kernel_ipsec_t, del_policy, status_t,
if (policy->used_by->get_count(policy->used_by) > 0)
{ /* policy is used by more SAs, keep in kernel */
DBG2(DBG_KNL, "policy still used by another CHILD_SA, not removed");
policy_sa_destroy(mapping, &id->dir, this);
policy_sa_destroy(mapping, id->dir, this);
if (!is_installed)
{ /* no need to update as the policy was not installed for this SA */
@ -2915,7 +2928,7 @@ METHOD(kernel_ipsec_t, del_policy, status_t,
}
this->policies->remove(this->policies, found, NULL);
policy_sa_destroy(mapping, &id->dir, this);
policy_sa_destroy(mapping, id->dir, this);
policy_entry_destroy(policy, this);
this->mutex->unlock(this->mutex);
@ -3088,8 +3101,7 @@ METHOD(kernel_ipsec_t, destroy, void,
lib->watcher->remove(lib->watcher, this->socket_events);
close(this->socket_events);
}
this->policies->invoke_function(this->policies,
(linked_list_invoke_t)policy_entry_destroy,
this->policies->invoke_function(this->policies, policy_entry_destroy_cb,
this);
this->policies->destroy(this->policies);
this->excludes->destroy(this->excludes);

View File

@ -601,9 +601,12 @@ typedef struct {
} rt_enumerator_t;
METHOD(enumerator_t, rt_enumerate, bool,
rt_enumerator_t *this, int *xtype, struct sockaddr **addr)
rt_enumerator_t *this, va_list args)
{
int i, type;
struct sockaddr **addr;
int i, type, *xtype;
VA_ARGS_VGET(args, xtype, addr);
if (this->remaining < sizeof(this->addr->sa_len) ||
this->remaining < this->addr->sa_len)
@ -637,7 +640,8 @@ static enumerator_t *create_rt_enumerator(int types, int remaining,
INIT(this,
.public = {
.enumerate = (void*)_rt_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _rt_enumerate,
.destroy = (void*)free,
},
.types = types,
@ -1050,41 +1054,45 @@ typedef struct {
kernel_address_type_t which;
} address_enumerator_t;
/**
* cleanup function for address enumerator
*/
static void address_enumerator_destroy(address_enumerator_t *data)
CALLBACK(address_enumerator_destroy, void,
address_enumerator_t *data)
{
data->this->lock->unlock(data->this->lock);
free(data);
}
/**
* filter for addresses
*/
static bool filter_addresses(address_enumerator_t *data,
addr_entry_t** in, host_t** out)
CALLBACK(filter_addresses, bool,
address_enumerator_t *data, enumerator_t *orig, va_list args)
{
host_t *ip;
if (!(data->which & ADDR_TYPE_VIRTUAL) && (*in)->virtual)
{ /* skip virtual interfaces added by us */
return FALSE;
}
if (!(data->which & ADDR_TYPE_REGULAR) && !(*in)->virtual)
{ /* address is regular, but not requested */
return FALSE;
}
ip = (*in)->ip;
if (ip->get_family(ip) == AF_INET6)
addr_entry_t *addr;
host_t *ip, **out;
struct sockaddr_in6 *sin6;
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &addr))
{
struct sockaddr_in6 *sin6 = (struct sockaddr_in6 *)ip->get_sockaddr(ip);
if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr))
{ /* skip addresses with a unusable scope */
return FALSE;
if (!(data->which & ADDR_TYPE_VIRTUAL) && addr->virtual)
{ /* skip virtual interfaces added by us */
continue;
}
if (!(data->which & ADDR_TYPE_REGULAR) && !addr->virtual)
{ /* address is regular, but not requested */
continue;
}
ip = addr->ip;
if (ip->get_family(ip) == AF_INET6)
{
sin6 = (struct sockaddr_in6 *)ip->get_sockaddr(ip);
if (IN6_IS_ADDR_LINKLOCAL(&sin6->sin6_addr))
{ /* skip addresses with a unusable scope */
continue;
}
}
*out = ip;
return TRUE;
}
*out = ip;
return TRUE;
return FALSE;
}
/**
@ -1094,29 +1102,34 @@ static enumerator_t *create_iface_enumerator(iface_entry_t *iface,
address_enumerator_t *data)
{
return enumerator_create_filter(iface->addrs->create_enumerator(iface->addrs),
(void*)filter_addresses, data, NULL);
filter_addresses, data, NULL);
}
/**
* filter for interfaces
*/
static bool filter_interfaces(address_enumerator_t *data, iface_entry_t** in,
iface_entry_t** out)
CALLBACK(filter_interfaces, bool,
address_enumerator_t *data, enumerator_t *orig, va_list args)
{
if (!(data->which & ADDR_TYPE_IGNORED) && !(*in)->usable)
{ /* skip interfaces excluded by config */
return FALSE;
iface_entry_t *iface, **out;
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &iface))
{
if (!(data->which & ADDR_TYPE_IGNORED) && !iface->usable)
{ /* skip interfaces excluded by config */
continue;
}
if (!(data->which & ADDR_TYPE_LOOPBACK) && (iface->flags & IFF_LOOPBACK))
{ /* ignore loopback devices */
continue;
}
if (!(data->which & ADDR_TYPE_DOWN) && !(iface->flags & IFF_UP))
{ /* skip interfaces not up */
continue;
}
*out = iface;
return TRUE;
}
if (!(data->which & ADDR_TYPE_LOOPBACK) && ((*in)->flags & IFF_LOOPBACK))
{ /* ignore loopback devices */
return FALSE;
}
if (!(data->which & ADDR_TYPE_DOWN) && !((*in)->flags & IFF_UP))
{ /* skip interfaces not up */
return FALSE;
}
*out = *in;
return TRUE;
return FALSE;
}
METHOD(kernel_net_t, create_address_enumerator, enumerator_t*,
@ -1133,9 +1146,9 @@ METHOD(kernel_net_t, create_address_enumerator, enumerator_t*,
return enumerator_create_nested(
enumerator_create_filter(
this->ifaces->create_enumerator(this->ifaces),
(void*)filter_interfaces, data, NULL),
filter_interfaces, data, NULL),
(void*)create_iface_enumerator, data,
(void*)address_enumerator_destroy);
address_enumerator_destroy);
}
METHOD(kernel_net_t, get_features, kernel_feature_t,
@ -1789,13 +1802,18 @@ METHOD(enumerator_t, destroy_subnet_enumerator, void,
}
METHOD(enumerator_t, enumerate_subnets, bool,
subnet_enumerator_t *this, host_t **net, uint8_t *mask, char **ifname)
subnet_enumerator_t *this, va_list args)
{
enumerator_t *enumerator;
host_t **net;
struct rt_msghdr *rtm;
struct sockaddr *addr;
uint8_t *mask;
char **ifname;
int type;
VA_ARGS_VGET(args, net, mask, ifname);
if (!this->current)
{
this->current = this->buf;
@ -1888,7 +1906,8 @@ METHOD(kernel_net_t, create_local_subnet_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_enumerate_subnets,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_subnets,
.destroy = _destroy_subnet_enumerator,
},
.buf = buf,

View File

@ -395,22 +395,28 @@ METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
return NULL;
}
/**
* Filter function for shared keys, returning ID matches
*/
static bool shared_filter(void *null, shared_key_t **in, shared_key_t **out,
void **un1, id_match_t *me, void **un2, id_match_t *other)
CALLBACK(shared_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
*out = *in;
if (me)
shared_key_t *key, **out;
id_match_t *me, *other;
VA_ARGS_VGET(args, out, me, other);
if (orig->enumerate(orig, &key))
{
*me = ID_MATCH_ANY;
*out = key;
if (me)
{
*me = ID_MATCH_ANY;
}
if (other)
{
*other = ID_MATCH_ANY;
}
return TRUE;
}
if (other)
{
*other = ID_MATCH_ANY;
}
return TRUE;
return FALSE;
}
METHOD(credential_set_t, create_shared_enumerator, enumerator_t*,
@ -431,7 +437,7 @@ METHOD(credential_set_t, create_shared_enumerator, enumerator_t*,
return NULL;
}
return enumerator_create_filter(enumerator_create_single(shared, NULL),
(void*)shared_filter, NULL, NULL);
shared_filter, NULL, NULL);
}
METHOD(load_tester_creds_t, destroy, void,

View File

@ -223,10 +223,11 @@ typedef struct {
} peer_enumerator_t;
METHOD(enumerator_t, peer_enumerator_enumerate, bool,
peer_enumerator_t *this, peer_cfg_t **cfg)
peer_enumerator_t *this, va_list args)
{
char *name, *local_net, *remote_net;
chunk_t me, other;
peer_cfg_t **cfg;
child_cfg_t *child_cfg;
auth_cfg_t *auth;
peer_cfg_create_t peer = {
@ -249,6 +250,8 @@ METHOD(enumerator_t, peer_enumerator_enumerate, bool,
.mode = MODE_TUNNEL,
};
VA_ARGS_VGET(args, cfg);
DESTROY_IF(this->current);
if (!this->inner->enumerate(this->inner, &name, &me, &other,
&local_net, &remote_net))
@ -295,7 +298,8 @@ METHOD(backend_t, create_peer_cfg_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_peer_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _peer_enumerator_enumerate,
.destroy = _peer_enumerator_destroy,
},
.ike = this->ike,

View File

@ -50,10 +50,13 @@ typedef struct {
} private_enumerator_t;
METHOD(enumerator_t, private_enumerator_enumerate, bool,
private_enumerator_t *this, private_key_t **key)
private_enumerator_t *this, va_list args)
{
private_key_t **key;
chunk_t chunk;
VA_ARGS_VGET(args, key);
DESTROY_IF(this->current);
while (this->inner->enumerate(this->inner, &chunk))
{
@ -92,7 +95,8 @@ METHOD(credential_set_t, create_private_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_private_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _private_enumerator_enumerate,
.destroy = _private_enumerator_destroy,
},
);
@ -123,11 +127,14 @@ typedef struct {
} cert_enumerator_t;
METHOD(enumerator_t, cert_enumerator_enumerate, bool,
cert_enumerator_t *this, certificate_t **cert)
cert_enumerator_t *this, va_list args)
{
certificate_t **cert;
public_key_t *public;
chunk_t chunk;
VA_ARGS_VGET(args, cert);
DESTROY_IF(this->current);
while (this->inner->enumerate(this->inner, &chunk))
{
@ -180,7 +187,8 @@ METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_cert_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _cert_enumerator_enumerate,
.destroy = _cert_enumerator_destroy,
},
.type = key,

View File

@ -52,12 +52,14 @@ typedef struct {
} cert_enumerator_t;
METHOD(enumerator_t, cert_enumerator_enumerate, bool,
cert_enumerator_t *this, certificate_t **cert)
cert_enumerator_t *this, va_list args)
{
certificate_t *trusted;
certificate_t *trusted, **cert;
public_key_t *public;
chunk_t chunk;
VA_ARGS_VGET(args, cert);
DESTROY_IF(this->current);
while (this->inner->enumerate(this->inner, &chunk))
{
@ -110,7 +112,8 @@ METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_cert_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _cert_enumerator_enumerate,
.destroy = _cert_enumerator_destroy,
},
.type = key,

View File

@ -218,12 +218,15 @@ METHOD(attribute_handler_t, release, void,
}
METHOD(enumerator_t, enumerate_dns, bool,
enumerator_t *this, configuration_attribute_type_t *type, chunk_t *data)
enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
*type = INTERNAL_IP4_DNS;
*data = chunk_empty;
/* stop enumeration */
this->enumerate = (void*)return_false;
this->venumerate = (void*)return_false;
return TRUE;
}
@ -234,7 +237,8 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t *,
enumerator_t *enumerator;
INIT(enumerator,
.enumerate = (void*)_enumerate_dns,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_dns,
.destroy = (void*)free,
);
return enumerator;

View File

@ -83,9 +83,12 @@ typedef struct {
} attr_enumerator_t;
METHOD(enumerator_t, enumerate_attrs, bool,
attr_enumerator_t *this, configuration_attribute_type_t *type,
chunk_t *data)
attr_enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
if (this->request_ipv4)
{
*type = P_CSCF_IP4_ADDRESS;
@ -103,12 +106,13 @@ METHOD(enumerator_t, enumerate_attrs, bool,
return FALSE;
}
/**
* Check if the given host has a matching address family
*/
static bool is_family(host_t *host, int *family)
CALLBACK(is_family, bool,
host_t *host, va_list args)
{
return host->get_family(host) == *family;
int family;
VA_ARGS_VGET(args, family);
return host->get_family(host) == family;
}
/**
@ -116,7 +120,7 @@ static bool is_family(host_t *host, int *family)
*/
static bool has_host_family(linked_list_t *list, int family)
{
return list->find_first(list, (void*)is_family, NULL, &family) == SUCCESS;
return list->find_first(list, is_family, NULL, family);
}
METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t *,
@ -132,7 +136,8 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t *,
INIT(enumerator,
.public = {
.enumerate = (void*)_enumerate_attrs,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_attrs,
.destroy = (void*)free,
},
);

View File

@ -391,10 +391,13 @@ typedef struct {
bool v6;
} attribute_enumerator_t;
static bool attribute_enumerate(attribute_enumerator_t *this,
configuration_attribute_type_t *type,
chunk_t *data)
METHOD(enumerator_t, attribute_enumerate, bool,
attribute_enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
if (this->v4)
{
*type = INTERNAL_IP4_DNS;
@ -443,7 +446,8 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)attribute_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _attribute_enumerate,
.destroy = (void*)free,
},
.v4 = has_host_family(vips, AF_INET),

View File

@ -504,11 +504,12 @@ typedef struct {
ike_cfg_t *current;
} ike_enumerator_t;
/**
* Implementation of ike_enumerator_t.public.enumerate
*/
static bool ike_enumerator_enumerate(ike_enumerator_t *this, ike_cfg_t **cfg)
METHOD(enumerator_t, ike_enumerator_enumerate, bool,
ike_enumerator_t *this, va_list args)
{
ike_cfg_t **cfg;
VA_ARGS_VGET(args, cfg);
DESTROY_IF(this->current);
this->current = build_ike_cfg(this->this, this->inner, this->me, this->other);
if (this->current)
@ -519,10 +520,8 @@ static bool ike_enumerator_enumerate(ike_enumerator_t *this, ike_cfg_t **cfg)
return FALSE;
}
/**
* Implementation of ike_enumerator_t.public.destroy
*/
static void ike_enumerator_destroy(ike_enumerator_t *this)
METHOD(enumerator_t, ike_enumerator_destroy, void,
ike_enumerator_t *this)
{
DESTROY_IF(this->current);
this->inner->destroy(this->inner);
@ -532,19 +531,22 @@ static void ike_enumerator_destroy(ike_enumerator_t *this)
METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
private_sql_config_t *this, host_t *me, host_t *other)
{
ike_enumerator_t *e = malloc_thing(ike_enumerator_t);
e->this = this;
e->me = me;
e->other = other;
e->current = NULL;
e->public.enumerate = (void*)ike_enumerator_enumerate;
e->public.destroy = (void*)ike_enumerator_destroy;
ike_enumerator_t *e;
INIT(e,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _ike_enumerator_enumerate,
.destroy = _ike_enumerator_destroy,
},
.this = this,
.me = me,
.other = other,
);
e->inner = this->db->query(this->db,
"SELECT id, certreq, force_encap, local, remote "
"FROM ike_configs",
DB_INT, DB_INT, DB_INT, DB_TEXT, DB_TEXT);
"SELECT id, certreq, force_encap, local, remote "
"FROM ike_configs",
DB_INT, DB_INT, DB_INT, DB_TEXT, DB_TEXT);
if (!e->inner)
{
free(e);
@ -569,11 +571,12 @@ typedef struct {
peer_cfg_t *current;
} peer_enumerator_t;
/**
* Implementation of peer_enumerator_t.public.enumerate
*/
static bool peer_enumerator_enumerate(peer_enumerator_t *this, peer_cfg_t **cfg)
METHOD(enumerator_t, peer_enumerator_enumerate, bool,
peer_enumerator_t *this, va_list args)
{
peer_cfg_t **cfg;
VA_ARGS_VGET(args, cfg);
DESTROY_IF(this->current);
this->current = build_peer_cfg(this->this, this->inner, this->me, this->other);
if (this->current)
@ -584,10 +587,8 @@ static bool peer_enumerator_enumerate(peer_enumerator_t *this, peer_cfg_t **cfg)
return FALSE;
}
/**
* Implementation of peer_enumerator_t.public.destroy
*/
static void peer_enumerator_destroy(peer_enumerator_t *this)
METHOD(enumerator_t, peer_enumerator_destroy, void,
peer_enumerator_t *this)
{
DESTROY_IF(this->current);
this->inner->destroy(this->inner);
@ -599,12 +600,16 @@ METHOD(backend_t, create_peer_cfg_enumerator, enumerator_t*,
{
peer_enumerator_t *e = malloc_thing(peer_enumerator_t);
e->this = this;
e->me = me;
e->other = other;
e->current = NULL;
e->public.enumerate = (void*)peer_enumerator_enumerate;
e->public.destroy = (void*)peer_enumerator_destroy;
INIT(e,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _peer_enumerator_enumerate,
.destroy = _peer_enumerator_destroy,
},
.this = this,
.me = me,
.other = other,
);
/* TODO: only get configs whose IDs match exactly or contain wildcards */
e->inner = this->db->query(this->db,

View File

@ -52,11 +52,14 @@ typedef struct {
} private_enumerator_t;
METHOD(enumerator_t, private_enumerator_enumerate, bool,
private_enumerator_t *this, private_key_t **key)
private_enumerator_t *this, va_list args)
{
private_key_t **key;
chunk_t blob;
int type;
VA_ARGS_VGET(args, key);
DESTROY_IF(this->current);
while (this->inner->enumerate(this->inner, &type, &blob))
{
@ -88,7 +91,8 @@ METHOD(credential_set_t, create_private_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_private_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _private_enumerator_enumerate,
.destroy = _private_enumerator_destroy,
},
);
@ -132,11 +136,14 @@ typedef struct {
} cert_enumerator_t;
METHOD(enumerator_t, cert_enumerator_enumerate, bool,
cert_enumerator_t *this, certificate_t **cert)
cert_enumerator_t *this, va_list args)
{
certificate_t **cert;
chunk_t blob;
int type;
VA_ARGS_VGET(args, cert);
DESTROY_IF(this->current);
while (this->inner->enumerate(this->inner, &type, &blob))
{
@ -169,7 +176,8 @@ METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_cert_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _cert_enumerator_enumerate,
.destroy = _cert_enumerator_destroy,
},
);
@ -221,12 +229,15 @@ typedef struct {
} shared_enumerator_t;
METHOD(enumerator_t, shared_enumerator_enumerate, bool,
shared_enumerator_t *this, shared_key_t **shared,
id_match_t *me, id_match_t *other)
shared_enumerator_t *this, va_list args)
{
shared_key_t **shared;
id_match_t *me, *other;
chunk_t blob;
int type;
VA_ARGS_VGET(args, shared, me, other);
DESTROY_IF(this->current);
while (this->inner->enumerate(this->inner, &type, &blob))
{
@ -265,7 +276,8 @@ METHOD(credential_set_t, create_shared_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_shared_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _shared_enumerator_enumerate,
.destroy = _shared_enumerator_destroy,
},
.me = me,
@ -340,9 +352,11 @@ typedef enum {
} cdp_type_t;
METHOD(enumerator_t, cdp_enumerator_enumerate, bool,
cdp_enumerator_t *this, char **uri)
cdp_enumerator_t *this, va_list args)
{
char *text;
char *text, **uri;
VA_ARGS_VGET(args, uri);
free(this->current);
while (this->inner->enumerate(this->inner, &text))
@ -384,7 +398,8 @@ METHOD(credential_set_t, create_cdp_enumerator, enumerator_t*,
}
INIT(e,
.public = {
.enumerate = (void*)_cdp_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _cdp_enumerator_enumerate,
.destroy = _cdp_enumerator_destroy,
},
);

View File

@ -178,28 +178,32 @@ METHOD(attribute_provider_t, release_address, bool,
return found;
}
/**
* Filter function to convert host to DNS configuration attributes
*/
static bool attr_filter(void *lock, host_t **in,
configuration_attribute_type_t *type,
void *dummy, chunk_t *data)
CALLBACK(attr_filter, bool,
void *lock, enumerator_t *orig, va_list args)
{
host_t *host = *in;
configuration_attribute_type_t *type;
chunk_t *data;
host_t *host;
switch (host->get_family(host))
VA_ARGS_VGET(args, type, data);
while (orig->enumerate(orig, &host))
{
case AF_INET:
*type = INTERNAL_IP4_DNS;
break;
case AF_INET6:
*type = INTERNAL_IP6_DNS;
break;
default:
return FALSE;
switch (host->get_family(host))
{
case AF_INET:
*type = INTERNAL_IP4_DNS;
break;
case AF_INET6:
*type = INTERNAL_IP6_DNS;
break;
default:
continue;
}
*data = host->get_address(host);
return TRUE;
}
*data = host->get_address(host);
return TRUE;
return FALSE;
}
METHOD(attribute_provider_t, create_attribute_enumerator, enumerator_t*,
@ -223,7 +227,7 @@ METHOD(attribute_provider_t, create_attribute_enumerator, enumerator_t*,
enumerator->destroy(enumerator);
return enumerator_create_filter(
attr->dns->create_enumerator(attr->dns),
(void*)attr_filter, this->lock,
attr_filter, this->lock,
(void*)this->lock->unlock);
}
}
@ -338,24 +342,28 @@ METHOD(stroke_attribute_t, del_dns, void,
this->lock->unlock(this->lock);
}
/**
* Pool enumerator filter function, converts pool_t to name, size, ...
*/
static bool pool_filter(void *lock, mem_pool_t **poolp, const char **name,
void *d1, u_int *size, void *d2, u_int *online,
void *d3, u_int *offline)
CALLBACK(pool_filter, bool,
void *lock, enumerator_t *orig, va_list args)
{
mem_pool_t *pool = *poolp;
mem_pool_t *pool;
const char **name;
u_int *size, *online, *offline;
if (pool->get_size(pool) == 0)
VA_ARGS_VGET(args, name, size, online, offline);
while (orig->enumerate(orig, &pool))
{
return FALSE;
if (pool->get_size(pool) == 0)
{
continue;
}
*name = pool->get_name(pool);
*size = pool->get_size(pool);
*online = pool->get_online(pool);
*offline = pool->get_offline(pool);
return TRUE;
}
*name = pool->get_name(pool);
*size = pool->get_size(pool);
*online = pool->get_online(pool);
*offline = pool->get_offline(pool);
return TRUE;
return FALSE;
}
METHOD(stroke_attribute_t, create_pool_enumerator, enumerator_t*,
@ -363,7 +371,7 @@ METHOD(stroke_attribute_t, create_pool_enumerator, enumerator_t*,
{
this->lock->read_lock(this->lock);
return enumerator_create_filter(this->pools->create_enumerator(this->pools),
(void*)pool_filter,
pool_filter,
this->lock, (void*)this->lock->unlock);
}

View File

@ -171,26 +171,30 @@ typedef struct {
identification_t *id;
} cert_data_t;
/**
* destroy cert_data
*/
static void cert_data_destroy(cert_data_t *data)
CALLBACK(cert_data_destroy, void,
cert_data_t *data)
{
data->this->lock->unlock(data->this->lock);
free(data);
}
/**
* filter function for certs enumerator
*/
static bool certs_filter(cert_data_t *data, ca_cert_t **in,
certificate_t **out)
CALLBACK(certs_filter, bool,
cert_data_t *data, enumerator_t *orig, va_list args)
{
ca_cert_t *cacert;
public_key_t *public;
certificate_t *cert = (*in)->cert;
certificate_t **out;
if (data->cert == CERT_ANY || data->cert == cert->get_type(cert))
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &cacert))
{
certificate_t *cert = cacert->cert;
if (data->cert != CERT_ANY && data->cert != cert->get_type(cert))
{
continue;
}
public = cert->get_public_key(cert);
if (public)
{
@ -208,9 +212,9 @@ static bool certs_filter(cert_data_t *data, ca_cert_t **in,
}
else if (data->key != KEY_ANY)
{
return FALSE;
continue;
}
if (data->id == NULL || cert->has_subject(cert, data->id))
if (!data->id || cert->has_subject(cert, data->id))
{
*out = cert;
return TRUE;
@ -235,8 +239,8 @@ METHOD(credential_set_t, create_cert_enumerator, enumerator_t*,
this->lock->read_lock(this->lock);
enumerator = this->certs->create_enumerator(this->certs);
return enumerator_create_filter(enumerator, (void*)certs_filter, data,
(void*)cert_data_destroy);
return enumerator_create_filter(enumerator, certs_filter, data,
cert_data_destroy);
}
/**
@ -354,11 +358,12 @@ METHOD(credential_set_t, create_cdp_enumerator, enumerator_t*,
data, (void*)cdp_data_destroy);
}
/**
* Compare the given certificate to the ca_cert_t items in the list
*/
static bool match_cert(ca_cert_t *item, certificate_t *cert)
CALLBACK(match_cert, bool,
ca_cert_t *item, va_list args)
{
certificate_t *cert;
VA_ARGS_VGET(args, cert);
return cert->equals(cert, item->cert);
}
@ -405,8 +410,7 @@ static certificate_t *add_cert_internal(private_stroke_ca_t *this,
{
ca_cert_t *found;
if (this->certs->find_first(this->certs, (linked_list_match_t)match_cert,
(void**)&found, cert) == SUCCESS)
if (this->certs->find_first(this->certs, match_cert, (void**)&found, cert))
{
cert->destroy(cert);
cert = found->cert->get_ref(found->cert);
@ -511,8 +515,7 @@ METHOD(stroke_ca_t, get_cert_ref, certificate_t*,
ca_cert_t *found;
this->lock->read_lock(this->lock);
if (this->certs->find_first(this->certs, (linked_list_match_t)match_cert,
(void**)&found, cert) == SUCCESS)
if (this->certs->find_first(this->certs, match_cert, (void**)&found, cert))
{
cert->destroy(cert);
cert = found->cert->get_ref(found->cert);

View File

@ -68,13 +68,20 @@ METHOD(backend_t, create_peer_cfg_enumerator, enumerator_t*,
(void*)this->mutex->unlock, this->mutex);
}
/**
* filter function for ike configs
*/
static bool ike_filter(void *data, peer_cfg_t **in, ike_cfg_t **out)
CALLBACK(ike_filter, bool,
void *data, enumerator_t *orig, va_list args)
{
*out = (*in)->get_ike_cfg(*in);
return TRUE;
peer_cfg_t *cfg;
ike_cfg_t **out;
VA_ARGS_VGET(args, out);
if (orig->enumerate(orig, &cfg))
{
*out = cfg->get_ike_cfg(cfg);
return TRUE;
}
return FALSE;
}
METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
@ -82,7 +89,7 @@ METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
{
this->mutex->lock(this->mutex);
return enumerator_create_filter(this->list->create_enumerator(this->list),
(void*)ike_filter, this->mutex,
ike_filter, this->mutex,
(void*)this->mutex->unlock);
}

View File

@ -62,35 +62,39 @@ static void attributes_destroy(attributes_t *this)
free(this);
}
/**
* Filter function to convert host to DNS configuration attributes
*/
static bool attr_filter(void *lock, host_t **in,
configuration_attribute_type_t *type,
void *dummy, chunk_t *data)
CALLBACK(attr_filter, bool,
void *lock, enumerator_t *orig, va_list args)
{
host_t *host = *in;
configuration_attribute_type_t *type;
chunk_t *data;
host_t *host;
switch (host->get_family(host))
VA_ARGS_VGET(args, type, data);
while (orig->enumerate(orig, &host))
{
case AF_INET:
*type = INTERNAL_IP4_DNS;
break;
case AF_INET6:
*type = INTERNAL_IP6_DNS;
break;
default:
return FALSE;
switch (host->get_family(host))
{
case AF_INET:
*type = INTERNAL_IP4_DNS;
break;
case AF_INET6:
*type = INTERNAL_IP6_DNS;
break;
default:
continue;
}
if (host->is_anyaddr(host))
{
*data = chunk_empty;
}
else
{
*data = host->get_address(host);
}
return TRUE;
}
if (host->is_anyaddr(host))
{
*data = chunk_empty;
}
else
{
*data = host->get_address(host);
}
return TRUE;
return FALSE;
}
METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t*,
@ -114,7 +118,7 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t*,
enumerator->destroy(enumerator);
return enumerator_create_filter(
attr->dns->create_enumerator(attr->dns),
(void*)attr_filter, this->lock,
attr_filter, this->lock,
(void*)this->lock->unlock);
}
}

View File

@ -958,8 +958,7 @@ static void list_plugins(FILE *out)
{
case FEATURE_PROVIDE:
fp = &features[i];
loaded = list->find_first(list, NULL,
(void**)&fp) == SUCCESS;
loaded = list->find_first(list, NULL, (void**)&fp);
fprintf(out, " %s%s\n",
str, loaded ? "" : " (not loaded)");
break;

View File

@ -118,11 +118,12 @@ static u_int create_rekey(char *string)
}
METHOD(enumerator_t, peer_enumerator_enumerate, bool,
peer_enumerator_t *this, peer_cfg_t **cfg)
peer_enumerator_t *this, va_list args)
{
char *name, *ike_proposal, *esp_proposal, *ike_rekey, *esp_rekey;
char *local_id, *local_addr, *local_net;
char *remote_id, *remote_addr, *remote_net;
peer_cfg_t **cfg;
child_cfg_t *child_cfg;
ike_cfg_t *ike_cfg;
auth_cfg_t *auth;
@ -145,6 +146,8 @@ METHOD(enumerator_t, peer_enumerator_enumerate, bool,
.mode = MODE_TUNNEL,
};
VA_ARGS_VGET(args, cfg);
/* defaults */
name = "unnamed";
local_id = NULL;
@ -212,7 +215,8 @@ METHOD(backend_t, create_peer_cfg_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_peer_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _peer_enumerator_enumerate,
.destroy = _peer_enumerator_destroy,
},
.inner = this->parser->create_section_enumerator(this->parser,
@ -241,10 +245,13 @@ typedef struct {
} ike_enumerator_t;
METHOD(enumerator_t, ike_enumerator_enumerate, bool,
ike_enumerator_t *this, ike_cfg_t **cfg)
ike_enumerator_t *this, va_list args)
{
ike_cfg_t **cfg;
char *local_addr, *remote_addr, *ike_proposal;
VA_ARGS_VGET(args, cfg);
/* defaults */
local_addr = "0.0.0.0";
remote_addr = "0.0.0.0";
@ -282,7 +289,8 @@ METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_ike_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _ike_enumerator_enumerate,
.destroy = _ike_enumerator_destroy,
},
.inner = this->parser->create_section_enumerator(this->parser,

View File

@ -52,12 +52,15 @@ typedef struct {
} shared_enumerator_t;
METHOD(enumerator_t, shared_enumerator_enumerate, bool,
shared_enumerator_t *this, shared_key_t **key, id_match_t *me,
id_match_t *other)
shared_enumerator_t *this, va_list args)
{
shared_key_t **key;
id_match_t *me, *other;
char *local_id, *remote_id, *psk;
identification_t *local, *remote;
VA_ARGS_VGET(args, key, me, other);
while (TRUE)
{
/* defaults */
@ -126,7 +129,8 @@ METHOD(credential_set_t, create_shared_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_shared_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _shared_enumerator_enumerate,
.destroy = _shared_enumerator_destroy,
},
.me = me,

View File

@ -58,11 +58,10 @@ typedef struct {
} section_enumerator_t;
METHOD(enumerator_t, section_enumerator_enumerate, bool,
section_enumerator_t *this, ...)
section_enumerator_t *this, va_list args)
{
struct uci_element *element;
char **value;
va_list args;
int i;
if (&this->current->list == this->list)
@ -70,8 +69,6 @@ METHOD(enumerator_t, section_enumerator_enumerate, bool,
return FALSE;
}
va_start(args, this);
value = va_arg(args, char**);
if (value)
{
@ -96,7 +93,6 @@ METHOD(enumerator_t, section_enumerator_enumerate, bool,
*value = uci_to_option(element)->value;
}
}
va_end(args);
this->current = list_to_element(this->current->list.next);
return TRUE;
@ -124,7 +120,13 @@ METHOD(uci_parser_t, create_section_enumerator, enumerator_t*,
i++;
}
va_end(args);
e = malloc(sizeof(section_enumerator_t) + sizeof(char*) * i);
INIT_EXTRA(e, sizeof(char*) * i,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _section_enumerator_enumerate,
.destroy = _section_enumerator_destroy,
},
);
i = 0;
va_start(args, this);
do
@ -134,9 +136,6 @@ METHOD(uci_parser_t, create_section_enumerator, enumerator_t*,
while (e->keywords[i++]);
va_end(args);
e->public.enumerate = (void*)_section_enumerator_enumerate;
e->public.destroy = _section_enumerator_destroy;
/* load uci context */
e->ctx = uci_alloc_context();
if (uci_load(e->ctx, this->package, &e->package) != UCI_OK)

View File

@ -368,9 +368,12 @@ typedef struct {
} attribute_enumerator_t;
METHOD(enumerator_t, enumerate_attributes, bool,
attribute_enumerator_t *this, configuration_attribute_type_t *type,
chunk_t *data)
attribute_enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *data;
VA_ARGS_VGET(args, type, data);
if (this->i < countof(attributes))
{
*type = attributes[this->i++];
@ -393,7 +396,8 @@ METHOD(attribute_handler_t, create_attribute_enumerator, enumerator_t *,
}
INIT(enumerator,
.public = {
.enumerate = (void*)_enumerate_attributes,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_attributes,
.destroy = (void*)free,
},
);
@ -407,24 +411,27 @@ typedef struct {
ike_sa_id_t *id;
} include_filter_t;
/**
* Include enumerator filter function
*/
static bool include_filter(include_filter_t *data,
entry_t **entry, traffic_selector_t **ts)
CALLBACK(include_filter, bool,
include_filter_t *data, enumerator_t *orig, va_list args)
{
if (data->id->equals(data->id, (*entry)->id))
entry_t *entry;
traffic_selector_t **ts;
VA_ARGS_VGET(args, ts);
while (orig->enumerate(orig, &entry))
{
*ts = (*entry)->ts;
return TRUE;
if (data->id->equals(data->id, entry->id))
{
*ts = entry->ts;
return TRUE;
}
}
return FALSE;
}
/**
* Destroy include filter data, unlock mutex
*/
static void destroy_filter(include_filter_t *data)
CALLBACK(destroy_filter, void,
include_filter_t *data)
{
data->mutex->unlock(data->mutex);
free(data);
@ -442,7 +449,7 @@ METHOD(unity_handler_t, create_include_enumerator, enumerator_t*,
data->mutex->lock(data->mutex);
return enumerator_create_filter(
this->include->create_enumerator(this->include),
(void*)include_filter, data, (void*)destroy_filter);
include_filter, data, destroy_filter);
}
METHOD(unity_handler_t, destroy, void,

View File

@ -77,12 +77,15 @@ static void append_ts(bio_writer_t *writer, traffic_selector_t *ts)
}
METHOD(enumerator_t, attribute_enumerate, bool,
attribute_enumerator_t *this, configuration_attribute_type_t *type,
chunk_t *attr)
attribute_enumerator_t *this, va_list args)
{
configuration_attribute_type_t *type;
chunk_t *attr;
traffic_selector_t *ts;
bio_writer_t *writer;
VA_ARGS_VGET(args, type, attr);
if (this->list->get_count(this->list) == 0)
{
return FALSE;
@ -183,7 +186,8 @@ METHOD(attribute_provider_t, create_attribute_enumerator, enumerator_t*,
INIT(attr_enum,
.public = {
.enumerate = (void*)_attribute_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _attribute_enumerate,
.destroy = _attribute_destroy,
},
.list = list,

View File

@ -122,9 +122,14 @@ typedef struct {
endecode_test_t *next;
} endecode_enum_t;
static bool endecode_enumerate(endecode_enum_t *this, vici_type_t *type,
char **name, chunk_t *data)
METHOD(enumerator_t, endecode_enumerate, bool,
endecode_enum_t *this, va_list args)
{
vici_type_t *type;
chunk_t *data;
char **name;
VA_ARGS_VGET(args, type, name, data);
if (this->next)
{
*type = this->next->type;
@ -149,7 +154,8 @@ static enumerator_t *endecode_create_enumerator(endecode_test_t *test)
INIT(enumerator,
.public = {
.enumerate = (void*)endecode_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _endecode_enumerate,
.destroy = (void*)free,
},
.next = test,

View File

@ -184,16 +184,22 @@ METHOD(attribute_provider_t, release_address, bool,
return found;
}
/**
* Filter mapping attribute_t to enumerated type/value arguments
*/
static bool attr_filter(void *data, attribute_t **attr,
configuration_attribute_type_t *type,
void *in, chunk_t *value)
CALLBACK(attr_filter, bool,
void *data, enumerator_t *orig, va_list args)
{
*type = (*attr)->type;
*value = (*attr)->value;
return TRUE;
attribute_t *attr;
configuration_attribute_type_t *type;
chunk_t *value;
VA_ARGS_VGET(args, type, value);
if (orig->enumerate(orig, &attr))
{
*type = attr->type;
*value = attr->value;
return TRUE;
}
return FALSE;
}
/**
@ -203,7 +209,7 @@ CALLBACK(create_nested, enumerator_t*,
pool_t *pool, void *this)
{
return enumerator_create_filter(array_create_enumerator(pool->attrs),
(void*)attr_filter, NULL, NULL);
attr_filter, NULL, NULL);
}
/**

View File

@ -141,13 +141,20 @@ METHOD(backend_t, create_peer_cfg_enumerator, enumerator_t*,
(void*)this->lock->unlock, this->lock);
}
/**
* Enumerator filter function for ike configs
*/
static bool ike_filter(void *data, peer_cfg_t **in, ike_cfg_t **out)
CALLBACK(ike_filter, bool,
void *data, enumerator_t *orig, va_list args)
{
*out = (*in)->get_ike_cfg(*in);
return TRUE;
peer_cfg_t *cfg;
ike_cfg_t **out;
VA_ARGS_VGET(args, out);
if (orig->enumerate(orig, &cfg))
{
*out = cfg->get_ike_cfg(cfg);
return TRUE;
}
return FALSE;
}
METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
@ -155,7 +162,7 @@ METHOD(backend_t, create_ike_cfg_enumerator, enumerator_t*,
{
this->lock->read_lock(this->lock);
return enumerator_create_filter(this->conns->create_enumerator(this->conns),
(void*)ike_filter, this->lock,
ike_filter, this->lock,
(void*)this->lock->unlock);
}

View File

@ -135,11 +135,16 @@ typedef struct {
} parse_enumerator_t;
METHOD(enumerator_t, parse_enumerate, bool,
parse_enumerator_t *this, vici_type_t *out, char **name, chunk_t *value)
parse_enumerator_t *this, va_list args)
{
vici_type_t *out;
chunk_t *value;
char **name;
uint8_t type;
chunk_t data;
VA_ARGS_VGET(args, out, name, value);
if (!this->reader->remaining(this->reader) ||
!this->reader->read_uint8(this->reader, &type))
{
@ -218,7 +223,8 @@ METHOD(vici_message_t, create_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_parse_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _parse_enumerate,
.destroy = _parse_destroy,
},
.reader = bio_reader_create(this->encoding),

View File

@ -119,14 +119,19 @@ METHOD(whitelist_listener_t, remove_, void,
DESTROY_IF(id);
}
/**
* Enumerator filter, from hashtable (key, value) to single identity
*/
static bool whitelist_filter(rwlock_t *lock, identification_t **key,
identification_t **id, identification_t **value)
CALLBACK(whitelist_filter, bool,
rwlock_t *lock, enumerator_t *orig, va_list args)
{
*id = *value;
return TRUE;
identification_t *key, *value, **out;
VA_ARGS_VGET(args, out);
if (orig->enumerate(orig, &key, &value))
{
*out = value;
return TRUE;
}
return FALSE;
}
METHOD(whitelist_listener_t, create_enumerator, enumerator_t*,
@ -134,7 +139,7 @@ METHOD(whitelist_listener_t, create_enumerator, enumerator_t*,
{
this->lock->read_lock(this->lock);
return enumerator_create_filter(this->ids->create_enumerator(this->ids),
(void*)whitelist_filter, this->lock,
whitelist_filter, this->lock,
(void*)this->lock->unlock);
}

View File

@ -435,10 +435,11 @@ struct policy_enumerator_t {
};
METHOD(enumerator_t, policy_enumerate, bool,
policy_enumerator_t *this, traffic_selector_t **my_out,
traffic_selector_t **other_out)
policy_enumerator_t *this, va_list args)
{
traffic_selector_t *other_ts;
traffic_selector_t *other_ts, **my_out, **other_out;
VA_ARGS_VGET(args, my_out, other_out);
while (this->ts || this->mine->enumerate(this->mine, &this->ts))
{
@ -487,7 +488,8 @@ METHOD(child_sa_t, create_policy_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_policy_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _policy_enumerate,
.destroy = _policy_destroy,
},
.mine = array_create_enumerator(this->my_ts),
@ -1402,13 +1404,13 @@ METHOD(child_sa_t, get_rekey_spi, uint32_t,
return this->rekey_spi;
}
/**
* Callback to reinstall a virtual IP
*/
static void reinstall_vip(host_t *vip, host_t *me)
CALLBACK(reinstall_vip, void,
host_t *vip, va_list args)
{
host_t *me;
char *iface;
VA_ARGS_VGET(args, me);
if (charon->kernel->get_interface(charon->kernel, me, &iface))
{
charon->kernel->del_ip(charon->kernel, vip, -1, TRUE);
@ -1530,7 +1532,7 @@ METHOD(child_sa_t, update, status_t,
/* we reinstall the virtual IP to handle interface roaming
* correctly */
vips->invoke_function(vips, (void*)reinstall_vip, me);
vips->invoke_function(vips, reinstall_vip, me);
/* reinstall updated policies */
install_policies_internal(this, me, other, my_ts, other_ts,

View File

@ -105,31 +105,38 @@ METHOD(eap_manager_t, remove_method, void,
this->lock->unlock(this->lock);
}
/**
* filter the registered methods
*/
static bool filter_methods(uintptr_t role, eap_entry_t **entry,
eap_type_t *type, void *in, uint32_t *vendor)
CALLBACK(filter_methods, bool,
uintptr_t role, enumerator_t *orig, va_list args)
{
if ((*entry)->role != (eap_role_t)role)
eap_entry_t *entry;
eap_type_t *type;
uint32_t *vendor;
VA_ARGS_VGET(args, type, vendor);
while (orig->enumerate(orig, &entry))
{
return FALSE;
if (entry->role != (eap_role_t)role)
{
continue;
}
if (entry->vendor == 0 &&
(entry->type < 4 || entry->type == EAP_EXPANDED ||
entry->type > EAP_EXPERIMENTAL))
{ /* filter invalid types */
continue;
}
if (type)
{
*type = entry->type;
}
if (vendor)
{
*vendor = entry->vendor;
}
return TRUE;
}
if ((*entry)->vendor == 0 &&
((*entry)->type < 4 || (*entry)->type == EAP_EXPANDED ||
(*entry)->type > EAP_EXPERIMENTAL))
{ /* filter invalid types */
return FALSE;
}
if (type)
{
*type = (*entry)->type;
}
if (vendor)
{
*vendor = (*entry)->vendor;
}
return TRUE;
return FALSE;
}
METHOD(eap_manager_t, create_enumerator, enumerator_t*,
@ -139,7 +146,7 @@ METHOD(eap_manager_t, create_enumerator, enumerator_t*,
return enumerator_create_cleaner(
enumerator_create_filter(
this->methods->create_enumerator(this->methods),
(void*)filter_methods, (void*)(uintptr_t)role, NULL),
filter_methods, (void*)(uintptr_t)role, NULL),
(void*)this->lock->unlock, this->lock);
}

View File

@ -1200,12 +1200,20 @@ METHOD(ike_sa_t, generate_message, status_t,
return status;
}
static bool filter_fragments(private_ike_sa_t *this, packet_t **fragment,
packet_t **packet)
CALLBACK(filter_fragments, bool,
private_ike_sa_t *this, enumerator_t *orig, va_list args)
{
*packet = (*fragment)->clone(*fragment);
set_dscp(this, *packet);
return TRUE;
packet_t *fragment, **packet;
VA_ARGS_VGET(args, packet);
if (orig->enumerate(orig, &fragment))
{
*packet = fragment->clone(fragment);
set_dscp(this, *packet);
return TRUE;
}
return FALSE;
}
METHOD(ike_sa_t, generate_message_fragmented, status_t,
@ -1265,7 +1273,7 @@ METHOD(ike_sa_t, generate_message_fragmented, status_t,
{
charon->bus->message(charon->bus, message, FALSE, FALSE);
}
*packets = enumerator_create_filter(fragments, (void*)filter_fragments,
*packets = enumerator_create_filter(fragments, filter_fragments,
this, NULL);
}
return status;
@ -1699,8 +1707,11 @@ typedef struct {
} child_enumerator_t;
METHOD(enumerator_t, child_enumerate, bool,
child_enumerator_t *this, child_sa_t **child_sa)
child_enumerator_t *this, va_list args)
{
child_sa_t **child_sa;
VA_ARGS_VGET(args, child_sa);
if (this->inner->enumerate(this->inner, &this->current))
{
*child_sa = this->current;
@ -1723,7 +1734,8 @@ METHOD(ike_sa_t, create_child_sa_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_child_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _child_enumerate,
.destroy = _child_enumerator_destroy,
},
.inner = array_create_enumerator(this->child_sas),
@ -2619,24 +2631,31 @@ METHOD(ike_sa_t, add_configuration_attribute, void,
array_insert(this->attributes, ARRAY_TAIL, &entry);
}
/**
* Enumerator filter for attributes
*/
static bool filter_attribute(void *null, attribute_entry_t **in,
configuration_attribute_type_t *type, void *in2,
chunk_t *data, void *in3, bool *handled)
CALLBACK(filter_attribute, bool,
void *null, enumerator_t *orig, va_list args)
{
*type = (*in)->type;
*data = (*in)->data;
*handled = (*in)->handler != NULL;
return TRUE;
attribute_entry_t *entry;
configuration_attribute_type_t *type;
chunk_t *data;
bool *handled;
VA_ARGS_VGET(args, type, data, handled);
if (orig->enumerate(orig, &entry))
{
*type = entry->type;
*data = entry->data;
*handled = entry->handler != NULL;
return TRUE;
}
return FALSE;
}
METHOD(ike_sa_t, create_attribute_enumerator, enumerator_t*,
private_ike_sa_t *this)
{
return enumerator_create_filter(array_create_enumerator(this->attributes),
(void*)filter_attribute, NULL, NULL);
filter_attribute, NULL, NULL);
}
METHOD(ike_sa_t, create_task_enumerator, enumerator_t*,

View File

@ -151,8 +151,10 @@ static entry_t *entry_create()
/**
* Function that matches entry_t objects by ike_sa_id_t.
*/
static bool entry_match_by_id(entry_t *entry, ike_sa_id_t *id)
static bool entry_match_by_id(entry_t *entry, void *arg)
{
ike_sa_id_t *id = arg;
if (id->equals(id, entry->ike_sa_id))
{
return TRUE;
@ -172,7 +174,7 @@ static bool entry_match_by_id(entry_t *entry, ike_sa_id_t *id)
/**
* Function that matches entry_t objects by ike_sa_t pointers.
*/
static bool entry_match_by_sa(entry_t *entry, ike_sa_t *ike_sa)
static bool entry_match_by_sa(entry_t *entry, void *ike_sa)
{
return entry->ike_sa == ike_sa;
}
@ -513,8 +515,13 @@ struct private_enumerator_t {
};
METHOD(enumerator_t, enumerate, bool,
private_enumerator_t *this, entry_t **entry, u_int *segment)
private_enumerator_t *this, va_list args)
{
entry_t **entry;
u_int *segment;
VA_ARGS_VGET(args, entry, segment);
if (this->entry)
{
this->entry->condvar->signal(this->entry->condvar);
@ -572,7 +579,8 @@ static enumerator_t* create_table_enumerator(private_ike_sa_manager_t *this)
INIT(enumerator,
.enumerator = {
.enumerate = (void*)_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate,
.destroy = _enumerator_destroy,
},
.manager = this,
@ -671,7 +679,7 @@ static void remove_entry_at(private_enumerator_t *this)
*/
static status_t get_entry_by_match_function(private_ike_sa_manager_t *this,
ike_sa_id_t *ike_sa_id, entry_t **entry, u_int *segment,
linked_list_match_t match, void *param)
bool (*match)(entry_t*,void*), void *param)
{
table_item_t *item;
u_int row, seg;
@ -704,7 +712,7 @@ static status_t get_entry_by_id(private_ike_sa_manager_t *this,
ike_sa_id_t *ike_sa_id, entry_t **entry, u_int *segment)
{
return get_entry_by_match_function(this, ike_sa_id, entry, segment,
(linked_list_match_t)entry_match_by_id, ike_sa_id);
entry_match_by_id, ike_sa_id);
}
/**
@ -715,7 +723,7 @@ static status_t get_entry_by_sa(private_ike_sa_manager_t *this,
ike_sa_id_t *ike_sa_id, ike_sa_t *ike_sa, entry_t **entry, u_int *segment)
{
return get_entry_by_match_function(this, ike_sa_id, entry, segment,
(linked_list_match_t)entry_match_by_sa, ike_sa);
entry_match_by_sa, ike_sa);
}
/**
@ -852,6 +860,15 @@ static void remove_half_open(private_ike_sa_manager_t *this, entry_t *entry)
lock->unlock(lock);
}
CALLBACK(id_matches, bool,
ike_sa_id_t *a, va_list args)
{
ike_sa_id_t *b;
VA_ARGS_VGET(args, b);
return a->equals(a, b);
}
/**
* Put an SA between two peers into the hash table.
*/
@ -880,8 +897,7 @@ static void put_connected_peers(private_ike_sa_manager_t *this, entry_t *entry)
entry->other_id, family))
{
if (connected_peers->sas->find_first(connected_peers->sas,
(linked_list_match_t)entry->ike_sa_id->equals,
NULL, entry->ike_sa_id) == SUCCESS)
id_matches, NULL, entry->ike_sa_id))
{
lock->unlock(lock);
return;
@ -1556,42 +1572,52 @@ METHOD(ike_sa_manager_t, checkout_by_name, ike_sa_t*,
return ike_sa;
}
/**
* enumerator filter function, waiting variant
*/
static bool enumerator_filter_wait(private_ike_sa_manager_t *this,
entry_t **in, ike_sa_t **out, u_int *segment)
CALLBACK(enumerator_filter_wait, bool,
private_ike_sa_manager_t *this, enumerator_t *orig, va_list args)
{
if (wait_for_entry(this, *in, *segment))
entry_t *entry;
u_int segment;
ike_sa_t **out;
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &entry, &segment))
{
*out = (*in)->ike_sa;
charon->bus->set_sa(charon->bus, *out);
return TRUE;
if (wait_for_entry(this, entry, segment))
{
*out = entry->ike_sa;
charon->bus->set_sa(charon->bus, *out);
return TRUE;
}
}
return FALSE;
}
/**
* enumerator filter function, skipping variant
*/
static bool enumerator_filter_skip(private_ike_sa_manager_t *this,
entry_t **in, ike_sa_t **out, u_int *segment)
CALLBACK(enumerator_filter_skip, bool,
private_ike_sa_manager_t *this, enumerator_t *orig, va_list args)
{
if (!(*in)->driveout_new_threads &&
!(*in)->driveout_waiting_threads &&
!(*in)->checked_out)
entry_t *entry;
u_int segment;
ike_sa_t **out;
VA_ARGS_VGET(args, out);
while (orig->enumerate(orig, &entry, &segment))
{
*out = (*in)->ike_sa;
charon->bus->set_sa(charon->bus, *out);
return TRUE;
if (!entry->driveout_new_threads &&
!entry->driveout_waiting_threads &&
!entry->checked_out)
{
*out = entry->ike_sa;
charon->bus->set_sa(charon->bus, *out);
return TRUE;
}
}
return FALSE;
}
/**
* Reset threads SA after enumeration
*/
static void reset_sa(void *data)
CALLBACK(reset_sa, void,
void *data)
{
charon->bus->set_sa(charon->bus, NULL);
}

View File

@ -450,22 +450,21 @@ static initiate_data_t *initiate_data_create(check_list_t *checklist,
return this;
}
/**
* Find an initiated connection by the peers' ids
*/
static bool match_initiated_by_ids(initiated_t *current, identification_t *id,
identification_t *peer_id)
CALLBACK(match_initiated_by_ids, bool,
initiated_t *current, va_list args)
{
identification_t *id, *peer_id;
VA_ARGS_VGET(args, id, peer_id);
return id->equals(id, current->id) && peer_id->equals(peer_id, current->peer_id);
}
static status_t get_initiated_by_ids(private_connect_manager_t *this,
identification_t *id,
identification_t *peer_id,
initiated_t **initiated)
static bool get_initiated_by_ids(private_connect_manager_t *this,
identification_t *id,
identification_t *peer_id,
initiated_t **initiated)
{
return this->initiated->find_first(this->initiated,
(linked_list_match_t)match_initiated_by_ids,
return this->initiated->find_first(this->initiated, match_initiated_by_ids,
(void**)initiated, id, peer_id);
}
@ -490,21 +489,20 @@ static void remove_initiated(private_connect_manager_t *this,
enumerator->destroy(enumerator);
}
/**
* Find the checklist with a specific connect ID
*/
static bool match_checklist_by_id(check_list_t *current, chunk_t *connect_id)
CALLBACK(match_checklist_by_id, bool,
check_list_t *current, va_list args)
{
return chunk_equals(*connect_id, current->connect_id);
chunk_t connect_id;
VA_ARGS_VGET(args, connect_id);
return chunk_equals(connect_id, current->connect_id);
}
static status_t get_checklist_by_id(private_connect_manager_t *this,
chunk_t connect_id,
check_list_t **check_list)
static bool get_checklist_by_id(private_connect_manager_t *this,
chunk_t connect_id, check_list_t **check_list)
{
return this->checklists->find_first(this->checklists,
(linked_list_match_t)match_checklist_by_id,
(void**)check_list, &connect_id);
return this->checklists->find_first(this->checklists, match_checklist_by_id,
(void**)check_list, connect_id);
}
/**
@ -528,19 +526,19 @@ static void remove_checklist(private_connect_manager_t *this,
enumerator->destroy(enumerator);
}
/**
* Checks if a list of endpoint_notify_t contains a certain host_t
*/
static bool match_endpoint_by_host(endpoint_notify_t *current, host_t *host)
CALLBACK(match_endpoint_by_host, bool,
endpoint_notify_t *current, va_list args)
{
host_t *host;
VA_ARGS_VGET(args, host);
return host->equals(host, current->get_host(current));
}
static status_t endpoints_contain(linked_list_t *endpoints, host_t *host,
static bool endpoints_contain(linked_list_t *endpoints, host_t *host,
endpoint_notify_t **endpoint)
{
return endpoints->find_first(endpoints,
(linked_list_match_t)match_endpoint_by_host,
return endpoints->find_first(endpoints, match_endpoint_by_host,
(void**)endpoint, host);
}
@ -560,39 +558,44 @@ static void insert_pair_by_priority(linked_list_t *pairs, endpoint_pair_t *pair)
enumerator->destroy(enumerator);
}
/**
* Searches a list of endpoint_pair_t for a pair with specific host_ts
*/
static bool match_pair_by_hosts(endpoint_pair_t *current, host_t *local,
host_t *remote)
CALLBACK(match_pair_by_hosts, bool,
endpoint_pair_t *current, va_list args)
{
return local->equals(local, current->local) && remote->equals(remote, current->remote);
host_t *local, *remote;
VA_ARGS_VGET(args, local, remote);
return local->equals(local, current->local) &&
remote->equals(remote, current->remote);
}
static status_t get_pair_by_hosts(linked_list_t *pairs, host_t *local,
host_t *remote, endpoint_pair_t **pair)
static bool get_pair_by_hosts(linked_list_t *pairs, host_t *local,
host_t *remote, endpoint_pair_t **pair)
{
return pairs->find_first(pairs, (linked_list_match_t)match_pair_by_hosts,
(void**)pair, local, remote);
return pairs->find_first(pairs, match_pair_by_hosts, (void**)pair, local,
remote);
}
static bool match_pair_by_id(endpoint_pair_t *current, uint32_t *id)
CALLBACK(match_pair_by_id, bool,
endpoint_pair_t *current, va_list args)
{
return current->id == *id;
uint32_t id;
VA_ARGS_VGET(args, id);
return current->id == id;
}
/**
* Searches for a pair with a specific id
*/
static status_t get_pair_by_id(check_list_t *checklist, uint32_t id,
endpoint_pair_t **pair)
static bool get_pair_by_id(check_list_t *checklist, uint32_t id,
endpoint_pair_t **pair)
{
return checklist->pairs->find_first(checklist->pairs,
(linked_list_match_t)match_pair_by_id,
(void**)pair, &id);
return checklist->pairs->find_first(checklist->pairs, match_pair_by_id,
(void**)pair, id);
}
static bool match_succeeded_pair(endpoint_pair_t *current)
CALLBACK(match_succeeded_pair, bool,
endpoint_pair_t *current, va_list args)
{
return current->state == CHECK_SUCCEEDED;
}
@ -600,15 +603,14 @@ static bool match_succeeded_pair(endpoint_pair_t *current)
/**
* Returns the best pair of state CHECK_SUCCEEDED from a checklist.
*/
static status_t get_best_valid_pair(check_list_t *checklist,
endpoint_pair_t **pair)
static bool get_best_valid_pair(check_list_t *checklist, endpoint_pair_t **pair)
{
return checklist->pairs->find_first(checklist->pairs,
(linked_list_match_t)match_succeeded_pair,
(void**)pair);
return checklist->pairs->find_first(checklist->pairs, match_succeeded_pair,
(void**)pair);
}
static bool match_waiting_pair(endpoint_pair_t *current)
CALLBACK(match_waiting_pair, bool,
endpoint_pair_t *current, va_list args)
{
return current->state == CHECK_WAITING;
}
@ -865,7 +867,7 @@ static job_requeue_t initiator_finish(callback_data_t *data)
this->mutex->lock(this->mutex);
check_list_t *checklist;
if (get_checklist_by_id(this, data->connect_id, &checklist) != SUCCESS)
if (!get_checklist_by_id(this, data->connect_id, &checklist))
{
DBG1(DBG_IKE, "checklist with id '%#B' not found, can't finish "
"connectivity checks", &data->connect_id);
@ -953,7 +955,7 @@ static job_requeue_t retransmit(callback_data_t *data)
this->mutex->lock(this->mutex);
check_list_t *checklist;
if (get_checklist_by_id(this, data->connect_id, &checklist) != SUCCESS)
if (!get_checklist_by_id(this, data->connect_id, &checklist))
{
DBG1(DBG_IKE, "checklist with id '%#B' not found, can't retransmit "
"connectivity check", &data->connect_id);
@ -962,7 +964,7 @@ static job_requeue_t retransmit(callback_data_t *data)
}
endpoint_pair_t *pair;
if (get_pair_by_id(checklist, data->mid, &pair) != SUCCESS)
if (!get_pair_by_id(checklist, data->mid, &pair))
{
DBG1(DBG_IKE, "pair with id '%d' not found, can't retransmit "
"connectivity check", data->mid);
@ -1108,7 +1110,7 @@ static job_requeue_t sender(callback_data_t *data)
this->mutex->lock(this->mutex);
check_list_t *checklist;
if (get_checklist_by_id(this, data->connect_id, &checklist) != SUCCESS)
if (!get_checklist_by_id(this, data->connect_id, &checklist))
{
DBG1(DBG_IKE, "checklist with id '%#B' not found, can't send "
"connectivity check", &data->connect_id);
@ -1124,9 +1126,8 @@ static job_requeue_t sender(callback_data_t *data)
{
DBG1(DBG_IKE, "no triggered check queued, sending an ordinary check");
if (checklist->pairs->find_first(checklist->pairs,
(linked_list_match_t)match_waiting_pair,
(void**)&pair) != SUCCESS)
if (!checklist->pairs->find_first(checklist->pairs, match_waiting_pair,
(void**)&pair))
{
this->mutex->unlock(this->mutex);
DBG1(DBG_IKE, "no pairs in waiting state, aborting");
@ -1182,7 +1183,7 @@ static job_requeue_t initiate_mediated(initiate_data_t *data)
initiated_t *initiated = data->initiated;
endpoint_pair_t *pair;
if (get_best_valid_pair(checklist, &pair) == SUCCESS)
if (get_best_valid_pair(checklist, &pair))
{
ike_sa_id_t *waiting_sa;
enumerator_t *enumerator = initiated->mediated->create_enumerator(
@ -1219,7 +1220,7 @@ static void finish_checks(private_connect_manager_t *this, check_list_t *checkli
{
initiated_t *initiated;
if (get_initiated_by_ids(this, checklist->initiator.id,
checklist->responder.id, &initiated) == SUCCESS)
checklist->responder.id, &initiated))
{
callback_job_t *job;
@ -1247,7 +1248,7 @@ static void process_response(private_connect_manager_t *this, check_t *check,
check_list_t *checklist)
{
endpoint_pair_t *pair;
if (get_pair_by_id(checklist, check->mid, &pair) == SUCCESS)
if (get_pair_by_id(checklist, check->mid, &pair))
{
if (pair->local->equals(pair->local, check->dst) &&
pair->remote->equals(pair->remote, check->src))
@ -1261,9 +1262,9 @@ static void process_response(private_connect_manager_t *this, check_t *check,
checklist->initiator.endpoints : checklist->responder.endpoints;
endpoint_notify_t *local_endpoint;
if (endpoints_contain(local_endpoints,
check->endpoint->get_host(check->endpoint),
&local_endpoint) != SUCCESS)
if (!endpoints_contain(local_endpoints,
check->endpoint->get_host(check->endpoint),
&local_endpoint))
{
local_endpoint = endpoint_notify_create_from_host(PEER_REFLEXIVE,
check->endpoint->get_host(check->endpoint), pair->local);
@ -1302,15 +1303,14 @@ static void process_request(private_connect_manager_t *this, check_t *check,
peer_reflexive->set_priority(peer_reflexive,
check->endpoint->get_priority(check->endpoint));
if (endpoints_contain(remote_endpoints, check->src, &remote_endpoint) != SUCCESS)
if (!endpoints_contain(remote_endpoints, check->src, &remote_endpoint))
{
remote_endpoint = peer_reflexive->clone(peer_reflexive);
remote_endpoints->insert_last(remote_endpoints, remote_endpoint);
}
endpoint_pair_t *pair;
if (get_pair_by_hosts(checklist->pairs, check->dst, check->src,
&pair) == SUCCESS)
if (get_pair_by_hosts(checklist->pairs, check->dst, check->src, &pair))
{
switch(pair->state)
{
@ -1389,7 +1389,7 @@ METHOD(connect_manager_t, process_check, void,
this->mutex->lock(this->mutex);
check_list_t *checklist;
if (get_checklist_by_id(this, check->connect_id, &checklist) != SUCCESS)
if (!get_checklist_by_id(this, check->connect_id, &checklist))
{
DBG1(DBG_IKE, "checklist with id '%#B' not found",
&check->connect_id);
@ -1423,6 +1423,15 @@ METHOD(connect_manager_t, process_check, void,
check_destroy(check);
}
CALLBACK(id_matches, bool,
ike_sa_id_t *a, va_list args)
{
ike_sa_id_t *b;
VA_ARGS_VGET(args, b);
return a->equals(a, b);
}
METHOD(connect_manager_t, check_and_register, bool,
private_connect_manager_t *this, identification_t *id,
identification_t *peer_id, ike_sa_id_t *mediated_sa)
@ -1432,7 +1441,7 @@ METHOD(connect_manager_t, check_and_register, bool,
this->mutex->lock(this->mutex);
if (get_initiated_by_ids(this, id, peer_id, &initiated) != SUCCESS)
if (!get_initiated_by_ids(this, id, peer_id, &initiated))
{
DBG2(DBG_IKE, "registered waiting mediated connection with '%Y'",
peer_id);
@ -1441,9 +1450,8 @@ METHOD(connect_manager_t, check_and_register, bool,
already_there = FALSE;
}
if (initiated->mediated->find_first(initiated->mediated,
(linked_list_match_t)mediated_sa->equals,
NULL, mediated_sa) != SUCCESS)
if (!initiated->mediated->find_first(initiated->mediated, id_matches,
NULL, mediated_sa))
{
initiated->mediated->insert_last(initiated->mediated,
mediated_sa->clone(mediated_sa));
@ -1462,7 +1470,7 @@ METHOD(connect_manager_t, check_and_initiate, void,
this->mutex->lock(this->mutex);
if (get_initiated_by_ids(this, id, peer_id, &initiated) != SUCCESS)
if (!get_initiated_by_ids(this, id, peer_id, &initiated))
{
DBG2(DBG_IKE, "no waiting mediated connections with '%Y'", peer_id);
this->mutex->unlock(this->mutex);
@ -1492,7 +1500,7 @@ METHOD(connect_manager_t, set_initiator_data, status_t,
this->mutex->lock(this->mutex);
if (get_checklist_by_id(this, connect_id, NULL) == SUCCESS)
if (get_checklist_by_id(this, connect_id, NULL))
{
DBG1(DBG_IKE, "checklist with id '%#B' already exists, aborting",
&connect_id);
@ -1517,7 +1525,7 @@ METHOD(connect_manager_t, set_responder_data, status_t,
this->mutex->lock(this->mutex);
if (get_checklist_by_id(this, connect_id, &checklist) != SUCCESS)
if (!get_checklist_by_id(this, connect_id, &checklist))
{
DBG1(DBG_IKE, "checklist with id '%#B' not found",
&connect_id);
@ -1547,7 +1555,7 @@ METHOD(connect_manager_t, stop_checks, status_t,
this->mutex->lock(this->mutex);
if (get_checklist_by_id(this, connect_id, &checklist) != SUCCESS)
if (!get_checklist_by_id(this, connect_id, &checklist))
{
DBG1(DBG_IKE, "checklist with id '%#B' not found",
&connect_id);

View File

@ -2079,13 +2079,20 @@ METHOD(task_manager_t, reset, void,
this->reset = TRUE;
}
/**
* Filter queued tasks
*/
static bool filter_queued(void *unused, queued_task_t **queued, task_t **task)
CALLBACK(filter_queued, bool,
void *unused, enumerator_t *orig, va_list args)
{
*task = (*queued)->task;
return TRUE;
queued_task_t *queued;
task_t **task;
VA_ARGS_VGET(args, task);
if (orig->enumerate(orig, &queued))
{
*task = queued->task;
return TRUE;
}
return FALSE;
}
METHOD(task_manager_t, create_task_enumerator, enumerator_t*,
@ -2100,7 +2107,7 @@ METHOD(task_manager_t, create_task_enumerator, enumerator_t*,
case TASK_QUEUE_QUEUED:
return enumerator_create_filter(
array_create_enumerator(this->queued_tasks),
(void*)filter_queued, NULL, NULL);
filter_queued, NULL, NULL);
default:
return enumerator_create_empty();
}

View File

@ -81,11 +81,12 @@ typedef struct {
bool check_delete_action;
} entry_t;
/**
* Check if the given entry is for the same CHILD_SA
*/
static bool match_child(entry_t *entry, child_sa_t *child_sa)
CALLBACK(match_child, bool,
entry_t *entry, va_list args)
{
child_sa_t *child_sa;
VA_ARGS_VGET(args, child_sa);
return entry->child_sa == child_sa;
}
@ -252,8 +253,8 @@ static void process_payloads(private_child_delete_t *this, message_t *message)
DBG1(DBG_IKE, "received DELETE for %N CHILD_SA with SPI %.8x",
protocol_id_names, protocol, ntohl(spi));
if (this->child_sas->find_first(this->child_sas,
(void*)match_child, NULL, child_sa) == SUCCESS)
if (this->child_sas->find_first(this->child_sas, match_child,
NULL, child_sa))
{
continue;
}

View File

@ -381,14 +381,24 @@ METHOD(shunt_manager_t, uninstall, bool,
}
CALLBACK(filter_entries, bool,
void *unused, entry_t **entry, char **ns, void **in, child_cfg_t **cfg)
void *unused, enumerator_t *orig, va_list args)
{
if (ns)
entry_t *entry;
child_cfg_t **cfg;
char **ns;
VA_ARGS_VGET(args, ns, cfg);
if (orig->enumerate(orig, &entry))
{
*ns = (*entry)->ns;
if (ns)
{
*ns = entry->ns;
}
*cfg = entry->cfg;
return TRUE;
}
*cfg = (*entry)->cfg;
return TRUE;
return FALSE;
}
METHOD(shunt_manager_t, create_enumerator, enumerator_t*,
@ -397,7 +407,7 @@ METHOD(shunt_manager_t, create_enumerator, enumerator_t*,
this->lock->read_lock(this->lock);
return enumerator_create_filter(
this->shunts->create_enumerator(this->shunts),
(void*)filter_entries, this->lock,
filter_entries, this->lock,
(void*)this->lock->unlock);
}

View File

@ -140,19 +140,21 @@ static void destroy_acquire(acquire_t *this)
free(this);
}
/**
* match an acquire entry by reqid
*/
static bool acquire_by_reqid(acquire_t *this, uint32_t *reqid)
CALLBACK(acquire_by_reqid, bool,
acquire_t *this, va_list args)
{
return this->reqid == *reqid;
uint32_t reqid;
VA_ARGS_VGET(args, reqid);
return this->reqid == reqid;
}
/**
* match an acquire entry by destination address
*/
static bool acquire_by_dst(acquire_t *this, host_t *dst)
CALLBACK(acquire_by_dst, bool,
acquire_t *this, va_list args)
{
host_t *dst;
VA_ARGS_VGET(args, dst);
return this->dst && this->dst->ip_equals(this->dst, dst);
}
@ -335,25 +337,32 @@ METHOD(trap_manager_t, uninstall, bool,
return TRUE;
}
/**
* convert enumerated entries to peer_cfg, child_sa
*/
static bool trap_filter(rwlock_t *lock, entry_t **entry, peer_cfg_t **peer_cfg,
void *none, child_sa_t **child_sa)
CALLBACK(trap_filter, bool,
rwlock_t *lock, enumerator_t *orig, va_list args)
{
if (!(*entry)->child_sa)
{ /* skip entries that are currently being installed */
return FALSE;
}
if (peer_cfg)
entry_t *entry;
peer_cfg_t **peer_cfg;
child_sa_t **child_sa;
VA_ARGS_VGET(args, peer_cfg, child_sa);
while (orig->enumerate(orig, &entry))
{
*peer_cfg = (*entry)->peer_cfg;
if (!entry->child_sa)
{ /* skip entries that are currently being installed */
continue;
}
if (peer_cfg)
{
*peer_cfg = entry->peer_cfg;
}
if (child_sa)
{
*child_sa = entry->child_sa;
}
return TRUE;
}
if (child_sa)
{
*child_sa = (*entry)->child_sa;
}
return TRUE;
return FALSE;
}
METHOD(trap_manager_t, create_enumerator, enumerator_t*,
@ -361,7 +370,7 @@ METHOD(trap_manager_t, create_enumerator, enumerator_t*,
{
this->lock->read_lock(this->lock);
return enumerator_create_filter(this->traps->create_enumerator(this->traps),
(void*)trap_filter, this->lock,
trap_filter, this->lock,
(void*)this->lock->unlock);
}
@ -432,8 +441,8 @@ METHOD(trap_manager_t, acquire, void,
uint8_t mask;
dst->to_subnet(dst, &host, &mask);
if (this->acquires->find_first(this->acquires, (void*)acquire_by_dst,
(void**)&acquire, host) == SUCCESS)
if (this->acquires->find_first(this->acquires, acquire_by_dst,
(void**)&acquire, host))
{
host->destroy(host);
ignore = TRUE;
@ -449,8 +458,8 @@ METHOD(trap_manager_t, acquire, void,
}
else
{
if (this->acquires->find_first(this->acquires, (void*)acquire_by_reqid,
(void**)&acquire, &reqid) == SUCCESS)
if (this->acquires->find_first(this->acquires, acquire_by_reqid,
(void**)&acquire, reqid))
{
ignore = TRUE;
}

View File

@ -269,19 +269,27 @@ kernel_ipsec_t *mock_ipsec_create()
return &this->public;
}
/**
* Filter SAs
*/
static bool filter_sas(void *data, entry_t **entry, ike_sa_t **ike_sa,
void *unused, uint32_t *spi)
CALLBACK(filter_sas, bool,
void *data, enumerator_t *orig, va_list args)
{
if ((*entry)->alloc)
entry_t *entry;
ike_sa_t **ike_sa;
uint32_t *spi;
VA_ARGS_VGET(args, ike_sa, spi);
while (orig->enumerate(orig, &entry, NULL))
{
return FALSE;
if (entry->alloc)
{
continue;
}
*ike_sa = entry->ike_sa;
*spi = entry->spi;
return TRUE;
}
*ike_sa = (*entry)->ike_sa;
*spi = (*entry)->spi;
return TRUE;
return FALSE;
}
/*
@ -291,5 +299,5 @@ enumerator_t *mock_ipsec_create_sa_enumerator()
{
return enumerator_create_filter(
instance->sas->create_enumerator(instance->sas),
(void*)filter_sas, NULL, NULL);
filter_sas, NULL, NULL);
}

View File

@ -179,7 +179,7 @@ METHOD(pa_tnc_attr_t, process, status_t,
u_char *pos;
if (this->offset == 0)
{
{
if (this->length < IETF_INSTALLED_PACKAGES_MIN_SIZE)
{
DBG1(DBG_TNC, "insufficient data for %N/%N", pen_names, PEN_IETF,
@ -291,15 +291,21 @@ METHOD(ietf_attr_installed_packages_t, add, void,
this->packages->insert_last(this->packages, entry);
}
/**
* Enumerate package filter entries
*/
static bool package_filter(void *null, package_entry_t **entry, chunk_t *name,
void *i2, chunk_t *version)
CALLBACK(package_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
*name = (*entry)->name;
*version = (*entry)->version;
return TRUE;
package_entry_t *entry;
chunk_t *name, *version;
VA_ARGS_VGET(args, name, version);
if (orig->enumerate(orig, &entry))
{
*name = entry->name;
*version = entry->version;
return TRUE;
}
return FALSE;
}
METHOD(ietf_attr_installed_packages_t, create_enumerator, enumerator_t*,
@ -307,7 +313,7 @@ METHOD(ietf_attr_installed_packages_t, create_enumerator, enumerator_t*,
{
return enumerator_create_filter(
this->packages->create_enumerator(this->packages),
(void*)package_filter, NULL, NULL);
package_filter, NULL, NULL);
}
METHOD(ietf_attr_installed_packages_t, get_count, uint16_t,

View File

@ -213,24 +213,31 @@ METHOD(ietf_attr_port_filter_t, add_port, void,
this->ports->insert_last(this->ports, entry);
}
/**
* Enumerate port filter entries
*/
static bool port_filter(void *null, port_entry_t **entry,
bool *blocked, void *i2, uint8_t *protocol, void *i3,
uint16_t *port)
CALLBACK(port_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
*blocked = (*entry)->blocked;
*protocol = (*entry)->protocol;
*port = (*entry)->port;
return TRUE;
port_entry_t *entry;
uint16_t *port;
uint8_t *protocol;
bool *blocked;
VA_ARGS_VGET(args, blocked, protocol, port);
if (orig->enumerate(orig, &entry))
{
*blocked = entry->blocked;
*protocol = entry->protocol;
*port = entry->port;
return TRUE;
}
return FALSE;
}
METHOD(ietf_attr_port_filter_t, create_port_enumerator, enumerator_t*,
private_ietf_attr_port_filter_t *this)
{
return enumerator_create_filter(this->ports->create_enumerator(this->ports),
(void*)port_filter, NULL, NULL);
port_filter, NULL, NULL);
}
/**

View File

@ -283,23 +283,20 @@ typedef struct {
} package_enumerator_t;
/**
* Implementation of package_enumerator.destroy.
*/
static void package_enumerator_destroy(package_enumerator_t *this)
METHOD(enumerator_t, package_enumerator_destroy, void,
package_enumerator_t *this)
{
pclose(this->file);
free(this);
}
/**
* Implementation of package_enumerator.enumerate
*/
static bool package_enumerator_enumerate(package_enumerator_t *this, ...)
METHOD(enumerator_t, package_enumerator_enumerate, bool,
package_enumerator_t *this, va_list args)
{
chunk_t *name, *version;
u_char *pos;
va_list args;
VA_ARGS_VGET(args, name, version);
while (TRUE)
{
@ -319,23 +316,16 @@ static bool package_enumerator_enumerate(package_enumerator_t *this, ...)
{
continue;
}
va_start(args, this);
name = va_arg(args, chunk_t*);
name->ptr = pos;
pos = strchr(pos, '\t');
if (!pos)
{
va_end(args);
return FALSE;
}
name->len = pos++ - name->ptr;
version = va_arg(args, chunk_t*);
version->ptr = pos;
version->len = strlen(pos) - 1;
va_end(args);
return TRUE;
}
}
@ -362,12 +352,14 @@ METHOD(imc_os_info_t, create_package_enumerator, enumerator_t*,
return NULL;
}
/* Create a package enumerator instance */
enumerator = malloc_thing(package_enumerator_t);
enumerator->public.enumerate = (void*)package_enumerator_enumerate;
enumerator->public.destroy = (void*)package_enumerator_destroy;
enumerator->file = file;
INIT(enumerator,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _package_enumerator_enumerate,
.destroy = _package_enumerator_destroy,
},
.file = file,
);
return (enumerator_t*)enumerator;
}

View File

@ -626,22 +626,13 @@ typedef struct {
} language_enumerator_t;
/**
* Implementation of language_enumerator.destroy.
*/
static void language_enumerator_destroy(language_enumerator_t *this)
{
free(this);
}
/**
* Implementation of language_enumerator.enumerate
*/
static bool language_enumerator_enumerate(language_enumerator_t *this, ...)
METHOD(enumerator_t, language_enumerator_enumerate, bool,
language_enumerator_t *this, va_list args)
{
char *pos, *cur_lang, **lang;
TNC_UInt32 len;
va_list args;
VA_ARGS_VGET(args, lang);
if (!this->lang_len)
{
@ -676,11 +667,7 @@ static bool language_enumerator_enumerate(language_enumerator_t *this, ...)
}
cur_lang[len] = '\0';
va_start(args, this);
lang = va_arg(args, char**);
*lang = cur_lang;
va_end(args);
return TRUE;
}
@ -689,10 +676,13 @@ METHOD(imv_agent_t, create_language_enumerator, enumerator_t*,
{
language_enumerator_t *e;
/* Create a language enumerator instance */
e = malloc_thing(language_enumerator_t);
e->public.enumerate = (void*)language_enumerator_enumerate;
e->public.destroy = (void*)language_enumerator_destroy;
INIT(e,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _language_enumerator_enumerate,
.destroy = (void*)free,
},
);
if (!this->get_attribute ||
!this->get_attribute(this->id, state->get_connection_id(state),

View File

@ -262,22 +262,29 @@ METHOD(ita_attr_settings_t, add, void,
this->list->insert_last(this->list, entry);
}
/**
* Enumerate name/value pairs
*/
static bool entry_filter(void *null, entry_t **entry, char **name,
void *i2, chunk_t *value)
CALLBACK(entry_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
*name = (*entry)->name;
*value = (*entry)->value;
return TRUE;
entry_t *entry;
chunk_t *value;
char **name;
VA_ARGS_VGET(args, name, value);
while (orig->enumerate(orig, &entry))
{
*name = entry->name;
*value = entry->value;
return TRUE;
}
return FALSE;
}
METHOD(ita_attr_settings_t, create_enumerator, enumerator_t*,
private_ita_attr_settings_t *this)
{
return enumerator_create_filter(this->list->create_enumerator(this->list),
(void*)entry_filter, NULL, NULL);
entry_filter, NULL, NULL);
}
/**

View File

@ -418,24 +418,24 @@ METHOD(imv_attestation_state_t, create_component, pts_component_t*,
}
}
/**
* Enumerate file measurement entries
*/
static bool entry_filter(void *null, func_comp_t **entry, uint8_t *flags,
void *i2, uint32_t *depth,
void *i3, pts_comp_func_name_t **comp_name)
CALLBACK(entry_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
pts_component_t *comp;
pts_comp_func_name_t *name;
func_comp_t *entry;
pts_comp_func_name_t **comp_name;
uint32_t *depth;
uint8_t *flags;
comp = (*entry)->comp;
name = (*entry)->name;
VA_ARGS_VGET(args, flags, depth, comp_name);
*flags = comp->get_evidence_flags(comp);
*depth = comp->get_depth(comp);
*comp_name = name;
return TRUE;
if (orig->enumerate(orig, &entry))
{
*flags = entry->comp->get_evidence_flags(entry->comp);
*depth = entry->comp->get_depth(entry->comp);
*comp_name = entry->name;
return TRUE;
}
return FALSE;
}
METHOD(imv_attestation_state_t, create_component_enumerator, enumerator_t*,
@ -443,7 +443,7 @@ METHOD(imv_attestation_state_t, create_component_enumerator, enumerator_t*,
{
return enumerator_create_filter(
this->components->create_enumerator(this->components),
(void*)entry_filter, NULL, NULL);
entry_filter, NULL, NULL);
}
METHOD(imv_attestation_state_t, get_component, pts_component_t*,

View File

@ -94,22 +94,29 @@ METHOD(pts_file_meas_t, add, void,
this->list->insert_last(this->list, entry);
}
/**
* Enumerate file measurement entries
*/
static bool entry_filter(void *null, entry_t **entry, char **filename,
void *i2, chunk_t *measurement)
CALLBACK(entry_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
*filename = (*entry)->filename;
*measurement = (*entry)->measurement;
return TRUE;
entry_t *entry;
chunk_t *measurement;
char **filename;
VA_ARGS_VGET(args, filename, measurement);
if (orig->enumerate(orig, &entry))
{
*filename = entry->filename;
*measurement = entry->measurement;
return TRUE;
}
return FALSE;
}
METHOD(pts_file_meas_t, create_enumerator, enumerator_t*,
private_pts_file_meas_t *this)
{
return enumerator_create_filter(this->list->create_enumerator(this->list),
(void*)entry_filter, NULL, NULL);
entry_filter, NULL, NULL);
}
METHOD(pts_file_meas_t, check, bool,

View File

@ -111,17 +111,12 @@ typedef struct {
private_pts_pcr_t *pcrs;
} pcr_enumerator_t;
/**
* Implementation of enumerator.enumerate
*/
static bool pcr_enumerator_enumerate(pcr_enumerator_t *this, ...)
METHOD(enumerator_t, pcr_enumerator_enumerate, bool,
pcr_enumerator_t *this, va_list args)
{
uint32_t *pcr, i, f;
va_list args;
uint32_t i, f, *pcr;
va_start(args, this);
pcr = va_arg(args, uint32_t*);
va_end(args);
VA_ARGS_VGET(args, pcr);
while (this->pcr <= this->pcrs->pcr_max)
{
@ -148,7 +143,8 @@ METHOD(pts_pcr_t, create_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)pcr_enumerator_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _pcr_enumerator_enumerate,
.destroy = (void*)free,
},
.pcrs = this,

View File

@ -115,18 +115,24 @@ struct entry_t {
pts_comp_func_name_t *name;
};
/**
* Enumerate functional component entries
*/
static bool entry_filter(void *null, entry_t **entry, uint8_t *flags,
void *i2, uint32_t *depth, void *i3,
pts_comp_func_name_t **name)
CALLBACK(entry_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
*flags = (*entry)->flags;
*depth = (*entry)->depth;
*name = (*entry)->name;
entry_t *entry;
pts_comp_func_name_t **name;
uint32_t *depth;
uint8_t *flags;
return TRUE;
VA_ARGS_VGET(args, flags, depth, name);
if (orig->enumerate(orig, &entry))
{
*flags = entry->flags;
*depth = entry->depth;
*name = entry->name;
return TRUE;
}
return FALSE;
}
/**
@ -318,7 +324,7 @@ METHOD(tcg_pts_attr_req_func_comp_evid_t, create_enumerator, enumerator_t*,
private_tcg_pts_attr_req_func_comp_evid_t *this)
{
return enumerator_create_filter(this->list->create_enumerator(this->list),
(void*)entry_filter, NULL, NULL);
entry_filter, NULL, NULL);
}
/**

View File

@ -224,42 +224,60 @@ static void flush_entries(private_ipsec_sa_mgr_t *this)
enumerator->destroy(enumerator);
}
/*
* Different match functions to find SAs in the linked list
*/
static bool match_entry_by_ptr(ipsec_sa_entry_t *item, ipsec_sa_entry_t *entry)
CALLBACK(match_entry_by_sa_ptr, bool,
ipsec_sa_entry_t *item, va_list args)
{
return item == entry;
}
ipsec_sa_t *sa;
static bool match_entry_by_sa_ptr(ipsec_sa_entry_t *item, ipsec_sa_t *sa)
{
VA_ARGS_VGET(args, sa);
return item->sa == sa;
}
static bool match_entry_by_spi_inbound(ipsec_sa_entry_t *item, uint32_t *spi,
bool *inbound)
CALLBACK(match_entry_by_spi_inbound, bool,
ipsec_sa_entry_t *item, va_list args)
{
return item->sa->get_spi(item->sa) == *spi &&
item->sa->is_inbound(item->sa) == *inbound;
uint32_t spi;
int inbound;
VA_ARGS_VGET(args, spi, inbound);
return item->sa->get_spi(item->sa) == spi &&
item->sa->is_inbound(item->sa) == inbound;
}
static bool match_entry_by_spi_src_dst(ipsec_sa_entry_t *item, uint32_t *spi,
static bool match_entry_by_spi_src_dst(ipsec_sa_entry_t *item, uint32_t spi,
host_t *src, host_t *dst)
{
return item->sa->match_by_spi_src_dst(item->sa, *spi, src, dst);
return item->sa->match_by_spi_src_dst(item->sa, spi, src, dst);
}
static bool match_entry_by_reqid_inbound(ipsec_sa_entry_t *item,
uint32_t *reqid, bool *inbound)
CALLBACK(match_entry_by_spi_src_dst_cb, bool,
ipsec_sa_entry_t *item, va_list args)
{
return item->sa->match_by_reqid(item->sa, *reqid, *inbound);
host_t *src, *dst;
uint32_t spi;
VA_ARGS_VGET(args, spi, src, dst);
return match_entry_by_spi_src_dst(item, spi, src, dst);
}
static bool match_entry_by_spi_dst(ipsec_sa_entry_t *item, uint32_t *spi,
host_t *dst)
CALLBACK(match_entry_by_reqid_inbound, bool,
ipsec_sa_entry_t *item, va_list args)
{
return item->sa->match_by_spi_dst(item->sa, *spi, dst);
uint32_t reqid;
int inbound;
VA_ARGS_VGET(args, reqid, inbound);
return item->sa->match_by_reqid(item->sa, reqid, inbound);
}
CALLBACK(match_entry_by_spi_dst, bool,
ipsec_sa_entry_t *item, va_list args)
{
host_t *dst;
uint32_t spi;
VA_ARGS_VGET(args, spi, dst);
return item->sa->match_by_spi_dst(item->sa, spi, dst);
}
/**
@ -296,8 +314,7 @@ static job_requeue_t sa_expired(ipsec_sa_expired_t *expired)
private_ipsec_sa_mgr_t *this = expired->manager;
this->mutex->lock(this->mutex);
if (this->sas->find_first(this->sas, (void*)match_entry_by_ptr,
NULL, expired->entry) == SUCCESS)
if (this->sas->find_first(this->sas, NULL, (void**)&expired->entry))
{
uint32_t hard_offset;
@ -383,8 +400,8 @@ static bool allocate_spi(private_ipsec_sa_mgr_t *this, uint32_t spi)
uint32_t *spi_alloc;
if (this->allocated_spis->get(this->allocated_spis, &spi) ||
this->sas->find_first(this->sas, (void*)match_entry_by_spi_inbound,
NULL, &spi, TRUE) == SUCCESS)
this->sas->find_first(this->sas, match_entry_by_spi_inbound,
NULL, spi, TRUE))
{
return FALSE;
}
@ -484,8 +501,8 @@ METHOD(ipsec_sa_mgr_t, add_sa, status_t,
free(spi_alloc);
}
if (this->sas->find_first(this->sas, (void*)match_entry_by_spi_src_dst,
NULL, &spi, src, dst) == SUCCESS)
if (this->sas->find_first(this->sas, match_entry_by_spi_src_dst_cb, NULL,
spi, src, dst))
{
this->mutex->unlock(this->mutex);
DBG1(DBG_ESP, "failed to install SAD entry: already installed");
@ -519,8 +536,8 @@ METHOD(ipsec_sa_mgr_t, update_sa, status_t,
}
this->mutex->lock(this->mutex);
if (this->sas->find_first(this->sas, (void*)match_entry_by_spi_src_dst,
(void**)&entry, &spi, src, dst) == SUCCESS &&
if (this->sas->find_first(this->sas, match_entry_by_spi_src_dst_cb,
(void**)&entry, spi, src, dst) &&
wait_for_entry(this, entry))
{
entry->sa->set_source(entry->sa, new_src);
@ -547,8 +564,8 @@ METHOD(ipsec_sa_mgr_t, query_sa, status_t,
ipsec_sa_entry_t *entry = NULL;
this->mutex->lock(this->mutex);
if (this->sas->find_first(this->sas, (void*)match_entry_by_spi_src_dst,
(void**)&entry, &spi, src, dst) == SUCCESS &&
if (this->sas->find_first(this->sas, match_entry_by_spi_src_dst_cb,
(void**)&entry, spi, src, dst) &&
wait_for_entry(this, entry))
{
entry->sa->get_usestats(entry->sa, bytes, packets, time);
@ -572,7 +589,7 @@ METHOD(ipsec_sa_mgr_t, del_sa, status_t,
enumerator = this->sas->create_enumerator(this->sas);
while (enumerator->enumerate(enumerator, (void**)&current))
{
if (match_entry_by_spi_src_dst(current, &spi, src, dst))
if (match_entry_by_spi_src_dst(current, spi, src, dst))
{
if (wait_remove_entry(this, current))
{
@ -602,8 +619,8 @@ METHOD(ipsec_sa_mgr_t, checkout_by_reqid, ipsec_sa_t*,
ipsec_sa_t *sa = NULL;
this->mutex->lock(this->mutex);
if (this->sas->find_first(this->sas, (void*)match_entry_by_reqid_inbound,
(void**)&entry, &reqid, &inbound) == SUCCESS &&
if (this->sas->find_first(this->sas, match_entry_by_reqid_inbound,
(void**)&entry, reqid, inbound) &&
wait_for_entry(this, entry))
{
sa = entry->sa;
@ -619,8 +636,8 @@ METHOD(ipsec_sa_mgr_t, checkout_by_spi, ipsec_sa_t*,
ipsec_sa_t *sa = NULL;
this->mutex->lock(this->mutex);
if (this->sas->find_first(this->sas, (void*)match_entry_by_spi_dst,
(void**)&entry, &spi, dst) == SUCCESS &&
if (this->sas->find_first(this->sas, match_entry_by_spi_dst,
(void**)&entry, spi, dst) &&
wait_for_entry(this, entry))
{
sa = entry->sa;
@ -635,8 +652,8 @@ METHOD(ipsec_sa_mgr_t, checkin, void,
ipsec_sa_entry_t *entry;
this->mutex->lock(this->mutex);
if (this->sas->find_first(this->sas, (void*)match_entry_by_sa_ptr,
(void**)&entry, sa) == SUCCESS)
if (this->sas->find_first(this->sas, match_entry_by_sa_ptr,
(void**)&entry, sa))
{
if (entry->locked)
{

View File

@ -59,8 +59,11 @@ typedef struct {
} mech_enumerator_t;
METHOD(enumerator_t, mech_enumerate, bool,
mech_enumerator_t *this, char **name)
mech_enumerator_t *this, va_list args)
{
char **name;
VA_ARGS_VGET(args, name);
while (this->i < countof(mechs))
{
if (mechs[this->i].server == this->server)
@ -83,7 +86,8 @@ enumerator_t* sasl_mechanism_create_enumerator(bool server)
INIT(enumerator,
.public = {
.enumerate = (void*)_mech_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _mech_enumerate,
.destroy = (void*)free,
},
.server = server,

View File

@ -244,8 +244,12 @@ typedef struct {
} attribute_enumerator_t;
METHOD(enumerator_t, attribute_enumerate, bool,
attribute_enumerator_t *this, int *type, chunk_t *data)
attribute_enumerator_t *this, va_list args)
{
chunk_t *data;
int *type;
VA_ARGS_VGET(args, type, data);
if (this->left == 0)
{
return FALSE;
@ -275,7 +279,8 @@ METHOD(radius_message_t, create_enumerator, enumerator_t*,
}
INIT(e,
.public = {
.enumerate = (void*)_attribute_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _attribute_enumerate,
.destroy = (void*)free,
},
.next = (rattr_t*)this->msg->attributes,
@ -299,12 +304,14 @@ typedef struct {
} vendor_enumerator_t;
METHOD(enumerator_t, vendor_enumerate, bool,
vendor_enumerator_t *this, int *vendor, int *type, chunk_t *data)
vendor_enumerator_t *this, va_list args)
{
chunk_t inner_data;
int inner_type;
chunk_t inner_data, *data;
int inner_type, *vendor, *type;
uint8_t type8, len;
VA_ARGS_VGET(args, vendor, type, data);
while (TRUE)
{
if (this->reader)
@ -354,7 +361,8 @@ METHOD(radius_message_t, create_vendor_enumerator, enumerator_t*,
INIT(e,
.public = {
.enumerate = (void*)_vendor_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _vendor_enumerate,
.destroy = _vendor_destroy,
},
.inner = create_enumerator(this),

View File

@ -222,17 +222,22 @@ METHOD(simaka_message_t, get_type, eap_type_t,
return this->hdr->type;
}
/**
* convert attr_t to type and data enumeration
*/
static bool attr_enum_filter(void *null, attr_t **in, simaka_attribute_t *type,
void *dummy, chunk_t *data)
CALLBACK(attr_enum_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
attr_t *attr = *in;
attr_t *attr;
simaka_attribute_t *type;
chunk_t *data;
*type = attr->type;
*data = chunk_create(attr->data, attr->len);
return TRUE;
VA_ARGS_VGET(args, type, data);
if (orig->enumerate(orig, &attr))
{
*type = attr->type;
*data = chunk_create(attr->data, attr->len);
return TRUE;
}
return FALSE;
}
METHOD(simaka_message_t, create_attribute_enumerator, enumerator_t*,
@ -240,7 +245,7 @@ METHOD(simaka_message_t, create_attribute_enumerator, enumerator_t*,
{
return enumerator_create_filter(
this->attributes->create_enumerator(this->attributes),
(void*)attr_enum_filter, NULL, NULL);
attr_enum_filter, NULL, NULL);
}
METHOD(simaka_message_t, add_attribute, void,

View File

@ -214,9 +214,11 @@ typedef struct {
} array_enumerator_t;
METHOD(enumerator_t, enumerate, bool,
array_enumerator_t *this, void **out)
array_enumerator_t *this, va_list args)
{
void *pos;
void *pos, **out;
VA_ARGS_VGET(args, out);
if (this->idx >= this->array->count)
{
@ -250,7 +252,8 @@ enumerator_t* array_create_enumerator(array_t *array)
INIT(enumerator,
.public = {
.enumerate = (void*)_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate,
.destroy = (void*)free,
},
.array = array,

View File

@ -1,7 +1,7 @@
/*
* Copyright (C) 2008-2013 Tobias Brunner
* Copyright (C) 2008-2017 Tobias Brunner
* Copyright (C) 2007 Martin Willi
* Hochschule fuer Technik Rapperswil
* HSR Hochschule fuer Technik Rapperswil
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@ -31,22 +31,43 @@
#include <utils/debug.h>
/**
* Implementation of enumerator_create_empty().enumerate
/*
* Described in header.
*/
static bool enumerate_empty(enumerator_t *enumerator, ...)
bool enumerator_enumerate_default(enumerator_t *enumerator, ...)
{
va_list args;
bool result;
if (!enumerator->venumerate)
{
DBG1(DBG_LIB, "!!! ENUMERATE DEFAULT: venumerate() missing !!!");
return FALSE;
}
va_start(args, enumerator);
result = enumerator->venumerate(enumerator, args);
va_end(args);
return result;
}
METHOD(enumerator_t, enumerate_empty, bool,
enumerator_t *enumerator, va_list args)
{
return FALSE;
}
/**
* See header
/*
* Described in header
*/
enumerator_t* enumerator_create_empty()
{
enumerator_t *this = malloc_thing(enumerator_t);
this->enumerate = enumerate_empty;
this->destroy = (void*)free;
enumerator_t *this;
INIT(this,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_empty,
.destroy = (void*)free,
);
return this;
}
@ -64,32 +85,31 @@ typedef struct {
char *full_end;
} dir_enum_t;
/**
* Implementation of enumerator_create_directory().destroy
*/
static void destroy_dir_enum(dir_enum_t *this)
METHOD(enumerator_t, destroy_dir_enum, void,
dir_enum_t *this)
{
closedir(this->dir);
free(this);
}
/**
* Implementation of enumerator_create_directory().enumerate
*/
static bool enumerate_dir_enum(dir_enum_t *this, char **relative,
char **absolute, struct stat *st)
METHOD(enumerator_t, enumerate_dir_enum, bool,
dir_enum_t *this, va_list args)
{
struct dirent *entry = readdir(this->dir);
struct stat *st;
size_t remaining;
char **relative, **absolute;
int len;
VA_ARGS_VGET(args, relative, absolute, st);
if (!entry)
{
return FALSE;
}
if (streq(entry->d_name, ".") || streq(entry->d_name, ".."))
{
return enumerate_dir_enum(this, relative, absolute, st);
return this->public.enumerate(&this->public, relative, absolute, st);
}
if (relative)
{
@ -122,15 +142,21 @@ static bool enumerate_dir_enum(dir_enum_t *this, char **relative,
return TRUE;
}
/**
* See header
/*
* Described in header
*/
enumerator_t* enumerator_create_directory(const char *path)
{
dir_enum_t *this;
int len;
dir_enum_t *this = malloc_thing(dir_enum_t);
this->public.enumerate = (void*)enumerate_dir_enum;
this->public.destroy = (void*)destroy_dir_enum;
INIT(this,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_dir_enum,
.destroy = _destroy_dir_enum,
},
);
if (*path == '\0')
{
@ -152,9 +178,10 @@ enumerator_t* enumerator_create_directory(const char *path)
this->full_end = &this->full[len];
this->dir = opendir(path);
if (this->dir == NULL)
if (!this->dir)
{
DBG1(DBG_LIB, "opening directory '%s' failed: %s", path, strerror(errno));
DBG1(DBG_LIB, "opening directory '%s' failed: %s", path,
strerror(errno));
free(this);
return NULL;
}
@ -177,21 +204,21 @@ typedef struct {
char full[PATH_MAX];
} glob_enum_t;
/**
* Implementation of enumerator_create_glob().destroy
*/
static void destroy_glob_enum(glob_enum_t *this)
METHOD(enumerator_t, destroy_glob_enum, void,
glob_enum_t *this)
{
globfree(&this->glob);
free(this);
}
/**
* Implementation of enumerator_create_glob().enumerate
*/
static bool enumerate_glob_enum(glob_enum_t *this, char **file, struct stat *st)
METHOD(enumerator_t, enumerate_glob_enum, bool,
glob_enum_t *this, va_list args)
{
struct stat *st;
char *match;
char **file;
VA_ARGS_VGET(args, file, st);
if (this->pos >= this->glob.gl_pathc)
{
@ -202,20 +229,17 @@ static bool enumerate_glob_enum(glob_enum_t *this, char **file, struct stat *st)
{
*file = match;
}
if (st)
if (st && stat(match, st))
{
if (stat(match, st))
{
DBG1(DBG_LIB, "stat() on '%s' failed: %s", match,
strerror(errno));
return FALSE;
}
DBG1(DBG_LIB, "stat() on '%s' failed: %s", match,
strerror(errno));
return FALSE;
}
return TRUE;
}
/**
* See header
/*
* Described in header
*/
enumerator_t* enumerator_create_glob(const char *pattern)
{
@ -229,8 +253,9 @@ enumerator_t* enumerator_create_glob(const char *pattern)
INIT(this,
.public = {
.enumerate = (void*)enumerate_glob_enum,
.destroy = (void*)destroy_glob_enum,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_glob_enum,
.destroy = _destroy_glob_enum,
},
);
@ -272,24 +297,22 @@ typedef struct {
const char *trim;
} token_enum_t;
/**
* Implementation of enumerator_create_token().destroy
*/
static void destroy_token_enum(token_enum_t *this)
METHOD(enumerator_t, destroy_token_enum, void,
token_enum_t *this)
{
free(this->string);
free(this);
}
/**
* Implementation of enumerator_create_token().enumerate
*/
static bool enumerate_token_enum(token_enum_t *this, char **token)
METHOD(enumerator_t, enumerate_token_enum, bool,
token_enum_t *this, va_list args)
{
const char *sep, *trim;
char *pos = NULL, *tmp;
char *pos = NULL, *tmp, **token;
bool last = FALSE;
VA_ARGS_VGET(args, token);
/* trim leading characters/separators */
while (*this->pos)
{
@ -390,52 +413,48 @@ static bool enumerate_token_enum(token_enum_t *this, char **token)
return FALSE;
}
/**
* See header
/*
* Described in header
*/
enumerator_t* enumerator_create_token(const char *string, const char *sep,
const char *trim)
{
token_enum_t *enumerator = malloc_thing(token_enum_t);
token_enum_t *this;
enumerator->public.enumerate = (void*)enumerate_token_enum;
enumerator->public.destroy = (void*)destroy_token_enum;
enumerator->string = strdup(string);
enumerator->pos = enumerator->string;
enumerator->sep = sep;
enumerator->trim = trim;
INIT(this,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_token_enum,
.destroy = _destroy_token_enum,
},
.string = strdup(string),
.sep = sep,
.trim = trim,
);
this->pos = this->string;
return &enumerator->public;
return &this->public;
}
/**
* enumerator for nested enumerations
* Enumerator for nested enumerations
*/
typedef struct {
/* implements enumerator_t */
enumerator_t public;
/* outer enumerator */
enumerator_t *outer;
/* inner enumerator */
enumerator_t *inner;
/* constructor for inner enumerator */
enumerator_t *(*create_inner)(void *outer, void *data);
/* data to pass to constructor above */
void *data;
/* destructor for data */
void (*destroy_data)(void *data);
void (*destructor)(void *data);
} nested_enumerator_t;
/**
* Implementation of enumerator_create_nested().enumerate()
*/
static bool enumerate_nested(nested_enumerator_t *this, void *v1, void *v2,
void *v3, void *v4, void *v5)
METHOD(enumerator_t, enumerate_nested, bool,
nested_enumerator_t *this, va_list args)
{
while (TRUE)
{
while (this->inner == NULL)
while (!this->inner)
{
void *outer;
@ -444,8 +463,13 @@ static bool enumerate_nested(nested_enumerator_t *this, void *v1, void *v2,
return FALSE;
}
this->inner = this->create_inner(outer, this->data);
if (this->inner && !this->inner->venumerate)
{
DBG1(DBG_LIB, "!!! ENUMERATE NESTED: venumerate() missing !!!");
return FALSE;
}
}
if (this->inner->enumerate(this->inner, v1, v2, v3, v4, v5))
if (this->inner->venumerate(this->inner, args))
{
return TRUE;
}
@ -454,103 +478,100 @@ static bool enumerate_nested(nested_enumerator_t *this, void *v1, void *v2,
}
}
/**
* Implementation of enumerator_create_nested().destroy()
**/
static void destroy_nested(nested_enumerator_t *this)
METHOD(enumerator_t, destroy_nested, void,
nested_enumerator_t *this)
{
if (this->destroy_data)
if (this->destructor)
{
this->destroy_data(this->data);
this->destructor(this->data);
}
DESTROY_IF(this->inner);
this->outer->destroy(this->outer);
free(this);
}
/**
* See header
/*
* Described in header
*/
enumerator_t *enumerator_create_nested(enumerator_t *outer,
enumerator_t *(inner_constructor)(void *outer, void *data),
void *data, void (*destroy_data)(void *data))
void *data, void (*destructor)(void *data))
{
nested_enumerator_t *enumerator = malloc_thing(nested_enumerator_t);
nested_enumerator_t *this;
enumerator->public.enumerate = (void*)enumerate_nested;
enumerator->public.destroy = (void*)destroy_nested;
enumerator->outer = outer;
enumerator->inner = NULL;
enumerator->create_inner = (void*)inner_constructor;
enumerator->data = data;
enumerator->destroy_data = destroy_data;
return &enumerator->public;
INIT(this,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_nested,
.destroy = _destroy_nested,
},
.outer = outer,
.create_inner = inner_constructor,
.data = data,
.destructor = destructor,
);
return &this->public;
}
/**
* enumerator for filtered enumerator
* Enumerator for filtered enumerator
*/
typedef struct {
enumerator_t public;
enumerator_t *unfiltered;
enumerator_t *orig;
void *data;
bool (*filter)(void *data, ...);
bool (*filter)(void*,enumerator_t*,va_list);
void (*destructor)(void *data);
} filter_enumerator_t;
/**
* Implementation of enumerator_create_filter().destroy
*/
static void destroy_filter(filter_enumerator_t *this)
METHOD(enumerator_t, destroy_filter, void,
filter_enumerator_t *this)
{
if (this->destructor)
{
this->destructor(this->data);
}
this->unfiltered->destroy(this->unfiltered);
this->orig->destroy(this->orig);
free(this);
}
/**
* Implementation of enumerator_create_filter().enumerate
*/
static bool enumerate_filter(filter_enumerator_t *this, void *o1, void *o2,
void *o3, void *o4, void *o5)
METHOD(enumerator_t, enumerate_filter, bool,
filter_enumerator_t *this, va_list args)
{
void *i1, *i2, *i3, *i4, *i5;
bool result = FALSE;
while (this->unfiltered->enumerate(this->unfiltered, &i1, &i2, &i3, &i4, &i5))
if (this->filter(this->data, this->orig, args))
{
if (this->filter(this->data, &i1, o1, &i2, o2, &i3, o3, &i4, o4, &i5, o5))
{
return TRUE;
}
result = TRUE;
}
return FALSE;
return result;
}
/**
* see header
/*
* Described in header
*/
enumerator_t *enumerator_create_filter(enumerator_t *unfiltered,
bool (*filter)(void *data, ...),
void *data, void (*destructor)(void *data))
enumerator_t *enumerator_create_filter(enumerator_t *orig,
bool (*filter)(void *data, enumerator_t *orig, va_list args),
void *data, void (*destructor)(void *data))
{
filter_enumerator_t *this = malloc_thing(filter_enumerator_t);
this->public.enumerate = (void*)enumerate_filter;
this->public.destroy = (void*)destroy_filter;
this->unfiltered = unfiltered;
this->filter = filter;
this->data = data;
this->destructor = destructor;
filter_enumerator_t *this;
INIT(this,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_filter,
.destroy = _destroy_filter,
},
.orig = orig,
.filter = filter,
.data = data,
.destructor = destructor,
);
return &this->public;
}
/**
* enumerator for cleaner enumerator
* Enumerator for cleaner enumerator
*/
typedef struct {
enumerator_t public;
@ -559,44 +580,48 @@ typedef struct {
void *data;
} cleaner_enumerator_t;
/**
* Implementation of enumerator_create_cleanup().destroy
*/
static void destroy_cleaner(cleaner_enumerator_t *this)
METHOD(enumerator_t, destroy_cleaner, void,
cleaner_enumerator_t *this)
{
this->cleanup(this->data);
this->wrapped->destroy(this->wrapped);
free(this);
}
/**
* Implementation of enumerator_create_cleaner().enumerate
*/
static bool enumerate_cleaner(cleaner_enumerator_t *this, void *v1, void *v2,
void *v3, void *v4, void *v5)
METHOD(enumerator_t, enumerate_cleaner, bool,
cleaner_enumerator_t *this, va_list args)
{
return this->wrapped->enumerate(this->wrapped, v1, v2, v3, v4, v5);
if (!this->wrapped->venumerate)
{
DBG1(DBG_LIB, "!!! CLEANER ENUMERATOR: venumerate() missing !!!");
return FALSE;
}
return this->wrapped->venumerate(this->wrapped, args);
}
/**
* see header
/*
* Described in header
*/
enumerator_t *enumerator_create_cleaner(enumerator_t *wrapped,
void (*cleanup)(void *data), void *data)
{
cleaner_enumerator_t *this = malloc_thing(cleaner_enumerator_t);
this->public.enumerate = (void*)enumerate_cleaner;
this->public.destroy = (void*)destroy_cleaner;
this->wrapped = wrapped;
this->cleanup = cleanup;
this->data = data;
cleaner_enumerator_t *this;
INIT(this,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_cleaner,
.destroy = _destroy_cleaner,
},
.wrapped = wrapped,
.cleanup = cleanup,
.data = data,
);
return &this->public;
}
/**
* enumerator for single enumerator
* Enumerator for single enumerator
*/
typedef struct {
enumerator_t public;
@ -605,10 +630,8 @@ typedef struct {
bool done;
} single_enumerator_t;
/**
* Implementation of enumerator_create_single().destroy
*/
static void destroy_single(single_enumerator_t *this)
METHOD(enumerator_t, destroy_single, void,
single_enumerator_t *this)
{
if (this->cleanup)
{
@ -617,11 +640,12 @@ static void destroy_single(single_enumerator_t *this)
free(this);
}
/**
* Implementation of enumerator_create_single().enumerate
*/
static bool enumerate_single(single_enumerator_t *this, void **item)
METHOD(enumerator_t, enumerate_single, bool,
single_enumerator_t *this, va_list args)
{
void **item;
VA_ARGS_VGET(args, item);
if (this->done)
{
return FALSE;
@ -631,19 +655,21 @@ static bool enumerate_single(single_enumerator_t *this, void **item)
return TRUE;
}
/**
* see header
/*
* Described in header
*/
enumerator_t *enumerator_create_single(void *item, void (*cleanup)(void *item))
{
single_enumerator_t *this = malloc_thing(single_enumerator_t);
this->public.enumerate = (void*)enumerate_single;
this->public.destroy = (void*)destroy_single;
this->item = item;
this->cleanup = cleanup;
this->done = FALSE;
single_enumerator_t *this;
INIT(this,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate_single,
.destroy = _destroy_single,
},
.item = item,
.cleanup = cleanup,
);
return &this->public;
}

View File

@ -1,7 +1,7 @@
/*
* Copyright (C) 2013 Tobias Brunner
* Copyright (C) 2013-2017 Tobias Brunner
* Copyright (C) 2007 Martin Willi
* Hochschule fuer Technik Rapperswil
* HSR Hochschule fuer Technik Rapperswil
*
* This program is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License as published by the
@ -34,8 +34,11 @@ struct enumerator_t {
/**
* Enumerate collection.
*
* The enumerate function takes a variable argument list containing
* pointers where the enumerated values get written.
* The enumerate() method takes a variable number of pointer arguments
* where the enumerated values get written to.
*
* @note Just assigning the generic enumerator_enumerate_default() function
* that calls the enumerator's venumerate() method is usually enough.
*
* @param ... variable list of enumerated items, implementation dependent
* @return TRUE if pointers returned
@ -43,11 +46,33 @@ struct enumerator_t {
bool (*enumerate)(enumerator_t *this, ...);
/**
* Destroy a enumerator instance.
* Enumerate collection.
*
* The venumerate() method takes a variable argument list containing
* pointers where the enumerated values get written to.
*
* To simplify the implementation the VA_ARGS_VGET() macro may be used.
*
* @param args variable list of enumerated items, implementation dependent
* @return TRUE if pointers returned
*/
bool (*venumerate)(enumerator_t *this, va_list args);
/**
* Destroy an enumerator_t instance.
*/
void (*destroy)(enumerator_t *this);
};
/**
* Generic implementation of enumerator_t::enumerate() that simply calls
* the enumerator's venumerate() method.
*
* @param enumerator the enumerator
* @param ... arguments passed to enumerate()
*/
bool enumerator_enumerate_default(enumerator_t *enumerator, ...);
/**
* Create an enumerator which enumerates over nothing
*
@ -147,38 +172,41 @@ enumerator_t* enumerator_create_token(const char *string, const char *sep,
/**
* Creates an enumerator which enumerates over enumerated enumerators :-).
*
* The variable argument list of enumeration values is limit to 5.
* The outer enumerator is expected to return objects that, when passed to
* inner_contructor, will create a new enumerator that will be enumerated until
* completion (to this enumerator will the pointer arguments that are passed to
* this enumerator be forwarded) at which point a new element from the outer
* enumerator is requested to create a new inner enumerator.
*
* @param outer outer enumerator
* @param inner_constructor constructor to inner enumerator
* @param inner_constructor constructor to create inner enumerator
* @param data data to pass to each inner_constructor call
* @param destroy_data destructor to pass to data
* @param destructor destructor function to clean up data after use
* @return the nested enumerator
*/
enumerator_t *enumerator_create_nested(enumerator_t *outer,
enumerator_t *(*inner_constructor)(void *outer, void *data),
void *data, void (*destroy_data)(void *data));
void *data, void (*destructor)(void *data));
/**
* Creates an enumerator which filters output of another enumerator.
* Creates an enumerator which filters/maps output of another enumerator.
*
* The filter function receives the user supplied "data" followed by a
* unfiltered enumeration item, followed by an output pointer where to write
* the filtered data. Then the next input/output pair follows.
* It returns TRUE to deliver the
* values to the caller of enumerate(), FALSE to filter this enumeration.
* The filter function receives the user supplied "data" followed by the
* original enumerator, followed by the arguments passed to the outer
* enumerator. It returns TRUE to deliver the values assigned to these
* arguments to the caller of enumerate() and FALSE to end the enumeration.
* Filtering items is simple as the filter function may just skip enumerated
* items from the original enumerator.
*
* The variable argument list of enumeration values is limit to 5.
*
* @param unfiltered unfiltered enumerator to wrap, gets destroyed
* @param orig original enumerator to wrap, gets destroyed
* @param filter filter function
* @param data user data to supply to filter
* @param destructor destructor function to clean up data after use
* @return the filtered enumerator
*/
enumerator_t *enumerator_create_filter(enumerator_t *unfiltered,
bool (*filter)(void *data, ...),
void *data, void (*destructor)(void *data));
enumerator_t *enumerator_create_filter(enumerator_t *orig,
bool (*filter)(void *data, enumerator_t *orig, va_list args),
void *data, void (*destructor)(void *data));
/**
* Create an enumerator wrapper which does a cleanup on destroy.

View File

@ -379,8 +379,13 @@ METHOD(hashtable_t, get_count, u_int,
}
METHOD(enumerator_t, enumerate, bool,
private_enumerator_t *this, const void **key, void **value)
private_enumerator_t *this, va_list args)
{
const void **key;
void **value;
VA_ARGS_VGET(args, key, value);
while (this->count && this->row < this->table->capacity)
{
this->prev = this->current;
@ -417,7 +422,8 @@ METHOD(hashtable_t, create_enumerator, enumerator_t*,
INIT(enumerator,
.enumerator = {
.enumerate = (void*)_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate,
.destroy = (void*)free,
},
.table = this,

View File

@ -47,6 +47,17 @@ struct element_t {
element_t *next;
};
/*
* Described in header
*/
bool linked_list_match_str(void *item, va_list args)
{
char *a = item, *b;
VA_ARGS_VGET(args, b);
return streq(a, b);
}
/**
* Creates an empty linked list object.
*/
@ -119,8 +130,12 @@ struct private_enumerator_t {
};
METHOD(enumerator_t, enumerate, bool,
private_enumerator_t *this, void **item)
private_enumerator_t *this, va_list args)
{
void **item;
VA_ARGS_VGET(args, item);
if (this->finished)
{
return FALSE;
@ -152,7 +167,8 @@ METHOD(linked_list_t, create_enumerator, enumerator_t*,
INIT(enumerator,
.enumerator = {
.enumerate = (void*)_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate,
.destroy = (void*)free,
},
.list = this,
@ -366,52 +382,68 @@ METHOD(linked_list_t, remove_at, void,
}
}
METHOD(linked_list_t, find_first, status_t,
private_linked_list_t *this, linked_list_match_t match,
void **item, void *d1, void *d2, void *d3, void *d4, void *d5)
METHOD(linked_list_t, find_first, bool,
private_linked_list_t *this, linked_list_match_t match, void **item, ...)
{
element_t *current = this->first;
va_list args;
bool matched = FALSE;
if (!match && !item)
{
return FALSE;
}
while (current)
{
if ((match && match(current->value, d1, d2, d3, d4, d5)) ||
(!match && item && current->value == *item))
if (match)
{
va_start(args, item);
matched = match(current->value, args);
va_end(args);
}
else
{
matched = current->value == *item;
}
if (matched)
{
if (item != NULL)
{
*item = current->value;
}
return SUCCESS;
return TRUE;
}
current = current->next;
}
return NOT_FOUND;
return FALSE;
}
METHOD(linked_list_t, invoke_offset, void,
private_linked_list_t *this, size_t offset,
void *d1, void *d2, void *d3, void *d4, void *d5)
private_linked_list_t *this, size_t offset)
{
element_t *current = this->first;
linked_list_invoke_t *method;
void (**method)(void*);
while (current)
{
method = current->value + offset;
(*method)(current->value, d1, d2, d3, d4, d5);
(*method)(current->value);
current = current->next;
}
}
METHOD(linked_list_t, invoke_function, void,
private_linked_list_t *this, linked_list_invoke_t fn,
void *d1, void *d2, void *d3, void *d4, void *d5)
private_linked_list_t *this, linked_list_invoke_t fn, ...)
{
element_t *current = this->first;
va_list args;
while (current)
{
fn(current->value, d1, d2, d3, d4, d5);
va_start(args, fn);
fn(current->value, args);
va_end(args);
current = current->next;
}
}
@ -542,7 +574,7 @@ linked_list_t *linked_list_create()
.reset_enumerator = (void*)_reset_enumerator,
.get_first = _get_first,
.get_last = _get_last,
.find_first = (void*)_find_first,
.find_first = _find_first,
.insert_first = _insert_first,
.insert_last = _insert_last,
.insert_before = (void*)_insert_before,
@ -550,8 +582,8 @@ linked_list_t *linked_list_create()
.remove_last = _remove_last,
.remove = _remove_,
.remove_at = (void*)_remove_at,
.invoke_offset = (void*)_invoke_offset,
.invoke_function = (void*)_invoke_function,
.invoke_offset = _invoke_offset,
.invoke_function = _invoke_function,
.clone_offset = _clone_offset,
.equals_offset = _equals_offset,
.equals_function = _equals_function,

View File

@ -1,5 +1,5 @@
/*
* Copyright (C) 2007-2015 Tobias Brunner
* Copyright (C) 2007-2017 Tobias Brunner
* Copyright (C) 2005-2008 Martin Willi
* Copyright (C) 2005 Jan Hutter
* Hochschule fuer Technik Rapperswil
@ -28,23 +28,30 @@ typedef struct linked_list_t linked_list_t;
#include <collections/enumerator.h>
/**
* Method to match elements in a linked list (used in find_* functions)
* Function to match elements in a linked list
*
* @param item current list item
* @param ... user supplied data (only pointers, at most 5)
* @return
* - TRUE, if the item matched
* - FALSE, otherwise
* @param args user supplied data
* @return TRUE, if the item matched, FALSE otherwise
*/
typedef bool (*linked_list_match_t)(void *item, ...);
typedef bool (*linked_list_match_t)(void *item, va_list args);
/**
* Method to be invoked on elements in a linked list (used in invoke_* functions)
* Helper function to match a string in a linked list of strings
*
* @param item list item (char*)
* @param args user supplied data (char*)
* @return
*/
bool linked_list_match_str(void *item, va_list args);
/**
* Function to be invoked on elements in a linked list
*
* @param item current list item
* @param ... user supplied data (only pointers, at most 5)
* @param args user supplied data
*/
typedef void (*linked_list_invoke_t)(void *item, ...);
typedef void (*linked_list_invoke_t)(void *item, va_list args);
/**
* Class implementing a double linked list.
@ -167,21 +174,20 @@ struct linked_list_t {
*
* The first object passed to the match function is the current list item,
* followed by the user supplied data.
* If the supplied function returns TRUE this function returns SUCCESS, and
* the current object is returned in the third parameter, otherwise,
* If the supplied function returns TRUE so does this function, and the
* current object is returned in the third parameter (if given), otherwise,
* the next item is checked.
*
* If match is NULL, *item and the current object are compared.
*
* @warning Only use pointers as user supplied data.
*
* @param match comparison function to call on each object, or NULL
* @param item the list item, if found
* @param ... user data to supply to match function (limited to 5 arguments)
* @return SUCCESS if found, NOT_FOUND otherwise
* @param item the list item, if found, or NULL
* @param ... user data to supply to match function
* @return TRUE if found, FALSE otherwise (or if neither match,
* nor item is supplied)
*/
status_t (*find_first) (linked_list_t *this, linked_list_match_t match,
void **item, ...);
bool (*find_first)(linked_list_t *this, linked_list_match_t match,
void **item, ...);
/**
* Invoke a method on all of the contained objects.
@ -192,22 +198,18 @@ struct linked_list_t {
* which can be evalutated at compile time using the offsetof
* macro, e.g.: list->invoke(list, offsetof(object_t, method));
*
* @warning Only use pointers as user supplied data.
*
* @param offset offset of the method to invoke on objects
* @param ... user data to supply to called function (limited to 5 arguments)
*/
void (*invoke_offset) (linked_list_t *this, size_t offset, ...);
void (*invoke_offset)(linked_list_t *this, size_t offset);
/**
* Invoke a function on all of the contained objects.
*
* @warning Only use pointers as user supplied data.
*
* @param function offset of the method to invoke on objects
* @param ... user data to supply to called function (limited to 5 arguments)
* @param function function to call for each object
* @param ... user data to supply to called function
*/
void (*invoke_function) (linked_list_t *this, linked_list_invoke_t function, ...);
void (*invoke_function)(linked_list_t *this, linked_list_invoke_t function,
...);
/**
* Clones a list and its objects using the objects' clone method.

View File

@ -146,12 +146,14 @@ typedef struct {
bool enumerated[AUTH_RULE_MAX];
} entry_enumerator_t;
/**
* enumerate function for item_enumerator_t
*/
static bool enumerate(entry_enumerator_t *this, auth_rule_t *type, void **value)
METHOD(enumerator_t, enumerate, bool,
entry_enumerator_t *this, va_list args)
{
auth_rule_t *type;
entry_t *entry;
void **value;
VA_ARGS_VGET(args, type, value);
while (this->inner->enumerate(this->inner, &entry))
{
@ -174,10 +176,8 @@ static bool enumerate(entry_enumerator_t *this, auth_rule_t *type, void **value)
return FALSE;
}
/**
* destroy function for item_enumerator_t
*/
static void entry_enumerator_destroy(entry_enumerator_t *this)
METHOD(enumerator_t, entry_enumerator_destroy, void,
entry_enumerator_t *this)
{
this->inner->destroy(this->inner);
free(this);
@ -190,8 +190,9 @@ METHOD(auth_cfg_t, create_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)enumerate,
.destroy = (void*)entry_enumerator_destroy,
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate,
.destroy = _entry_enumerator_destroy,
},
.inner = array_create_enumerator(this->entries),
);

View File

@ -163,17 +163,23 @@ METHOD(credential_factory_t, create, void*,
return construct;
}
/**
* Filter function for builder enumerator
*/
static bool builder_filter(void *null, entry_t **entry, credential_type_t *type,
void *dummy1, int *subtype)
CALLBACK(builder_filter, bool,
void *null, enumerator_t *orig, va_list args)
{
if ((*entry)->final)
entry_t *entry;
credential_type_t *type;
int *subtype;
VA_ARGS_VGET(args, type, subtype);
while (orig->enumerate(orig, &entry))
{
*type = (*entry)->type;
*subtype = (*entry)->subtype;
return TRUE;
if (entry->final)
{
*type = entry->type;
*subtype = entry->subtype;
return TRUE;
}
}
return FALSE;
}
@ -184,7 +190,7 @@ METHOD(credential_factory_t, create_builder_enumerator, enumerator_t*,
this->lock->read_lock(this->lock);
return enumerator_create_filter(
this->constructors->create_enumerator(this->constructors),
(void*)builder_filter, this->lock, (void*)this->lock->unlock);
builder_filter, this->lock, (void*)this->lock->unlock);
}
METHOD(credential_factory_t, destroy, void,

View File

@ -155,8 +155,12 @@ METHOD(credential_manager_t, call_hook, void,
}
METHOD(enumerator_t, sets_enumerate, bool,
sets_enumerator_t *this, credential_set_t **set)
sets_enumerator_t *this, va_list args)
{
credential_set_t **set;
VA_ARGS_VGET(args, set);
if (this->exclusive)
{
if (this->exclusive->enumerate(this->exclusive, set))
@ -202,7 +206,8 @@ static enumerator_t *create_sets_enumerator(private_credential_manager_t *this)
INIT(enumerator,
.public = {
.enumerate = (void*)_sets_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _sets_enumerate,
.destroy = _sets_destroy,
},
);
@ -807,11 +812,12 @@ static bool verify_trust_chain(private_credential_manager_t *this,
return trusted;
}
/**
* List find match function for certificates
*/
static bool cert_equals(certificate_t *a, certificate_t *b)
CALLBACK(cert_equals, bool,
certificate_t *a, va_list args)
{
certificate_t *b;
VA_ARGS_VGET(args, b);
return a->equals(a, b);
}
@ -840,9 +846,12 @@ typedef struct {
} trusted_enumerator_t;
METHOD(enumerator_t, trusted_enumerate, bool,
trusted_enumerator_t *this, certificate_t **cert, auth_cfg_t **auth)
trusted_enumerator_t *this, va_list args)
{
certificate_t *current;
certificate_t *current, **cert;
auth_cfg_t **auth;
VA_ARGS_VGET(args, cert, auth);
DESTROY_IF(this->auth);
this->auth = auth_cfg_create();
@ -888,8 +897,7 @@ METHOD(enumerator_t, trusted_enumerate, bool,
continue;
}
if (this->failed->find_first(this->failed, (void*)cert_equals,
NULL, current) == SUCCESS)
if (this->failed->find_first(this->failed, cert_equals, NULL, current))
{ /* check each candidate only once */
continue;
}
@ -931,7 +939,8 @@ METHOD(credential_manager_t, create_trusted_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_trusted_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _trusted_enumerate,
.destroy = _trusted_destroy,
},
.this = this,
@ -960,9 +969,13 @@ typedef struct {
} public_enumerator_t;
METHOD(enumerator_t, public_enumerate, bool,
public_enumerator_t *this, public_key_t **key, auth_cfg_t **auth)
public_enumerator_t *this, va_list args)
{
certificate_t *cert;
public_key_t **key;
auth_cfg_t **auth;
VA_ARGS_VGET(args, key, auth);
while (this->inner->enumerate(this->inner, &cert, auth))
{
@ -1001,7 +1014,8 @@ METHOD(credential_manager_t, create_public_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_public_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _public_enumerate,
.destroy = _public_destroy,
},
.inner = create_trusted_enumerator(this, type, id, online),

View File

@ -272,8 +272,12 @@ typedef struct {
} private_enumerator_t;
METHOD(enumerator_t, signature_schemes_enumerate, bool,
private_enumerator_t *this, signature_scheme_t *scheme)
private_enumerator_t *this, va_list args)
{
signature_scheme_t *scheme;
VA_ARGS_VGET(args, scheme);
while (++this->index < countof(scheme_map))
{
if (this->type == scheme_map[this->index].type &&
@ -296,7 +300,8 @@ enumerator_t *signature_schemes_for_key(key_type_t type, int size)
INIT(this,
.public = {
.enumerate = (void*)_signature_schemes_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _signature_schemes_enumerate,
.destroy = (void*)free,
},
.index = -1,

View File

@ -112,15 +112,15 @@ static bool fetch_cert(wrapper_enumerator_t *enumerator,
return TRUE;
}
/**
* enumerate function for wrapper_enumerator_t
*/
static bool enumerate(wrapper_enumerator_t *this, certificate_t **cert)
METHOD(enumerator_t, enumerate, bool,
wrapper_enumerator_t *this, va_list args)
{
auth_rule_t rule;
certificate_t *current;
certificate_t *current, **cert;
public_key_t *public;
VA_ARGS_VGET(args, cert);
while (this->inner->enumerate(this->inner, &rule, &current))
{
if (rule == AUTH_HELPER_IM_HASH_URL ||
@ -164,10 +164,8 @@ static bool enumerate(wrapper_enumerator_t *this, certificate_t **cert)
return FALSE;
}
/**
* destroy function for wrapper_enumerator_t
*/
static void wrapper_enumerator_destroy(wrapper_enumerator_t *this)
METHOD(enumerator_t, wrapper_enumerator_destroy, void,
wrapper_enumerator_t *this)
{
this->inner->destroy(this->inner);
free(this);
@ -183,14 +181,18 @@ METHOD(credential_set_t, create_enumerator, enumerator_t*,
{
return NULL;
}
enumerator = malloc_thing(wrapper_enumerator_t);
enumerator->auth = this->auth;
enumerator->cert = cert;
enumerator->key = key;
enumerator->id = id;
enumerator->inner = this->auth->create_enumerator(this->auth);
enumerator->public.enumerate = (void*)enumerate;
enumerator->public.destroy = (void*)wrapper_enumerator_destroy;
INIT(enumerator,
.public = {
.enumerate = enumerator_enumerate_default,
.venumerate = _enumerate,
.destroy = _wrapper_enumerator_destroy,
},
.auth = this->auth,
.cert = cert,
.key = key,
.id = id,
.inner = this->auth->create_enumerator(this->auth),
);
return &enumerator->public;
}

View File

@ -60,9 +60,12 @@ typedef struct {
} shared_enumerator_t;
METHOD(enumerator_t, shared_enumerate, bool,
shared_enumerator_t *this, shared_key_t **out,
id_match_t *match_me, id_match_t *match_other)
shared_enumerator_t *this, va_list args)
{
shared_key_t **out;
id_match_t *match_me, *match_other;
VA_ARGS_VGET(args, out, match_me, match_other);
DESTROY_IF(this->current);
this->current = this->this->cb.shared(this->this->data, this->type,
this->me, this->other, match_me, match_other);
@ -89,7 +92,8 @@ METHOD(credential_set_t, create_shared_enumerator, enumerator_t*,
INIT(enumerator,
.public = {
.enumerate = (void*)_shared_enumerate,
.enumerate = enumerator_enumerate_default,
.venumerate = _shared_enumerate,
.destroy = _shared_destroy,
},
.this = this,

Some files were not shown because too many files have changed in this diff Show More