Re: ipoib lockdep warning

From: Michael S. Tsirkin
Date: Wed Jul 12 2006 - 07:08:20 EST


Quoting r. Ingo Molnar <mingo@xxxxxxx>:
> But i also think that you should avoid using GFP_ATOMIC for any sort of
> reliable IO path and push as much work into process context as possible.
> Is it acceptable for your infiniband IO model to fail with -ENOMEM if
> GFP_ATOMIC happens to fail, and is the IO retried transparently?

Yes, this is true for users that pass GFP_ATOMIC to sa_query, at least. But
might not be so for other users: send_mad in sa_query actually gets gfp_flags
parameter, but for some reason it does not pass it to idr_pre_get, which means
even sa query done with GFP_KERNEL flag is likely to fail.

Sean, it seems we need something like the following - what do you think?

--

Avoid bogus out out memory errors: fix sa_query to actually pass gfp_mask
supplied by the user to idr_pre_get.

Signed-off-by: Michael S. Tsirkin <mst@xxxxxxxxxxxxxx>

diff --git a/drivers/infiniband/core/sa_query.c b/drivers/infiniband/core/sa_query.c
index e911c99..aeda484 100644
--- a/drivers/infiniband/core/sa_query.c
+++ b/drivers/infiniband/core/sa_query.c
@@ -488,13 +488,13 @@ static void init_mad(struct ib_sa_mad *m
spin_unlock_irqrestore(&tid_lock, flags);
}

-static int send_mad(struct ib_sa_query *query, int timeout_ms)
+static int send_mad(struct ib_sa_query *query, int timeout_ms, gfp_t gfp_mask)
{
unsigned long flags;
int ret, id;

retry:
- if (!idr_pre_get(&query_idr, GFP_ATOMIC))
+ if (!idr_pre_get(&query_idr, gfp_mask))
return -ENOMEM;
spin_lock_irqsave(&idr_lock, flags);
ret = idr_get_new(&query_idr, query, &id);
@@ -630,7 +630,7 @@ int ib_sa_path_rec_get(struct ib_device

*sa_query = &query->sa_query;

- ret = send_mad(&query->sa_query, timeout_ms);
+ ret = send_mad(&query->sa_query, timeout_ms, gfp_mask);
if (ret < 0)
goto err2;

@@ -752,7 +752,7 @@ int ib_sa_service_rec_query(struct ib_de

*sa_query = &query->sa_query;

- ret = send_mad(&query->sa_query, timeout_ms);
+ ret = send_mad(&query->sa_query, timeout_ms, gfp_mask);
if (ret < 0)
goto err2;

@@ -844,7 +844,7 @@ int ib_sa_mcmember_rec_query(struct ib_d

*sa_query = &query->sa_query;

- ret = send_mad(&query->sa_query, timeout_ms);
+ ret = send_mad(&query->sa_query, timeout_ms, gfp_mask);
if (ret < 0)
goto err2;



--
MST
-
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majordomo@xxxxxxxxxxxxxxx
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/