1 /*
2  * Copyright (c) 2021, The Linux Foundation. All rights reserved.
3  * Copyright (c) 2022 Qualcomm Innovation Center, Inc. All rights reserved.
4  *
5  * Permission to use, copy, modify, and/or distribute this software for any
6  * purpose with or without fee is hereby granted, provided that the above
7  * copyright notice and this permission notice appear in all copies.
8  *
9  * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
10  * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
11  * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
12  * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
13  * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
14  * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
15  * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
16  */
17 
18 /**
19  * DOC: wlan_hdd_sysfs_eht_rate.c
20  *
21  * implementation for creating sysfs file 11be_rate
22  *
23  */
24 
25 #include "wlan_hdd_main.h"
26 #include "wlan_hdd_eht.h"
27 #include "wlan_hdd_sysfs.h"
28 #include "wlan_hdd_sysfs_eht_rate.h"
29 #include "osif_sync.h"
30 
31 static ssize_t
__hdd_sysfs_set_11be_fixed_rate(struct net_device * net_dev,char const * buf,size_t count)32 __hdd_sysfs_set_11be_fixed_rate(struct net_device *net_dev, char const *buf,
33 				size_t count)
34 {
35 	struct hdd_adapter *adapter = WLAN_HDD_GET_PRIV_PTR(net_dev);
36 	struct hdd_context *hdd_ctx;
37 	char buf_local[MAX_SYSFS_USER_COMMAND_SIZE_LENGTH + 1];
38 	int ret;
39 	uint16_t rate_code;
40 	char *sptr, *token;
41 
42 	if (hdd_validate_adapter(adapter)) {
43 		hdd_err_rl("invalid adapter");
44 		return -EINVAL;
45 	}
46 
47 	hdd_ctx = WLAN_HDD_GET_CTX(adapter);
48 	ret = wlan_hdd_validate_context(hdd_ctx);
49 	if (ret) {
50 		hdd_err_rl("invalid hdd context");
51 		return ret;
52 	}
53 
54 	if (!wlan_hdd_validate_modules_state(hdd_ctx)) {
55 		hdd_err_rl("invalid module state");
56 		return -EINVAL;
57 	}
58 
59 	ret = hdd_sysfs_validate_and_copy_buf(buf_local, sizeof(buf_local),
60 					      buf, count);
61 	if (ret) {
62 		hdd_err_rl("invalid input");
63 		return ret;
64 	}
65 
66 	sptr = buf_local;
67 	token = strsep(&sptr, " ");
68 	if (!token || kstrtou16(token, 0, &rate_code)) {
69 		hdd_err_rl("invalid input");
70 		return -EINVAL;
71 	}
72 
73 	hdd_set_11be_rate_code(adapter, rate_code);
74 
75 	return count;
76 }
77 
hdd_sysfs_set_11be_fixed_rate(struct device * dev,struct device_attribute * attr,char const * buf,size_t count)78 static ssize_t hdd_sysfs_set_11be_fixed_rate(
79 			     struct device *dev, struct device_attribute *attr,
80 			     char const *buf, size_t count)
81 {
82 	struct net_device *net_dev = container_of(dev, struct net_device, dev);
83 	struct osif_vdev_sync *vdev_sync;
84 	ssize_t err_size;
85 
86 	err_size = osif_vdev_sync_op_start(net_dev, &vdev_sync);
87 	if (err_size)
88 		return err_size;
89 
90 	err_size = __hdd_sysfs_set_11be_fixed_rate(net_dev, buf, count);
91 
92 	osif_vdev_sync_op_stop(vdev_sync);
93 
94 	return err_size;
95 }
96 
97 static DEVICE_ATTR(11be_rate, 0220, NULL, hdd_sysfs_set_11be_fixed_rate);
98 
hdd_sysfs_11be_rate_create(struct hdd_adapter * adapter)99 void hdd_sysfs_11be_rate_create(struct hdd_adapter *adapter)
100 {
101 	int error;
102 
103 	error = device_create_file(&adapter->dev->dev, &dev_attr_11be_rate);
104 	if (error)
105 		hdd_err("could not create sysfs file to set 11be rate");
106 }
107 
hdd_sysfs_11be_rate_destroy(struct hdd_adapter * adapter)108 void hdd_sysfs_11be_rate_destroy(struct hdd_adapter *adapter)
109 {
110 	device_remove_file(&adapter->dev->dev, &dev_attr_11be_rate);
111 }
112 
113