Skip to content

Commit 120085e

Browse files
committed
add CallbackManager
1 parent 9dfc7f7 commit 120085e

File tree

10 files changed

+127
-118
lines changed

10 files changed

+127
-118
lines changed

config.m4

-1
Original file line numberDiff line numberDiff line change
@@ -470,7 +470,6 @@ if test "$PHP_SWOOLE" != "no"; then
470470
src/protocol/ssl.c \
471471
src/protocol/websocket.c \
472472
src/reactor/base.cc \
473-
src/reactor/defer_task.cc \
474473
src/reactor/epoll.c \
475474
src/reactor/kqueue.c \
476475
src/reactor/poll.c \

include/async.h

-1
Original file line numberDiff line numberDiff line change
@@ -77,7 +77,6 @@ typedef struct
7777

7878
extern swAsyncIO SwooleAIO;
7979

80-
void swAio_free(void);
8180
int swAio_dispatch(const swAio_event *request);
8281
swAio_event* swAio_dispatch2(const swAio_event *request);
8382
int swAio_cancel(int task_id);

include/swoole.h

+2-4
Original file line numberDiff line numberDiff line change
@@ -1664,7 +1664,7 @@ struct _swReactor
16641664
void (*free)(swReactor *);
16651665

16661666
void *defer_tasks;
1667-
void (*do_defer_tasks)(swReactor *);
1667+
void *destroy_callbacks;
16681668

16691669
swDefer_callback idle_task;
16701670
swDefer_callback future_task;
@@ -1891,6 +1891,7 @@ static sw_inline int swReactor_events(int fdtype)
18911891

18921892
int swReactor_create(swReactor *reactor, int max_event);
18931893
void swReactor_destory(swReactor *reactor);
1894+
void swReactor_add_destroy_callback(swReactor *reactor, swCallback cb, void *data);
18941895

