1 /* SPDX-License-Identifier: BSD-3-Clause 2 * Copyright 2020 Mellanox Technologies, Ltd 3 */ 4 5 #ifndef RTE_PMD_MLX5_COMMON_OS_H_ 6 #define RTE_PMD_MLX5_COMMON_OS_H_ 7 8 #include <stdio.h> 9 #include <malloc.h> 10 11 #include <rte_compat.h> 12 #include <rte_pci.h> 13 #include <bus_pci_driver.h> 14 #include <rte_debug.h> 15 #include <rte_atomic.h> 16 #include <rte_log.h> 17 #include <rte_kvargs.h> 18 #include <rte_devargs.h> 19 #include <rte_interrupts.h> 20 21 #include "mlx5_autoconf.h" 22 #include "mlx5_glue.h" 23 #include "mlx5_malloc.h" 24 25 /** 26 * Get device name. Given an ibv_device pointer - return a 27 * pointer to the corresponding device name. 28 * 29 * @param[in] dev 30 * Pointer to ibv device. 31 * 32 * @return 33 * Pointer to device name if dev is valid, NULL otherwise. 34 */ 35 static inline const char * 36 mlx5_os_get_dev_device_name(void *dev) 37 { 38 if (!dev) 39 return NULL; 40 return ((struct ibv_device *)dev)->name; 41 } 42 43 /** 44 * Get ibv device name. Given an ibv_context pointer - return a 45 * pointer to the corresponding device name. 46 * 47 * @param[in] ctx 48 * Pointer to ibv context. 49 * 50 * @return 51 * Pointer to device name if ctx is valid, NULL otherwise. 52 */ 53 static inline const char * 54 mlx5_os_get_ctx_device_name(void *ctx) 55 { 56 if (!ctx) 57 return NULL; 58 return ((struct ibv_context *)ctx)->device->name; 59 } 60 61 /** 62 * Get ibv device path name. Given an ibv_context pointer - return a 63 * pointer to the corresponding device path name. 64 * 65 * @param[in] ctx 66 * Pointer to ibv context. 67 * 68 * @return 69 * Pointer to device path name if ctx is valid, NULL otherwise. 70 */ 71 72 static inline const char * 73 mlx5_os_get_ctx_device_path(void *ctx) 74 { 75 if (!ctx) 76 return NULL; 77 78 return ((struct ibv_context *)ctx)->device->ibdev_path; 79 } 80 81 /** 82 * Get umem id. Given a pointer to umem object of type 83 * 'struct mlx5dv_devx_umem *' - return its id. 84 * 85 * @param[in] umem 86 * Pointer to umem object. 87 * 88 * @return 89 * The umem id if umem is valid, 0 otherwise. 90 */ 91 static inline uint32_t 92 mlx5_os_get_umem_id(void *umem) 93 { 94 if (!umem) 95 return 0; 96 return ((struct mlx5dv_devx_umem *)umem)->umem_id; 97 } 98 99 /** 100 * Get fd. Given a pointer to DevX channel object of type 101 * 'struct mlx5dv_devx_event_channel*' - return its fd. 102 * 103 * @param[in] channel 104 * Pointer to channel object. 105 * 106 * @return 107 * The fd if channel is valid, 0 otherwise. 108 */ 109 static inline int 110 mlx5_os_get_devx_channel_fd(void *channel) 111 { 112 if (!channel) 113 return 0; 114 return ((struct mlx5dv_devx_event_channel *)channel)->fd; 115 } 116 117 /** 118 * Get mmap offset. Given a pointer to an DevX UAR object of type 119 * 'struct mlx5dv_devx_uar *' - return its mmap offset. 120 * 121 * @param[in] uar 122 * Pointer to UAR object. 123 * 124 * @return 125 * The mmap offset if uar is valid, 0 otherwise. 126 */ 127 static inline off_t 128 mlx5_os_get_devx_uar_mmap_offset(void *uar) 129 { 130 #ifdef HAVE_MLX5DV_DEVX_UAR_OFFSET 131 if (!uar) 132 return 0; 133 return ((struct mlx5dv_devx_uar *)uar)->mmap_off; 134 #else 135 RTE_SET_USED(uar); 136 return 0; 137 #endif 138 } 139 140 /** 141 * Get base addr pointer. Given a pointer to an UAR object of type 142 * 'struct mlx5dv_devx_uar *' - return its base address. 143 * 144 * @param[in] uar 145 * Pointer to an UAR object. 146 * 147 * @return 148 * The base address if UAR is valid, 0 otherwise. 149 */ 150 static inline void * 151 mlx5_os_get_devx_uar_base_addr(void *uar) 152 { 153 #ifdef HAVE_MLX5DV_DEVX_UAR_OFFSET 154 if (!uar) 155 return NULL; 156 return ((struct mlx5dv_devx_uar *)uar)->base_addr; 157 #else 158 RTE_SET_USED(uar); 159 return NULL; 160 #endif 161 } 162 163 /** 164 * Get reg addr pointer. Given a pointer to an UAR object of type 165 * 'struct mlx5dv_devx_uar *' - return its reg address. 166 * 167 * @param[in] uar 168 * Pointer to an UAR object. 169 * 170 * @return 171 * The reg address if UAR is valid, 0 otherwise. 172 */ 173 static inline void * 174 mlx5_os_get_devx_uar_reg_addr(void *uar) 175 { 176 #ifdef HAVE_MLX5DV_DEVX_UAR_OFFSET 177 if (!uar) 178 return NULL; 179 return ((struct mlx5dv_devx_uar *)uar)->reg_addr; 180 #else 181 RTE_SET_USED(uar); 182 return NULL; 183 #endif 184 } 185 186 /** 187 * Get page id. Given a pointer to an UAR object of type 188 * 'struct mlx5dv_devx_uar *' - return its page id. 189 * 190 * @param[in] uar 191 * Pointer to an UAR object. 192 * 193 * @return 194 * The page id if UAR is valid, 0 otherwise. 195 */ 196 static inline uint32_t 197 mlx5_os_get_devx_uar_page_id(void *uar) 198 { 199 #ifdef HAVE_MLX5DV_DEVX_UAR_OFFSET 200 if (!uar) 201 return 0; 202 return ((struct mlx5dv_devx_uar *)uar)->page_id; 203 #else 204 RTE_SET_USED(uar); 205 return 0; 206 #endif 207 } 208 209 __rte_internal 210 static inline void * 211 mlx5_os_umem_reg(void *ctx, void *addr, size_t size, uint32_t access) 212 { 213 return mlx5_glue->devx_umem_reg(ctx, addr, size, access); 214 } 215 216 __rte_internal 217 static inline int 218 mlx5_os_umem_dereg(void *pumem) 219 { 220 return mlx5_glue->devx_umem_dereg(pumem); 221 } 222 223 static inline void * 224 mlx5_os_devx_create_event_channel(void *ctx, int flags) 225 { 226 return mlx5_glue->devx_create_event_channel(ctx, flags); 227 } 228 229 static inline void 230 mlx5_os_devx_destroy_event_channel(void *eventc) 231 { 232 mlx5_glue->devx_destroy_event_channel(eventc); 233 } 234 235 static inline int 236 mlx5_os_devx_subscribe_devx_event(void *eventc, 237 void *obj, 238 uint16_t events_sz, uint16_t events_num[], 239 uint64_t cookie) 240 { 241 return mlx5_glue->devx_subscribe_devx_event(eventc, obj, events_sz, 242 events_num, cookie); 243 } 244 245 /** 246 * Memory allocation optionally with alignment. 247 * 248 * @param[in] align 249 * Alignment size (may be zero) 250 * @param[in] size 251 * Size in bytes to allocate 252 * 253 * @return 254 * Valid pointer to allocated memory, NULL in case of failure 255 */ 256 static inline void * 257 mlx5_os_malloc(size_t align, size_t size) 258 { 259 void *buf; 260 261 if (posix_memalign(&buf, align, size)) 262 return NULL; 263 return buf; 264 } 265 266 /** 267 * This API de-allocates a memory that originally could have been 268 * allocated aligned or non-aligned. In Linux it is a wrapper 269 * around free(). 270 * 271 * @param[in] addr 272 * Pointer to address to free 273 * 274 */ 275 static inline void 276 mlx5_os_free(void *addr) 277 { 278 free(addr); 279 } 280 281 void 282 mlx5_set_context_attr(struct rte_device *dev, struct ibv_context *ctx); 283 284 /** 285 * This is used to query system_image_guid as describing in PRM. 286 * 287 * @param dev[in] 288 * Pointer to a device instance as PCIe id. 289 * @param guid[out] 290 * Pointer to the buffer to hold device guid. 291 * Guid is uint64_t and corresponding to 17 bytes string. 292 * @param len[in] 293 * Guid buffer length, 17 bytes at least. 294 * 295 * @return 296 * -1 if internal failure. 297 * 0 if OFED doesn't support. 298 * >0 if success. 299 */ 300 __rte_internal 301 int 302 mlx5_get_device_guid(const struct rte_pci_addr *dev, uint8_t *guid, size_t len); 303 304 __rte_internal 305 struct rte_intr_handle * 306 mlx5_os_interrupt_handler_create(int mode, bool set_fd_nonblock, int fd, 307 rte_intr_callback_fn cb, void *cb_arg); 308 309 __rte_internal 310 void 311 mlx5_os_interrupt_handler_destroy(struct rte_intr_handle *intr_handle, 312 rte_intr_callback_fn cb, void *cb_arg); 313 314 #endif /* RTE_PMD_MLX5_COMMON_OS_H_ */ 315