summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorGuillaume Nault <g.nault@alphalink.fr>2014-11-12 16:35:14 +0100
committerDmitry Kozlov <xeb@mail.ru>2014-11-17 17:49:50 +0300
commitbe476ff24258d1c3a043c69040ab147e6ed59c5a (patch)
treec79b758f4a67df4540304dc511139711c8103008
parentcfead0b09e56c0740d6dae50b8ac7a0b07c06dc4 (diff)
downloadaccel-ppp-be476ff24258d1c3a043c69040ab147e6ed59c5a.tar.gz
accel-ppp-be476ff24258d1c3a043c69040ab147e6ed59c5a.zip
triton: lock pending calls list in triton_cancel_call()
The pending_calls field of struct _triton_context_t can be concurrently used by other contexts. So it must only be accessed or modified under protection of the context's lock (like in triton_context_call() or ctx_thread()). Signed-off-by: Guillaume Nault <g.nault@alphalink.fr>
-rw-r--r--accel-pppd/triton/triton.c11
1 files changed, 9 insertions, 2 deletions
diff --git a/accel-pppd/triton/triton.c b/accel-pppd/triton/triton.c
index 2807da82..b190187d 100644
--- a/accel-pppd/triton/triton.c
+++ b/accel-pppd/triton/triton.c
@@ -520,11 +520,18 @@ void __export triton_cancel_call(struct triton_context_t *ud, void (*func)(void
struct _triton_context_t *ctx = ud ? (struct _triton_context_t *)ud->tpd : (struct _triton_context_t *)default_ctx.tpd;
struct list_head *pos, *n;
struct _triton_ctx_call_t *call;
+ LIST_HEAD(rem_calls);
+ spin_lock(&ctx->lock);
list_for_each_safe(pos, n, &ctx->pending_calls) {
call = list_entry(pos, typeof(*call), entry);
- if (call->func != func)
- continue;
+ if (call->func == func)
+ list_move(&call->entry, &rem_calls);
+ }
+ spin_unlock(&ctx->lock);
+
+ while (!list_empty(&rem_calls)) {
+ call = list_first_entry(&rem_calls, typeof(*call), entry);
list_del(&call->entry);
mempool_free(call);
}