xref: /OK3568_Linux_fs/external/rkwifibt/drivers/rtl8822cs/core/rtw_mem.c (revision 4882a59341e53eb6f0b4789bf948001014eff981)
1 /******************************************************************************
2  *
3  * Copyright(c) 2016 - 2017 Realtek Corporation.
4  *
5  * This program is free software; you can redistribute it and/or modify it
6  * under the terms of version 2 of the GNU General Public License as
7  * published by the Free Software Foundation.
8  *
9  * This program is distributed in the hope that it will be useful, but WITHOUT
10  * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11  * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
12  * more details.
13  *
14  *****************************************************************************/
15 
16 #include <drv_types.h>
17 #include <rtw_mem.h>
18 
19 MODULE_LICENSE("GPL");
20 MODULE_DESCRIPTION("Realtek Wireless Lan Driver");
21 MODULE_AUTHOR("Realtek Semiconductor Corp.");
22 MODULE_VERSION("DRIVERVERSION");
23 
24 /* for MAX_RECVBUF_SZ */
25 #if defined(CONFIG_RTL8188E)
26 #include <rtl8188e_hal.h>
27 #elif defined(CONFIG_RTL8188F)
28 #include <rtl8188f_hal.h>
29 #elif defined(CONFIG_RTL8188GTV)
30 #include <rtl8188gtv_hal.h>
31 #elif defined(CONFIG_RTL8710B)
32 #include <rtl8710b_hal.h>
33 #elif defined(CONFIG_RTL8192E)
34 #include <rtl8192e_hal.h>
35 #elif defined(CONFIG_RTL8192F)
36 #include <rtl8192f_hal.h>
37 #elif defined(CONFIG_RTL8723B)
38 #include <rtl8723b_hal.h>
39 #elif defined(CONFIG_RTL8703B)
40 #include <rtl8703b_hal.h>
41 #elif defined(CONFIG_RTL8723D)
42 #include <rtl8723d_hal.h>
43 #elif defined(CONFIG_RTL8812A) || defined(CONFIG_RTL8821A)
44 #include <rtl8812a_hal.h>
45 #elif defined(CONFIG_RTL8822B)
46 #include <rtl8822b_hal.h>
47 #elif defined(CONFIG_RTL8822C)
48 #include <rtl8822c_hal.h>
49 #elif defined(CONFIG_RTL8814A)
50 #include <rtl8814a_hal.h>
51 #elif defined(CONFIG_RTL8814B)
52 #include <rtl8814b_hal.h>
53 #endif
54 
55 #if defined(CONFIG_SDIO_HCI) || defined(CONFIG_GSPI_HCI)
56 #define MAX_RTKM_RECVBUF_SZ		MAX_RECVBUF_SZ
57 #define MAX_RTKM_NR_PREALLOC_RECV_SKB	NR_RECVBUFF
58 #else /* !CONFIG_SDIO_HCI */
59 #ifdef CONFIG_PLATFORM_MSTAR_HIGH
60 	#define MAX_RTKM_RECVBUF_SZ (31744) /* 31k */
61 #else
62 	#define MAX_RTKM_RECVBUF_SZ (15360) /* 15k */
63 #endif /* CONFIG_PLATFORM_MSTAR_HIGH */
64 #define MAX_RTKM_NR_PREALLOC_RECV_SKB 16
65 #endif /* !CONFIG_SDIO_HCI */
66 
67 struct sk_buff_head rtk_skb_mem_q;
68 struct u8 *rtk_buf_mem[NR_RECVBUFF];
69 
rtw_get_buf_premem(int index)70 struct u8	*rtw_get_buf_premem(int index)
71 {
72 	printk("%s, rtk_buf_mem index : %d\n", __func__, index);
73 	return rtk_buf_mem[index];
74 }
75 
rtw_rtkm_get_buff_size(void)76 u16 rtw_rtkm_get_buff_size(void)
77 {
78 	return MAX_RTKM_RECVBUF_SZ;
79 }
80 EXPORT_SYMBOL(rtw_rtkm_get_buff_size);
81 
rtw_rtkm_get_nr_recv_skb(void)82 u8 rtw_rtkm_get_nr_recv_skb(void)
83 {
84 	return MAX_RTKM_NR_PREALLOC_RECV_SKB;
85 }
86 EXPORT_SYMBOL(rtw_rtkm_get_nr_recv_skb);
87 
rtw_alloc_skb_premem(u16 in_size)88 struct sk_buff *rtw_alloc_skb_premem(u16 in_size)
89 {
90 	struct sk_buff *skb = NULL;
91 
92 	if (in_size > MAX_RTKM_RECVBUF_SZ) {
93 		pr_info("warning %s: driver buffer size(%d) > rtkm buffer size(%d)\n", __func__, in_size, MAX_RTKM_RECVBUF_SZ);
94 		WARN_ON(1);
95 		return skb;
96 	}
97 
98 	skb = skb_dequeue(&rtk_skb_mem_q);
99 
100 	printk("%s, rtk_skb_mem_q len : %d\n", __func__, skb_queue_len(&rtk_skb_mem_q));
101 
102 	return skb;
103 }
104 EXPORT_SYMBOL(rtw_alloc_skb_premem);
105 
rtw_free_skb_premem(struct sk_buff * pskb)106 int rtw_free_skb_premem(struct sk_buff *pskb)
107 {
108 	if (!pskb)
109 		return -1;
110 
111 	if (skb_queue_len(&rtk_skb_mem_q) >= MAX_RTKM_NR_PREALLOC_RECV_SKB)
112 		return -1;
113 
114 	skb_queue_tail(&rtk_skb_mem_q, pskb);
115 
116 	printk("%s, rtk_skb_mem_q len : %d\n", __func__, skb_queue_len(&rtk_skb_mem_q));
117 
118 	return 0;
119 }
120 EXPORT_SYMBOL(rtw_free_skb_premem);
121 
rtw_mem_init(void)122 static int __init rtw_mem_init(void)
123 {
124 	int i;
125 	SIZE_PTR tmpaddr = 0;
126 	SIZE_PTR alignment = 0;
127 	struct sk_buff *pskb = NULL;
128 
129 	printk("%s\n", __func__);
130 	pr_info("MAX_RTKM_NR_PREALLOC_RECV_SKB: %d\n", MAX_RTKM_NR_PREALLOC_RECV_SKB);
131 	pr_info("MAX_RTKM_RECVBUF_SZ: %d\n", MAX_RTKM_RECVBUF_SZ);
132 
133 #ifdef CONFIG_USE_USB_BUFFER_ALLOC_RX
134 	for (i = 0; i < NR_RECVBUFF; i++)
135 		rtk_buf_mem[i] = usb_buffer_alloc(dev, size, (in_interrupt() ? GFP_ATOMIC : GFP_KERNEL), dma);
136 #endif /* CONFIG_USE_USB_BUFFER_ALLOC_RX */
137 
138 	skb_queue_head_init(&rtk_skb_mem_q);
139 
140 	for (i = 0; i < MAX_RTKM_NR_PREALLOC_RECV_SKB; i++) {
141 		pskb = __dev_alloc_skb(MAX_RTKM_RECVBUF_SZ + RECVBUFF_ALIGN_SZ, in_interrupt() ? GFP_ATOMIC : GFP_KERNEL);
142 		if (pskb) {
143 			tmpaddr = (SIZE_PTR)pskb->data;
144 			alignment = tmpaddr & (RECVBUFF_ALIGN_SZ - 1);
145 			skb_reserve(pskb, (RECVBUFF_ALIGN_SZ - alignment));
146 
147 			skb_queue_tail(&rtk_skb_mem_q, pskb);
148 		} else
149 			printk("%s, alloc skb memory fail!\n", __func__);
150 
151 		pskb = NULL;
152 	}
153 
154 	printk("%s, rtk_skb_mem_q len : %d\n", __func__, skb_queue_len(&rtk_skb_mem_q));
155 
156 	return 0;
157 
158 }
159 
rtw_mem_exit(void)160 static void __exit rtw_mem_exit(void)
161 {
162 	if (skb_queue_len(&rtk_skb_mem_q))
163 		printk("%s, rtk_skb_mem_q len : %d\n", __func__, skb_queue_len(&rtk_skb_mem_q));
164 
165 	skb_queue_purge(&rtk_skb_mem_q);
166 
167 	printk("%s\n", __func__);
168 }
169 
170 module_init(rtw_mem_init);
171 module_exit(rtw_mem_exit);
172