1 /* SPDX-License-Identifier: (GPL-2.0+ OR BSD-3-Clause) */ 2 /* 3 * Copyright (c) 2017-2018 Mellanox Technologies. All rights reserved. 4 */ 5 6 #ifndef _RDMA_RESTRACK_H_ 7 #define _RDMA_RESTRACK_H_ 8 9 #include <linux/typecheck.h> 10 #include <linux/rwsem.h> 11 #include <linux/sched.h> 12 #include <linux/kref.h> 13 #include <linux/completion.h> 14 15 /** 16 * enum rdma_restrack_type - HW objects to track 17 */ 18 enum rdma_restrack_type { 19 /** 20 * @RDMA_RESTRACK_PD: Protection domain (PD) 21 */ 22 RDMA_RESTRACK_PD, 23 /** 24 * @RDMA_RESTRACK_CQ: Completion queue (CQ) 25 */ 26 RDMA_RESTRACK_CQ, 27 /** 28 * @RDMA_RESTRACK_QP: Queue pair (QP) 29 */ 30 RDMA_RESTRACK_QP, 31 /** 32 * @RDMA_RESTRACK_MAX: Last entry, used for array dclarations 33 */ 34 RDMA_RESTRACK_MAX 35 }; 36 37 #define RDMA_RESTRACK_HASH_BITS 8 38 /** 39 * struct rdma_restrack_root - main resource tracking management 40 * entity, per-device 41 */ 42 struct rdma_restrack_root { 43 /* 44 * @rwsem: Read/write lock to protect lists 45 */ 46 struct rw_semaphore rwsem; 47 /** 48 * @hash: global database for all resources per-device 49 */ 50 DECLARE_HASHTABLE(hash, RDMA_RESTRACK_HASH_BITS); 51 }; 52 53 /** 54 * struct rdma_restrack_entry - metadata per-entry 55 */ 56 struct rdma_restrack_entry { 57 /** 58 * @valid: validity indicator 59 * 60 * The entries are filled during rdma_restrack_add, 61 * can be attempted to be free during rdma_restrack_del. 62 * 63 * As an example for that, see mlx5 QPs with type MLX5_IB_QPT_HW_GSI 64 */ 65 bool valid; 66 /* 67 * @kref: Protect destroy of the resource 68 */ 69 struct kref kref; 70 /* 71 * @comp: Signal that all consumers of resource are completed their work 72 */ 73 struct completion comp; 74 /** 75 * @task: owner of resource tracking entity 76 * 77 * There are two types of entities: created by user and created 78 * by kernel. 79 * 80 * This is relevant for the entities created by users. 81 * For the entities created by kernel, this pointer will be NULL. 82 */ 83 struct task_struct *task; 84 /** 85 * @kern_name: name of owner for the kernel created entities. 86 */ 87 const char *kern_name; 88 /** 89 * @node: hash table entry 90 */ 91 struct hlist_node node; 92 /** 93 * @type: various objects in restrack database 94 */ 95 enum rdma_restrack_type type; 96 }; 97 98 /** 99 * rdma_restrack_init() - initialize resource tracking 100 * @res: resource tracking root 101 */ 102 void rdma_restrack_init(struct rdma_restrack_root *res); 103 104 /** 105 * rdma_restrack_clean() - clean resource tracking 106 * @res: resource tracking root 107 */ 108 void rdma_restrack_clean(struct rdma_restrack_root *res); 109 110 /** 111 * rdma_restrack_count() - the current usage of specific object 112 * @res: resource entry 113 * @type: actual type of object to operate 114 * @ns: PID namespace 115 */ 116 int rdma_restrack_count(struct rdma_restrack_root *res, 117 enum rdma_restrack_type type, 118 struct pid_namespace *ns); 119 120 /** 121 * rdma_restrack_add() - add object to the reource tracking database 122 * @res: resource entry 123 */ 124 void rdma_restrack_add(struct rdma_restrack_entry *res); 125 126 /** 127 * rdma_restrack_del() - delete object from the reource tracking database 128 * @res: resource entry 129 * @type: actual type of object to operate 130 */ 131 void rdma_restrack_del(struct rdma_restrack_entry *res); 132 133 /** 134 * rdma_is_kernel_res() - check the owner of resource 135 * @res: resource entry 136 */ 137 static inline bool rdma_is_kernel_res(struct rdma_restrack_entry *res) 138 { 139 return !res->task; 140 } 141 142 /** 143 * rdma_restrack_get() - grab to protect resource from release 144 * @res: resource entry 145 */ 146 int __must_check rdma_restrack_get(struct rdma_restrack_entry *res); 147 148 /** 149 * rdma_restrack_put() - relase resource 150 * @res: resource entry 151 */ 152 int rdma_restrack_put(struct rdma_restrack_entry *res); 153 #endif /* _RDMA_RESTRACK_H_ */ 154