1 | /* |
2 | * Copyright (c) 2013-2015, Mellanox Technologies. All rights reserved. |
3 | * |
4 | * This software is available to you under a choice of one of two |
5 | * licenses. You may choose to be licensed under the terms of the GNU |
6 | * General Public License (GPL) Version 2, available from the file |
7 | * COPYING in the main directory of this source tree, or the |
8 | * OpenIB.org BSD license below: |
9 | * |
10 | * Redistribution and use in source and binary forms, with or |
11 | * without modification, are permitted provided that the following |
12 | * conditions are met: |
13 | * |
14 | * - Redistributions of source code must retain the above |
15 | * copyright notice, this list of conditions and the following |
16 | * disclaimer. |
17 | * |
18 | * - Redistributions in binary form must reproduce the above |
19 | * copyright notice, this list of conditions and the following |
20 | * disclaimer in the documentation and/or other materials |
21 | * provided with the distribution. |
22 | * |
23 | * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, |
24 | * EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF |
25 | * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND |
26 | * NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS |
27 | * BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN |
28 | * ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN |
29 | * CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE |
30 | * SOFTWARE. |
31 | */ |
32 | |
33 | #include <linux/kernel.h> |
34 | #include <linux/mlx5/driver.h> |
35 | #include <linux/mlx5/qp.h> |
36 | #include "mlx5_core.h" |
37 | |
38 | int mlx5_core_create_mkey(struct mlx5_core_dev *dev, u32 *mkey, u32 *in, |
39 | int inlen) |
40 | { |
41 | u32 lout[MLX5_ST_SZ_DW(create_mkey_out)] = {}; |
42 | u32 mkey_index; |
43 | int err; |
44 | |
45 | MLX5_SET(create_mkey_in, in, opcode, MLX5_CMD_OP_CREATE_MKEY); |
46 | |
47 | err = mlx5_cmd_exec(dev, in, in_size: inlen, out: lout, out_size: sizeof(lout)); |
48 | if (err) |
49 | return err; |
50 | |
51 | mkey_index = MLX5_GET(create_mkey_out, lout, mkey_index); |
52 | *mkey = MLX5_GET(create_mkey_in, in, memory_key_mkey_entry.mkey_7_0) | |
53 | mlx5_idx_to_mkey(mkey_idx: mkey_index); |
54 | |
55 | mlx5_core_dbg(dev, "out 0x%x, mkey 0x%x\n" , mkey_index, *mkey); |
56 | return 0; |
57 | } |
58 | EXPORT_SYMBOL(mlx5_core_create_mkey); |
59 | |
60 | int mlx5_core_destroy_mkey(struct mlx5_core_dev *dev, u32 mkey) |
61 | { |
62 | u32 in[MLX5_ST_SZ_DW(destroy_mkey_in)] = {}; |
63 | |
64 | MLX5_SET(destroy_mkey_in, in, opcode, MLX5_CMD_OP_DESTROY_MKEY); |
65 | MLX5_SET(destroy_mkey_in, in, mkey_index, mlx5_mkey_to_idx(mkey)); |
66 | return mlx5_cmd_exec_in(dev, destroy_mkey, in); |
67 | } |
68 | EXPORT_SYMBOL(mlx5_core_destroy_mkey); |
69 | |
70 | int mlx5_core_query_mkey(struct mlx5_core_dev *dev, u32 mkey, u32 *out, |
71 | int outlen) |
72 | { |
73 | u32 in[MLX5_ST_SZ_DW(query_mkey_in)] = {}; |
74 | |
75 | memset(out, 0, outlen); |
76 | MLX5_SET(query_mkey_in, in, opcode, MLX5_CMD_OP_QUERY_MKEY); |
77 | MLX5_SET(query_mkey_in, in, mkey_index, mlx5_mkey_to_idx(mkey)); |
78 | return mlx5_cmd_exec(dev, in, in_size: sizeof(in), out, out_size: outlen); |
79 | } |
80 | EXPORT_SYMBOL(mlx5_core_query_mkey); |
81 | |
82 | static inline u32 mlx5_get_psv(u32 *out, int psv_index) |
83 | { |
84 | switch (psv_index) { |
85 | case 1: return MLX5_GET(create_psv_out, out, psv1_index); |
86 | case 2: return MLX5_GET(create_psv_out, out, psv2_index); |
87 | case 3: return MLX5_GET(create_psv_out, out, psv3_index); |
88 | default: return MLX5_GET(create_psv_out, out, psv0_index); |
89 | } |
90 | } |
91 | |
92 | int mlx5_core_create_psv(struct mlx5_core_dev *dev, u32 pdn, |
93 | int npsvs, u32 *sig_index) |
94 | { |
95 | u32 out[MLX5_ST_SZ_DW(create_psv_out)] = {}; |
96 | u32 in[MLX5_ST_SZ_DW(create_psv_in)] = {}; |
97 | int i, err; |
98 | |
99 | if (npsvs > MLX5_MAX_PSVS) |
100 | return -EINVAL; |
101 | |
102 | MLX5_SET(create_psv_in, in, opcode, MLX5_CMD_OP_CREATE_PSV); |
103 | MLX5_SET(create_psv_in, in, pd, pdn); |
104 | MLX5_SET(create_psv_in, in, num_psv, npsvs); |
105 | |
106 | err = mlx5_cmd_exec_inout(dev, create_psv, in, out); |
107 | if (err) |
108 | return err; |
109 | |
110 | for (i = 0; i < npsvs; i++) |
111 | sig_index[i] = mlx5_get_psv(out, psv_index: i); |
112 | |
113 | return err; |
114 | } |
115 | EXPORT_SYMBOL(mlx5_core_create_psv); |
116 | |
117 | int mlx5_core_destroy_psv(struct mlx5_core_dev *dev, int psv_num) |
118 | { |
119 | u32 in[MLX5_ST_SZ_DW(destroy_psv_in)] = {}; |
120 | |
121 | MLX5_SET(destroy_psv_in, in, opcode, MLX5_CMD_OP_DESTROY_PSV); |
122 | MLX5_SET(destroy_psv_in, in, psvn, psv_num); |
123 | return mlx5_cmd_exec_in(dev, destroy_psv, in); |
124 | } |
125 | EXPORT_SYMBOL(mlx5_core_destroy_psv); |
126 | |
127 | __be32 mlx5_core_get_terminate_scatter_list_mkey(struct mlx5_core_dev *dev) |
128 | { |
129 | u32 out[MLX5_ST_SZ_DW(query_special_contexts_out)] = {}; |
130 | u32 in[MLX5_ST_SZ_DW(query_special_contexts_in)] = {}; |
131 | u32 mkey; |
132 | |
133 | if (!MLX5_CAP_GEN(dev, terminate_scatter_list_mkey)) |
134 | return MLX5_TERMINATE_SCATTER_LIST_LKEY; |
135 | |
136 | MLX5_SET(query_special_contexts_in, in, opcode, |
137 | MLX5_CMD_OP_QUERY_SPECIAL_CONTEXTS); |
138 | if (mlx5_cmd_exec_inout(dev, query_special_contexts, in, out)) |
139 | return MLX5_TERMINATE_SCATTER_LIST_LKEY; |
140 | |
141 | mkey = MLX5_GET(query_special_contexts_out, out, |
142 | terminate_scatter_list_mkey); |
143 | return cpu_to_be32(mkey); |
144 | } |
145 | EXPORT_SYMBOL(mlx5_core_get_terminate_scatter_list_mkey); |
146 | |