1
/*******************************************************************************
3
Copyright(c) 2004 Intel Corporation. All rights reserved.
5
Portions of this file are based on the WEP enablement code provided by the
6
Host AP project hostap-drivers v0.1.3
7
Copyright (c) 2001-2002, SSH Communications Security Corp and Jouni Malinen
9
Copyright (c) 2002-2003, Jouni Malinen <jkmaline@cc.hut.fi>
11
This program is free software; you can redistribute it and/or modify it
12
under the terms of version 2 of the GNU General Public License as
13
published by the Free Software Foundation.
15
This program is distributed in the hope that it will be useful, but WITHOUT
16
ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
17
FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for
20
You should have received a copy of the GNU General Public License along with
21
this program; if not, write to the Free Software Foundation, Inc., 59
22
Temple Place - Suite 330, Boston, MA 02111-1307, USA.
24
The full GNU General Public License is included in this distribution in the
28
James P. Ketrenos <ipw2100-admin@linux.intel.com>
29
Intel Corporation, 5200 N.E. Elam Young Parkway, Hillsboro, OR 97124-6497
31
*******************************************************************************/
33
#include <linux/compiler.h>
34
#include <linux/errno.h>
35
#include <linux/if_arp.h>
36
#include <linux/in6.h>
39
#include <linux/kernel.h>
40
#include <linux/module.h>
41
#include <linux/netdevice.h>
42
#include <linux/pci.h>
43
#include <linux/proc_fs.h>
44
#include <linux/skbuff.h>
45
#include <linux/slab.h>
46
#include <linux/tcp.h>
47
#include <linux/types.h>
48
#include <linux/version.h>
49
#include <linux/wireless.h>
50
#include <linux/etherdevice.h>
51
#include <asm/uaccess.h>
57
#ifndef BUILT_IN_RTLLIB
58
MODULE_DESCRIPTION("802.11 data/management/control stack");
59
MODULE_AUTHOR("Copyright (C) 2004 Intel Corporation <jketreno@linux.intel.com>");
60
MODULE_LICENSE("GPL");
64
#define DRV_NAME "rtllib_92ce"
65
#elif defined RTL8192SE
66
#define DRV_NAME "rtllib_92se"
67
#elif defined RTL8192E
68
#define DRV_NAME "rtllib_92e"
69
#elif defined RTL8190P
70
#define DRV_NAME "rtllib_90p"
71
#elif defined RTL8192SU
72
#define DRV_NAME "rtllib_92su"
73
#elif defined RTL8192U
74
#define DRV_NAME "rtllib_92u"
76
#define DRV_NAME "rtllib_9x"
79
#ifdef CONFIG_CFG_80211
80
#ifdef CONFIG_RTL_RFKILL
81
static inline void rtllib_rfkill_poll(struct wiphy *wiphy)
83
struct rtllib_device *rtllib = NULL;
85
rtllib = (struct rtllib_device *)wiphy_priv(wiphy);
87
rtllib = (struct rtllib_device *)netdev_priv_rsl(rtllib->dev);
89
if (rtllib->rtllib_rfkill_poll)
90
rtllib->rtllib_rfkill_poll(rtllib->dev);
93
static inline void rtllib_rfkill_poll(struct wiphy *wiphy) {}
95
struct cfg80211_ops rtllib_config_ops = {.rfkill_poll = rtllib_rfkill_poll };
96
void *rtllib_wiphy_privid = &rtllib_wiphy_privid;
99
void _setup_timer( struct timer_list* ptimer, void* fun, unsigned long data )
101
ptimer->function = fun;
103
init_timer( ptimer );
106
#ifdef _RTL8192_EXT_PATCH_
107
static inline int rtllib_mesh_networks_allocate(struct rtllib_device *ieee)
109
if (ieee->mesh_networks)
112
ieee->mesh_networks = kmalloc(
113
MAX_NETWORK_COUNT * sizeof(struct rtllib_network),
116
if (!ieee->mesh_networks) {
117
printk(KERN_WARNING "%s: Out of memory allocating beacons\n",
122
memset(ieee->mesh_networks, 0,
123
MAX_NETWORK_COUNT * sizeof(struct rtllib_network));
128
static inline void rtllib_mesh_networks_free(struct rtllib_device *ieee)
130
if (!ieee->mesh_networks)
132
kfree(ieee->mesh_networks);
133
ieee->mesh_networks = NULL;
137
static inline int rtllib_networks_allocate(struct rtllib_device *ieee)
142
#ifndef RTK_DMP_PLATFORM
143
ieee->networks = kmalloc(
144
MAX_NETWORK_COUNT * sizeof(struct rtllib_network),
147
ieee->networks = dvr_malloc(MAX_NETWORK_COUNT * sizeof(struct rtllib_network));
149
if (!ieee->networks) {
150
printk(KERN_WARNING "%s: Out of memory allocating beacons\n",
155
memset(ieee->networks, 0,
156
MAX_NETWORK_COUNT * sizeof(struct rtllib_network));
161
static inline void rtllib_networks_free(struct rtllib_device *ieee)
165
#ifndef RTK_DMP_PLATFORM
166
kfree(ieee->networks);
168
dvr_free(ieee->networks);
170
ieee->networks = NULL;
173
static inline void rtllib_networks_initialize(struct rtllib_device *ieee)
177
INIT_LIST_HEAD(&ieee->network_free_list);
178
INIT_LIST_HEAD(&ieee->network_list);
179
for (i = 0; i < MAX_NETWORK_COUNT; i++)
180
list_add_tail(&ieee->networks[i].list, &ieee->network_free_list);
181
#ifdef _RTL8192_EXT_PATCH_
182
INIT_LIST_HEAD(&ieee->mesh_network_free_list);
183
INIT_LIST_HEAD(&ieee->mesh_network_list);
184
for (i = 0; i < MAX_NETWORK_COUNT; i++)
185
list_add_tail(&ieee->mesh_networks[i].list, &ieee->mesh_network_free_list);
189
#if defined CONFIG_CFG_80211
190
static bool rtllib_wdev_alloc(struct rtllib_device *ieee, int sizeof_priv)
193
struct rtllib_device *rtllib = NULL;
195
priv_size = ALIGN(sizeof(struct rtllib_device),NETDEV_ALIGN) + sizeof_priv;
197
ieee->wdev.wiphy = wiphy_new(&rtllib_config_ops, priv_size);
198
if (!ieee->wdev.wiphy) {
199
RTLLIB_ERROR("Unable to allocate wiphy.\n");
203
rtllib = (struct rtllib_device *)wiphy_priv(ieee->wdev.wiphy);
204
rtllib->dev = ieee->dev;
206
ieee->dev->ieee80211_ptr = &ieee->wdev;
207
ieee->wdev.iftype = NL80211_IFTYPE_STATION;
209
/* Fill-out wiphy structure bits we know... Not enough info
210
* here to call set_wiphy_dev or set MAC address or channel info
211
* -- have to do that in ->ndo_init... */
212
ieee->wdev.wiphy->privid = rtllib_wiphy_privid;
214
ieee->wdev.wiphy->max_scan_ssids = 1;
215
ieee->wdev.wiphy->max_scan_ie_len = 0;
216
ieee->wdev.wiphy->interface_modes = BIT(NL80211_IFTYPE_STATION) | BIT(NL80211_IFTYPE_ADHOC);
221
wiphy_free(ieee->wdev.wiphy);
226
struct net_device *alloc_rtllib(int sizeof_priv)
228
struct rtllib_device *ieee = NULL;
229
struct net_device *dev;
232
RTLLIB_DEBUG_INFO("Initializing...\n");
234
dev = alloc_etherdev(sizeof(struct rtllib_device) + sizeof_priv);
236
RTLLIB_ERROR("Unable to network device.\n");
239
ieee = (struct rtllib_device *)netdev_priv_rsl(dev);
240
memset(ieee, 0, sizeof(struct rtllib_device)+sizeof_priv);
243
#ifdef CONFIG_CFG_80211
244
if(!rtllib_wdev_alloc(ieee, sizeof_priv))
247
err = rtllib_networks_allocate(ieee);
249
RTLLIB_ERROR("Unable to allocate beacon storage: %d\n",
253
#ifdef _RTL8192_EXT_PATCH_
254
err = rtllib_mesh_networks_allocate(ieee);
256
RTLLIB_ERROR("Unable to allocate mesh_beacon storage: %d\n",
261
rtllib_networks_initialize(ieee);
264
/* Default fragmentation threshold is maximum payload size */
265
ieee->fts = DEFAULT_FTS;
266
ieee->scan_age = DEFAULT_MAX_SCAN_AGE;
269
/* Default to enabling full open WEP with host based encrypt/decrypt */
270
ieee->host_encrypt = 1;
271
ieee->host_decrypt = 1;
272
ieee->ieee802_1x = 1; /* Default to supporting 802.1x */
274
INIT_LIST_HEAD(&ieee->crypt_deinit_list);
275
_setup_timer(&ieee->crypt_deinit_timer,
276
rtllib_crypt_deinit_handler,
277
(unsigned long) ieee);
278
ieee->rtllib_ap_sec_type = rtllib_ap_sec_type;
280
spin_lock_init(&ieee->lock);
281
spin_lock_init(&ieee->wpax_suitlist_lock);
282
spin_lock_init(&ieee->bw_spinlock);
283
spin_lock_init(&ieee->reorder_spinlock);
284
atomic_set(&(ieee->atm_chnlop), 0);
285
atomic_set(&(ieee->atm_swbw), 0);
287
ieee->bHalfNMode = false;
288
ieee->wpa_enabled = 0;
289
ieee->tkip_countermeasures = 0;
290
ieee->drop_unencrypted = 0;
291
ieee->privacy_invoked = 0;
292
ieee->ieee802_1x = 1;
294
ieee->hwsec_active = 0;
296
#ifdef _RTL8192_EXT_PATCH_
297
for (i=0; i<MAX_MP; i++)
299
ieee->cryptlist[i] = (struct rtllib_crypt_data_list*) kmalloc(sizeof(struct rtllib_crypt_data_list), GFP_KERNEL);
300
if (NULL == ieee->cryptlist[i])
302
printk("error kmalloc cryptlist\n");
305
memset(ieee->cryptlist[i], 0, sizeof(struct rtllib_crypt_data_list));
307
memset(ieee->swmeshcamtable,0,sizeof(SW_CAM_TABLE)*32);
309
memset(ieee->swcamtable,0,sizeof(SW_CAM_TABLE)*32);
310
rtllib_softmac_init(ieee);
312
#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,6,13))
313
ieee->pHTInfo = (RT_HIGH_THROUGHPUT*)kzalloc(sizeof(RT_HIGH_THROUGHPUT), GFP_KERNEL);
315
ieee->pHTInfo = (RT_HIGH_THROUGHPUT*)kmalloc(sizeof(RT_HIGH_THROUGHPUT), GFP_KERNEL);
316
memset(ieee->pHTInfo,0,sizeof(RT_HIGH_THROUGHPUT));
318
if (ieee->pHTInfo == NULL)
320
RTLLIB_DEBUG(RTLLIB_DL_ERR, "can't alloc memory for HTInfo\n");
323
HTUpdateDefaultSetting(ieee);
324
HTInitializeHTInfo(ieee);
327
INIT_WORK_RSL(&ieee->ht_onAssRsp, (void(*)(void*)) HTOnAssocRsp_wq, ieee);
329
for (i = 0; i < IEEE_IBSS_MAC_HASH_SIZE; i++)
330
INIT_LIST_HEAD(&ieee->ibss_mac_hash[i]);
332
#ifdef _RTL8192_EXT_PATCH_
333
for (i = 0; i < IEEE_MESH_MAC_HASH_SIZE; i++)
334
INIT_LIST_HEAD(&ieee->mesh_mac_hash[i]);
337
for (i = 0; i < 17; i++) {
338
ieee->last_rxseq_num[i] = -1;
339
ieee->last_rxfrag_num[i] = -1;
340
ieee->last_packet_time[i] = 0;
350
#ifdef _RTL8192_EXT_PATCH_
351
for (i=0; i<MAX_MP; i++)
353
if (ieee->cryptlist[i]==NULL){
356
kfree(ieee->cryptlist[i]);
357
ieee->cryptlist[i] = NULL;
363
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
372
void free_rtllib(struct net_device *dev)
374
struct rtllib_device *ieee = (struct rtllib_device *)netdev_priv_rsl(dev);
376
#ifdef _RTL8192_EXT_PATCH_
378
struct list_head *p, *q;
379
struct rtllib_crypt_data *crypt = NULL;
382
if (ieee->pHTInfo != NULL)
384
kfree(ieee->pHTInfo);
385
ieee->pHTInfo = NULL;
388
rtllib_softmac_free(ieee);
389
del_timer_sync(&ieee->crypt_deinit_timer);
390
rtllib_crypt_deinit_entries(ieee, 1);
392
#ifdef _RTL8192_EXT_PATCH_
393
for (j=0;j<MAX_MP; j++)
395
if (ieee->cryptlist[j] == NULL)
397
for (i = 0; i < WEP_KEYS; i++) {
398
crypt = ieee->cryptlist[j]->crypt[i];
403
crypt->ops->deinit(crypt->priv);
404
printk("===>%s():j is %d,i is %d\n",__FUNCTION__,j,i);
405
#ifndef BUILT_IN_RTLLIB
406
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
407
module_put(crypt->ops->owner);
409
__MOD_DEC_USE_COUNT(crypt->ops->owner);
414
ieee->cryptlist[j]->crypt[i] = NULL;
417
kfree(ieee->cryptlist[j]);
419
for (i = 0; i < WEP_KEYS; i++) {
420
crypt = ieee->sta_crypt[i];
424
crypt->ops->deinit(crypt->priv);
425
#ifndef BUILT_IN_RTLLIB
426
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
427
module_put(crypt->ops->owner);
429
__MOD_DEC_USE_COUNT(crypt->ops->owner);
435
ieee->sta_crypt[i] = NULL;
438
for (i = 0; i < WEP_KEYS; i++) {
439
struct rtllib_crypt_data *crypt = ieee->crypt[i];
442
crypt->ops->deinit(crypt->priv);
443
#ifndef BUILT_IN_RTLLIB
444
#if LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0)
445
module_put(crypt->ops->owner);
447
__MOD_DEC_USE_COUNT(crypt->ops->owner);
452
ieee->crypt[i] = NULL;
457
rtllib_networks_free(ieee);
458
#ifdef _RTL8192_EXT_PATCH_
459
rtllib_mesh_networks_free(ieee);
462
for (i = 0; i < IEEE_IBSS_MAC_HASH_SIZE; i++) {
463
list_for_each_safe(p, q, &ieee->ibss_mac_hash[i]) {
464
kfree(list_entry(p, struct ieee_ibss_seq, list));
470
#ifdef _RTL8192_EXT_PATCH_
471
for (i = 0; i < IEEE_MESH_MAC_HASH_SIZE; i++) {
472
list_for_each_safe(p, q, &ieee->mesh_mac_hash[i]) {
473
kfree(list_entry(p, struct ieee_mesh_seq, list));
478
#if defined (RTL8192S_WAPI_SUPPORT)
479
if (ieee->WapiSupport)
481
WapiFreeAllStaInfo(ieee);
484
#if (LINUX_VERSION_CODE >= KERNEL_VERSION(2,5,0))
485
#ifdef CONFIG_CFG_80211
486
wiphy_unregister(ieee->wdev.wiphy);
487
wiphy_free(ieee->wdev.wiphy);
495
#ifdef CONFIG_RTLLIB_DEBUG
497
u32 rtllib_debug_level = 0;
501
struct proc_dir_entry *rtllib_proc = NULL;
503
static int show_debug_level(char *page, char **start, off_t offset,
504
int count, int *eof, void *data)
506
return snprintf(page, count, "0x%08X\n", rtllib_debug_level);
509
static int store_debug_level(struct file *file, const char *buffer,
510
unsigned long count, void *data)
512
char buf[] = "0x00000000";
513
unsigned long len = min((unsigned long)sizeof(buf) - 1, count);
514
char *p = (char *)buf;
517
if (copy_from_user(buf, buffer, len))
520
if (p[1] == 'x' || p[1] == 'X' || p[0] == 'x' || p[0] == 'X') {
522
if (p[0] == 'x' || p[0] == 'X')
524
val = simple_strtoul(p, &p, 16);
526
val = simple_strtoul(p, &p, 10);
528
printk(KERN_INFO DRV_NAME
529
": %s is not in hex or decimal form.\n", buf);
531
rtllib_debug_level = val;
533
return strnlen(buf, count);
536
int __init rtllib_init(void)
538
#ifdef CONFIG_RTLLIB_DEBUG
539
struct proc_dir_entry *e;
541
rtllib_debug_level = debug;
542
#if(LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24))
543
rtllib_proc = create_proc_entry(DRV_NAME, S_IFDIR, proc_net);
545
rtllib_proc = create_proc_entry(DRV_NAME, S_IFDIR, init_net.proc_net);
547
if (rtllib_proc == NULL) {
548
RTLLIB_ERROR("Unable to create " DRV_NAME
549
" proc directory\n");
552
e = create_proc_entry("debug_level", S_IFREG | S_IRUGO | S_IWUSR,
555
#if(LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24))
556
remove_proc_entry(DRV_NAME, proc_net);
558
remove_proc_entry(DRV_NAME, init_net.proc_net);
563
e->read_proc = show_debug_level;
564
e->write_proc = store_debug_level;
571
void __exit rtllib_exit(void)
573
#ifdef CONFIG_RTLLIB_DEBUG
575
remove_proc_entry("debug_level", rtllib_proc);
576
#if(LINUX_VERSION_CODE < KERNEL_VERSION(2,6,24))
577
remove_proc_entry(DRV_NAME, proc_net);
579
remove_proc_entry(DRV_NAME, init_net.proc_net);
586
#ifndef BUILT_IN_RTLLIB
587
#if (LINUX_VERSION_CODE > KERNEL_VERSION(2,5,0))
588
#include <linux/moduleparam.h>
589
module_param(debug, int, 0444);
590
MODULE_PARM_DESC(debug, "debug output mask");
593
module_exit(rtllib_exit);
594
module_init(rtllib_init);
597
EXPORT_SYMBOL_RSL(alloc_rtllib);
598
EXPORT_SYMBOL_RSL(free_rtllib);
599
EXPORT_SYMBOL_RSL(rtllib_debug_level);