forked from Mirrors/freeswitch
add log and event object recycling to reduce malloc per sec in high call load
git-svn-id: http://svn.freeswitch.org/svn/freeswitch/trunk@5768 d0543943-73ff-0310-b7d9-9358b9ac24b2
This commit is contained in:
parent
8f963f4aea
commit
1a316ca6db
@ -50,11 +50,11 @@ SWITCH_BEGIN_EXTERN_C
|
||||
/*! The complete log message */
|
||||
char *data;
|
||||
/*! The file where the message originated */
|
||||
char *file;
|
||||
char file[80];
|
||||
/*! The line number where the message originated */
|
||||
uint32_t line;
|
||||
/*! The function where the message originated */
|
||||
char *func;
|
||||
char func[80];
|
||||
/*! The log level of the message */
|
||||
switch_log_level_t level;
|
||||
/*! The time when the log line was sent */
|
||||
|
@ -50,7 +50,8 @@ static int POOL_COUNT_MAX = SWITCH_CORE_QUEUE_LEN;
|
||||
static switch_hash_t *CUSTOM_HASH = NULL;
|
||||
static int THREAD_RUNNING = 0;
|
||||
static int EVENT_QUEUE_HAVEMORE = 0;
|
||||
|
||||
static switch_queue_t *EVENT_RECYCLE_QUEUE = NULL;
|
||||
static switch_queue_t *EVENT_HEADER_RECYCLE_QUEUE = NULL;
|
||||
#if 0
|
||||
static void *locked_alloc(switch_size_t len)
|
||||
{
|
||||
@ -97,7 +98,7 @@ static char *my_dup (const char *s)
|
||||
#define DUP(str) my_dup(str)
|
||||
#endif
|
||||
#ifndef FREE
|
||||
#define FREE(ptr) if (ptr) free(ptr)
|
||||
#define FREE(ptr) switch_safe_free(ptr)
|
||||
#endif
|
||||
|
||||
/* make sure this is synced with the switch_event_types_t enum in switch_types.h
|
||||
@ -365,6 +366,7 @@ SWITCH_DECLARE(switch_status_t) switch_event_reserve_subclass_detailed(char *own
|
||||
SWITCH_DECLARE(switch_status_t) switch_event_shutdown(void)
|
||||
{
|
||||
int x = 0, last = 0;
|
||||
void *pop;
|
||||
|
||||
if (THREAD_RUNNING > 0) {
|
||||
THREAD_RUNNING = -1;
|
||||
@ -403,6 +405,17 @@ SWITCH_DECLARE(switch_status_t) switch_event_shutdown(void)
|
||||
}
|
||||
|
||||
switch_core_hash_destroy(&CUSTOM_HASH);
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CONSOLE, "Returning %d recycled event node(s) and %d recycled event header node(s)\n",
|
||||
switch_queue_size(EVENT_RECYCLE_QUEUE),switch_queue_size(EVENT_HEADER_RECYCLE_QUEUE));
|
||||
|
||||
|
||||
while (switch_queue_trypop(EVENT_HEADER_RECYCLE_QUEUE, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||
free(pop);
|
||||
}
|
||||
while (switch_queue_trypop(EVENT_RECYCLE_QUEUE, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||
free(pop);
|
||||
}
|
||||
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
@ -433,6 +446,10 @@ SWITCH_DECLARE(switch_status_t) switch_event_init(switch_memory_pool_t *pool)
|
||||
switch_queue_create(&EVENT_QUEUE[0], POOL_COUNT_MAX + 10, THRUNTIME_POOL);
|
||||
switch_queue_create(&EVENT_QUEUE[1], POOL_COUNT_MAX + 10, THRUNTIME_POOL);
|
||||
switch_queue_create(&EVENT_QUEUE[2], POOL_COUNT_MAX + 10, THRUNTIME_POOL);
|
||||
switch_queue_create(&EVENT_RECYCLE_QUEUE, SWITCH_CORE_QUEUE_LEN, THRUNTIME_POOL);
|
||||
switch_queue_create(&EVENT_HEADER_RECYCLE_QUEUE, SWITCH_CORE_QUEUE_LEN, THRUNTIME_POOL);
|
||||
|
||||
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_INFO, "Activate Eventing Engine.\n");
|
||||
switch_mutex_init(&BLOCK, SWITCH_MUTEX_NESTED, RUNTIME_POOL);
|
||||
@ -453,14 +470,19 @@ SWITCH_DECLARE(switch_status_t) switch_event_init(switch_memory_pool_t *pool)
|
||||
|
||||
SWITCH_DECLARE(switch_status_t) switch_event_create_subclass(switch_event_t **event, switch_event_types_t event_id, const char *subclass_name)
|
||||
{
|
||||
|
||||
void *pop;
|
||||
|
||||
if (event_id != SWITCH_EVENT_CUSTOM && subclass_name) {
|
||||
return SWITCH_STATUS_GENERR;
|
||||
}
|
||||
|
||||
if ((*event = ALLOC(sizeof(switch_event_t))) == 0) {
|
||||
return SWITCH_STATUS_MEMERR;
|
||||
|
||||
if (switch_queue_trypop(EVENT_RECYCLE_QUEUE, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||
*event = (switch_event_t *) pop;
|
||||
} else {
|
||||
*event = ALLOC(sizeof(switch_event_t));
|
||||
assert(*event);
|
||||
}
|
||||
|
||||
memset(*event, 0, sizeof(switch_event_t));
|
||||
|
||||
(*event)->event_id = event_id;
|
||||
@ -519,7 +541,7 @@ SWITCH_DECLARE(switch_status_t) switch_event_del_header(switch_event_t *event, c
|
||||
}
|
||||
FREE(hp->name);
|
||||
FREE(hp->value);
|
||||
FREE(hp);
|
||||
switch_queue_push(EVENT_HEADER_RECYCLE_QUEUE, hp);
|
||||
status = SWITCH_STATUS_SUCCESS;
|
||||
break;
|
||||
}
|
||||
@ -543,9 +565,13 @@ SWITCH_DECLARE(switch_status_t) switch_event_add_header(switch_event_t *event, s
|
||||
return SWITCH_STATUS_MEMERR;
|
||||
} else {
|
||||
switch_event_header_t *header, *hp;
|
||||
void *pop;
|
||||
|
||||
if ((header = ALLOC(sizeof(*header))) == 0) {
|
||||
return SWITCH_STATUS_MEMERR;
|
||||
if (switch_queue_trypop(EVENT_HEADER_RECYCLE_QUEUE, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||
header = (switch_event_header_t *) pop;
|
||||
} else {
|
||||
header = ALLOC(sizeof(*header));
|
||||
assert(header);
|
||||
}
|
||||
|
||||
memset(header, 0, sizeof(*header));
|
||||
@ -603,10 +629,10 @@ SWITCH_DECLARE(void) switch_event_destroy(switch_event_t **event)
|
||||
hp = hp->next;
|
||||
FREE(this->name);
|
||||
FREE(this->value);
|
||||
FREE(this);
|
||||
switch_queue_push(EVENT_HEADER_RECYCLE_QUEUE, this);
|
||||
}
|
||||
FREE(ep->body);
|
||||
FREE(ep);
|
||||
switch_queue_push(EVENT_RECYCLE_QUEUE, ep);
|
||||
}
|
||||
*event = NULL;
|
||||
}
|
||||
|
@ -57,6 +57,7 @@ static switch_memory_pool_t *LOG_POOL = NULL;
|
||||
static switch_log_binding_t *BINDINGS = NULL;
|
||||
static switch_mutex_t *BINDLOCK = NULL;
|
||||
static switch_queue_t *LOG_QUEUE = NULL;
|
||||
static switch_queue_t *LOG_RECYCLE_QUEUE = NULL;
|
||||
static int8_t THREAD_RUNNING = 0;
|
||||
static uint8_t MAX_LEVEL = 0;
|
||||
|
||||
@ -133,7 +134,6 @@ static void *SWITCH_THREAD_FUNC log_thread(switch_thread_t * thread, void *obj)
|
||||
}
|
||||
|
||||
node = (switch_log_node_t *) pop;
|
||||
|
||||
switch_mutex_lock(BINDLOCK);
|
||||
for (binding = BINDINGS; binding; binding = binding->next) {
|
||||
if (binding->level >= node->level) {
|
||||
@ -141,21 +141,9 @@ static void *SWITCH_THREAD_FUNC log_thread(switch_thread_t * thread, void *obj)
|
||||
}
|
||||
}
|
||||
switch_mutex_unlock(BINDLOCK);
|
||||
if (node) {
|
||||
if (node->data) {
|
||||
free(node->data);
|
||||
}
|
||||
|
||||
if (node->file) {
|
||||
free(node->file);
|
||||
}
|
||||
|
||||
if (node->func) {
|
||||
free(node->func);
|
||||
}
|
||||
|
||||
free(node);
|
||||
}
|
||||
|
||||
switch_safe_free(node->data);
|
||||
switch_queue_push(LOG_RECYCLE_QUEUE, node);
|
||||
}
|
||||
|
||||
THREAD_RUNNING = 0;
|
||||
@ -177,6 +165,7 @@ SWITCH_DECLARE(void) switch_log_printf(switch_text_channel_t channel, const char
|
||||
switch_time_t now = switch_time_now();
|
||||
uint32_t len;
|
||||
const char *extra_fmt = "%s [%s] %s:%d %s()%c%s";
|
||||
|
||||
va_start(ap, fmt);
|
||||
|
||||
handle = switch_core_data_channel(channel);
|
||||
@ -225,27 +214,28 @@ SWITCH_DECLARE(void) switch_log_printf(switch_text_channel_t channel, const char
|
||||
free(data);
|
||||
} else if (level <= MAX_LEVEL) {
|
||||
switch_log_node_t *node;
|
||||
void *pop = NULL;
|
||||
|
||||
if ((node = malloc(sizeof(*node)))) {
|
||||
node->data = data;
|
||||
node->file = strdup(filep);
|
||||
node->func = strdup(funcp);
|
||||
node->line = line;
|
||||
node->level = level;
|
||||
node->content = content;
|
||||
node->timestamp = now;
|
||||
switch_queue_push(LOG_QUEUE, node);
|
||||
if (switch_queue_trypop(LOG_RECYCLE_QUEUE, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||
node = (switch_log_node_t *) pop;
|
||||
} else {
|
||||
free(data);
|
||||
node = malloc(sizeof(*node));
|
||||
assert(node);
|
||||
}
|
||||
|
||||
node->data = data;
|
||||
switch_set_string(node->file, filep);
|
||||
switch_set_string(node->func, funcp);
|
||||
node->line = line;
|
||||
node->level = level;
|
||||
node->content = content;
|
||||
node->timestamp = now;
|
||||
switch_queue_push(LOG_QUEUE, node);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (new_fmt) {
|
||||
free(new_fmt);
|
||||
}
|
||||
|
||||
switch_safe_free(new_fmt);
|
||||
fflush(handle);
|
||||
}
|
||||
|
||||
@ -264,6 +254,7 @@ SWITCH_DECLARE(switch_status_t) switch_log_init(switch_memory_pool_t *pool)
|
||||
|
||||
|
||||
switch_queue_create(&LOG_QUEUE, SWITCH_CORE_QUEUE_LEN, LOG_POOL);
|
||||
switch_queue_create(&LOG_RECYCLE_QUEUE, SWITCH_CORE_QUEUE_LEN, LOG_POOL);
|
||||
switch_mutex_init(&BINDLOCK, SWITCH_MUTEX_NESTED, LOG_POOL);
|
||||
switch_threadattr_stacksize_set(thd_attr, SWITCH_THREAD_STACKSIZE);
|
||||
switch_thread_create(&thread, thd_attr, log_thread, NULL, LOG_POOL);
|
||||
@ -276,11 +267,19 @@ SWITCH_DECLARE(switch_status_t) switch_log_init(switch_memory_pool_t *pool)
|
||||
|
||||
SWITCH_DECLARE(switch_status_t) switch_log_shutdown(void)
|
||||
{
|
||||
void *pop;
|
||||
|
||||
THREAD_RUNNING = -1;
|
||||
switch_queue_push(LOG_QUEUE, NULL);
|
||||
while (THREAD_RUNNING) {
|
||||
switch_yield(1000);
|
||||
}
|
||||
|
||||
switch_log_printf(SWITCH_CHANNEL_LOG, SWITCH_LOG_CONSOLE, "Returning %d recycled log node(s)\n", switch_queue_size(LOG_RECYCLE_QUEUE));
|
||||
while (switch_queue_trypop(LOG_RECYCLE_QUEUE, &pop) == SWITCH_STATUS_SUCCESS) {
|
||||
free(pop);
|
||||
}
|
||||
|
||||
return SWITCH_STATUS_SUCCESS;
|
||||
}
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user