Skip to content

Commit

Permalink
Merge pull request #2498 from swoole/timer-iterator
Browse files Browse the repository at this point in the history
Timer Enhancement
  • Loading branch information
matyhtf authored Apr 15, 2019
2 parents 823ccb2 + 843f34d commit 3116923
Show file tree
Hide file tree
Showing 20 changed files with 450 additions and 223 deletions.
1 change: 1 addition & 0 deletions include/hashmap.h
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,7 @@ int swHashMap_del(swHashMap *hmap, char *key, uint16_t key_len);
int swHashMap_del_int(swHashMap *hmap, uint64_t key);
int swHashMap_move(swHashMap *hmap, char *old_key, uint16_t old_key_len, char *new_key, uint16_t new_key_len);
int swHashMap_move_int(swHashMap *hmap, uint64_t old_key, uint64_t new_key);
void swHashMap_rewind(swHashMap* hmap);
void* swHashMap_each(swHashMap* hmap, char **key);
void* swHashMap_each_int(swHashMap* hmap, uint64_t *key);
#define swHashMap_each_reset(hmap) (hmap->iterator = NULL)
Expand Down
12 changes: 6 additions & 6 deletions include/swoole.h
Original file line number Diff line number Diff line change
Expand Up @@ -2165,15 +2165,15 @@ enum swTimer_type

struct _swTimer_node
{
swHeap_node *heap_node;
void *data;
swTimerCallback callback;
long id;
enum swTimer_type type;
int64_t exec_msec;
int64_t interval;
uint64_t round;
long id;
enum swTimer_type type;
uint8_t remove;
uint8_t removed;
swTimerCallback callback;
void *data;
swHeap_node *heap_node;
};

struct _swTimer
Expand Down
88 changes: 59 additions & 29 deletions php_swoole.h
Original file line number Diff line number Diff line change
Expand Up @@ -254,6 +254,7 @@ typedef struct

#define SW_LONG_CONNECTION_KEY_LEN 64

extern zend_class_entry *swoole_timer_ce;
extern zend_class_entry *swoole_socket_coro_ce;
extern zend_class_entry *swoole_client_ce;
extern zend_class_entry *swoole_server_ce;
Expand Down Expand Up @@ -312,13 +313,6 @@ PHP_FUNCTION(swoole_client_select);
PHP_FUNCTION(swoole_async_set);
PHP_FUNCTION(swoole_async_dns_lookup_coro);
//---------------------------------------------------------
// timer
//---------------------------------------------------------
PHP_FUNCTION(swoole_timer_after);
PHP_FUNCTION(swoole_timer_tick);
PHP_FUNCTION(swoole_timer_exists);
PHP_FUNCTION(swoole_timer_clear);
//---------------------------------------------------------
// error
//---------------------------------------------------------
#define SW_STRERROR_SYSTEM 0
Expand All @@ -338,35 +332,40 @@ PHP_FUNCTION(swoole_fast_serialize);
PHP_FUNCTION(swoole_unserialize);
#endif

void swoole_server_init(int module_number);
void swoole_server_port_init(int module_number);
void swoole_async_coro_init(int module_number);
/** <Sort by dependency> **/
// base
void swoole_atomic_init(int module_number);
void swoole_buffer_init(int module_number);
void swoole_lock_init(int module_number);
void swoole_process_init(int module_number);
void swoole_process_pool_init(int module_number);
void swoole_table_init(int module_number);
void swoole_timer_init(int module_number);
// coroutine
void swoole_async_coro_init(int module_number);
void swoole_coroutine_util_init(int module_number);
void swoole_channel_coro_init(int module_number);
void swoole_runtime_init(int module_number);
void swoole_lock_init(int module_number);
void swoole_atomic_init(int module_number);
void swoole_client_init(int module_number);
// client
void swoole_socket_coro_init(int module_number);
void swoole_client_init(int module_number);
void swoole_client_coro_init(int module_number);
void swoole_redis_coro_init(int module_number);
#ifdef SW_USE_POSTGRESQL
void swoole_postgresql_coro_init (int module_number);
#endif
void swoole_mysql_coro_init(int module_number);
void swoole_http_client_coro_init(int module_number);
void swoole_coroutine_util_init(int module_number);
void swoole_coroutine_util_destroy();
void swoole_redis_server_init(int module_number);
void swoole_process_init(int module_number);
void swoole_process_pool_init(int module_number);
void swoole_http_server_init(int module_number);
void swoole_mysql_coro_init(int module_number);
void swoole_redis_coro_init(int module_number);
#ifdef SW_USE_HTTP2
void swoole_http2_client_coro_init(int module_number);
#endif
void swoole_websocket_init(int module_number);
void swoole_buffer_init(int module_number);
void swoole_channel_init(int module_number);
void swoole_channel_coro_init(int module_number);
#ifdef SW_USE_POSTGRESQL
void swoole_postgresql_coro_init(int module_number);
#endif
// server
void swoole_server_init(int module_number);
void swoole_server_port_init(int module_number);
void swoole_http_server_init(int module_number);
void swoole_websocket_server_init(int module_number);
void swoole_redis_server_init(int module_number);
// others
#ifdef SW_USE_FAST_SERIALIZE
void swoole_serialize_init(int module_number);
#endif
Expand All @@ -388,12 +387,19 @@ static sw_inline void php_swoole_check_reactor()
}
}

