From 3cb431c1a5b8f84602c568b541840c7a95e3799b Mon Sep 17 00:00:00 2001 From: Sultanxda Date: Wed, 3 Jan 2018 12:40:12 -0800 Subject: [PATCH 1/2] qcacld-3.0: Load driver on device initcall when not built as a module Requiring userspace to write to /sys/kernel/boot_wlan/boot_wlan to boot up the wlan device is unnecessary and blocks userspace for the large amount of time it takes for wlan boot to finish. Instead, load the driver asynchronously on device_initcall. Change-Id: I4d696b9d46de032158fd223c60d9a7dbde26cc3f Signed-off-by: Sultanxda Signed-off-by: Nathan Chancellor Signed-off-by: Jami Kettunen Combines: https://github.com/moto-SDM660/android_kernel_motorola_sdm660/commit/071d5c9cb37a6f3889dd8cb3f374af83a82cc67c https://github.com/moto-SDM660/android_kernel_motorola_sdm660/commit/aded485ca746b72c1337a469079527d18234f264 https://github.com/moto-SDM660/android_kernel_motorola_sdm660/commit/494bc76e6eea881655e16aa9319af5aede6f1c96 --- .../qcacld-3.0/core/hdd/src/wlan_hdd_main.c | 186 ++---------------- 1 file changed, 20 insertions(+), 166 deletions(-) diff --git a/drivers/staging/qcacld-3.0/core/hdd/src/wlan_hdd_main.c b/drivers/staging/qcacld-3.0/core/hdd/src/wlan_hdd_main.c index 181b5f17799a..d4358d14f218 100644 --- a/drivers/staging/qcacld-3.0/core/hdd/src/wlan_hdd_main.c +++ b/drivers/staging/qcacld-3.0/core/hdd/src/wlan_hdd_main.c @@ -146,25 +146,7 @@ static struct cdev wlan_hdd_state_cdev; static struct class *class; static dev_t device; #ifndef MODULE -static struct gwlan_loader *wlan_loader; -static ssize_t wlan_boot_cb(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, size_t count); -struct gwlan_loader { - bool loaded_state; - struct kobject *boot_wlan_obj; - struct attribute_group *attr_group; -}; - -static struct kobj_attribute wlan_boot_attribute = - __ATTR(boot_wlan, 0220, NULL, wlan_boot_cb); - -static struct attribute *attrs[] = { - &wlan_boot_attribute.attr, - NULL, -}; - -#define MODULE_INITIALIZED 1 +static struct work_struct boot_work; #endif #define HDD_OPS_INACTIVITY_TIMEOUT (120000) @@ -399,6 +381,7 @@ int hdd_validate_channel_and_bandwidth(hdd_adapter_t *adapter, return 0; } +#ifdef MODULE /** * hdd_wait_for_recovery_completion() - Wait for cds recovery completion * @@ -438,6 +421,7 @@ static bool hdd_wait_for_recovery_completion(void) hdd_info("Recovery completed successfully!"); return true; } +#endif static int __hdd_netdev_notifier_call(struct notifier_block *nb, @@ -12688,6 +12672,7 @@ dev_alloc_err: return -ENODEV; } +#ifdef MODULE static void wlan_hdd_state_ctrl_param_destroy(void) { cdev_del(&wlan_hdd_state_cdev); @@ -12697,6 +12682,7 @@ static void wlan_hdd_state_ctrl_param_destroy(void) pr_info("Device node unregistered"); } +#endif /** * __hdd_module_init - Module init helper @@ -12750,7 +12736,7 @@ err_hdd_init: return ret; } - +#ifdef MODULE /** * __hdd_module_exit - Module exit helper * @@ -12780,135 +12766,6 @@ static void __hdd_module_exit(void) wlan_hdd_state_ctrl_param_destroy(); } -#ifndef MODULE -/** - * wlan_boot_cb() - Wlan boot callback - * @kobj: object whose directory we're creating the link in. - * @attr: attribute the user is interacting with - * @buff: the buffer containing the user data - * @count: number of bytes in the buffer - * - * This callback is invoked when the fs is ready to start the - * wlan driver initialization. - * - * Return: 'count' on success or a negative error code in case of failure - */ -static ssize_t wlan_boot_cb(struct kobject *kobj, - struct kobj_attribute *attr, - const char *buf, - size_t count) -{ - - if (wlan_loader->loaded_state) { - pr_err("%s: wlan driver already initialized\n", __func__); - return -EALREADY; - } - - if (__hdd_module_init()) { - pr_err("%s: wlan driver initialization failed\n", __func__); - return -EIO; - } - - wlan_loader->loaded_state = MODULE_INITIALIZED; - - return count; -} - -/** - * hdd_sysfs_cleanup() - cleanup sysfs - * - * Return: None - * - */ -static void hdd_sysfs_cleanup(void) -{ - /* remove from group */ - if (wlan_loader->boot_wlan_obj && wlan_loader->attr_group) - sysfs_remove_group(wlan_loader->boot_wlan_obj, - wlan_loader->attr_group); - - /* unlink the object from parent */ - kobject_del(wlan_loader->boot_wlan_obj); - - /* free the object */ - kobject_put(wlan_loader->boot_wlan_obj); - - kfree(wlan_loader->attr_group); - kfree(wlan_loader); - - wlan_loader = NULL; -} - -/** - * wlan_init_sysfs() - Creates the sysfs to be invoked when the fs is - * ready - * - * This is creates the syfs entry boot_wlan. Which shall be invoked - * when the filesystem is ready. - * - * QDF API cannot be used here since this function is called even before - * initializing WLAN driver. - * - * Return: 0 for success, errno on failure - */ -static int wlan_init_sysfs(void) -{ - int ret = -ENOMEM; - - wlan_loader = kzalloc(sizeof(*wlan_loader), GFP_KERNEL); - if (!wlan_loader) - return -ENOMEM; - - wlan_loader->boot_wlan_obj = NULL; - wlan_loader->attr_group = kzalloc(sizeof(*(wlan_loader->attr_group)), - GFP_KERNEL); - if (!wlan_loader->attr_group) - goto error_return; - - wlan_loader->loaded_state = 0; - wlan_loader->attr_group->attrs = attrs; - - wlan_loader->boot_wlan_obj = kobject_create_and_add("boot_wlan", - kernel_kobj); - if (!wlan_loader->boot_wlan_obj) { - pr_err("%s: sysfs create and add failed\n", __func__); - goto error_return; - } - - ret = sysfs_create_group(wlan_loader->boot_wlan_obj, - wlan_loader->attr_group); - if (ret) { - pr_err("%s: sysfs create group failed %d\n", __func__, ret); - goto error_return; - } - - return 0; - -error_return: - hdd_sysfs_cleanup(); - - return ret; -} - -/** - * wlan_deinit_sysfs() - Removes the sysfs created to initialize the wlan - * - * Return: 0 on success or errno on failure - */ -static int wlan_deinit_sysfs(void) -{ - if (!wlan_loader) { - hdd_err("wlan loader context is Null!"); - return -EINVAL; - } - - hdd_sysfs_cleanup(); - return 0; -} - -#endif /* MODULE */ - -#ifdef MODULE /** * __hdd_module_init - Module init helper * @@ -12925,21 +12782,7 @@ static int hdd_module_init(void) return 0; } -#else -static int __init hdd_module_init(void) -{ - int ret = -EINVAL; - ret = wlan_init_sysfs(); - if (ret) - pr_err("Failed to create sysfs entry for loading wlan"); - - return ret; -} -#endif - - -#ifdef MODULE /** * hdd_module_exit() - Exit function * @@ -12952,10 +12795,17 @@ static void __exit hdd_module_exit(void) __hdd_module_exit(); } #else -static void __exit hdd_module_exit(void) +static void wlan_hdd_boot_fn(struct work_struct *work) { - __hdd_module_exit(); - wlan_deinit_sysfs(); + __hdd_module_init(); +} + +static int __init hdd_module_init(void) +{ + INIT_WORK(&boot_work, wlan_hdd_boot_fn); + schedule_work(&boot_work); + + return 0; } #endif @@ -13747,8 +13597,12 @@ void hdd_drv_ops_inactivity_handler(unsigned long arg) } /* Register the module init/exit functions */ +#ifdef MODULE module_init(hdd_module_init); module_exit(hdd_module_exit); +#else +device_initcall(hdd_module_init); +#endif MODULE_LICENSE("Dual BSD/GPL"); MODULE_AUTHOR("Qualcomm Atheros, Inc."); From 3278251d40ace61a9633fba3523082b9cfd538f8 Mon Sep 17 00:00:00 2001 From: Jami Kettunen Date: Fri, 18 Dec 2020 13:15:31 +0200 Subject: [PATCH 2/2] Build QCA WLAN driver as a built-in again as now it works --- arch/arm64/configs/lineage_oneplus5_defconfig | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/arch/arm64/configs/lineage_oneplus5_defconfig b/arch/arm64/configs/lineage_oneplus5_defconfig index e8c426b0719e..90b7a94436a1 100644 --- a/arch/arm64/configs/lineage_oneplus5_defconfig +++ b/arch/arm64/configs/lineage_oneplus5_defconfig @@ -3960,7 +3960,7 @@ CONFIG_ION_MSM=y # # Qualcomm Atheros CLD WLAN module # -CONFIG_QCA_CLD_WLAN=m +CONFIG_QCA_CLD_WLAN=y CONFIG_QCACLD_WLAN_LFR3=y CONFIG_PRIMA_WLAN_OKC=y CONFIG_PRIMA_WLAN_11AC_HIGH_TP=y