aboutsummaryrefslogtreecommitdiff
path: root/sys/rpc/replay.c
diff options
context:
space:
mode:
authorPawel Jakub Dawidek <pjd@FreeBSD.org>2010-08-26 23:33:04 +0000
committerPawel Jakub Dawidek <pjd@FreeBSD.org>2010-08-26 23:33:04 +0000
commit0778b1d117532b23072229cc35a664c9ba5c8544 (patch)
tree0bed83afcab7f600ce99cdd9e205703a46bac78c /sys/rpc/replay.c
parent4136388a1815ef48cd2b2005b254293a0986c376 (diff)
downloadsrc-0778b1d117532b23072229cc35a664c9ba5c8544.tar.gz
src-0778b1d117532b23072229cc35a664c9ba5c8544.zip
- Check the result of malloc(M_NOWAIT) in replay_alloc(). The caller
(replay_alloc()) knows how to handle replay_alloc() failure. - Eliminate 'freed_one' variable, it is not needed - when no entry is found rce will be NULL. - Add locking assertions where we expect a rc_lock to be held. Reviewed by: rmacklem MFC after: 2 weeks
Notes
Notes: svn path=/head/; revision=211853
Diffstat (limited to 'sys/rpc/replay.c')
-rw-r--r--sys/rpc/replay.c45
1 files changed, 25 insertions, 20 deletions
diff --git a/sys/rpc/replay.c b/sys/rpc/replay.c
index 2e92017689a1..1bd5378d9fbe 100644
--- a/sys/rpc/replay.c
+++ b/sys/rpc/replay.c
@@ -113,8 +113,12 @@ replay_alloc(struct replay_cache *rc,
{
struct replay_cache_entry *rce;
+ mtx_assert(&rc->rc_lock, MA_OWNED);
+
rc->rc_count++;
rce = malloc(sizeof(*rce), M_RPC, M_NOWAIT|M_ZERO);
+ if (!rce)
+ return (NULL);
rce->rce_hash = h;
rce->rce_msg = *msg;
bcopy(addr, &rce->rce_addr, addr->sa_len);
@@ -129,6 +133,8 @@ static void
replay_free(struct replay_cache *rc, struct replay_cache_entry *rce)
{
+ mtx_assert(&rc->rc_lock, MA_OWNED);
+
rc->rc_count--;
TAILQ_REMOVE(&rc->rc_cache[rce->rce_hash], rce, rce_link);
TAILQ_REMOVE(&rc->rc_all, rce, rce_alllink);
@@ -143,26 +149,25 @@ static void
replay_prune(struct replay_cache *rc)
{
struct replay_cache_entry *rce;
- bool_t freed_one;
-
- if (rc->rc_count >= REPLAY_MAX || rc->rc_size > rc->rc_maxsize) {
- do {
- freed_one = FALSE;
- /*
- * Try to free an entry. Don't free in-progress entries
- */
- TAILQ_FOREACH_REVERSE(rce, &rc->rc_all,
- replay_cache_list, rce_alllink) {
- if (rce->rce_repmsg.rm_xid) {
- replay_free(rc, rce);
- freed_one = TRUE;
- break;
- }
- }
- } while (freed_one
- && (rc->rc_count >= REPLAY_MAX
- || rc->rc_size > rc->rc_maxsize));
- }
+
+ mtx_assert(&rc->rc_lock, MA_OWNED);
+
+ if (rc->rc_count < REPLAY_MAX && rc->rc_size <= rc->rc_maxsize)
+ return;
+
+ do {
+ /*
+ * Try to free an entry. Don't free in-progress entries.
+ */
+ TAILQ_FOREACH_REVERSE(rce, &rc->rc_all, replay_cache_list,
+ rce_alllink) {
+ if (rce->rce_repmsg.rm_xid)
+ break;
+ }
+ if (rce)
+ replay_free(rc, rce);
+ } while (rce && (rc->rc_count >= REPLAY_MAX
+ || rc->rc_size > rc->rc_maxsize));
}
enum replay_state