// shutdown
void php_swoole_register_shutdown_function(const char *function);
void php_swoole_register_shutdown_function_prepend(const char *function);

// event
void php_swoole_event_init();
void php_swoole_event_wait();
void php_swoole_event_exit();
void php_swoole_clear_all_timer();

// timer
enum swBool_type php_swoole_timer_clear(swTimer_node *tnode);
enum swBool_type php_swoole_timer_clear_all();

void php_swoole_register_callback(swServer *serv);
void php_swoole_trace_check(void *arg);
void php_swoole_client_free(zval *zobject, swClient *cli);
Expand Down Expand Up @@ -788,6 +794,30 @@ static sw_inline int add_assoc_ulong_safe(zval *arg, const char *key, zend_ulong
} \
} while (0)

#define SW_FUNCTION_ALIAS(origin_function_table, origin, alias_function_table, alias) \
sw_zend_register_function_alias(origin_function_table, ZEND_STRL(origin), alias_function_table, ZEND_STRL(alias))

static sw_inline int sw_zend_register_function_alias
(
HashTable *origin_function_table, const char *origin, size_t origin_length,
HashTable *alias_function_table, const char *alias, size_t alias_length
)
{
zend_string *lowercase_origin = zend_string_alloc(origin_length, 0);
zend_str_tolower_copy(ZSTR_VAL(lowercase_origin), origin, origin_length);
zend_function *origin_function = (zend_function *) zend_hash_find_ptr(origin_function_table, lowercase_origin);
zend_string_release(lowercase_origin);
if (UNEXPECTED(!origin_function))
{
return FAILURE;
}
SW_ASSERT(origin_function->common.type == ZEND_INTERNAL_FUNCTION);
char _alias[alias_length + 1];
strncpy(_alias, alias, alias_length)[alias_length] = '\0';
zend_function_entry zfe[] = {{_alias, origin_function->internal_function.handler, ((zend_internal_arg_info *) origin_function->common.arg_info) - 1, origin_function->common.num_args, 0 }, PHP_FE_END};
return zend_register_functions(origin_function->common.scope, zfe, alias_function_table, origin_function->common.type);
}

