ibcore: Add some functions and definitions for selecting and querying retryable ucontext cleanup.

Linux commit:
1c77483e4c50339b0306572167ccbff6b55d051b

MFC after:	1 week
Reviewed by:	kib
Sponsored by:	Mellanox Technologies // NVIDIA Networking
This commit is contained in:
Hans Petter Selasky 2021-06-16 15:02:00 +02:00
parent 9dfa21486e
commit f60da09dbb
2 changed files with 57 additions and 0 deletions

View file

@ -365,6 +365,7 @@ ssize_t ib_uverbs_get_context(struct ib_uverbs_file *file,
ucontext->tgid = get_pid(task_pid_group_leader(current));
rcu_read_unlock();
ucontext->closing = 0;
ucontext->cleanup_retryable = false;
#ifdef CONFIG_INFINIBAND_ON_DEMAND_PAGING
ucontext->umem_tree = RB_ROOT;

View file

@ -1364,6 +1364,20 @@ struct ib_fmr_attr {
struct ib_umem;
enum rdma_remove_reason {
/*
* Userspace requested uobject deletion or initial try
* to remove uobject via cleanup. Call could fail
*/
RDMA_REMOVE_DESTROY,
/* Context deletion. This call should delete the actual object itself */
RDMA_REMOVE_CLOSE,
/* Driver is being hot-unplugged. This call should delete the actual object itself */
RDMA_REMOVE_DRIVER_REMOVE,
/* uobj is being cleaned-up before being committed */
RDMA_REMOVE_ABORT,
};
struct ib_ucontext {
struct ib_device *device;
struct list_head pd_list;
@ -1379,6 +1393,8 @@ struct ib_ucontext {
struct list_head rwq_ind_tbl_list;
int closing;
bool cleanup_retryable;
pid_t tgid;
#ifdef CONFIG_INFINIBAND_ON_DEMAND_PAGING
struct rb_root umem_tree;
@ -2213,6 +2229,46 @@ static inline bool ib_is_udata_cleared(struct ib_udata *udata,
return ret;
}
/**
* ib_is_destroy_retryable - Check whether the uobject destruction
* is retryable.
* @ret: The initial destruction return code
* @why: remove reason
* @uobj: The uobject that is destroyed
*
* This function is a helper function that IB layer and low-level drivers
* can use to consider whether the destruction of the given uobject is
* retry-able.
* It checks the original return code, if it wasn't success the destruction
* is retryable according to the ucontext state (i.e. cleanup_retryable) and
* the remove reason. (i.e. why).
* Must be called with the object locked for destroy.
*/
static inline bool ib_is_destroy_retryable(int ret, enum rdma_remove_reason why,
struct ib_uobject *uobj)
{
return ret && (why == RDMA_REMOVE_DESTROY ||
uobj->context->cleanup_retryable);
}
/**
* ib_destroy_usecnt - Called during destruction to check the usecnt
* @usecnt: The usecnt atomic
* @why: remove reason
* @uobj: The uobject that is destroyed
*
* Non-zero usecnts will block destruction unless destruction was triggered by
* a ucontext cleanup.
*/
static inline int ib_destroy_usecnt(atomic_t *usecnt,
enum rdma_remove_reason why,
struct ib_uobject *uobj)
{
if (atomic_read(usecnt) && ib_is_destroy_retryable(-EBUSY, why, uobj))
return -EBUSY;
return 0;
}
/**
* ib_modify_qp_is_ok - Check that the supplied attribute mask
* contains all required attributes and no attributes not allowed for