198c4a35cSTomasz Jozwiak /* SPDX-License-Identifier: BSD-3-Clause 2e0a67610SKai Ji * Copyright(c) 2018-2022 Intel Corporation 398c4a35cSTomasz Jozwiak */ 498c4a35cSTomasz Jozwiak 590f5eedeSFiona Trahe #include <rte_string_fns.h> 647c3f7a4SArek Kusztal #include <rte_devargs.h> 747c3f7a4SArek Kusztal #include <ctype.h> 890f5eedeSFiona Trahe 998c4a35cSTomasz Jozwiak #include "qat_device.h" 1098c4a35cSTomasz Jozwiak #include "adf_transport_access_macros.h" 11e0a67610SKai Ji #include "qat_sym.h" 12a124830aSFiona Trahe #include "qat_comp_pmd.h" 13b17d16fbSArek Kusztal #include "adf_pf2vf_msg.h" 14c546d6e3SArek Kusztal #include "qat_pf2vf.h" 15b17d16fbSArek Kusztal 167b1374b1SArkadiusz Kusztal #define NOT_NULL(arg, func, msg, ...) \ 177b1374b1SArkadiusz Kusztal do { \ 187b1374b1SArkadiusz Kusztal if (arg == NULL) { \ 197b1374b1SArkadiusz Kusztal QAT_LOG(ERR, \ 207b1374b1SArkadiusz Kusztal msg, ##__VA_ARGS__); \ 217b1374b1SArkadiusz Kusztal func; \ 227b1374b1SArkadiusz Kusztal } \ 237b1374b1SArkadiusz Kusztal } while (0) 247b1374b1SArkadiusz Kusztal 2504dd78d1SFan Zhang /* Hardware device information per generation */ 2604dd78d1SFan Zhang struct qat_gen_hw_data qat_gen_config[QAT_N_GENS]; 2704dd78d1SFan Zhang struct qat_dev_hw_spec_funcs *qat_dev_hw_spec[QAT_N_GENS]; 2804dd78d1SFan Zhang 29477d7d05SArkadiusz Kusztal struct qat_service qat_service[QAT_MAX_SERVICES]; 30477d7d05SArkadiusz Kusztal 319904ff68SArek Kusztal /* per-process array of device data */ 329904ff68SArek Kusztal struct qat_device_info qat_pci_devs[RTE_PMD_QAT_MAX_PCI_DEVICES]; 3398c4a35cSTomasz Jozwiak static int qat_nb_pci_devices; 3498c4a35cSTomasz Jozwiak 3598c4a35cSTomasz Jozwiak /* 3698c4a35cSTomasz Jozwiak * The set of PCI devices this driver supports 3798c4a35cSTomasz Jozwiak */ 3898c4a35cSTomasz Jozwiak 3998c4a35cSTomasz Jozwiak static const struct rte_pci_id pci_id_qat_map[] = { 4098c4a35cSTomasz Jozwiak { 4198c4a35cSTomasz Jozwiak RTE_PCI_DEVICE(0x8086, 0x0443), 4298c4a35cSTomasz Jozwiak }, 4398c4a35cSTomasz Jozwiak { 4498c4a35cSTomasz Jozwiak RTE_PCI_DEVICE(0x8086, 0x37c9), 4598c4a35cSTomasz Jozwiak }, 4698c4a35cSTomasz Jozwiak { 4798c4a35cSTomasz Jozwiak RTE_PCI_DEVICE(0x8086, 0x19e3), 4898c4a35cSTomasz Jozwiak }, 4998c4a35cSTomasz Jozwiak { 5098c4a35cSTomasz Jozwiak RTE_PCI_DEVICE(0x8086, 0x6f55), 5198c4a35cSTomasz Jozwiak }, 521f5e4053SFiona Trahe { 537b08003bSAdam Dybkowski RTE_PCI_DEVICE(0x8086, 0x18ef), 547b08003bSAdam Dybkowski }, 557b08003bSAdam Dybkowski { 561f5e4053SFiona Trahe RTE_PCI_DEVICE(0x8086, 0x18a1), 571f5e4053SFiona Trahe }, 588f393c4fSArek Kusztal { 59f925068aSCiara Power RTE_PCI_DEVICE(0x8086, 0x578b), 60f925068aSCiara Power }, 61f925068aSCiara Power { 628f393c4fSArek Kusztal RTE_PCI_DEVICE(0x8086, 0x4941), 638f393c4fSArek Kusztal }, 64f4eac3a0SArek Kusztal { 65f4eac3a0SArek Kusztal RTE_PCI_DEVICE(0x8086, 0x4943), 66f4eac3a0SArek Kusztal }, 674728d843SCiara Power { 684728d843SCiara Power RTE_PCI_DEVICE(0x8086, 0x4945), 694728d843SCiara Power }, 7059cda512SCiara Power { 7159cda512SCiara Power RTE_PCI_DEVICE(0x8086, 0x4947), 7259cda512SCiara Power }, 73e9271821SNishikant Nayak { 74e9271821SNishikant Nayak RTE_PCI_DEVICE(0x8086, 0x1454), 75e9271821SNishikant Nayak }, 762e98e808SArkadiusz Kusztal { 772e98e808SArkadiusz Kusztal RTE_PCI_DEVICE(0x8086, 0x0da5), 782e98e808SArkadiusz Kusztal }, 7998c4a35cSTomasz Jozwiak {.device_id = 0}, 8098c4a35cSTomasz Jozwiak }; 8198c4a35cSTomasz Jozwiak 825438e4ecSFan Zhang static int 835438e4ecSFan Zhang qat_pci_get_extra_size(enum qat_device_gen qat_dev_gen) 845438e4ecSFan Zhang { 855438e4ecSFan Zhang struct qat_dev_hw_spec_funcs *ops_hw = 865438e4ecSFan Zhang qat_dev_hw_spec[qat_dev_gen]; 878f1d23ecSDavid Marchand if (ops_hw->qat_dev_get_extra_size == NULL) 888f1d23ecSDavid Marchand return -ENOTSUP; 895438e4ecSFan Zhang return ops_hw->qat_dev_get_extra_size(); 905438e4ecSFan Zhang } 915438e4ecSFan Zhang 9298c4a35cSTomasz Jozwiak static struct qat_pci_device * 9398c4a35cSTomasz Jozwiak qat_pci_get_named_dev(const char *name) 9498c4a35cSTomasz Jozwiak { 9598c4a35cSTomasz Jozwiak unsigned int i; 9698c4a35cSTomasz Jozwiak 9798c4a35cSTomasz Jozwiak if (name == NULL) 9898c4a35cSTomasz Jozwiak return NULL; 9998c4a35cSTomasz Jozwiak 10098c4a35cSTomasz Jozwiak for (i = 0; i < RTE_PMD_QAT_MAX_PCI_DEVICES; i++) { 1019904ff68SArek Kusztal if (qat_pci_devs[i].mz && 1029904ff68SArek Kusztal (strcmp(((struct qat_pci_device *) 1039904ff68SArek Kusztal qat_pci_devs[i].mz->addr)->name, name) 1049904ff68SArek Kusztal == 0)) 1059904ff68SArek Kusztal return (struct qat_pci_device *) 1069904ff68SArek Kusztal qat_pci_devs[i].mz->addr; 10798c4a35cSTomasz Jozwiak } 10898c4a35cSTomasz Jozwiak 10998c4a35cSTomasz Jozwiak return NULL; 11098c4a35cSTomasz Jozwiak } 11198c4a35cSTomasz Jozwiak 11298c4a35cSTomasz Jozwiak static uint8_t 11398c4a35cSTomasz Jozwiak qat_pci_find_free_device_index(void) 11498c4a35cSTomasz Jozwiak { 11598c4a35cSTomasz Jozwiak uint8_t dev_id; 11698c4a35cSTomasz Jozwiak 1179904ff68SArek Kusztal for (dev_id = 0; dev_id < RTE_PMD_QAT_MAX_PCI_DEVICES; 1189904ff68SArek Kusztal dev_id++) { 1199904ff68SArek Kusztal if (qat_pci_devs[dev_id].mz == NULL) 12098c4a35cSTomasz Jozwiak break; 12198c4a35cSTomasz Jozwiak } 12298c4a35cSTomasz Jozwiak return dev_id; 12398c4a35cSTomasz Jozwiak } 12498c4a35cSTomasz Jozwiak 125477d7d05SArkadiusz Kusztal static struct qat_pci_device * 12698c4a35cSTomasz Jozwiak qat_get_qat_dev_from_pci_dev(struct rte_pci_device *pci_dev) 12798c4a35cSTomasz Jozwiak { 12898c4a35cSTomasz Jozwiak char name[QAT_DEV_NAME_MAX_LEN]; 12998c4a35cSTomasz Jozwiak 13098c4a35cSTomasz Jozwiak rte_pci_device_name(&pci_dev->addr, name, sizeof(name)); 13198c4a35cSTomasz Jozwiak 13298c4a35cSTomasz Jozwiak return qat_pci_get_named_dev(name); 13398c4a35cSTomasz Jozwiak } 13498c4a35cSTomasz Jozwiak 1357b1374b1SArkadiusz Kusztal static enum qat_device_gen 1367b1374b1SArkadiusz Kusztal pick_gen(const struct rte_pci_device *pci_dev) 1377b1374b1SArkadiusz Kusztal { 1387b1374b1SArkadiusz Kusztal switch (pci_dev->id.device_id) { 1397b1374b1SArkadiusz Kusztal case 0x0443: 1407b1374b1SArkadiusz Kusztal return QAT_GEN1; 1417b1374b1SArkadiusz Kusztal case 0x37c9: 1427b1374b1SArkadiusz Kusztal case 0x19e3: 1437b1374b1SArkadiusz Kusztal case 0x6f55: 1447b1374b1SArkadiusz Kusztal case 0x18ef: 1457b1374b1SArkadiusz Kusztal return QAT_GEN2; 1467b1374b1SArkadiusz Kusztal case 0x18a1: 147f925068aSCiara Power case 0x578b: 1487b1374b1SArkadiusz Kusztal return QAT_GEN3; 1497b1374b1SArkadiusz Kusztal case 0x4941: 1507b1374b1SArkadiusz Kusztal case 0x4943: 1517b1374b1SArkadiusz Kusztal case 0x4945: 1527b1374b1SArkadiusz Kusztal return QAT_GEN4; 15359cda512SCiara Power case 0x4947: 15459cda512SCiara Power return QAT_GEN5; 155e9271821SNishikant Nayak case 0x1454: 156e9271821SNishikant Nayak return QAT_GEN_LCE; 1572e98e808SArkadiusz Kusztal case 0x0da5: 1582e98e808SArkadiusz Kusztal return QAT_VQAT; 1597b1374b1SArkadiusz Kusztal default: 1607b1374b1SArkadiusz Kusztal QAT_LOG(ERR, "Invalid dev_id, can't determine generation"); 1617b1374b1SArkadiusz Kusztal return QAT_N_GENS; 1627b1374b1SArkadiusz Kusztal } 1637b1374b1SArkadiusz Kusztal } 1647b1374b1SArkadiusz Kusztal 165f925068aSCiara Power static int 166f925068aSCiara Power wireless_slice_support(uint16_t pci_dev_id) 167f925068aSCiara Power { 16859cda512SCiara Power return pci_dev_id == 0x578b || 16959cda512SCiara Power pci_dev_id == 0x4947; 170f925068aSCiara Power } 171f925068aSCiara Power 17299ab2806SArkadiusz Kusztal /* This function base on the atoi function peculiarity, non integral part 17399ab2806SArkadiusz Kusztal * other than the equals sign is ignored. It will not work with other conversion 17499ab2806SArkadiusz Kusztal * functions like strt*. 17599ab2806SArkadiusz Kusztal */ 17699ab2806SArkadiusz Kusztal char *qat_dev_cmdline_get_val(struct qat_pci_device *qat_dev, 17799ab2806SArkadiusz Kusztal const char *key) 17899ab2806SArkadiusz Kusztal { 17999ab2806SArkadiusz Kusztal if (qat_dev->command_line == NULL) 18099ab2806SArkadiusz Kusztal return NULL; 18199ab2806SArkadiusz Kusztal key = strstr(qat_dev->command_line, key); 18299ab2806SArkadiusz Kusztal /* At this point, a key should be validated */ 18399ab2806SArkadiusz Kusztal return key ? strchr(key, '=') + 1 : NULL; 18499ab2806SArkadiusz Kusztal } 18599ab2806SArkadiusz Kusztal 18699ab2806SArkadiusz Kusztal static int cmdline_validate(const char *arg) 18799ab2806SArkadiusz Kusztal { 18899ab2806SArkadiusz Kusztal int i, len; 18999ab2806SArkadiusz Kusztal char *eq_sign = strchr(arg, '='); 19099ab2806SArkadiusz Kusztal /* Check for the equal sign */ 19199ab2806SArkadiusz Kusztal if (eq_sign == NULL) { 19299ab2806SArkadiusz Kusztal QAT_LOG(ERR, "malformed string, no equals sign, %s", arg); 19399ab2806SArkadiusz Kusztal return 0; 19499ab2806SArkadiusz Kusztal } 19599ab2806SArkadiusz Kusztal /* Check if an argument is not empty */ 19699ab2806SArkadiusz Kusztal len = strlen(eq_sign) - 1; 19799ab2806SArkadiusz Kusztal if (len == 0) { 19899ab2806SArkadiusz Kusztal QAT_LOG(ERR, "malformed string, empty argument, %s", arg); 19999ab2806SArkadiusz Kusztal return 0; 20099ab2806SArkadiusz Kusztal } 20199ab2806SArkadiusz Kusztal len = eq_sign - arg; 20299ab2806SArkadiusz Kusztal for (i = 0; i < QAT_MAX_SERVICES + 1; i++) { 20399ab2806SArkadiusz Kusztal int j = 0; 20499ab2806SArkadiusz Kusztal const char *def = NULL; 20599ab2806SArkadiusz Kusztal 20699ab2806SArkadiusz Kusztal if (!qat_cmdline_defines[i]) 20799ab2806SArkadiusz Kusztal continue; 20899ab2806SArkadiusz Kusztal while ((def = qat_cmdline_defines[i][j++])) { 20999ab2806SArkadiusz Kusztal if (strncmp(def, arg, len)) 21099ab2806SArkadiusz Kusztal continue; 21199ab2806SArkadiusz Kusztal QAT_LOG(DEBUG, "Found %s command line argument", 21299ab2806SArkadiusz Kusztal def); 21399ab2806SArkadiusz Kusztal return 1; 21499ab2806SArkadiusz Kusztal } 21599ab2806SArkadiusz Kusztal } 21699ab2806SArkadiusz Kusztal return 0; 21799ab2806SArkadiusz Kusztal } 21899ab2806SArkadiusz Kusztal 21999ab2806SArkadiusz Kusztal static int 22099ab2806SArkadiusz Kusztal qat_dev_parse_command_line(struct qat_pci_device *qat_dev, 22199ab2806SArkadiusz Kusztal struct rte_devargs *devargs) 22299ab2806SArkadiusz Kusztal { 22399ab2806SArkadiusz Kusztal int len = 0; 22499ab2806SArkadiusz Kusztal char *token = NULL; 22599ab2806SArkadiusz Kusztal 22699ab2806SArkadiusz Kusztal if (!devargs) 22799ab2806SArkadiusz Kusztal return 0; 22899ab2806SArkadiusz Kusztal 22999ab2806SArkadiusz Kusztal len = strlen(devargs->drv_str); 23099ab2806SArkadiusz Kusztal if (len == 0) 23199ab2806SArkadiusz Kusztal return 0; 23299ab2806SArkadiusz Kusztal /* Allocate per-device command line */ 23399ab2806SArkadiusz Kusztal qat_dev->command_line = rte_malloc(NULL, len, 0); 23499ab2806SArkadiusz Kusztal if (qat_dev->command_line == NULL) { 23599ab2806SArkadiusz Kusztal QAT_LOG(ERR, "Cannot allocate memory for command line"); 23699ab2806SArkadiusz Kusztal return -1; 23799ab2806SArkadiusz Kusztal } 23899ab2806SArkadiusz Kusztal strcpy(qat_dev->command_line, devargs->drv_str); 23999ab2806SArkadiusz Kusztal token = strtok(qat_dev->command_line, ","); 24099ab2806SArkadiusz Kusztal while (token != NULL) { 24199ab2806SArkadiusz Kusztal if (!cmdline_validate(token)) { 24299ab2806SArkadiusz Kusztal QAT_LOG(ERR, "Incorrect command line argument: %s", 24399ab2806SArkadiusz Kusztal token); 24499ab2806SArkadiusz Kusztal return -1; 24599ab2806SArkadiusz Kusztal } 24699ab2806SArkadiusz Kusztal token = strtok(NULL, ","); 24799ab2806SArkadiusz Kusztal } 24899ab2806SArkadiusz Kusztal /* Copy once againe the entire string, strtok already altered the contents */ 24999ab2806SArkadiusz Kusztal strcpy(qat_dev->command_line, devargs->drv_str); 25099ab2806SArkadiusz Kusztal return 0; 25199ab2806SArkadiusz Kusztal } 25299ab2806SArkadiusz Kusztal 25399ab2806SArkadiusz Kusztal static struct qat_pci_device * 25499ab2806SArkadiusz Kusztal qat_pci_device_allocate(struct rte_pci_device *pci_dev) 25598c4a35cSTomasz Jozwiak { 25698c4a35cSTomasz Jozwiak struct qat_pci_device *qat_dev; 2575438e4ecSFan Zhang enum qat_device_gen qat_dev_gen; 2589904ff68SArek Kusztal uint8_t qat_dev_id = 0; 25998c4a35cSTomasz Jozwiak char name[QAT_DEV_NAME_MAX_LEN]; 26047c3f7a4SArek Kusztal struct rte_devargs *devargs = pci_dev->device.devargs; 2615438e4ecSFan Zhang struct qat_dev_hw_spec_funcs *ops_hw; 2625438e4ecSFan Zhang struct rte_mem_resource *mem_resource; 2635438e4ecSFan Zhang const struct rte_memzone *qat_dev_mz; 2645438e4ecSFan Zhang int qat_dev_size, extra_size; 26599ab2806SArkadiusz Kusztal char *cmdline = NULL; 26698c4a35cSTomasz Jozwiak 26798c4a35cSTomasz Jozwiak rte_pci_device_name(&pci_dev->addr, name, sizeof(name)); 26898c4a35cSTomasz Jozwiak snprintf(name+strlen(name), QAT_DEV_NAME_MAX_LEN-strlen(name), "_qat"); 2699904ff68SArek Kusztal 2707b1374b1SArkadiusz Kusztal qat_dev_gen = pick_gen(pci_dev); 2717b1374b1SArkadiusz Kusztal if (qat_dev_gen == QAT_N_GENS) { 2725438e4ecSFan Zhang QAT_LOG(ERR, "Invalid dev_id, can't determine generation"); 2735438e4ecSFan Zhang return NULL; 2745438e4ecSFan Zhang } 2755438e4ecSFan Zhang 2769904ff68SArek Kusztal if (rte_eal_process_type() == RTE_PROC_SECONDARY) { 2779904ff68SArek Kusztal const struct rte_memzone *mz = rte_memzone_lookup(name); 2789904ff68SArek Kusztal 2799904ff68SArek Kusztal if (mz == NULL) { 2809904ff68SArek Kusztal QAT_LOG(ERR, 2819904ff68SArek Kusztal "Secondary can't find %s mz, did primary create device?", 2829904ff68SArek Kusztal name); 2839904ff68SArek Kusztal return NULL; 2849904ff68SArek Kusztal } 2859904ff68SArek Kusztal qat_dev = mz->addr; 2869904ff68SArek Kusztal qat_pci_devs[qat_dev->qat_dev_id].mz = mz; 2879904ff68SArek Kusztal qat_pci_devs[qat_dev->qat_dev_id].pci_dev = pci_dev; 2889904ff68SArek Kusztal qat_nb_pci_devices++; 2899904ff68SArek Kusztal QAT_LOG(DEBUG, "QAT device %d found, name %s, total QATs %d", 2909904ff68SArek Kusztal qat_dev->qat_dev_id, qat_dev->name, qat_nb_pci_devices); 2919904ff68SArek Kusztal return qat_dev; 2929904ff68SArek Kusztal } 2939904ff68SArek Kusztal 29498c4a35cSTomasz Jozwiak if (qat_pci_get_named_dev(name) != NULL) { 29598c4a35cSTomasz Jozwiak QAT_LOG(ERR, "QAT device with name %s already allocated!", 29698c4a35cSTomasz Jozwiak name); 29798c4a35cSTomasz Jozwiak return NULL; 29898c4a35cSTomasz Jozwiak } 29998c4a35cSTomasz Jozwiak 30098c4a35cSTomasz Jozwiak qat_dev_id = qat_pci_find_free_device_index(); 30198c4a35cSTomasz Jozwiak if (qat_dev_id == RTE_PMD_QAT_MAX_PCI_DEVICES) { 30298c4a35cSTomasz Jozwiak QAT_LOG(ERR, "Reached maximum number of QAT devices"); 30398c4a35cSTomasz Jozwiak return NULL; 30498c4a35cSTomasz Jozwiak } 30598c4a35cSTomasz Jozwiak 3065438e4ecSFan Zhang extra_size = qat_pci_get_extra_size(qat_dev_gen); 3075438e4ecSFan Zhang if (extra_size < 0) { 3085438e4ecSFan Zhang QAT_LOG(ERR, "QAT internal error: no pci pointer for gen %d", 3095438e4ecSFan Zhang qat_dev_gen); 3105438e4ecSFan Zhang return NULL; 3115438e4ecSFan Zhang } 3125438e4ecSFan Zhang 313477d7d05SArkadiusz Kusztal qat_dev_size = sizeof(struct qat_pci_device) + sizeof(void *) * 314477d7d05SArkadiusz Kusztal QAT_MAX_SERVICES + extra_size; 3155438e4ecSFan Zhang qat_dev_mz = rte_memzone_reserve(name, qat_dev_size, 3169904ff68SArek Kusztal rte_socket_id(), 0); 3179904ff68SArek Kusztal 3185438e4ecSFan Zhang if (qat_dev_mz == NULL) { 3199904ff68SArek Kusztal QAT_LOG(ERR, "Error when allocating memzone for QAT_%d", 3209904ff68SArek Kusztal qat_dev_id); 3219904ff68SArek Kusztal return NULL; 3229904ff68SArek Kusztal } 3239904ff68SArek Kusztal 3245438e4ecSFan Zhang qat_dev = qat_dev_mz->addr; 3255438e4ecSFan Zhang memset(qat_dev, 0, qat_dev_size); 3265438e4ecSFan Zhang qat_dev->dev_private = qat_dev + 1; 32790f5eedeSFiona Trahe strlcpy(qat_dev->name, name, QAT_DEV_NAME_MAX_LEN); 32898c4a35cSTomasz Jozwiak qat_dev->qat_dev_id = qat_dev_id; 3295438e4ecSFan Zhang qat_dev->qat_dev_gen = qat_dev_gen; 3302e98e808SArkadiusz Kusztal qat_pci_devs[qat_dev_id].pci_dev = pci_dev; 33198c4a35cSTomasz Jozwiak 332f925068aSCiara Power if (wireless_slice_support(pci_dev->id.device_id)) 333b7bd72d8SArkadiusz Kusztal qat_dev->options.has_wireless_slice = 1; 334f925068aSCiara Power 3355438e4ecSFan Zhang ops_hw = qat_dev_hw_spec[qat_dev->qat_dev_gen]; 3367b1374b1SArkadiusz Kusztal NOT_NULL(ops_hw->qat_dev_get_misc_bar, goto error, 3377b1374b1SArkadiusz Kusztal "QAT internal error! qat_dev_get_misc_bar function not set"); 3385438e4ecSFan Zhang if (ops_hw->qat_dev_get_misc_bar(&mem_resource, pci_dev) == 0) { 3395438e4ecSFan Zhang if (mem_resource->addr == NULL) { 3405438e4ecSFan Zhang QAT_LOG(ERR, "QAT cannot get access to VF misc bar"); 3417b1374b1SArkadiusz Kusztal goto error; 342b17d16fbSArek Kusztal } 3435438e4ecSFan Zhang qat_dev->misc_bar_io_addr = mem_resource->addr; 3445438e4ecSFan Zhang } else 3455438e4ecSFan Zhang qat_dev->misc_bar_io_addr = NULL; 346b17d16fbSArek Kusztal 34799ab2806SArkadiusz Kusztal /* Parse the command line */ 34899ab2806SArkadiusz Kusztal if (qat_dev_parse_command_line(qat_dev, devargs)) 34999ab2806SArkadiusz Kusztal goto error; 35099ab2806SArkadiusz Kusztal 35199ab2806SArkadiusz Kusztal /* Parse the arguments */ 35299ab2806SArkadiusz Kusztal cmdline = qat_dev_cmdline_get_val(qat_dev, QAT_LEGACY_CAPA); 35399ab2806SArkadiusz Kusztal if (cmdline) 354b7bd72d8SArkadiusz Kusztal qat_dev->options.legacy_alg = atoi(cmdline); 35547c3f7a4SArek Kusztal 356960ff4d6SArek Kusztal if (qat_read_qp_config(qat_dev)) { 3578f393c4fSArek Kusztal QAT_LOG(ERR, 3588f393c4fSArek Kusztal "Cannot acquire ring configuration for QAT_%d", 3598f393c4fSArek Kusztal qat_dev_id); 3607b1374b1SArkadiusz Kusztal goto error; 3618f393c4fSArek Kusztal } 3627b1374b1SArkadiusz Kusztal NOT_NULL(ops_hw->qat_dev_reset_ring_pairs, goto error, 3637b1374b1SArkadiusz Kusztal "QAT internal error! Reset ring pairs function not set, gen : %d", 3647b1374b1SArkadiusz Kusztal qat_dev_gen); 3657b1374b1SArkadiusz Kusztal if (ops_hw->qat_dev_reset_ring_pairs(qat_dev)) { 3667b1374b1SArkadiusz Kusztal QAT_LOG(ERR, 3677b1374b1SArkadiusz Kusztal "Cannot reset ring pairs, does pf driver supports pf2vf comms?" 3687b1374b1SArkadiusz Kusztal ); 3697b1374b1SArkadiusz Kusztal goto error; 3707b1374b1SArkadiusz Kusztal } 3717b1374b1SArkadiusz Kusztal NOT_NULL(ops_hw->qat_dev_get_slice_map, goto error, 3727b1374b1SArkadiusz Kusztal "QAT internal error! Read slice function not set, gen : %d", 3737b1374b1SArkadiusz Kusztal qat_dev_gen); 374b7bd72d8SArkadiusz Kusztal if (ops_hw->qat_dev_get_slice_map(&qat_dev->options.slice_map, pci_dev) < 0) { 37530d38a71SDavid Marchand QAT_LOG(ERR, 37630d38a71SDavid Marchand "Cannot read slice configuration"); 3777b1374b1SArkadiusz Kusztal goto error; 3787b1374b1SArkadiusz Kusztal } 3797b1374b1SArkadiusz Kusztal rte_spinlock_init(&qat_dev->arb_csr_lock); 3805438e4ecSFan Zhang 3815438e4ecSFan Zhang /* No errors when allocating, attach memzone with 3825438e4ecSFan Zhang * qat_dev to list of devices 3835438e4ecSFan Zhang */ 3845438e4ecSFan Zhang qat_pci_devs[qat_dev_id].mz = qat_dev_mz; 38598c4a35cSTomasz Jozwiak qat_nb_pci_devices++; 38698c4a35cSTomasz Jozwiak 3879904ff68SArek Kusztal QAT_LOG(DEBUG, "QAT device %d found, name %s, total QATs %d", 38898c4a35cSTomasz Jozwiak qat_dev->qat_dev_id, qat_dev->name, qat_nb_pci_devices); 38998c4a35cSTomasz Jozwiak 39098c4a35cSTomasz Jozwiak return qat_dev; 3917b1374b1SArkadiusz Kusztal error: 39299ab2806SArkadiusz Kusztal rte_free(qat_dev->command_line); 393*1af60a8cSStephen Hemminger rte_memzone_free(qat_dev_mz); 3947b1374b1SArkadiusz Kusztal return NULL; 39598c4a35cSTomasz Jozwiak } 39698c4a35cSTomasz Jozwiak 3979904ff68SArek Kusztal static int 39898c4a35cSTomasz Jozwiak qat_pci_device_release(struct rte_pci_device *pci_dev) 39998c4a35cSTomasz Jozwiak { 40098c4a35cSTomasz Jozwiak struct qat_pci_device *qat_dev; 40198c4a35cSTomasz Jozwiak char name[QAT_DEV_NAME_MAX_LEN]; 402477d7d05SArkadiusz Kusztal int busy = 0, i; 40398c4a35cSTomasz Jozwiak 40498c4a35cSTomasz Jozwiak if (pci_dev == NULL) 40598c4a35cSTomasz Jozwiak return -EINVAL; 40698c4a35cSTomasz Jozwiak 40798c4a35cSTomasz Jozwiak rte_pci_device_name(&pci_dev->addr, name, sizeof(name)); 40898c4a35cSTomasz Jozwiak snprintf(name+strlen(name), QAT_DEV_NAME_MAX_LEN-strlen(name), "_qat"); 40998c4a35cSTomasz Jozwiak qat_dev = qat_pci_get_named_dev(name); 41098c4a35cSTomasz Jozwiak if (qat_dev != NULL) { 41198c4a35cSTomasz Jozwiak 4129904ff68SArek Kusztal struct qat_device_info *inst = 4139904ff68SArek Kusztal &qat_pci_devs[qat_dev->qat_dev_id]; 41498c4a35cSTomasz Jozwiak /* Check that there are no service devs still on pci device */ 41598c4a35cSTomasz Jozwiak 4169904ff68SArek Kusztal if (rte_eal_process_type() == RTE_PROC_PRIMARY) { 417477d7d05SArkadiusz Kusztal for (i = 0; i < QAT_MAX_SERVICES; i++) { 418d77817d0SArkadiusz Kusztal if (qat_dev->pmd[i] != NULL) { 419477d7d05SArkadiusz Kusztal QAT_LOG(DEBUG, "QAT %s device %s is busy", 420477d7d05SArkadiusz Kusztal qat_service[i].name, name); 4219904ff68SArek Kusztal busy = 1; 422d77817d0SArkadiusz Kusztal } 423d77817d0SArkadiusz Kusztal } 4249904ff68SArek Kusztal if (busy) 4259904ff68SArek Kusztal return -EBUSY; 4269904ff68SArek Kusztal rte_memzone_free(inst->mz); 4279904ff68SArek Kusztal } 4289904ff68SArek Kusztal memset(inst, 0, sizeof(struct qat_device_info)); 4299904ff68SArek Kusztal qat_nb_pci_devices--; 43098c4a35cSTomasz Jozwiak QAT_LOG(DEBUG, "QAT device %s released, total QATs %d", 43198c4a35cSTomasz Jozwiak name, qat_nb_pci_devices); 4329904ff68SArek Kusztal } 43398c4a35cSTomasz Jozwiak return 0; 43498c4a35cSTomasz Jozwiak } 43598c4a35cSTomasz Jozwiak 43698c4a35cSTomasz Jozwiak static int 43798c4a35cSTomasz Jozwiak qat_pci_dev_destroy(struct qat_pci_device *qat_pci_dev, 43898c4a35cSTomasz Jozwiak struct rte_pci_device *pci_dev) 43998c4a35cSTomasz Jozwiak { 440477d7d05SArkadiusz Kusztal int i; 441477d7d05SArkadiusz Kusztal 442477d7d05SArkadiusz Kusztal for (i = 0; i < QAT_MAX_SERVICES; i++) { 443d77817d0SArkadiusz Kusztal if (!qat_service[i].dev_destroy) 444477d7d05SArkadiusz Kusztal continue; 445477d7d05SArkadiusz Kusztal qat_service[i].dev_destroy(qat_pci_dev); 446477d7d05SArkadiusz Kusztal } 44798c4a35cSTomasz Jozwiak return qat_pci_device_release(pci_dev); 44898c4a35cSTomasz Jozwiak } 44998c4a35cSTomasz Jozwiak 45098c4a35cSTomasz Jozwiak static int qat_pci_probe(struct rte_pci_driver *pci_drv __rte_unused, 45198c4a35cSTomasz Jozwiak struct rte_pci_device *pci_dev) 45298c4a35cSTomasz Jozwiak { 453477d7d05SArkadiusz Kusztal int i, ret = 0, num_pmds_created = 0; 45498c4a35cSTomasz Jozwiak struct qat_pci_device *qat_pci_dev; 45598c4a35cSTomasz Jozwiak 45698c4a35cSTomasz Jozwiak QAT_LOG(DEBUG, "Found QAT device at %02x:%02x.%x", 45798c4a35cSTomasz Jozwiak pci_dev->addr.bus, 45898c4a35cSTomasz Jozwiak pci_dev->addr.devid, 45998c4a35cSTomasz Jozwiak pci_dev->addr.function); 46098c4a35cSTomasz Jozwiak 46199ab2806SArkadiusz Kusztal qat_pci_dev = qat_pci_device_allocate(pci_dev); 46298c4a35cSTomasz Jozwiak if (qat_pci_dev == NULL) 46398c4a35cSTomasz Jozwiak return -ENODEV; 46498c4a35cSTomasz Jozwiak 465477d7d05SArkadiusz Kusztal for (i = 0; i < QAT_MAX_SERVICES; i++) { 466477d7d05SArkadiusz Kusztal if (!qat_service[i].dev_create) 467477d7d05SArkadiusz Kusztal continue; 468477d7d05SArkadiusz Kusztal ret = qat_service[i].dev_create(qat_pci_dev); 469477d7d05SArkadiusz Kusztal if (ret == 0) 4708451f04dSFiona Trahe num_pmds_created++; 471477d7d05SArkadiusz Kusztal else { 472477d7d05SArkadiusz Kusztal QAT_LOG(WARNING, "Failed to create %s PMD on device %s", 473477d7d05SArkadiusz Kusztal qat_service[i].name, 474477d7d05SArkadiusz Kusztal qat_pci_dev->name); 47547c3f7a4SArek Kusztal } 476477d7d05SArkadiusz Kusztal } 4778451f04dSFiona Trahe 4788451f04dSFiona Trahe if (num_pmds_created == 0) 4798451f04dSFiona Trahe qat_pci_dev_destroy(qat_pci_dev, pci_dev); 48098c4a35cSTomasz Jozwiak 48198c4a35cSTomasz Jozwiak return 0; 48298c4a35cSTomasz Jozwiak } 48398c4a35cSTomasz Jozwiak 4845438e4ecSFan Zhang static int 4855438e4ecSFan Zhang qat_pci_remove(struct rte_pci_device *pci_dev) 48698c4a35cSTomasz Jozwiak { 48798c4a35cSTomasz Jozwiak struct qat_pci_device *qat_pci_dev; 48898c4a35cSTomasz Jozwiak 48998c4a35cSTomasz Jozwiak if (pci_dev == NULL) 49098c4a35cSTomasz Jozwiak return -EINVAL; 49198c4a35cSTomasz Jozwiak 49298c4a35cSTomasz Jozwiak qat_pci_dev = qat_get_qat_dev_from_pci_dev(pci_dev); 49398c4a35cSTomasz Jozwiak if (qat_pci_dev == NULL) 49498c4a35cSTomasz Jozwiak return 0; 49598c4a35cSTomasz Jozwiak 49698c4a35cSTomasz Jozwiak return qat_pci_dev_destroy(qat_pci_dev, pci_dev); 49798c4a35cSTomasz Jozwiak } 49898c4a35cSTomasz Jozwiak 49998c4a35cSTomasz Jozwiak static struct rte_pci_driver rte_qat_pmd = { 50098c4a35cSTomasz Jozwiak .id_table = pci_id_qat_map, 50198c4a35cSTomasz Jozwiak .drv_flags = RTE_PCI_DRV_NEED_MAPPING, 50298c4a35cSTomasz Jozwiak .probe = qat_pci_probe, 50398c4a35cSTomasz Jozwiak .remove = qat_pci_remove 50498c4a35cSTomasz Jozwiak }; 50598c4a35cSTomasz Jozwiak 50698c4a35cSTomasz Jozwiak RTE_PMD_REGISTER_PCI(QAT_PCI_NAME, rte_qat_pmd); 50798c4a35cSTomasz Jozwiak RTE_PMD_REGISTER_PCI_TABLE(QAT_PCI_NAME, pci_id_qat_map); 508a0fe0cc5SDidier Pallard RTE_PMD_REGISTER_KMOD_DEP(QAT_PCI_NAME, "* igb_uio | uio_pci_generic | vfio-pci"); 509