static sw_inline int sw_zend_register_class_alias(const char *name, size_t name_len, zend_class_entry *ce)
{
zend_string *_name;
Expand Down
29 changes: 9 additions & 20 deletions src/core/hashmap.c
Original file line number Diff line number Diff line change
Expand Up @@ -66,28 +66,11 @@ static sw_inline int swHashMap_node_add(swHashMap_node *root, swHashMap_node *ad

static sw_inline swHashMap_node* swHashMap_node_each(swHashMap* hmap)
{
swHashMap_node *iterator = hmap->iterator;
swHashMap_node *tmp;

if (hmap->root->hh.tbl->num_items == 0)
{
return NULL;
}
if (iterator == NULL)
if (hmap->iterator)
{
iterator = hmap->root;
}
tmp = iterator->hh.next;
if (tmp)
{
hmap->iterator = tmp;
return tmp;
}
else
{
hmap->iterator = NULL;
return NULL;
return hmap->iterator = hmap->iterator->hh.next;
}
return NULL;
}

swHashMap* swHashMap_new(uint32_t bucket_num, swHashMap_dtor dtor)
Expand All @@ -108,6 +91,7 @@ swHashMap* swHashMap_new(uint32_t bucket_num, swHashMap_dtor dtor)

bzero(hmap, sizeof(swHashMap));
hmap->root = root;
hmap->iterator = root;

bzero(root, sizeof(swHashMap_node));

Expand Down Expand Up @@ -331,6 +315,11 @@ int swHashMap_move_int(swHashMap *hmap, uint64_t old_key, uint64_t new_key)
return SW_OK;
}

void swHashMap_rewind(swHashMap* hmap)
{
hmap->iterator = hmap->root;
}

void* swHashMap_each(swHashMap* hmap, char **key)
{
swHashMap_node *node = swHashMap_node_each(hmap);
Expand Down
10 changes: 5 additions & 5 deletions src/network/timer.c
Original file line number Diff line number Diff line change
Expand Up @@ -151,7 +151,7 @@ swTimer_node* swTimer_add(swTimer *timer, long _msec, int interval, void *data,
tnode->type = SW_TIMER_TYPE_KERNEL;
tnode->exec_msec = now_msec + _msec;
tnode->interval = interval ? _msec : 0;
tnode->remove = 0;
tnode->removed = 0;
tnode->callback = callback;
tnode->round = timer->round;

Expand Down Expand Up @@ -186,13 +186,13 @@ swTimer_node* swTimer_add(swTimer *timer, long _msec, int interval, void *data,

enum swBool_type swTimer_del_ex(swTimer *timer, swTimer_node *tnode, swTimerDtor dtor)
{
if (unlikely(!tnode || tnode->remove))
if (unlikely(!tnode || tnode->removed))
{
return SW_FALSE;
}
if (unlikely(SwooleG.timer._current_id > 0 && tnode->id == SwooleG.timer._current_id))
{
tnode->remove = 1;
tnode->removed = 1;
swTraceLog(SW_TRACE_TIMER, "set-remove: id=%ld, exec_msec=%" PRId64 ", round=%" PRIu64 ", exist=%u", tnode->id, tnode->exec_msec, tnode->round, timer->num);
return SW_TRUE;
}
Expand Down Expand Up @@ -241,15 +241,15 @@ int swTimer_select(swTimer *timer)
}

timer->_current_id = tnode->id;
if (!tnode->remove)
if (!tnode->removed)
{
swTraceLog(SW_TRACE_TIMER, "id=%ld, exec_msec=%" PRId64 ", round=%" PRIu64 ", exist=%u", tnode->id, tnode->exec_msec, tnode->round, timer->num - 1);
tnode->callback(timer, tnode);
}
timer->_current_id = -1;

//persistent timer
if (tnode->interval > 0 && !tnode->remove)
if (tnode->interval > 0 && !tnode->removed)
{
while (tnode->exec_msec <= now_msec)
{
Expand Down
2 changes: 2 additions & 0 deletions src/server/manager.cc
Original file line number Diff line number Diff line change
Expand Up @@ -631,6 +631,7 @@ void swManager_kill_user_worker(swServer *serv)
int __stat_loc;

//kill user process
swHashMap_rewind(serv->user_worker_map);
while (1)
{
user_worker = (swWorker *) swHashMap_each_int(serv->user_worker_map, &key);
Expand All @@ -643,6 +644,7 @@ void swManager_kill_user_worker(swServer *serv)
}

//wait user process
swHashMap_rewind(serv->user_worker_map);
while (1)
{
user_worker = (swWorker *) swHashMap_each_int(serv->user_worker_map, &key);
Expand Down
2 changes: 1 addition & 1 deletion src/wrapper/timer.cc
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,7 @@ uchar swoole_timer_exists(long timer_id)
return false;
}
auto tnode = swTimer_get(&SwooleG.timer, timer_id);
return (tnode && !tnode->remove);
return (tnode && !tnode->removed);
}

uchar swoole_timer_clear(long timer_id)
Expand Down
Loading

0 comments on commit 3116923

Please sign in to comment.