Skip to content

Commit 3f1ec97

Browse files
Weili Qianherbertx
authored andcommitted
crypto: hisilicon/qm - Put device finding logic into QM
Use struct hisi_qm to maintain device list. Meanwhile, add two external interface into qm, merge find proper device and create qp into QP alloc logic, merge release qps into QP free logic. Signed-off-by: Weili Qian <[email protected]> Signed-off-by: Shukun Tan <[email protected]> Reviewed-by: Zhou Wang <[email protected]> Reviewed-by: Zaibo Xu <[email protected]> Signed-off-by: Herbert Xu <[email protected]>
1 parent 0eae14a commit 3f1ec97

File tree

2 files changed

+156
-0
lines changed

2 files changed

+156
-0
lines changed

drivers/crypto/hisilicon/qm.c

Lines changed: 125 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -272,6 +272,12 @@ struct qm_doorbell {
272272
__le16 priority;
273273
};
274274

275+
struct hisi_qm_resource {
276+
struct hisi_qm *qm;
277+
int distance;
278+
struct list_head list;
279+
};
280+
275281
struct hisi_qm_hw_ops {
276282
int (*get_vft)(struct hisi_qm *qm, u32 *base, u32 *number);
277283
void (*qm_db)(struct hisi_qm *qm, u16 qn,
@@ -2174,6 +2180,125 @@ void hisi_qm_dev_err_uninit(struct hisi_qm *qm)
21742180
}
21752181
EXPORT_SYMBOL_GPL(hisi_qm_dev_err_uninit);
21762182

2183+
/**
2184+
* hisi_qm_free_qps() - free multiple queue pairs.
2185+
* @qps: The queue pairs need to be freed.
2186+
* @qp_num: The num of queue pairs.
2187+
*/
2188+
void hisi_qm_free_qps(struct hisi_qp **qps, int qp_num)
2189+
{
2190+
int i;
2191+
2192+
if (!qps || qp_num <= 0)
2193+
return;
2194+
2195+
for (i = qp_num - 1; i >= 0; i--)
2196+
hisi_qm_release_qp(qps[i]);
2197+
}
2198+
EXPORT_SYMBOL_GPL(hisi_qm_free_qps);
2199+
2200+
static void free_list(struct list_head *head)
2201+
{
2202+
struct hisi_qm_resource *res, *tmp;
2203+
2204+
list_for_each_entry_safe(res, tmp, head, list) {
2205+
list_del(&res->list);
2206+
kfree(res);
2207+
}
2208+
}
2209+
2210+
static int hisi_qm_sort_devices(int node, struct list_head *head,
2211+
struct hisi_qm_list *qm_list)
2212+
{
2213+
struct hisi_qm_resource *res, *tmp;
2214+
struct hisi_qm *qm;
2215+
struct list_head *n;
2216+
struct device *dev;
2217+
int dev_node = 0;
2218+
2219+
list_for_each_entry(qm, &qm_list->list, list) {
2220+
dev = &qm->pdev->dev;
2221+
2222+
if (IS_ENABLED(CONFIG_NUMA)) {
2223+
dev_node = dev_to_node(dev);
2224+
if (dev_node < 0)
2225+
dev_node = 0;
2226+
}
2227+
2228+
res = kzalloc(sizeof(*res), GFP_KERNEL);
2229+
if (!res)
2230+
return -ENOMEM;
2231+
2232+
res->qm = qm;
2233+
res->distance = node_distance(dev_node, node);
2234+
n = head;
2235+
list_for_each_entry(tmp, head, list) {
2236+
if (res->distance < tmp->distance) {
2237+
n = &tmp->list;
2238+
break;
2239+
}
2240+
}
2241+
list_add_tail(&res->list, n);
2242+
}
2243+
2244+
return 0;
2245+
}
2246+
2247+
/**
2248+
* hisi_qm_alloc_qps_node() - Create multiple queue pairs.
2249+
* @qm_list: The list of all available devices.
2250+
* @qp_num: The number of queue pairs need created.
2251+
* @alg_type: The algorithm type.
2252+
* @node: The numa node.
2253+
* @qps: The queue pairs need created.
2254+
*
2255+
* This function will sort all available device according to numa distance.
2256+
* Then try to create all queue pairs from one device, if all devices do
2257+
* not meet the requirements will return error.
2258+
*/
2259+
int hisi_qm_alloc_qps_node(struct hisi_qm_list *qm_list, int qp_num,
2260+
u8 alg_type, int node, struct hisi_qp **qps)
2261+
{
2262+
struct hisi_qm_resource *tmp;
2263+
int ret = -ENODEV;
2264+
LIST_HEAD(head);
2265+
int i;
2266+
2267+
if (!qps || !qm_list || qp_num <= 0)
2268+
return -EINVAL;
2269+
2270+
mutex_lock(&qm_list->lock);
2271+
if (hisi_qm_sort_devices(node, &head, qm_list)) {
2272+
mutex_unlock(&qm_list->lock);
2273+
goto err;
2274+
}
2275+
2276+
list_for_each_entry(tmp, &head, list) {
2277+
for (i = 0; i < qp_num; i++) {
2278+
qps[i] = hisi_qm_create_qp(tmp->qm, alg_type);
2279+
if (IS_ERR(qps[i])) {
2280+
hisi_qm_free_qps(qps, i);
2281+
break;
2282+
}
2283+
}
2284+
2285+
if (i == qp_num) {
2286+
ret = 0;
2287+
break;
2288+
}
2289+
}
2290+
2291+
mutex_unlock(&qm_list->lock);
2292+
if (ret)
2293+
pr_info("Failed to create qps, node[%d], alg[%d], qp[%d]!\n",
2294+
node, alg_type, qp_num);
2295+
2296+
err:
2297+
free_list(&head);
2298+
return ret;
2299+
}
2300+
EXPORT_SYMBOL_GPL(hisi_qm_alloc_qps_node);
2301+
21772302
static pci_ers_result_t qm_dev_err_handle(struct hisi_qm *qm)
21782303
{
21792304
u32 err_sts;

drivers/crypto/hisilicon/qm.h

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -145,6 +145,11 @@ struct hisi_qm_err_ini {
145145
struct hisi_qm_err_info err_info;
146146
};
147147

148+
struct hisi_qm_list {
149+
struct mutex lock;
150+
struct list_head list;
151+
};
152+
148153
struct hisi_qm {
149154
enum qm_hw_ver ver;
150155
enum qm_fun_type fun_type;
@@ -156,6 +161,7 @@ struct hisi_qm {
156161
u32 qp_num;
157162
u32 qp_in_used;
158163
u32 ctrl_qp_num;
164+
struct list_head list;
159165

160166
struct qm_dma qdma;
161167
struct qm_sqc *sqc;
@@ -228,6 +234,28 @@ struct hisi_qp {
228234
struct uacce_queue *uacce_q;
229235
};
230236

237+
static inline void hisi_qm_init_list(struct hisi_qm_list *qm_list)
238+
{
239+
INIT_LIST_HEAD(&qm_list->list);
240+
mutex_init(&qm_list->lock);
241+
}
242+
243+
static inline void hisi_qm_add_to_list(struct hisi_qm *qm,
244+
struct hisi_qm_list *qm_list)
245+
{
246+
mutex_lock(&qm_list->lock);
247+
list_add_tail(&qm->list, &qm_list->list);
248+
mutex_unlock(&qm_list->lock);
249+
}
250+
251+
static inline void hisi_qm_del_from_list(struct hisi_qm *qm,
252+
struct hisi_qm_list *qm_list)
253+
{
254+
mutex_lock(&qm_list->lock);
255+
list_del(&qm->list);
256+
mutex_unlock(&qm_list->lock);
257+
}
258+
231259
int hisi_qm_init(struct hisi_qm *qm);
232260
void hisi_qm_uninit(struct hisi_qm *qm);
233261
int hisi_qm_start(struct hisi_qm *qm);
@@ -258,4 +286,7 @@ struct hisi_acc_sgl_pool *hisi_acc_create_sgl_pool(struct device *dev,
258286
u32 count, u32 sge_nr);
259287
void hisi_acc_free_sgl_pool(struct device *dev,
260288
struct hisi_acc_sgl_pool *pool);
289+
int hisi_qm_alloc_qps_node(struct hisi_qm_list *qm_list, int qp_num,
290+
u8 alg_type, int node, struct hisi_qp **qps);
291+
void hisi_qm_free_qps(struct hisi_qp **qps, int qp_num);
261292
#endif

0 commit comments

Comments
 (0)