summaryrefslogtreecommitdiff
path: root/drivers/net/wireless/ath/ar5523/ar5523.h
blob: 00c6fd346d48225e92a865ff8938a1c9f921e6aa (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
/*
 * Copyright (c) 2006 Damien Bergamini <damien.bergamini@free.fr>
 * Copyright (c) 2006 Sam Leffler, Errno Consulting
 * Copyright (c) 2007 Christoph Hellwig <hch@lst.de>
 * Copyright (c) 2008-2009 Weongyo Jeong <weongyo@freebsd.org>
 * Copyright (c) 2012 Pontus Fuchs <pontus.fuchs@gmail.com>
 *
 * Permission to use, copy, modify, and/or distribute this software for any
 * purpose with or without fee is hereby granted, provided that the above
 * copyright notice and this permission notice appear in all copies.
 *
 * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES
 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR
 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF
 * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
 */

#define AR5523_FLAG_PRE_FIRMWARE	(1 << 0)
#define AR5523_FLAG_ABG			(1 << 1)

#define AR5523_FIRMWARE_FILE	"ar5523.bin"

#define AR5523_CMD_TX_PIPE	0x01
#define	AR5523_DATA_TX_PIPE	0x02
#define	AR5523_CMD_RX_PIPE	0x81
#define	AR5523_DATA_RX_PIPE	0x82

#define ar5523_cmd_tx_pipe(dev) \
	usb_sndbulkpipe((dev), AR5523_CMD_TX_PIPE)
#define ar5523_data_tx_pipe(dev) \
	usb_sndbulkpipe((dev), AR5523_DATA_TX_PIPE)
#define ar5523_cmd_rx_pipe(dev) \
	usb_rcvbulkpipe((dev), AR5523_CMD_RX_PIPE)
#define ar5523_data_rx_pipe(dev) \
	usb_rcvbulkpipe((dev), AR5523_DATA_RX_PIPE)

#define	AR5523_DATA_TIMEOUT	10000
#define	AR5523_CMD_TIMEOUT	1000

#define AR5523_TX_DATA_COUNT		8
#define AR5523_TX_DATA_RESTART_COUNT	2
#define AR5523_RX_DATA_COUNT		16
#define AR5523_RX_DATA_REFILL_COUNT	8

#define AR5523_CMD_ID	1
#define AR5523_DATA_ID	2

#define AR5523_TX_WD_TIMEOUT	(HZ * 2)
#define AR5523_FLUSH_TIMEOUT	(HZ * 3)

enum AR5523_flags {
	AR5523_HW_UP,
	AR5523_USB_DISCONNECTED,
	AR5523_CONNECTED
};

struct ar5523_tx_cmd {
	struct ar5523		*ar;
	struct urb		*urb_tx;
	void			*buf_tx;
	void			*odata;
	int			olen;
	int			flags;
	int			res;
	struct completion	done;
};

/* This struct is placed in tx_info->driver_data. It must not be larger
 *  than IEEE80211_TX_INFO_DRIVER_DATA_SIZE.
 */
struct ar5523_tx_data {
	struct list_head	list;
	struct ar5523		*ar;
	struct sk_buff		*skb;
	struct urb		*urb;
};

struct ar5523_rx_data {
	struct	list_head	list;
	struct ar5523		*ar;
	struct urb		*urb;
	struct sk_buff		*skb;
};

struct ar5523 {
	struct usb_device	*dev;
	struct ieee80211_hw	*hw;

	unsigned long		flags;
	struct mutex		mutex;
	struct workqueue_struct *wq;

	struct ar5523_tx_cmd	tx_cmd;

	struct delayed_work	stat_work;

	struct timer_list	tx_wd_timer;
	struct work_struct	tx_wd_work;
	struct work_struct	tx_work;
	struct list_head	tx_queue_pending;
	struct list_head	tx_queue_submitted;
	spinlock_t		tx_data_list_lock;
	wait_queue_head_t	tx_flush_waitq;

	/* Queued + Submitted TX frames */
	atomic_t		tx_nr_total;

	/* Submitted TX frames */
	atomic_t		tx_nr_pending;

	void			*rx_cmd_buf;
	struct urb		*rx_cmd_urb;

	struct ar5523_rx_data	rx_data[AR5523_RX_DATA_COUNT];
	spinlock_t		rx_data_list_lock;
	struct list_head	rx_data_free;
	struct list_head	rx_data_used;
	atomic_t		rx_data_free_cnt;

	struct work_struct	rx_refill_work;

	unsigned int		rxbufsz;
	u8			serial[16];

	struct ieee80211_channel channels[14];
	struct ieee80211_rate	rates[12];
	struct ieee80211_supported_band band;
	struct ieee80211_vif	*vif;
};

/* flags for sending firmware commands */
#define AR5523_CMD_FLAG_READ	(1 << 1)
#define AR5523_CMD_FLAG_MAGIC	(1 << 2)

#define ar5523_dbg(ar, format, arg...) \
	dev_dbg(&(ar)->dev->dev, format, ## arg)

/* On USB hot-unplug there can be a lot of URBs in flight and they'll all
 * fail. Instead of dealing with them in every possible place just surpress
 * any messages on USB disconnect.
 */
#define ar5523_err(ar, format, arg...) \
do { \
	if (!test_bit(AR5523_USB_DISCONNECTED, &ar->flags)) { \
		dev_err(&(ar)->dev->dev, format, ## arg); \
	} \
} while (0)
#define ar5523_info(ar, format, arg...)	\
	dev_info(&(ar)->dev->dev, format, ## arg)