Loading Documentation/devicetree/bindings/cnss/cnss-wlan.txt +55 −1 Original line number Diff line number Diff line Loading @@ -14,6 +14,7 @@ Required properties: - compatible: "qcom,cnss" for QCA6174 device "qcom,cnss-qca6290" for QCA6290 device "qcom,cnss-qca6390" for QCA6390 device "qcom,cnss-qca-converged" for converged QCA devices - wlan-en-gpio: WLAN_EN GPIO signal specified by the chip specifications - vdd-wlan-supply: phandle to the regulator device tree node - pinctrl-names: Names corresponding to the numbered pinctrl states Loading @@ -35,6 +36,10 @@ Optional properties: - vdd-wlan-xtal-aon-supply: phandle to the LDO-4 regulator. This is needed on platforms where XTAL regulator depends on always on regulator in VDDmin. - vdd-wlan-ctrl1-supply: phandle to the DBU1 - 1.8V for QCA6595 or 3.3V for QCA6174 on auto platform. - vdd-wlan-ctrl2-supply: phandle to the DBU4 - 2.2V for QCA6595 or 3.85V for QCA6696 on auto platform. - vdd-wlan-core-supply: phandle to the 1.3V CORE regulator for QCA6174 - vdd-wlan-sp2t-supply: phandle to the 2.7V SP2T regulator for QCA6174 - qcom,smmu-s1-enable: Boolean property to decide whether to enable SMMU Loading @@ -56,7 +61,32 @@ Optional properties: WLAN_EN pin is a gpio or fixed regulator. - qcom,mhi: phandle to indicate the device which needs MHI support. - qcom,cap-tsf-gpio: WLAN_TSF_CAPTURED GPIO signal specified by the chip specifications, should be drived depending on products specifications, should be drived depending on products. - cnss-daemon-support: Boolean property to decide whether cnss_daemon userspace QMI client is supported. - qcom,converged-dt: Boolean property to decide whether it supports multiple chips. - qcom,bus-type: U32 property to specify the bus type, is required when 'qcom,converged-dt' being present. - wlan_vregs: String array to decide which vregs are required, is required when 'qcom,converged-dt' being present. - <supply-name>-supply: phandle to the regulator device tree node. optional "supply-name" is "vdd-wlan-rfa". - qcom,<supply-name>-info: Specifies configuration for supply. Should be specified in <min_uV max_uV load_uA delay_us>. - pcie-disable-l1: Boolean property to decide whether to disable PCIe L1 PM. - pcie-disable-l1ss: Boolean property to decide whether to disable PCIe L1ss. - qcom,set-wlaon-pwr-ctrl: Boolean property to indicate if set WLAON_QFPROM_PWR_CTRL_REG register during power on and off sequences. List of chip specific sub nodes: - chip_cfg@X: represent chip specific configurations Each sub node has the following required properties: - wlan_vregs: String array to decide which vregs are required, property being present but no values means no additional vregs. - supported-ids: U32 array to decide which device ids are supported by sub node. Example: Loading @@ -76,3 +106,27 @@ Example: qcom,mhi = <&mhi_wlan>; qcom,cap-tsf-gpio = <&tlmm 126 1>; }; qcom,cnss-qca-converged { compatible = "qcom,cnss-qca-converged"; qcom,converged-dt; qcom,bus-type=<0>; vdd-wlan-ctrl1-supply = <&vreg_conn_pa>; vdd-wlan-ctrl2-supply = <&vreg_conn_1p8>; vdd-wlan-supply = <&vreg_wlan>; wlan_vregs = "vdd-wlan-ctrl1", "vdd-wlan-ctrl2"; qcom,vdd-wlan-ctrl1-info = <0 0 0 0>; qcom,vdd-wlan-ctrl2-info = <0 0 0 0>; wlan-en-gpio = <&tlmm 169 0>; pinctrl-names = "wlan_en_active", "wlan_en_sleep"; pinctrl-0 = <&cnss_wlan_en_active>; pinctrl-1 = <&cnss_wlan_en_sleep>; qcom,wlan-rc-num = <0>; chip_cfg@1 { supported-ids = <0x003e>; wlan_vregs = "vdd-wlan"; qcom,vdd-wlan-info = <0 0 0 10>; }; }; drivers/net/wireless/cnss2/Makefile +1 −0 Original line number Diff line number Diff line Loading @@ -6,4 +6,5 @@ cnss2-y += debug.o cnss2-y += pci.o cnss2-y += usb.o cnss2-y += power.o cnss2-$(CONFIG_CNSS2_DEBUG) += genl.o cnss2-$(CONFIG_CNSS2_QMI) += qmi.o wlan_firmware_service_v01.o drivers/net/wireless/cnss2/bus.c +77 −19 Original line number Diff line number Diff line /* Copyright (c) 2018, The Linux Foundation. All rights reserved. /* Copyright (c) 2018-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading Loading @@ -29,40 +29,52 @@ enum cnss_dev_bus_type cnss_get_dev_bus_type(struct device *dev) return CNSS_BUS_NONE; } enum cnss_dev_bus_type cnss_get_bus_type(unsigned long device_id) enum cnss_dev_bus_type cnss_get_bus_type(struct cnss_plat_data *plat_priv) { switch (device_id) { int ret; struct device *dev; u32 bus_type = CNSS_BUS_NONE; if (plat_priv->is_converged_dt) { dev = &plat_priv->plat_dev->dev; ret = of_property_read_u32(dev->of_node, "qcom,bus-type", &bus_type); if (!ret) cnss_pr_dbg("Got bus type[%u] from dt\n", bus_type); else cnss_pr_err("No bus type for converged dt\n"); return bus_type; } /* Get bus type according to device id if it's not converged DT */ switch (plat_priv->device_id) { case QCA6174_DEVICE_ID: case QCA6290_EMULATION_DEVICE_ID: case QCA6290_DEVICE_ID: return CNSS_BUS_PCI; case QCA6390_DEVICE_ID: case QCN7605_DEVICE_ID: bus_type = CNSS_BUS_PCI; break; case QCN7605_COMPOSITE_DEVICE_ID: case QCN7605_STANDALONE_DEVICE_ID: return CNSS_BUS_USB; bus_type = CNSS_BUS_USB; break; default: cnss_pr_err("Unknown device_id: 0x%lx\n", device_id); return CNSS_BUS_NONE; cnss_pr_err("Unknown device: 0x%lx\n", plat_priv->device_id); break; } return bus_type; } bool cnss_bus_req_mem_ind_valid(struct cnss_plat_data *plat_priv) { if (cnss_get_bus_type(plat_priv->device_id) == CNSS_BUS_USB) if (cnss_get_bus_type(plat_priv) == CNSS_BUS_USB) return false; else return true; } bool cnss_bus_dev_cal_rep_valid(struct cnss_plat_data *plat_priv) { bool ret = false; if (cnss_get_bus_type(plat_priv->device_id) == CNSS_BUS_USB) ret = true; return ret; } void *cnss_bus_dev_to_bus_priv(struct device *dev) { if (!dev) Loading Loading @@ -161,6 +173,37 @@ int cnss_bus_alloc_fw_mem(struct cnss_plat_data *plat_priv) } } int cnss_bus_alloc_qdss_mem(struct cnss_plat_data *plat_priv) { if (!plat_priv) return -ENODEV; switch (plat_priv->bus_type) { case CNSS_BUS_PCI: return cnss_pci_alloc_qdss_mem(plat_priv->bus_priv); default: cnss_pr_err("Unsupported bus type: %d\n", plat_priv->bus_type); return -EINVAL; } } void cnss_bus_free_qdss_mem(struct cnss_plat_data *plat_priv) { if (!plat_priv) return; switch (plat_priv->bus_type) { case CNSS_BUS_PCI: cnss_pci_free_qdss_mem(plat_priv->bus_priv); return; default: cnss_pr_err("Unsupported bus type: %d\n", plat_priv->bus_type); return; } } u32 cnss_bus_get_wake_irq(struct cnss_plat_data *plat_priv) { if (!plat_priv) Loading Loading @@ -388,3 +431,18 @@ int cnss_bus_update_status(struct cnss_plat_data *plat_priv, return -EINVAL; } } int cnss_get_msi_assignment(struct cnss_plat_data *plat_priv, char *msi_name, int *num_vectors, u32 *user_base_data, u32 *base_vector) { struct cnss_pci_data *pci_priv; pci_priv = plat_priv->bus_priv; return cnss_get_user_msi_assignment(&pci_priv->pci_dev->dev, msi_name, num_vectors, user_base_data, base_vector); } drivers/net/wireless/cnss2/bus.h +14 −11 Original line number Diff line number Diff line /* Copyright (c) 2018, The Linux Foundation. All rights reserved. /* Copyright (c) 2018-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading @@ -22,27 +22,28 @@ #define QCA6174_REV3_2_VERSION 0x5030000 #define QCA6290_VENDOR_ID 0x17CB #define QCA6290_DEVICE_ID 0x1100 #define QCA6290_EMULATION_VENDOR_ID 0x168C #define QCA6290_EMULATION_DEVICE_ID 0xABCD #define QCA6390_VENDOR_ID 0x17CB #define QCA6390_EMULATION_DEVICE_ID 0x0108 #define QCA6390_DEVICE_ID 0x1101 #define QCN7605_VENDOR_ID 0x17CB #define QCN7605_DEVICE_ID 0x1102 #define QCN7605_USB_VENDOR_ID 0x05C6 #define QCN7605_COMPOSITE_DEVICE_ID QCN7605_COMPOSITE_PRODUCT_ID #define QCN7605_STANDALONE_DEVICE_ID QCN7605_STANDALONE_PRODUCT_ID #define QCN7605_STANDALONE_PRODUCT_ID 0x9900 #define QCN7605_COMPOSITE_PRODUCT_ID 0x9901 #define QCN7605_COMPOSITE_DEVICE_ID QCN7605_COMPOSITE_PRODUCT_ID #define QCN7605_STANDALONE_DEVICE_ID QCN7605_STANDALONE_PRODUCT_ID enum cnss_dev_bus_type cnss_get_dev_bus_type(struct device *dev); enum cnss_dev_bus_type cnss_get_bus_type(unsigned long device_id); enum cnss_dev_bus_type cnss_get_bus_type(struct cnss_plat_data *plat_priv); void *cnss_bus_dev_to_bus_priv(struct device *dev); struct cnss_plat_data *cnss_bus_dev_to_plat_priv(struct device *dev); int cnss_bus_init(struct cnss_plat_data *plat_priv); void cnss_bus_deinit(struct cnss_plat_data *plat_priv); int cnss_bus_load_m3(struct cnss_plat_data *plat_priv); int cnss_bus_alloc_fw_mem(struct cnss_plat_data *plat_priv); int cnss_bus_alloc_qdss_mem(struct cnss_plat_data *plat_priv); void cnss_bus_free_qdss_mem(struct cnss_plat_data *plat_priv); u32 cnss_bus_get_wake_irq(struct cnss_plat_data *plat_priv); int cnss_bus_force_fw_assert_hdlr(struct cnss_plat_data *plat_priv); void cnss_bus_fw_boot_timeout_hdlr(unsigned long data); Loading @@ -60,8 +61,10 @@ int cnss_bus_call_driver_modem_status(struct cnss_plat_data *plat_priv, int modem_current_status); int cnss_bus_update_status(struct cnss_plat_data *plat_priv, enum cnss_driver_status status); int cnss_bus_recovery_update_status(struct cnss_plat_data *plat_priv); bool cnss_bus_req_mem_ind_valid(struct cnss_plat_data *plat_priv); bool cnss_bus_dev_cal_rep_valid(struct cnss_plat_data *plat_priv); int cnss_get_msi_assignment(struct cnss_plat_data *plat_priv, char *msi_name, int *num_vectors, u32 *user_base_data, u32 *base_vector); #endif /* _CNSS_BUS_H */ drivers/net/wireless/cnss2/debug.c +151 −1 Original line number Diff line number Diff line /* Copyright (c) 2016-2018, The Linux Foundation. All rights reserved. /* Copyright (c) 2016-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading Loading @@ -85,6 +85,12 @@ static int cnss_stats_show_state(struct seq_file *s, case CNSS_DRIVER_UNLOADING: seq_puts(s, "DRIVER_UNLOADING"); continue; case CNSS_DRIVER_IDLE_RESTART: seq_puts(s, "IDLE_RESTART"); continue; case CNSS_DRIVER_IDLE_SHUTDOWN: seq_puts(s, "IDLE_SHUTDOWN"); continue; case CNSS_DRIVER_PROBED: seq_puts(s, "DRIVER_PROBED"); continue; Loading @@ -100,6 +106,9 @@ static int cnss_stats_show_state(struct seq_file *s, case CNSS_DRIVER_DEBUG: seq_puts(s, "DRIVER_DEBUG"); continue; case CNSS_IN_SUSPEND_RESUME: seq_puts(s, "IN_SUSPEND_RESUME"); continue; } seq_printf(s, "UNKNOWN-%d", i); Loading Loading @@ -504,6 +513,145 @@ static const struct file_operations cnss_runtime_pm_debug_fops = { .llseek = seq_lseek, }; static ssize_t cnss_control_params_debug_write(struct file *fp, const char __user *user_buf, size_t count, loff_t *off) { struct cnss_plat_data *plat_priv = ((struct seq_file *)fp->private_data)->private; char buf[64]; char *sptr, *token; char *cmd; u32 val; unsigned int len = 0; const char *delim = " "; if (!plat_priv) return -ENODEV; len = min(count, sizeof(buf) - 1); if (copy_from_user(buf, user_buf, len)) return -EFAULT; buf[len] = '\0'; sptr = buf; token = strsep(&sptr, delim); if (!token) return -EINVAL; if (!sptr) return -EINVAL; cmd = token; token = strsep(&sptr, delim); if (!token) return -EINVAL; if (kstrtou32(token, 0, &val)) return -EINVAL; if (strcmp(cmd, "quirks") == 0) plat_priv->ctrl_params.quirks = val; else if (strcmp(cmd, "mhi_timeout") == 0) plat_priv->ctrl_params.mhi_timeout = val; else if (strcmp(cmd, "qmi_timeout") == 0) plat_priv->ctrl_params.qmi_timeout = val; else if (strcmp(cmd, "bdf_type") == 0) plat_priv->ctrl_params.bdf_type = val; else return -EINVAL; return count; } static int cnss_show_quirks_state(struct seq_file *s, struct cnss_plat_data *plat_priv) { enum cnss_debug_quirks i; int skip = 0; unsigned long state; seq_printf(s, "quirks: 0x%lx (", plat_priv->ctrl_params.quirks); for (i = 0, state = plat_priv->ctrl_params.quirks; state != 0; state >>= 1, i++) { if (!(state & 0x1)) continue; if (skip++) seq_puts(s, " | "); switch (i) { case LINK_DOWN_SELF_RECOVERY: seq_puts(s, "LINK_DOWN_SELF_RECOVERY"); continue; case SKIP_DEVICE_BOOT: seq_puts(s, "SKIP_DEVICE_BOOT"); continue; case USE_CORE_ONLY_FW: seq_puts(s, "USE_CORE_ONLY_FW"); continue; case SKIP_RECOVERY: seq_puts(s, "SKIP_RECOVERY"); continue; case QMI_BYPASS: seq_puts(s, "QMI_BYPASS"); continue; case ENABLE_WALTEST: seq_puts(s, "WALTEST"); continue; case ENABLE_PCI_LINK_DOWN_PANIC: seq_puts(s, "PCI_LINK_DOWN_PANIC"); continue; case FBC_BYPASS: seq_puts(s, "FBC_BYPASS"); continue; case ENABLE_DAEMON_SUPPORT: seq_puts(s, "DAEMON_SUPPORT"); continue; case IGNORE_PCI_LINK_FAILURE: seq_puts(s, "IGNORE_PCI_LINK_FAILURE"); continue; } seq_printf(s, "UNKNOWN-%d", i); } seq_puts(s, ")\n"); return 0; } static int cnss_control_params_debug_show(struct seq_file *s, void *data) { struct cnss_plat_data *cnss_priv = s->private; seq_puts(s, "\nUsage: echo <params_name> <value> > <debugfs_path>/cnss/control_params\n"); seq_puts(s, "<params_name> can be one of below:\n"); seq_puts(s, "quirks: Debug quirks for driver\n"); seq_puts(s, "mhi_timeout: Timeout for MHI operation in milliseconds\n"); seq_puts(s, "qmi_timeout: Timeout for QMI message in milliseconds\n"); seq_puts(s, "bdf_type: Type of board data file to be downloaded\n"); seq_puts(s, "\nCurrent value:\n"); cnss_show_quirks_state(s, cnss_priv); seq_printf(s, "mhi_timeout: %u\n", cnss_priv->ctrl_params.mhi_timeout); seq_printf(s, "qmi_timeout: %u\n", cnss_priv->ctrl_params.qmi_timeout); seq_printf(s, "bdf_type: %u\n", cnss_priv->ctrl_params.bdf_type); return 0; } static int cnss_control_params_debug_open(struct inode *inode, struct file *file) { return single_open(file, cnss_control_params_debug_show, inode->i_private); } static const struct file_operations cnss_control_params_debug_fops = { .read = seq_read, .write = cnss_control_params_debug_write, .open = cnss_control_params_debug_open, .owner = THIS_MODULE, .llseek = seq_lseek, }; #ifdef CONFIG_CNSS2_DEBUG static int cnss_create_debug_only_node(struct cnss_plat_data *plat_priv) { Loading @@ -517,6 +665,8 @@ static int cnss_create_debug_only_node(struct cnss_plat_data *plat_priv) &cnss_reg_write_debug_fops); debugfs_create_file("runtime_pm", 0600, root_dentry, plat_priv, &cnss_runtime_pm_debug_fops); debugfs_create_file("control_params", 0600, root_dentry, plat_priv, &cnss_control_params_debug_fops); return 0; } Loading Loading
Documentation/devicetree/bindings/cnss/cnss-wlan.txt +55 −1 Original line number Diff line number Diff line Loading @@ -14,6 +14,7 @@ Required properties: - compatible: "qcom,cnss" for QCA6174 device "qcom,cnss-qca6290" for QCA6290 device "qcom,cnss-qca6390" for QCA6390 device "qcom,cnss-qca-converged" for converged QCA devices - wlan-en-gpio: WLAN_EN GPIO signal specified by the chip specifications - vdd-wlan-supply: phandle to the regulator device tree node - pinctrl-names: Names corresponding to the numbered pinctrl states Loading @@ -35,6 +36,10 @@ Optional properties: - vdd-wlan-xtal-aon-supply: phandle to the LDO-4 regulator. This is needed on platforms where XTAL regulator depends on always on regulator in VDDmin. - vdd-wlan-ctrl1-supply: phandle to the DBU1 - 1.8V for QCA6595 or 3.3V for QCA6174 on auto platform. - vdd-wlan-ctrl2-supply: phandle to the DBU4 - 2.2V for QCA6595 or 3.85V for QCA6696 on auto platform. - vdd-wlan-core-supply: phandle to the 1.3V CORE regulator for QCA6174 - vdd-wlan-sp2t-supply: phandle to the 2.7V SP2T regulator for QCA6174 - qcom,smmu-s1-enable: Boolean property to decide whether to enable SMMU Loading @@ -56,7 +61,32 @@ Optional properties: WLAN_EN pin is a gpio or fixed regulator. - qcom,mhi: phandle to indicate the device which needs MHI support. - qcom,cap-tsf-gpio: WLAN_TSF_CAPTURED GPIO signal specified by the chip specifications, should be drived depending on products specifications, should be drived depending on products. - cnss-daemon-support: Boolean property to decide whether cnss_daemon userspace QMI client is supported. - qcom,converged-dt: Boolean property to decide whether it supports multiple chips. - qcom,bus-type: U32 property to specify the bus type, is required when 'qcom,converged-dt' being present. - wlan_vregs: String array to decide which vregs are required, is required when 'qcom,converged-dt' being present. - <supply-name>-supply: phandle to the regulator device tree node. optional "supply-name" is "vdd-wlan-rfa". - qcom,<supply-name>-info: Specifies configuration for supply. Should be specified in <min_uV max_uV load_uA delay_us>. - pcie-disable-l1: Boolean property to decide whether to disable PCIe L1 PM. - pcie-disable-l1ss: Boolean property to decide whether to disable PCIe L1ss. - qcom,set-wlaon-pwr-ctrl: Boolean property to indicate if set WLAON_QFPROM_PWR_CTRL_REG register during power on and off sequences. List of chip specific sub nodes: - chip_cfg@X: represent chip specific configurations Each sub node has the following required properties: - wlan_vregs: String array to decide which vregs are required, property being present but no values means no additional vregs. - supported-ids: U32 array to decide which device ids are supported by sub node. Example: Loading @@ -76,3 +106,27 @@ Example: qcom,mhi = <&mhi_wlan>; qcom,cap-tsf-gpio = <&tlmm 126 1>; }; qcom,cnss-qca-converged { compatible = "qcom,cnss-qca-converged"; qcom,converged-dt; qcom,bus-type=<0>; vdd-wlan-ctrl1-supply = <&vreg_conn_pa>; vdd-wlan-ctrl2-supply = <&vreg_conn_1p8>; vdd-wlan-supply = <&vreg_wlan>; wlan_vregs = "vdd-wlan-ctrl1", "vdd-wlan-ctrl2"; qcom,vdd-wlan-ctrl1-info = <0 0 0 0>; qcom,vdd-wlan-ctrl2-info = <0 0 0 0>; wlan-en-gpio = <&tlmm 169 0>; pinctrl-names = "wlan_en_active", "wlan_en_sleep"; pinctrl-0 = <&cnss_wlan_en_active>; pinctrl-1 = <&cnss_wlan_en_sleep>; qcom,wlan-rc-num = <0>; chip_cfg@1 { supported-ids = <0x003e>; wlan_vregs = "vdd-wlan"; qcom,vdd-wlan-info = <0 0 0 10>; }; };
drivers/net/wireless/cnss2/Makefile +1 −0 Original line number Diff line number Diff line Loading @@ -6,4 +6,5 @@ cnss2-y += debug.o cnss2-y += pci.o cnss2-y += usb.o cnss2-y += power.o cnss2-$(CONFIG_CNSS2_DEBUG) += genl.o cnss2-$(CONFIG_CNSS2_QMI) += qmi.o wlan_firmware_service_v01.o
drivers/net/wireless/cnss2/bus.c +77 −19 Original line number Diff line number Diff line /* Copyright (c) 2018, The Linux Foundation. All rights reserved. /* Copyright (c) 2018-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading Loading @@ -29,40 +29,52 @@ enum cnss_dev_bus_type cnss_get_dev_bus_type(struct device *dev) return CNSS_BUS_NONE; } enum cnss_dev_bus_type cnss_get_bus_type(unsigned long device_id) enum cnss_dev_bus_type cnss_get_bus_type(struct cnss_plat_data *plat_priv) { switch (device_id) { int ret; struct device *dev; u32 bus_type = CNSS_BUS_NONE; if (plat_priv->is_converged_dt) { dev = &plat_priv->plat_dev->dev; ret = of_property_read_u32(dev->of_node, "qcom,bus-type", &bus_type); if (!ret) cnss_pr_dbg("Got bus type[%u] from dt\n", bus_type); else cnss_pr_err("No bus type for converged dt\n"); return bus_type; } /* Get bus type according to device id if it's not converged DT */ switch (plat_priv->device_id) { case QCA6174_DEVICE_ID: case QCA6290_EMULATION_DEVICE_ID: case QCA6290_DEVICE_ID: return CNSS_BUS_PCI; case QCA6390_DEVICE_ID: case QCN7605_DEVICE_ID: bus_type = CNSS_BUS_PCI; break; case QCN7605_COMPOSITE_DEVICE_ID: case QCN7605_STANDALONE_DEVICE_ID: return CNSS_BUS_USB; bus_type = CNSS_BUS_USB; break; default: cnss_pr_err("Unknown device_id: 0x%lx\n", device_id); return CNSS_BUS_NONE; cnss_pr_err("Unknown device: 0x%lx\n", plat_priv->device_id); break; } return bus_type; } bool cnss_bus_req_mem_ind_valid(struct cnss_plat_data *plat_priv) { if (cnss_get_bus_type(plat_priv->device_id) == CNSS_BUS_USB) if (cnss_get_bus_type(plat_priv) == CNSS_BUS_USB) return false; else return true; } bool cnss_bus_dev_cal_rep_valid(struct cnss_plat_data *plat_priv) { bool ret = false; if (cnss_get_bus_type(plat_priv->device_id) == CNSS_BUS_USB) ret = true; return ret; } void *cnss_bus_dev_to_bus_priv(struct device *dev) { if (!dev) Loading Loading @@ -161,6 +173,37 @@ int cnss_bus_alloc_fw_mem(struct cnss_plat_data *plat_priv) } } int cnss_bus_alloc_qdss_mem(struct cnss_plat_data *plat_priv) { if (!plat_priv) return -ENODEV; switch (plat_priv->bus_type) { case CNSS_BUS_PCI: return cnss_pci_alloc_qdss_mem(plat_priv->bus_priv); default: cnss_pr_err("Unsupported bus type: %d\n", plat_priv->bus_type); return -EINVAL; } } void cnss_bus_free_qdss_mem(struct cnss_plat_data *plat_priv) { if (!plat_priv) return; switch (plat_priv->bus_type) { case CNSS_BUS_PCI: cnss_pci_free_qdss_mem(plat_priv->bus_priv); return; default: cnss_pr_err("Unsupported bus type: %d\n", plat_priv->bus_type); return; } } u32 cnss_bus_get_wake_irq(struct cnss_plat_data *plat_priv) { if (!plat_priv) Loading Loading @@ -388,3 +431,18 @@ int cnss_bus_update_status(struct cnss_plat_data *plat_priv, return -EINVAL; } } int cnss_get_msi_assignment(struct cnss_plat_data *plat_priv, char *msi_name, int *num_vectors, u32 *user_base_data, u32 *base_vector) { struct cnss_pci_data *pci_priv; pci_priv = plat_priv->bus_priv; return cnss_get_user_msi_assignment(&pci_priv->pci_dev->dev, msi_name, num_vectors, user_base_data, base_vector); }
drivers/net/wireless/cnss2/bus.h +14 −11 Original line number Diff line number Diff line /* Copyright (c) 2018, The Linux Foundation. All rights reserved. /* Copyright (c) 2018-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading @@ -22,27 +22,28 @@ #define QCA6174_REV3_2_VERSION 0x5030000 #define QCA6290_VENDOR_ID 0x17CB #define QCA6290_DEVICE_ID 0x1100 #define QCA6290_EMULATION_VENDOR_ID 0x168C #define QCA6290_EMULATION_DEVICE_ID 0xABCD #define QCA6390_VENDOR_ID 0x17CB #define QCA6390_EMULATION_DEVICE_ID 0x0108 #define QCA6390_DEVICE_ID 0x1101 #define QCN7605_VENDOR_ID 0x17CB #define QCN7605_DEVICE_ID 0x1102 #define QCN7605_USB_VENDOR_ID 0x05C6 #define QCN7605_COMPOSITE_DEVICE_ID QCN7605_COMPOSITE_PRODUCT_ID #define QCN7605_STANDALONE_DEVICE_ID QCN7605_STANDALONE_PRODUCT_ID #define QCN7605_STANDALONE_PRODUCT_ID 0x9900 #define QCN7605_COMPOSITE_PRODUCT_ID 0x9901 #define QCN7605_COMPOSITE_DEVICE_ID QCN7605_COMPOSITE_PRODUCT_ID #define QCN7605_STANDALONE_DEVICE_ID QCN7605_STANDALONE_PRODUCT_ID enum cnss_dev_bus_type cnss_get_dev_bus_type(struct device *dev); enum cnss_dev_bus_type cnss_get_bus_type(unsigned long device_id); enum cnss_dev_bus_type cnss_get_bus_type(struct cnss_plat_data *plat_priv); void *cnss_bus_dev_to_bus_priv(struct device *dev); struct cnss_plat_data *cnss_bus_dev_to_plat_priv(struct device *dev); int cnss_bus_init(struct cnss_plat_data *plat_priv); void cnss_bus_deinit(struct cnss_plat_data *plat_priv); int cnss_bus_load_m3(struct cnss_plat_data *plat_priv); int cnss_bus_alloc_fw_mem(struct cnss_plat_data *plat_priv); int cnss_bus_alloc_qdss_mem(struct cnss_plat_data *plat_priv); void cnss_bus_free_qdss_mem(struct cnss_plat_data *plat_priv); u32 cnss_bus_get_wake_irq(struct cnss_plat_data *plat_priv); int cnss_bus_force_fw_assert_hdlr(struct cnss_plat_data *plat_priv); void cnss_bus_fw_boot_timeout_hdlr(unsigned long data); Loading @@ -60,8 +61,10 @@ int cnss_bus_call_driver_modem_status(struct cnss_plat_data *plat_priv, int modem_current_status); int cnss_bus_update_status(struct cnss_plat_data *plat_priv, enum cnss_driver_status status); int cnss_bus_recovery_update_status(struct cnss_plat_data *plat_priv); bool cnss_bus_req_mem_ind_valid(struct cnss_plat_data *plat_priv); bool cnss_bus_dev_cal_rep_valid(struct cnss_plat_data *plat_priv); int cnss_get_msi_assignment(struct cnss_plat_data *plat_priv, char *msi_name, int *num_vectors, u32 *user_base_data, u32 *base_vector); #endif /* _CNSS_BUS_H */
drivers/net/wireless/cnss2/debug.c +151 −1 Original line number Diff line number Diff line /* Copyright (c) 2016-2018, The Linux Foundation. All rights reserved. /* Copyright (c) 2016-2020, The Linux Foundation. All rights reserved. * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License version 2 and Loading Loading @@ -85,6 +85,12 @@ static int cnss_stats_show_state(struct seq_file *s, case CNSS_DRIVER_UNLOADING: seq_puts(s, "DRIVER_UNLOADING"); continue; case CNSS_DRIVER_IDLE_RESTART: seq_puts(s, "IDLE_RESTART"); continue; case CNSS_DRIVER_IDLE_SHUTDOWN: seq_puts(s, "IDLE_SHUTDOWN"); continue; case CNSS_DRIVER_PROBED: seq_puts(s, "DRIVER_PROBED"); continue; Loading @@ -100,6 +106,9 @@ static int cnss_stats_show_state(struct seq_file *s, case CNSS_DRIVER_DEBUG: seq_puts(s, "DRIVER_DEBUG"); continue; case CNSS_IN_SUSPEND_RESUME: seq_puts(s, "IN_SUSPEND_RESUME"); continue; } seq_printf(s, "UNKNOWN-%d", i); Loading Loading @@ -504,6 +513,145 @@ static const struct file_operations cnss_runtime_pm_debug_fops = { .llseek = seq_lseek, }; static ssize_t cnss_control_params_debug_write(struct file *fp, const char __user *user_buf, size_t count, loff_t *off) { struct cnss_plat_data *plat_priv = ((struct seq_file *)fp->private_data)->private; char buf[64]; char *sptr, *token; char *cmd; u32 val; unsigned int len = 0; const char *delim = " "; if (!plat_priv) return -ENODEV; len = min(count, sizeof(buf) - 1); if (copy_from_user(buf, user_buf, len)) return -EFAULT; buf[len] = '\0'; sptr = buf; token = strsep(&sptr, delim); if (!token) return -EINVAL; if (!sptr) return -EINVAL; cmd = token; token = strsep(&sptr, delim); if (!token) return -EINVAL; if (kstrtou32(token, 0, &val)) return -EINVAL; if (strcmp(cmd, "quirks") == 0) plat_priv->ctrl_params.quirks = val; else if (strcmp(cmd, "mhi_timeout") == 0) plat_priv->ctrl_params.mhi_timeout = val; else if (strcmp(cmd, "qmi_timeout") == 0) plat_priv->ctrl_params.qmi_timeout = val; else if (strcmp(cmd, "bdf_type") == 0) plat_priv->ctrl_params.bdf_type = val; else return -EINVAL; return count; } static int cnss_show_quirks_state(struct seq_file *s, struct cnss_plat_data *plat_priv) { enum cnss_debug_quirks i; int skip = 0; unsigned long state; seq_printf(s, "quirks: 0x%lx (", plat_priv->ctrl_params.quirks); for (i = 0, state = plat_priv->ctrl_params.quirks; state != 0; state >>= 1, i++) { if (!(state & 0x1)) continue; if (skip++) seq_puts(s, " | "); switch (i) { case LINK_DOWN_SELF_RECOVERY: seq_puts(s, "LINK_DOWN_SELF_RECOVERY"); continue; case SKIP_DEVICE_BOOT: seq_puts(s, "SKIP_DEVICE_BOOT"); continue; case USE_CORE_ONLY_FW: seq_puts(s, "USE_CORE_ONLY_FW"); continue; case SKIP_RECOVERY: seq_puts(s, "SKIP_RECOVERY"); continue; case QMI_BYPASS: seq_puts(s, "QMI_BYPASS"); continue; case ENABLE_WALTEST: seq_puts(s, "WALTEST"); continue; case ENABLE_PCI_LINK_DOWN_PANIC: seq_puts(s, "PCI_LINK_DOWN_PANIC"); continue; case FBC_BYPASS: seq_puts(s, "FBC_BYPASS"); continue; case ENABLE_DAEMON_SUPPORT: seq_puts(s, "DAEMON_SUPPORT"); continue; case IGNORE_PCI_LINK_FAILURE: seq_puts(s, "IGNORE_PCI_LINK_FAILURE"); continue; } seq_printf(s, "UNKNOWN-%d", i); } seq_puts(s, ")\n"); return 0; } static int cnss_control_params_debug_show(struct seq_file *s, void *data) { struct cnss_plat_data *cnss_priv = s->private; seq_puts(s, "\nUsage: echo <params_name> <value> > <debugfs_path>/cnss/control_params\n"); seq_puts(s, "<params_name> can be one of below:\n"); seq_puts(s, "quirks: Debug quirks for driver\n"); seq_puts(s, "mhi_timeout: Timeout for MHI operation in milliseconds\n"); seq_puts(s, "qmi_timeout: Timeout for QMI message in milliseconds\n"); seq_puts(s, "bdf_type: Type of board data file to be downloaded\n"); seq_puts(s, "\nCurrent value:\n"); cnss_show_quirks_state(s, cnss_priv); seq_printf(s, "mhi_timeout: %u\n", cnss_priv->ctrl_params.mhi_timeout); seq_printf(s, "qmi_timeout: %u\n", cnss_priv->ctrl_params.qmi_timeout); seq_printf(s, "bdf_type: %u\n", cnss_priv->ctrl_params.bdf_type); return 0; } static int cnss_control_params_debug_open(struct inode *inode, struct file *file) { return single_open(file, cnss_control_params_debug_show, inode->i_private); } static const struct file_operations cnss_control_params_debug_fops = { .read = seq_read, .write = cnss_control_params_debug_write, .open = cnss_control_params_debug_open, .owner = THIS_MODULE, .llseek = seq_lseek, }; #ifdef CONFIG_CNSS2_DEBUG static int cnss_create_debug_only_node(struct cnss_plat_data *plat_priv) { Loading @@ -517,6 +665,8 @@ static int cnss_create_debug_only_node(struct cnss_plat_data *plat_priv) &cnss_reg_write_debug_fops); debugfs_create_file("runtime_pm", 0600, root_dentry, plat_priv, &cnss_runtime_pm_debug_fops); debugfs_create_file("control_params", 0600, root_dentry, plat_priv, &cnss_control_params_debug_fops); return 0; } Loading