18951896
static inline void swReactor_before_wait(swReactor *reactor)
18961897
{
@@ -1902,9 +1903,6 @@ static inline void swReactor_before_wait(swReactor *reactor)
19021903

19031904
int swReactor_empty(swReactor *reactor);
19041905

1905-
void swReactor_defer_task_create(swReactor *reactor);
1906-
void swReactor_defer_task_destroy(swReactor *reactor);
1907-
19081906
static sw_inline swConnection* swReactor_get(swReactor *reactor, int fd)
19091907
{
19101908
swConnection *socket = reactor->thread ? &reactor->socket_list[fd] : (swConnection*) swArray_alloc(reactor->socket_array, fd);

include/swoole_cxx.h

+43-2
Original file line numberDiff line numberDiff line change
@@ -2,12 +2,13 @@
22

33
#include "swoole.h"
44

5+
#include <list>
56
#include <memory>
67
#include <string>
78
#include <cstdio>
89

9-
namespace swoole
10-
{
10+
namespace swoole {
11+
//-------------------------------------------------------------------------------
1112
namespace cpp_string
1213
{
1314
template<typename ...Args>
@@ -30,4 +31,44 @@ inline std::string vformat(const char *format, va_list args)
3031
return std::string(buf.get(), buf.get() + size - 1); // We don't want the '\0' inside
3132
}
3233
}
34+
35+
struct Callback
36+
{
37+
swCallback callback;
38+
void *private_data;
39+
40+
Callback(swCallback cb, void *_private_data)
41+
42+
{
43+
callback = cb;
44+
private_data = _private_data;
45+
}
46+
};
47+
48+
class CallbackManager
49+
{
50+
public:
51+
inline void append(swCallback cb, void *private_data)
52+
{
53+
list_.push_back(new Callback(cb, private_data));
54+
}
55+
inline void prepend(swCallback cb, void *private_data)
56+
{
57+
list_.push_front(new Callback(cb, private_data));
58+
}
59+
inline void execute()
60+
{
61+
while (!list_.empty())
62+
{
63+
Callback *task = list_.front();
64+
list_.pop_front();
65+
task->callback(task->private_data);
66+
delete task;
67+
}
68+
}
69+
protected:
70+
std::list<Callback *> list_;
71+
};
72+
73+
//-------------------------------------------------------------------------------
3374
}

src/network/async_thread.cc

+5-1
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,8 @@ typedef swAio_event async_event;
3030

3131
swAsyncIO SwooleAIO;
3232

33+
static void swAio_free(void *private_data);
34+
3335
class async_event_queue
3436
{
3537
public:
@@ -317,6 +319,8 @@ static int swAio_init()
317319
SwooleAIO.max_thread_count = SwooleAIO.min_thread_count;
318320
}
319321

322+
swReactor_add_destroy_callback(SwooleG.main_reactor, swAio_free, nullptr);
323+
320324
pool = new async_thread_pool(SwooleAIO.min_thread_count, SwooleAIO.min_thread_count);
321325
pool->start();
322326
SwooleAIO.init = 1;
@@ -345,7 +349,7 @@ swAio_event* swAio_dispatch2(const swAio_event *request)
345349
return pool->dispatch(request);
346350
}
347351

348-
void swAio_free(void)
352+
static void swAio_free(void *private_data)
349353
{
350354
if (!SwooleAIO.init)
351355
{

src/reactor/base.cc

+65-13
Original file line numberDiff line numberDiff line change
@@ -15,9 +15,12 @@
1515
*/
1616

1717
#include "swoole.h"
18+
#include "swoole_cxx.h"
1819
#include "connection.h"
1920
#include "async.h"
2021

22+
using swoole::CallbackManager;
23+
2124
#ifdef SW_USE_MALLOC_TRIM
2225
#ifdef __APPLE__
2326
#include <sys/malloc.h>
@@ -26,9 +29,11 @@
2629
#endif
2730
#endif
2831

29-
static void swReactor_onTimeout(swReactor *reactor);
30-
static void swReactor_onFinish(swReactor *reactor);
31-
static void swReactor_onBegin(swReactor *reactor);
32+
static void reactor_timeout(swReactor *reactor);
33+
static void reactor_finish(swReactor *reactor);
34+
static void reactor_begin(swReactor *reactor);
35+
static void defer_task_do(swReactor *reactor);
36+
static void defer_task_add(swReactor *reactor, swCallback callback, void *data);
3237

3338
int swReactor_create(swReactor *reactor, int max_event)
3439
{
@@ -47,13 +52,15 @@ int swReactor_create(swReactor *reactor, int max_event)
4752

4853
reactor->running = 1;
4954

50-
reactor->onFinish = swReactor_onFinish;
51-
reactor->onTimeout = swReactor_onTimeout;
55+
reactor->onFinish = reactor_finish;
56+
reactor->onTimeout = reactor_timeout;
5257
reactor->is_empty = swReactor_empty;
5358

5459
reactor->write = swReactor_write;
5560
reactor->close = swReactor_close;
56-
swReactor_defer_task_create(reactor);
61+
62+
reactor->defer = defer_task_add;
63+
reactor->defer_tasks = nullptr;
5764

5865
reactor->socket_array = swArray_new(1024, sizeof(swConnection));
5966
if (!reactor->socket_array)
@@ -132,15 +139,18 @@ int swReactor_empty(swReactor *reactor)
132139
/**
133140
* execute when reactor timeout and reactor finish
134141
*/
135-
static void swReactor_onFinish(swReactor *reactor)
142+
static void reactor_finish(swReactor *reactor)
136143
{
137144
//check timer
138145
if (reactor->check_timer)
139146
{
140147
swTimer_select(&SwooleG.timer);
141148
}
142149
//defer tasks
143-
reactor->do_defer_tasks(reactor);
150+
if (reactor->defer_tasks)
151+
{
152+
defer_task_do(reactor);
153+
}
144154
//callback at the end
145155
if (reactor->idle_task.callback)
146156
{
@@ -167,9 +177,9 @@ static void swReactor_onFinish(swReactor *reactor)
167177
#endif
168178
}
169179

170-
static void swReactor_onTimeout(swReactor *reactor)
180+
static void reactor_timeout(swReactor *reactor)
171181
{
172-
swReactor_onFinish(reactor);
182+
reactor_finish(reactor);
173183

174184
if (reactor->disable_accept)
175185
{
@@ -180,10 +190,10 @@ static void swReactor_onTimeout(swReactor *reactor)
180190

181191
void swReactor_activate_future_task(swReactor *reactor)
182192
{
183-
reactor->onBegin = swReactor_onBegin;
193+
reactor->onBegin = reactor_begin;
184194
}
185195

186-
static void swReactor_onBegin(swReactor *reactor)
196+
static void reactor_begin(swReactor *reactor)
187197
{
188198
if (reactor->future_task.callback)
189199
{
@@ -397,8 +407,50 @@ int swReactor_wait_write_buffer(swReactor *reactor, int fd)
397407
return SW_OK;
398408
}
399409

410+
void swReactor_add_destroy_callback(swReactor *reactor, swCallback cb, void *data)
411+
{
412+
CallbackManager *cm = (CallbackManager *) reactor->destroy_callbacks;
413+
if (cm == nullptr)
414+
{
415+
cm = new CallbackManager;
416+
reactor->destroy_callbacks = cm;
417+
}
418+
cm->append(cb, data);
419+
}
420+
421+
void swReactor_defer_task_destroy(swReactor *reactor)
422+
{
423+
CallbackManager *tasks = (CallbackManager *) reactor->defer_tasks;
424+
delete tasks;
425+
}
426+
427+
static void defer_task_do(swReactor *reactor)
428+
{
429+
CallbackManager *cm = (CallbackManager *) reactor->defer_tasks;
430+
cm->execute();
431+
reactor->defer_tasks = nullptr;
432+
delete cm;
433+
}
434+
435+
static void defer_task_add(swReactor *reactor, swCallback callback, void *data)
436+
{
437+
CallbackManager *cm = (CallbackManager *) reactor->defer_tasks;
438+
if (cm == nullptr)
439+
{
440+
cm = new CallbackManager;
441+
reactor->defer_tasks = cm;
442+
}
443+
cm->append(callback, data);
444+
}
445+
400446
void swReactor_destory(swReactor *reactor)
401447
{
402-
swAio_free();
448+
if (reactor->destroy_callbacks)
449+
{
450+
CallbackManager *cm = (CallbackManager *) reactor->destroy_callbacks;
451+
cm->execute();
452+
reactor->destroy_callbacks = nullptr;
453+
delete cm;
454+
}
403455
reactor->free(reactor);
404456
}

src/reactor/defer_task.cc

-74
This file was deleted.

swoole.cc

+3-18
Original file line numberDiff line numberDiff line change
@@ -28,21 +28,13 @@
2828
#include <ifaddrs.h>
2929
#include <sys/ioctl.h>
3030

31-
#include <queue>
32-
3331
#include "zend_exceptions.h"
3432

3533
ZEND_DECLARE_MODULE_GLOBALS(swoole)
3634

3735
extern sapi_module_struct sapi_module;
3836

39-
struct rshutdown_func
40-
{
41-
swCallback callback;
42-
void *private_data;
43-
};
44-
45-
std::queue<rshutdown_func *> rshutdown_functions;
37+
static swoole::CallbackManager rshutdown_callbacks;
4638

4739
ZEND_BEGIN_ARG_INFO_EX(arginfo_swoole_void, 0, 0, 0)
4840
ZEND_END_ARG_INFO()
@@ -321,19 +313,12 @@ void php_swoole_register_shutdown_function_prepend(const char *function)
321313

322314
void php_swoole_register_rshutdown_callback(swCallback cb, void *private_data)
323315
{
324-
rshutdown_func *rf = (rshutdown_func*) emalloc(sizeof(rshutdown_func));
325-
rshutdown_functions.push(rf);
316+
rshutdown_callbacks.append(cb, private_data);
326317
}
327318

328319
static void execute_rshutdown_callback()
329320
{
330-
while(!rshutdown_functions.empty())
331-
{
332-
rshutdown_func *rf = rshutdown_functions.front();
333-
rshutdown_functions.pop();
334-
rf->callback(rf->private_data);
335-
efree(rf);
336-
}
321+
rshutdown_callbacks.execute();
337322
}
338323

339324
static void fatal_error(int code, const char *format, ...)

0 commit comments

Comments
 (0)