summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorDmitry Kozlov <xeb@mail.ru>2010-11-21 17:31:00 +0300
committerDmitry Kozlov <xeb@mail.ru>2010-11-21 17:31:00 +0300
commita09fdabf7939819581c6b7797b180a18c4f477fa (patch)
tree4cfaa02377ff7a660c53099c300de0890dff5d3f
parentddad202eca1c0a1d95321bd396df0dda01620a2b (diff)
downloadaccel-ppp-a09fdabf7939819581c6b7797b180a18c4f477fa.tar.gz
accel-ppp-a09fdabf7939819581c6b7797b180a18c4f477fa.zip
bug fixes
-rw-r--r--README2
-rw-r--r--accel-pptpd/CMakeLists.txt3
-rw-r--r--accel-pptpd/cli/telnet.c2
-rw-r--r--accel-pptpd/ctrl/l2tp/l2tp.c12
-rw-r--r--accel-pptpd/ctrl/pppoe/pppoe.c12
-rw-r--r--accel-pptpd/ctrl/pptp/pptp.c19
-rw-r--r--accel-pptpd/log.c2
-rw-r--r--accel-pptpd/logs/log_file.c2
-rw-r--r--accel-pptpd/memdebug.c2
-rw-r--r--accel-pptpd/ppp/ppp.c18
-rw-r--r--accel-pptpd/ppp/ppp_auth.c21
-rw-r--r--accel-pptpd/ppp/ppp_fsm.c8
-rw-r--r--accel-pptpd/radius/req.c2
-rw-r--r--accel-pptpd/triton/md.c35
-rw-r--r--accel-pptpd/triton/mempool.c24
-rw-r--r--accel-pptpd/triton/spinlock.h26
-rw-r--r--accel-pptpd/triton/timer.c33
-rw-r--r--accel-pptpd/triton/triton.c26
18 files changed, 167 insertions, 82 deletions
diff --git a/README b/README
index 1a78f7e..c75e250 100644
--- a/README
+++ b/README
@@ -20,7 +20,7 @@ Features
8. Supported MPPE
9. Compression is not supported
10. Extensible logging engine with per session logging support, implemented log to file and log to PostgreSQL targets
-11. Extensible user/password database, implemented only Radius source
+11. Extensible user/password database, implemented Radius, chap-secret sources
12. Extensible IP pool, implemented Radius and static pools
13. Supported pppd compatible ip-up/ip-down scripts
14. Builtin tbf shaper manager
diff --git a/accel-pptpd/CMakeLists.txt b/accel-pptpd/CMakeLists.txt
index d95bcad..1222085 100644
--- a/accel-pptpd/CMakeLists.txt
+++ b/accel-pptpd/CMakeLists.txt
@@ -11,7 +11,8 @@ IF (NOT HAVE_SSL)
MESSAGE(FATAL_ERROR "openssl headers not found")
ENDIF (NOT HAVE_SSL)
-SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -fvisibility=hidden -D_GNU_SOURCE -DGCC_SPINLOCK -DMEMDEBUG -fPIC")
+SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -fvisibility=hidden -D_GNU_SOURCE -DPTHREAD_SPINLOCK -DMEMDEBUG -fPIC")
+#SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -fvisibility=hidden -D_GNU_SOURCE -DFUTEX_SPINLOCK -DMEMDEBUG -fPIC")
INCLUDE_DIRECTORIES(include)
diff --git a/accel-pptpd/cli/telnet.c b/accel-pptpd/cli/telnet.c
index fef9b0a..c7a3c7a 100644
--- a/accel-pptpd/cli/telnet.c
+++ b/accel-pptpd/cli/telnet.c
@@ -263,7 +263,7 @@ static int telnet_input_char(struct telnet_client_t *cln, uint8_t c)
return -1;
}
cln->auth = 1;
- } else {
+ } else if (cln->cmdline_len) {
b = _malloc(sizeof(*b) + cln->cmdline_len);
memcpy(b->buf, cln->cmdline, cln->cmdline_len);
b->size = cln->cmdline_len;
diff --git a/accel-pptpd/ctrl/l2tp/l2tp.c b/accel-pptpd/ctrl/l2tp/l2tp.c
index 18ba6d0..b860f57 100644
--- a/accel-pptpd/ctrl/l2tp/l2tp.c
+++ b/accel-pptpd/ctrl/l2tp/l2tp.c
@@ -119,11 +119,11 @@ static void l2tp_disconnect(struct l2tp_conn_t *conn)
triton_timer_del(&conn->hello_timer);
if (conn->state == STATE_PPP) {
- __sync_fetch_and_sub(&stat_active, 1);
+ stat_active--;
conn->state = STATE_FIN;
ppp_terminate(&conn->ppp, TERM_USER_REQUEST, 1);
} else if (conn->state != STATE_FIN)
- __sync_fetch_and_sub(&stat_starting, 1);
+ stat_starting--;
pthread_mutex_lock(&l2tp_lock);
l2tp_conn[conn->tid] = NULL;
@@ -211,6 +211,7 @@ static void l2tp_conn_close(struct triton_context_t *ctx)
struct l2tp_conn_t *conn = container_of(ctx, typeof(*conn), ctx);
if (conn->state == STATE_PPP) {
+ stat_active--;
conn->state = STATE_FIN;
ppp_terminate(&conn->ppp, TERM_ADMIN_RESET, 1);
}
@@ -330,7 +331,7 @@ static int l2tp_tunnel_alloc(struct l2tp_serv_t *serv, struct l2tp_packet_t *pac
triton_context_call(&conn->ctx, (triton_event_func)l2tp_send_SCCRP, conn);
- __sync_fetch_and_add(&stat_starting, 1);
+ stat_starting++;
return 0;
@@ -392,8 +393,8 @@ static int l2tp_connect(struct l2tp_conn_t *conn)
if (establish_ppp(&conn->ppp))
return -1;
- __sync_fetch_and_sub(&stat_starting, 1);
- __sync_fetch_and_add(&stat_active, 1);
+ stat_starting--;
+ stat_active++;
conn->state = STATE_PPP;
@@ -803,6 +804,7 @@ static int l2tp_recv_CDN(struct l2tp_conn_t *conn, struct l2tp_packet_t *pack)
}
if (conn->state == STATE_PPP) {
+ stat_active--;
conn->state = STATE_FIN;
ppp_terminate(&conn->ppp, TERM_USER_REQUEST, 1);
}
diff --git a/accel-pptpd/ctrl/pppoe/pppoe.c b/accel-pptpd/ctrl/pppoe/pppoe.c
index eacecc9..0ff166c 100644
--- a/accel-pptpd/ctrl/pppoe/pppoe.c
+++ b/accel-pptpd/ctrl/pppoe/pppoe.c
@@ -80,7 +80,7 @@ void pppoe_server_free(struct pppoe_serv_t *serv);
static void disconnect(struct pppoe_conn_t *conn)
{
if (conn->ppp_started) {
- __sync_fetch_and_sub(&stat_active, 1);
+ stat_active--;
conn->ppp_started = 0;
ppp_terminate(&conn->ppp, TERM_USER_REQUEST, 1);
}
@@ -130,9 +130,9 @@ static void ppp_finished(struct ppp_t *ppp)
log_ppp_debug("pppoe: ppp finished\n");
if (conn->ppp_started) {
- __sync_fetch_and_sub(&stat_active, 1);
+ stat_active--;
conn->ppp_started = 0;
- disconnect(conn);
+ triton_context_call(&conn->ctx, (triton_event_func)disconnect, conn);
}
}
@@ -534,7 +534,7 @@ static void free_delayed_pado(struct delayed_pado_t *pado)
{
triton_timer_del(&pado->timer);
- __sync_fetch_and_sub(&stat_delayed_pado, 1);
+ stat_delayed_pado--;
list_del(&pado->entry);
if (pado->host_uniq)
@@ -643,7 +643,7 @@ static void pppoe_recv_PADI(struct pppoe_serv_t *serv, uint8_t *pack, int size)
triton_timer_add(&serv->ctx, &pado->timer, 0);
list_add_tail(&pado->entry, &serv->pado_list);
- __sync_fetch_and_add(&stat_delayed_pado, 1);
+ stat_delayed_pado++;
} else
pppoe_send_PADO(serv, ethhdr->h_source, host_uniq_tag, relay_sid_tag, service_name_tag);
}
@@ -744,7 +744,7 @@ static void pppoe_recv_PADR(struct pppoe_serv_t *serv, uint8_t *pack, int size)
if (connect_channel(conn))
disconnect(conn);
else {
- __sync_fetch_and_add(&stat_active, 1);
+ stat_active++;
conn->ppp_started = 1;
}
}
diff --git a/accel-pptpd/ctrl/pptp/pptp.c b/accel-pptpd/ctrl/pptp/pptp.c
index a07b21e..608be30 100644
--- a/accel-pptpd/ctrl/pptp/pptp.c
+++ b/accel-pptpd/ctrl/pptp/pptp.c
@@ -82,11 +82,11 @@ static void disconnect(struct pptp_conn_t *conn)
triton_timer_del(&conn->echo_timer);
if (conn->state == STATE_PPP) {
- __sync_fetch_and_sub(&stat_active, 1);
+ stat_active--;
conn->state = STATE_CLOSE;
ppp_terminate(&conn->ppp, TERM_USER_REQUEST, 1);
} else if (conn->state != STATE_CLOSE)
- __sync_fetch_and_sub(&stat_starting, 1);
+ stat_starting--;
triton_event_fire(EV_CTRL_FINISHED, &conn->ppp);
@@ -329,8 +329,8 @@ static int pptp_out_call_rqst(struct pptp_conn_t *conn)
return -1;
}
conn->state = STATE_PPP;
- __sync_fetch_and_sub(&stat_starting, 1);
- __sync_fetch_and_add(&stat_active, 1);
+ stat_starting--;
+ stat_active++;
if (conn->timeout_timer.tpd)
triton_timer_del(&conn->timeout_timer);
@@ -367,11 +367,10 @@ static int pptp_call_clear_rqst(struct pptp_conn_t *conn)
log_ppp_info("recv [PPTP Call-Clear-Request <Call-ID %x>]\n", ntohs(rqst->call_id));
if (conn->state == STATE_PPP) {
- __sync_fetch_and_sub(&stat_active, 1);
+ stat_active--;
conn->state = STATE_CLOSE;
ppp_terminate(&conn->ppp, TERM_USER_REQUEST, 1);
- } else
- __sync_fetch_and_sub(&stat_starting, 1);
+ }
return send_pptp_call_disconnect_notify(conn, 4);
}
@@ -550,7 +549,7 @@ static void pptp_close(struct triton_context_t *ctx)
{
struct pptp_conn_t *conn = container_of(ctx, typeof(*conn), ctx);
if (conn->state == STATE_PPP) {
- __sync_fetch_and_sub(&stat_active, 1);
+ stat_active--;
conn->state = STATE_CLOSE;
ppp_terminate(&conn->ppp, TERM_ADMIN_RESET, 1);
if (send_pptp_call_disconnect_notify(conn, 3)) {
@@ -580,7 +579,7 @@ static void ppp_finished(struct ppp_t *ppp)
if (conn->state != STATE_CLOSE) {
log_ppp_debug("pptp: ppp finished\n");
conn->state = STATE_CLOSE;
- __sync_fetch_and_sub(&stat_active, 1);
+ stat_active--;
if (send_pptp_call_disconnect_notify(conn, 3))
triton_context_call(&conn->ctx, (void (*)(void*))disconnect, conn);
@@ -668,7 +667,7 @@ static int pptp_connect(struct triton_md_handler_t *h)
triton_event_fire(EV_CTRL_STARTING, &conn->ppp);
- __sync_fetch_and_add(&stat_starting, 1);
+ stat_starting++;
}
return 0;
}
diff --git a/accel-pptpd/log.c b/accel-pptpd/log.c
index e8f47b6..f87f115 100644
--- a/accel-pptpd/log.c
+++ b/accel-pptpd/log.c
@@ -252,7 +252,7 @@ static struct log_msg_t *clone_msg(struct _log_msg_t *msg)
m->timestamp = msg->timestamp;
m->level = msg->level;
- __sync_add_and_fetch(&msg->refs, 1);
+ msg->refs++;
//printf("clone msg %p\n", m);
return m;
diff --git a/accel-pptpd/logs/log_file.c b/accel-pptpd/logs/log_file.c
index db08aa2..4c4b382 100644
--- a/accel-pptpd/logs/log_file.c
+++ b/accel-pptpd/logs/log_file.c
@@ -395,7 +395,7 @@ static void ev_ctrl_started(struct ppp_t *ppp)
return;
}
- lpd->tmp = __sync_fetch_and_add(&temp_seq, 1);
+ lpd->tmp = temp_seq++;
strcpy(fname, conf_per_session_dir);
strcat(fname, "/tmp");
sprintf(fname + strlen(fname), "%lu", lpd->tmp);
diff --git a/accel-pptpd/memdebug.c b/accel-pptpd/memdebug.c
index 2acdc7a..d36779e 100644
--- a/accel-pptpd/memdebug.c
+++ b/accel-pptpd/memdebug.c
@@ -39,7 +39,7 @@ struct mem_t
};
static LIST_HEAD(mem_list);
-static spinlock_t mem_list_lock;
+static spinlock_t mem_list_lock = SPINLOCK_INITIALIZER;
struct mem_t *_md_malloc(size_t size, const char *fname, int line)
{
diff --git a/accel-pptpd/ppp/ppp.c b/accel-pptpd/ppp/ppp.c
index acda605..408383e 100644
--- a/accel-pptpd/ppp/ppp.c
+++ b/accel-pptpd/ppp/ppp.c
@@ -152,7 +152,7 @@ int __export establish_ppp(struct ppp_t *ppp)
triton_md_enable_handler(&ppp->unit_hnd, MD_MODE_READ);
ppp->state = PPP_STATE_STARTING;
- __sync_fetch_and_add(&ppp_stat.starting, 1);
+ ppp_stat.starting++;
pthread_rwlock_wrlock(&ppp_lock);
list_add_tail(&ppp->entry, &ppp_list);
@@ -184,13 +184,13 @@ static void destablish_ppp(struct ppp_t *ppp)
switch (ppp->state) {
case PPP_STATE_ACTIVE:
- __sync_fetch_and_sub(&ppp_stat.active, 1);
+ ppp_stat.active--;
break;
case PPP_STATE_STARTING:
- __sync_fetch_and_sub(&ppp_stat.starting, 1);
+ ppp_stat.starting--;
break;
case PPP_STATE_FINISHING:
- __sync_fetch_and_sub(&ppp_stat.finishing, 1);
+ ppp_stat.finishing--;
break;
}
@@ -374,8 +374,8 @@ void __export ppp_layer_started(struct ppp_t *ppp, struct ppp_layer_data_t *d)
if (n->entry.next == &ppp->layers) {
ppp->state = PPP_STATE_ACTIVE;
- __sync_fetch_and_sub(&ppp_stat.starting, 1);
- __sync_fetch_and_add(&ppp_stat.active, 1);
+ ppp_stat.starting--;
+ ppp_stat.active++;
ppp->ctrl->started(ppp);
triton_event_fire(EV_PPP_STARTED, ppp);
} else {
@@ -430,10 +430,10 @@ void __export ppp_terminate(struct ppp_t *ppp, int cause, int hard)
ppp->terminating = 1;
if (ppp->state == PPP_STATE_ACTIVE)
- __sync_fetch_and_sub(&ppp_stat.active, 1);
+ ppp_stat.active--;
else
- __sync_fetch_and_sub(&ppp_stat.starting, 1);
- __sync_fetch_and_add(&ppp_stat.finishing, 1);
+ ppp_stat.starting--;
+ ppp_stat.finishing++;
ppp->state = PPP_STATE_FINISHING;
log_ppp_debug("ppp_terminate\n");
diff --git a/accel-pptpd/ppp/ppp_auth.c b/accel-pptpd/ppp/ppp_auth.c
index c993414..0683593 100644
--- a/accel-pptpd/ppp/ppp_auth.c
+++ b/accel-pptpd/ppp/ppp_auth.c
@@ -34,6 +34,7 @@ struct auth_option_t
struct list_head auth_list;
struct auth_data_t *auth;
struct auth_data_t *peer_auth;
+ int started:1;
};
struct auth_layer_data_t
@@ -41,7 +42,6 @@ struct auth_layer_data_t
struct ppp_layer_data_t ld;
struct auth_option_t auth_opt;
struct ppp_t *ppp;
- int started:1;
};
static struct lcp_option_handler_t auth_opt_hnd =
@@ -92,6 +92,11 @@ static void auth_free(struct ppp_lcp_t *lcp, struct lcp_option_t *opt)
struct auth_option_t *auth_opt = container_of(opt, typeof(*auth_opt), opt);
struct auth_data_t *d;
+ if (auth_opt->started && auth_opt->auth) {
+ auth_opt->auth->h->finish(lcp->ppp, auth_opt->auth);
+ auth_opt->started = 0;
+ }
+
while(!list_empty(&auth_opt->auth_list)) {
d = list_entry(auth_opt->auth_list.next, typeof(*d), entry);
list_del(&d->entry);
@@ -258,12 +263,11 @@ static int auth_layer_start(struct ppp_layer_data_t *ld)
struct auth_layer_data_t *ad = container_of(ld,typeof(*ad),ld);
log_ppp_debug("auth_layer_start\n");
-
- ad->started = 1;
-
- if (ad->auth_opt.auth)
+
+ if (ad->auth_opt.auth) {
+ ad->auth_opt.started = 1;
ad->auth_opt.auth->h->start(ad->ppp, ad->auth_opt.auth);
- else {
+ } else {
log_ppp_debug("auth_layer_started\n");
ppp_layer_started(ad->ppp, ld);
}
@@ -280,7 +284,7 @@ static void auth_layer_finish(struct ppp_layer_data_t *ld)
if (ad->auth_opt.auth)
ad->auth_opt.auth->h->finish(ad->ppp, ad->auth_opt.auth);
- ad->started = 0;
+ ad->auth_opt.started = 0;
log_ppp_debug("auth_layer_finished\n");
ppp_layer_finished(ad->ppp, ld);
@@ -292,9 +296,6 @@ static void auth_layer_free(struct ppp_layer_data_t *ld)
log_ppp_debug("auth_layer_free\n");
- if (ad->started && ad->auth_opt.auth)
- ad->auth_opt.auth->h->finish(ad->ppp, ad->auth_opt.auth);
-
_free(ad);
}
diff --git a/accel-pptpd/ppp/ppp_fsm.c b/accel-pptpd/ppp/ppp_fsm.c
index 495b346..46b6215 100644
--- a/accel-pptpd/ppp/ppp_fsm.c
+++ b/accel-pptpd/ppp/ppp_fsm.c
@@ -192,8 +192,8 @@ void ppp_fsm_timeout1(struct ppp_fsm_t *layer)
case FSM_Req_Sent:
case FSM_Ack_Sent:
stop_timer(layer);
- if (layer->layer_finished) layer->layer_finished(layer);
layer->fsm_state=FSM_Stopped;
+ if (layer->layer_finished) layer->layer_finished(layer);
break;
default:
break;
@@ -417,8 +417,8 @@ void ppp_fsm_recv_term_ack(struct ppp_fsm_t *layer)
if (layer->layer_finished) layer->layer_finished(layer);
break;
case FSM_Stopping:
- if (layer->layer_finished) layer->layer_finished(layer);
layer->fsm_state=FSM_Stopped;
+ if (layer->layer_finished) layer->layer_finished(layer);
break;
case FSM_Ack_Rcvd:
layer->fsm_state=FSM_Req_Sent;
@@ -462,15 +462,15 @@ void ppp_fsm_recv_code_rej_bad(struct ppp_fsm_t *layer)
layer->fsm_state=FSM_Stopping;
break;
case FSM_Closing:
- if (layer->layer_finished) layer->layer_finished(layer);
layer->fsm_state=FSM_Closed;
+ if (layer->layer_finished) layer->layer_finished(layer);
break;
case FSM_Stopping:
case FSM_Req_Sent:
case FSM_Ack_Rcvd:
case FSM_Ack_Sent:
- if (layer->layer_finished) layer->layer_finished(layer);
layer->fsm_state=FSM_Stopped;
+ if (layer->layer_finished) layer->layer_finished(layer);
break;
default:
break;
diff --git a/accel-pptpd/radius/req.c b/accel-pptpd/radius/req.c
index e945839..27a661b 100644
--- a/accel-pptpd/radius/req.c
+++ b/accel-pptpd/radius/req.c
@@ -221,7 +221,7 @@ static int rad_req_read(struct triton_md_handler_t *h)
req_wakeup(req);
- return 0;
+ return 1;
}
static void rad_req_timeout(struct triton_timer_t *t)
{
diff --git a/accel-pptpd/triton/md.c b/accel-pptpd/triton/md.c
index 444aebf..7833031 100644
--- a/accel-pptpd/triton/md.c
+++ b/accel-pptpd/triton/md.c
@@ -20,6 +20,10 @@ static void *md_thread(void *arg);
static mempool_t *md_pool;
+static pthread_mutex_t freed_list_lock = PTHREAD_MUTEX_INITIALIZER;
+static LIST_HEAD(freed_list);
+static LIST_HEAD(freed_list2);
+
int md_init(void)
{
epoll_fd = epoll_create(1);
@@ -74,6 +78,8 @@ static void *md_thread(void *arg)
for(i = 0; i < n; i++) {
h = (struct _triton_md_handler_t *)epoll_events[i].data.ptr;
+ if (!h->ud)
+ continue;
spin_lock(&h->ctx->lock);
if (h->ud) {
h->trig_epoll_events |= epoll_events[i].events;
@@ -89,6 +95,20 @@ static void *md_thread(void *arg)
if (r)
triton_thread_wakeup(h->ctx->thread);
}
+
+ while (!list_empty(&freed_list2)) {
+ h = list_entry(freed_list2.next, typeof(*h), entry);
+ list_del(&h->entry);
+ mempool_free(h);
+ }
+
+ pthread_mutex_lock(&freed_list_lock);
+ while (!list_empty(&freed_list)) {
+ h = list_entry(freed_list.next, typeof(*h), entry);
+ list_del(&h->entry);
+ list_add(&h->entry, &freed_list2);
+ }
+ pthread_mutex_unlock(&freed_list_lock);
}
return NULL;
@@ -109,22 +129,27 @@ void __export triton_md_register_handler(struct triton_context_t *ctx, struct tr
list_add_tail(&h->entry, &h->ctx->handlers);
spin_unlock(&h->ctx->lock);
- __sync_fetch_and_add(&triton_stat.md_handler_count, 1);
+ triton_stat.md_handler_count++;
}
void __export triton_md_unregister_handler(struct triton_md_handler_t *ud)
{
struct _triton_md_handler_t *h = (struct _triton_md_handler_t *)ud->tpd;
triton_md_disable_handler(ud, MD_MODE_READ | MD_MODE_WRITE);
+
spin_lock(&h->ctx->lock);
+ h->ud = NULL;
list_del(&h->entry);
if (h->pending)
list_del(&h->entry2);
- h->ud = NULL;
spin_unlock(&h->ctx->lock);
+
sched_yield();
- mempool_free(h);
-
- __sync_fetch_and_sub(&triton_stat.md_handler_count, 1);
+
+ pthread_mutex_lock(&freed_list_lock);
+ list_add_tail(&h->entry, &freed_list);
+ pthread_mutex_unlock(&freed_list_lock);
+
+ triton_stat.md_handler_count--;
}
int __export triton_md_enable_handler(struct triton_md_handler_t *ud, int mode)
{
diff --git a/accel-pptpd/triton/mempool.c b/accel-pptpd/triton/mempool.c
index 0ba4ebe..51cde51 100644
--- a/accel-pptpd/triton/mempool.c
+++ b/accel-pptpd/triton/mempool.c
@@ -70,7 +70,7 @@ void __export *mempool_alloc(mempool_t *pool)
list_del(&it->entry);
spin_unlock(&p->lock);
- __sync_fetch_and_sub(&triton_stat.mempool_available, size);
+ triton_stat.mempool_available -= size;
it->magic1 = MAGIC1;
@@ -88,7 +88,7 @@ void __export *mempool_alloc(mempool_t *pool)
it->magic2 = p->magic;
*(uint64_t*)(it->data + p->size) = it->magic2;
- __sync_fetch_and_add(&triton_stat.mempool_allocated, size);
+ triton_stat.mempool_allocated += size;
return it->ptr;
}
@@ -110,7 +110,7 @@ void __export *mempool_alloc_md(mempool_t *pool, const char *fname, int line)
it->fname = fname;
it->line = line;
- __sync_fetch_and_sub(&triton_stat.mempool_available, size);
+ triton_stat.mempool_available -= size;
it->magic1 = MAGIC1;
@@ -134,7 +134,7 @@ void __export *mempool_alloc_md(mempool_t *pool, const char *fname, int line)
list_add(&it->entry, &p->ditems);
spin_unlock(&p->lock);
- __sync_fetch_and_add(&triton_stat.mempool_allocated, size);
+ triton_stat.mempool_allocated += size;
return it->ptr;
}
@@ -168,10 +168,16 @@ void __export mempool_free(void *ptr)
#ifdef MEMDEBUG
list_del(&it->entry);
#endif
+#ifndef MEMPOOL_DISABLE
list_add_tail(&it->entry,&it->owner->items);
+#endif
spin_unlock(&it->owner->lock);
- __sync_fetch_and_add(&triton_stat.mempool_available, size);
+#ifdef MEMPOOL_DISABLE
+ _free(it);
+#endif
+
+ triton_stat.mempool_available += size;
}
void __export mempool_clean(mempool_t *pool)
@@ -185,8 +191,8 @@ void __export mempool_clean(mempool_t *pool)
it = list_entry(p->items.next, typeof(*it), entry);
list_del(&it->entry);
_free(it);
- __sync_fetch_and_sub(&triton_stat.mempool_allocated, size);
- __sync_fetch_and_sub(&triton_stat.mempool_available, size);
+ triton_stat.mempool_allocated -= size;
+ triton_stat.mempool_available -= size;
}
spin_unlock(&p->lock);
}
@@ -220,8 +226,8 @@ void sigclean(int num)
it = list_entry(p->items.next, typeof(*it), entry);
list_del(&it->entry);
_free(it);
- __sync_fetch_and_sub(&triton_stat.mempool_allocated, size);
- __sync_fetch_and_sub(&triton_stat.mempool_available, size);
+ triton_stat.mempool_allocated -= size;
+ triton_stat.mempool_available -= size;
}
spin_unlock(&p->lock);
}
diff --git a/accel-pptpd/triton/spinlock.h b/accel-pptpd/triton/spinlock.h
index 61f9b01..bb8dcf4 100644
--- a/accel-pptpd/triton/spinlock.h
+++ b/accel-pptpd/triton/spinlock.h
@@ -1,13 +1,35 @@
#ifndef __TRITON_SPINLOCK_H
#define __TRITON_SPINLOCK_H
-#ifdef GCC_SPINLOCK
-typedef volatile unsigned int spinlock_t;
+#if defined(FUTEX_SPINLOCK)
+
+/*#include <unistd.h>
+#include <sys/syscall.h>
+#include <linux/futex.h>
+typedef volatile int __attribute__((aligned)) spinlock_t;
+static inline void _spin_lock(spinlock_t *l)
+{
+ syscall(SYS_futex, l, FUTEX_WAIT, r, NULL, NULL, 0);
+}
+static inline void _spin_unlock(spinlock_t *l)
+{
+ syscall(SYS_futex, l, FUTEX_WAKE, 2, NULL, NULL, 0);
+}
+#define spin_lock(l) _spin_lock(l)
+#define spin_unlock(l) _spin_unlock(l)
+#define SPINLOCK_INITIALIZER 1
+#define spinlock_init(l) {*(l)=1;}*/
+
+#elif defined(GCC_SPINLOCK)
+
+typedef volatile int __attribute__((aligned)) spinlock_t;
#define spin_lock(l) {while(__sync_lock_test_and_set(l,1));}
#define spin_unlock(l) __sync_lock_release(l)
#define SPINLOCK_INITIALIZER 0
#define spinlock_init(l) {*(l)=0;}
+
#else
+
#include <pthread.h>
typedef pthread_mutex_t spinlock_t;
#define spin_lock(l) pthread_mutex_lock(l)
diff --git a/accel-pptpd/triton/timer.c b/accel-pptpd/triton/timer.c
index 43cb56f..95a540a 100644
--- a/accel-pptpd/triton/timer.c
+++ b/accel-pptpd/triton/timer.c
@@ -26,6 +26,10 @@ static void *timer_thread(void *arg);
static mempool_t *timer_pool;
+static pthread_mutex_t freed_list_lock = PTHREAD_MUTEX_INITIALIZER;
+static LIST_HEAD(freed_list);
+static LIST_HEAD(freed_list2);
+
int timer_init(void)
{
epoll_fd = epoll_create(1);
@@ -81,6 +85,8 @@ void *timer_thread(void *arg)
for(i = 0; i < n; i++) {
t = (struct _triton_timer_t *)epoll_events[i].data.ptr;
+ if (!t->ud)
+ continue;
spin_lock(&t->ctx->lock);
if (t->ud) {
if (!t->pending) {
@@ -95,6 +101,20 @@ void *timer_thread(void *arg)
if (r)
triton_thread_wakeup(t->ctx->thread);
}
+
+ while (!list_empty(&freed_list2)) {
+ t = list_entry(freed_list2.next, typeof(*t), entry);
+ list_del(&t->entry);
+ mempool_free(t);
+ }
+
+ pthread_mutex_lock(&freed_list_lock);
+ while (!list_empty(&freed_list)) {
+ t = list_entry(freed_list.next, typeof(*t), entry);
+ list_del(&t->entry);
+ list_add(&t->entry, &freed_list2);
+ }
+ pthread_mutex_unlock(&freed_list_lock);
}
return NULL;
@@ -143,7 +163,7 @@ int __export triton_timer_add(struct triton_context_t *ctx, struct triton_timer_
goto out_err;
}
- __sync_fetch_and_add(&triton_stat.timer_count, 1);
+ triton_stat.timer_count++;
return 0;
@@ -179,15 +199,20 @@ void __export triton_timer_del(struct triton_timer_t *ud)
epoll_ctl(epoll_fd, EPOLL_CTL_DEL, t->fd, &t->epoll_event);
close(t->fd);
spin_lock(&t->ctx->lock);
+ t->ud = NULL;
list_del(&t->entry);
if (t->pending)
list_del(&t->entry2);
- t->ud = NULL;
spin_unlock(&t->ctx->lock);
+
sched_yield();
- mempool_free(t);
+
+ pthread_mutex_lock(&freed_list_lock);
+ list_add_tail(&t->entry, &freed_list);
+ pthread_mutex_unlock(&freed_list_lock);
+
ud->tpd = NULL;
- __sync_fetch_and_sub(&triton_stat.timer_count, 1);
+ triton_stat.timer_count--;
}
diff --git a/accel-pptpd/triton/triton.c b/accel-pptpd/triton/triton.c
index e7855cc..34c526e 100644
--- a/accel-pptpd/triton/triton.c
+++ b/accel-pptpd/triton/triton.c
@@ -60,7 +60,7 @@ static void* triton_thread(struct _triton_thread_t *thread)
thread->ctx->thread = thread;
thread->ctx->queued = 0;
spin_unlock(&thread->ctx->lock);
- __sync_fetch_and_sub(&triton_stat.context_pending, 1);
+ triton_stat.context_pending--;
} else {
//printf("thread: %p: sleeping\n", thread);
if (!terminate)
@@ -69,11 +69,11 @@ static void* triton_thread(struct _triton_thread_t *thread)
if (terminate)
return NULL;
- __sync_fetch_and_sub(&triton_stat.thread_active, 1);
+ triton_stat.thread_active--;
//printf("thread %p: enter sigwait\n", thread);
sigwait(&set, &sig);
//printf("thread %p: exit sigwait\n", thread);
- __sync_fetch_and_add(&triton_stat.thread_active, 1);
+ triton_stat.thread_active++;
if (!thread->ctx)
continue;
@@ -106,6 +106,8 @@ cont:
if (thread->ctx->need_free) {
//printf("- context %p removed\n", thread->ctx);
+ spin_lock(&thread->ctx->lock);
+ spin_unlock(&thread->ctx->lock);
mempool_free(thread->ctx->uctx.uc_stack.ss_sp);
mempool_free(thread->ctx);
}
@@ -148,10 +150,12 @@ static void ctx_thread(struct _triton_context_t *ctx)
spin_unlock(&ctx->lock);
if (h->trig_epoll_events & (EPOLLIN | EPOLLERR | EPOLLHUP))
if (h->ud && h->ud->read)
- h->ud->read(h->ud);
+ if (h->ud->read(h->ud))
+ continue;
if (h->trig_epoll_events & (EPOLLOUT | EPOLLERR | EPOLLHUP))
if (h->ud && h->ud->write)
- h->ud->write(h->ud);
+ if (h->ud->write(h->ud))
+ continue;
h->trig_epoll_events = 0;
continue;
}
@@ -212,7 +216,7 @@ int triton_queue_ctx(struct _triton_context_t *ctx)
spin_unlock(&threads_lock);
ctx->queued = 1;
//printf("ctx %p: queued\n", ctx);
- __sync_fetch_and_add(&triton_stat.context_pending, 1);
+ triton_stat.context_pending++;
return 0;
}
@@ -265,8 +269,8 @@ int __export triton_context_register(struct triton_context_t *ud, void *bf_arg)
list_add_tail(&ctx->entry, &ctx_list);
spin_unlock(&ctx_list_lock);
- __sync_fetch_and_add(&triton_stat.context_sleeping, 1);
- __sync_fetch_and_add(&triton_stat.context_count, 1);
+ triton_stat.context_sleeping++;
+ triton_stat.context_count++;
return 0;
}
@@ -313,7 +317,7 @@ void __export triton_context_unregister(struct triton_context_t *ud)
terminate = 1;
spin_unlock(&ctx_list_lock);
- __sync_fetch_and_sub(&triton_stat.context_count, 1);
+ triton_stat.context_count--;
if (terminate) {
list_for_each_entry(t, &threads, entry)
@@ -343,7 +347,7 @@ void __export triton_context_schedule(struct triton_context_t *ud)
ctx->thread = NULL;
spin_unlock(&ctx->lock);
- __sync_fetch_and_add(&triton_stat.context_sleeping, 1);
+ triton_stat.context_sleeping++;
if (swapcontext(&ctx->uctx, uctx))
triton_log_error("swaswpntext: %s\n", strerror(errno));
@@ -375,7 +379,7 @@ int __export triton_context_wakeup(struct triton_context_t *ud)
if (r)
triton_thread_wakeup(ctx->thread);
- __sync_fetch_and_sub(&triton_stat.context_sleeping, 1);
+ triton_stat.context_sleeping--;
return 0;
}