xref: /openwifi/driver/sdr.c (revision 76b1a6a12c79b0f64f2a7118c486c6b7678bdfd3)
1 // Author: Xianjun Jiao, Michael Mehari, Wei Liu, Jetmir Haxhibeqiri, Pablo Avila Campos
2 // SPDX-FileCopyrightText: 2022 UGent
3 // SPDX-License-Identifier: AGPL-3.0-or-later
4 
5 #include <linux/bitops.h>
6 #include <linux/dmapool.h>
7 #include <linux/io.h>
8 #include <linux/iopoll.h>
9 #include <linux/of_address.h>
10 #include <linux/of_platform.h>
11 #include <linux/of_irq.h>
12 #include <linux/slab.h>
13 #include <linux/clk.h>
14 #include <linux/io-64-nonatomic-lo-hi.h>
15 
16 #include <linux/delay.h>
17 #include <linux/interrupt.h>
18 
19 #include <linux/dmaengine.h>
20 #include <linux/slab.h>
21 #include <linux/delay.h>
22 #include <linux/etherdevice.h>
23 
24 #include <linux/init.h>
25 #include <linux/kthread.h>
26 #include <linux/module.h>
27 #include <linux/of_dma.h>
28 #include <linux/platform_device.h>
29 #include <linux/random.h>
30 #include <linux/slab.h>
31 #include <linux/wait.h>
32 #include <linux/sched/task.h>
33 #include <linux/dma/xilinx_dma.h>
34 #include <linux/spi/spi.h>
35 #include <net/mac80211.h>
36 
37 #include <linux/clk.h>
38 #include <linux/clkdev.h>
39 #include <linux/clk-provider.h>
40 
41 #include <linux/iio/iio.h>
42 #include <linux/iio/sysfs.h>
43 
44 #include <linux/gpio.h>
45 #include <linux/leds.h>
46 
47 #define IIO_AD9361_USE_PRIVATE_H_
48 #include <../../drivers/iio/adc/ad9361_regs.h>
49 #include <../../drivers/iio/adc/ad9361.h>
50 #include <../../drivers/iio/adc/ad9361_private.h>
51 
52 #include <../../drivers/iio/frequency/cf_axi_dds.h>
53 extern int ad9361_get_tx_atten(struct ad9361_rf_phy *phy, u32 tx_num);
54 extern int ad9361_set_tx_atten(struct ad9361_rf_phy *phy, u32 atten_mdb,
55 			       bool tx1, bool tx2, bool immed);
56 extern int ad9361_ctrl_outs_setup(struct ad9361_rf_phy *phy,
57 				  struct ctrl_outs_control *ctrl);
58 
59 #include "../user_space/sdrctl_src/nl80211_testmode_def.h"
60 #include "hw_def.h"
61 #include "sdr.h"
62 #include "git_rev.h"
63 
64 // driver API of component driver
65 extern struct tx_intf_driver_api *tx_intf_api;
66 extern struct rx_intf_driver_api *rx_intf_api;
67 extern struct openofdm_tx_driver_api *openofdm_tx_api;
68 extern struct openofdm_rx_driver_api *openofdm_rx_api;
69 extern struct xpu_driver_api *xpu_api;
70 
71 u32 gen_mpdu_crc(u8 *data_in, u32 num_bytes);
72 u8 gen_mpdu_delim_crc(u16 m);
73 
74 #include "sdrctl_intf.c"
75 #include "sysfs_intf.c"
76 
77 static int test_mode = 0; // bit0: aggregation enable(1)/disable(0); NO USE ANY MORE: bit1: tx offset tuning enable(0)/disable(1)
78 // Internal indication variables after parsing test_mode
79 static bool AGGR_ENABLE = false;
80 static bool TX_OFFSET_TUNING_ENABLE = false;
81 
82 static int init_tx_att = 0;
83 
84 MODULE_AUTHOR("Xianjun Jiao");
85 MODULE_DESCRIPTION("SDR driver");
86 MODULE_LICENSE("GPL v2");
87 
88 module_param(test_mode, int, 0);
89 MODULE_PARM_DESC(myint, "test_mode. bit0: aggregation enable(1)/disable(0)");
90 
91 module_param(init_tx_att, int, 0);
92 MODULE_PARM_DESC(myint, "init_tx_att. TX attenuation in dB*1000	example: set to 3000 for 3dB attenuation");
93 
94 // ---------------rfkill---------------------------------------
95 static bool openwifi_is_radio_enabled(struct openwifi_priv *priv)
96 {
97 	int reg;
98 
99 	if (priv->tx_intf_cfg==TX_INTF_BW_20MHZ_AT_0MHZ_ANT0 || priv->tx_intf_cfg==TX_INTF_BW_20MHZ_AT_N_10MHZ_ANT0 || priv->tx_intf_cfg==TX_INTF_BW_20MHZ_AT_0MHZ_ANT_BOTH)
100 		reg = ad9361_get_tx_atten(priv->ad9361_phy, 1);
101 	else
102 		reg = ad9361_get_tx_atten(priv->ad9361_phy, 2);
103 
104 	if (reg == (AD9361_RADIO_ON_TX_ATT+priv->rf_reg_val[RF_TX_REG_IDX_ATT]))
105 		return true;// 0 off, 1 on
106 	return false;
107 }
108 
109 void openwifi_rfkill_init(struct ieee80211_hw *hw)
110 {
111 	struct openwifi_priv *priv = hw->priv;
112 
113 	priv->rfkill_off = openwifi_is_radio_enabled(priv);
114 	printk("%s openwifi_rfkill_init: wireless switch is %s\n", sdr_compatible_str, priv->rfkill_off ? "on" : "off");
115 	wiphy_rfkill_set_hw_state(hw->wiphy, !priv->rfkill_off);
116 	wiphy_rfkill_start_polling(hw->wiphy);
117 }
118 
119 void openwifi_rfkill_poll(struct ieee80211_hw *hw)
120 {
121 	bool enabled;
122 	struct openwifi_priv *priv = hw->priv;
123 
124 	enabled = openwifi_is_radio_enabled(priv);
125 	// printk("%s openwifi_rfkill_poll: wireless radio switch turned %s\n", sdr_compatible_str, enabled ? "on" : "off");
126 	if (unlikely(enabled != priv->rfkill_off)) {
127 		priv->rfkill_off = enabled;
128 		printk("%s openwifi_rfkill_poll: WARNING wireless radio switch turned %s\n", sdr_compatible_str, enabled ? "on" : "off");
129 		wiphy_rfkill_set_hw_state(hw->wiphy, !enabled);
130 	}
131 }
132 
133 void openwifi_rfkill_exit(struct ieee80211_hw *hw)
134 {
135 	printk("%s openwifi_rfkill_exit\n", sdr_compatible_str);
136 	wiphy_rfkill_stop_polling(hw->wiphy);
137 }
138 //----------------rfkill end-----------------------------------
139 
140 //static void ad9361_rf_init(void);
141 //static void ad9361_rf_stop(void);
142 //static void ad9361_rf_calc_rssi(void);
143 static void ad9361_rf_set_channel(struct ieee80211_hw *dev,
144 				  struct ieee80211_conf *conf)
145 {
146 	struct openwifi_priv *priv = dev->priv;
147 	u32 actual_rx_lo = conf->chandef.chan->center_freq - priv->rx_freq_offset_to_lo_MHz + priv->drv_rx_reg_val[DRV_RX_REG_IDX_EXTRA_FO];
148 	u32 actual_tx_lo;
149 	bool change_flag = (actual_rx_lo != priv->actual_rx_lo);
150 	int static_lbt_th, auto_lbt_th, fpga_lbt_th;
151 
152 	if (change_flag) {
153 		priv->actual_rx_lo = actual_rx_lo;
154 		priv->actual_tx_lo = actual_tx_lo;
155 
156 		actual_tx_lo = conf->chandef.chan->center_freq - priv->tx_freq_offset_to_lo_MHz;
157 
158 		clk_set_rate(priv->ad9361_phy->clks[RX_RFPLL], ( ((u64)1000000ull)*((u64)actual_rx_lo )>>1) );
159 		clk_set_rate(priv->ad9361_phy->clks[TX_RFPLL], ( ((u64)1000000ull)*((u64)actual_tx_lo )>>1) );
160 
161 		if (actual_rx_lo<2412) {
162 			priv->rssi_correction = 153;
163 		} else if (actual_rx_lo<=2484) {
164 			priv->rssi_correction = 153;
165 		} else if (actual_rx_lo<5160) {
166 			priv->rssi_correction = 153;
167 		} else if (actual_rx_lo<=5240) {
168 			priv->rssi_correction = 145;
169 		} else if (actual_rx_lo<=5320) {
170 			priv->rssi_correction = 148;
171 		} else {
172 			priv->rssi_correction = 148;
173 		}
174 
175 		// xpu_api->XPU_REG_LBT_TH_write((priv->rssi_correction-62)<<1); // -62dBm
176 		// xpu_api->XPU_REG_LBT_TH_write((priv->rssi_correction-62-16)<<1); // wei's magic value is 135, here is 134 @ ch 44
177 		auto_lbt_th = ((priv->rssi_correction-62-16)<<1);
178 		static_lbt_th = priv->drv_xpu_reg_val[DRV_XPU_REG_IDX_LBT_TH];
179 		fpga_lbt_th = (static_lbt_th==0?auto_lbt_th:static_lbt_th);
180 		xpu_api->XPU_REG_LBT_TH_write(fpga_lbt_th);
181 
182 		priv->last_auto_fpga_lbt_th = auto_lbt_th;
183 
184 		if (actual_rx_lo < 2500) {
185 			//priv->slot_time = 20; //20 is default slot time in ERP(OFDM)/11g 2.4G; short one is 9.
186 			//xpu_api->XPU_REG_BAND_CHANNEL_write(BAND_2_4GHZ<<16);
187 			if (priv->band != BAND_2_4GHZ) {
188 				priv->band = BAND_2_4GHZ;
189 				xpu_api->XPU_REG_BAND_CHANNEL_write( (priv->use_short_slot<<24)|(priv->band<<16) );
190 			}
191 			// //xpu_api->XPU_REG_RECV_ACK_COUNT_TOP_write( (((45+2)*10)<<16) | 10 ); // high 16 bits to cover sig valid of ACK packet, low 16 bits is adjustment of fcs valid waiting time.  let's add 2us for those device that is really "slow"!
192 			// xpu_api->XPU_REG_RECV_ACK_COUNT_TOP_write( (((45+2+2)*10)<<16) | 10 );//add 2us for longer fir. BUT corrding to FPGA probing test, we do not need this
193 			// xpu_api->XPU_REG_SEND_ACK_WAIT_TOP_write( 0 );
194 			// tx_intf_api->TX_INTF_REG_CTS_TOSELF_WAIT_SIFS_TOP_write(((10)*10)<<16);
195 		}
196 		else {
197 			//priv->slot_time = 9; //default slot time of OFDM PHY (OFDM by default means 5GHz)
198 			// xpu_api->XPU_REG_BAND_CHANNEL_write(BAND_5_8GHZ<<16);
199 			if (priv->band != BAND_5_8GHZ) {
200 				priv->band = BAND_5_8GHZ;
201 				xpu_api->XPU_REG_BAND_CHANNEL_write( (priv->use_short_slot<<24)|(priv->band<<16) );
202 			}
203 			// //xpu_api->XPU_REG_RECV_ACK_COUNT_TOP_write( (((51+2)*10)<<16) | 10 ); // because 5GHz needs longer SIFS (16 instead of 10), we need 58 instead of 48 for XPU low mac setting.  let's add 2us for those device that is really "slow"!
204 			// xpu_api->XPU_REG_RECV_ACK_COUNT_TOP_write( (((51+2+2)*10)<<16) | 10 );//add 2us for longer fir.  BUT corrding to FPGA probing test, we do not need this
205 			// //xpu_api->XPU_REG_SEND_ACK_WAIT_TOP_write( 60*10 );
206 			// xpu_api->XPU_REG_SEND_ACK_WAIT_TOP_write( 50*10 );// for longer fir we need this delay 1us shorter
207 			// tx_intf_api->TX_INTF_REG_CTS_TOSELF_WAIT_SIFS_TOP_write(((16)*10)<<16);
208 		}
209 		//printk("%s ad9361_rf_set_channel %dM rssi_correction %d\n", sdr_compatible_str,conf->chandef.chan->center_freq,priv->rssi_correction);
210 		// //-- use less
211 		//clk_prepare_enable(priv->ad9361_phy->clks[RX_RFPLL]);
212 		//printk("%s ad9361_rf_set_channel tune to %d read back %llu\n", sdr_compatible_str,conf->chandef.chan->center_freq,2*priv->ad9361_phy->state->current_rx_lo_freq);
213 		//ad9361_set_trx_clock_chain_default(priv->ad9361_phy);
214 		//printk("%s ad9361_rf_set_channel tune to %d read back %llu\n", sdr_compatible_str,conf->chandef.chan->center_freq,2*priv->ad9361_phy->state->current_rx_lo_freq);
215 		printk("%s ad9361_rf_set_channel %dM rssi_correction %d (change flag %d) fpga_lbt_th %d (auto %d static %d)\n", sdr_compatible_str,conf->chandef.chan->center_freq,priv->rssi_correction,change_flag,fpga_lbt_th,auto_lbt_th,static_lbt_th);
216 	}
217 }
218 
219 const struct openwifi_rf_ops ad9361_rf_ops = {
220 	.name		= "ad9361",
221 //	.init		= ad9361_rf_init,
222 //	.stop		= ad9361_rf_stop,
223 	.set_chan	= ad9361_rf_set_channel,
224 //	.calc_rssi	= ad9361_rf_calc_rssi,
225 };
226 
227 u16 reverse16(u16 d) {
228 	union u16_byte2 tmp0, tmp1;
229 	tmp0.a = d;
230 	tmp1.c[0] = tmp0.c[1];
231 	tmp1.c[1] = tmp0.c[0];
232 	return(tmp1.a);
233 }
234 
235 u32 reverse32(u32 d) {
236 	union u32_byte4 tmp0, tmp1;
237 	tmp0.a = d;
238 	tmp1.c[0] = tmp0.c[3];
239 	tmp1.c[1] = tmp0.c[2];
240 	tmp1.c[2] = tmp0.c[1];
241 	tmp1.c[3] = tmp0.c[0];
242 	return(tmp1.a);
243 }
244 
245 static int openwifi_init_tx_ring(struct openwifi_priv *priv, int ring_idx)
246 {
247 	struct openwifi_ring *ring = &(priv->tx_ring[ring_idx]);
248 	int i;
249 
250 	ring->stop_flag = 0;
251 	ring->bd_wr_idx = 0;
252 	ring->bd_rd_idx = 0;
253 	ring->bds = kmalloc(sizeof(struct openwifi_buffer_descriptor)*NUM_TX_BD,GFP_KERNEL);
254 	if (ring->bds==NULL) {
255 		printk("%s openwifi_init_tx_ring: WARNING Cannot allocate TX ring\n",sdr_compatible_str);
256 		return -ENOMEM;
257 	}
258 
259 	for (i = 0; i < NUM_TX_BD; i++) {
260 		ring->bds[i].skb_linked=0; // for tx, skb is from upper layer
261 		//at first right after skb allocated, head, data, tail are the same.
262 		ring->bds[i].dma_mapping_addr = 0; // for tx, mapping is done after skb is received from upper layer in tx routine
263 		ring->bds[i].seq_no = 0;
264 	}
265 
266 	return 0;
267 }
268 
269 static void openwifi_free_tx_ring(struct openwifi_priv *priv, int ring_idx)
270 {
271 	struct openwifi_ring *ring = &(priv->tx_ring[ring_idx]);
272 	int i;
273 
274 	ring->stop_flag = 0;
275 	ring->bd_wr_idx = 0;
276 	ring->bd_rd_idx = 0;
277 	for (i = 0; i < NUM_TX_BD; i++) {
278 		if (ring->bds[i].skb_linked == 0 && ring->bds[i].dma_mapping_addr == 0)
279 			continue;
280 		if (ring->bds[i].dma_mapping_addr != 0)
281 			dma_unmap_single(priv->tx_chan->device->dev, ring->bds[i].dma_mapping_addr,ring->bds[i].skb_linked->len, DMA_MEM_TO_DEV);
282 //		if (ring->bds[i].skb_linked!=NULL)
283 //			dev_kfree_skb(ring->bds[i].skb_linked); // only use dev_kfree_skb when there is exception
284 		if ( (ring->bds[i].dma_mapping_addr != 0 && ring->bds[i].skb_linked == 0) ||
285 		     (ring->bds[i].dma_mapping_addr == 0 && ring->bds[i].skb_linked != 0))
286 			printk("%s openwifi_free_tx_ring: WARNING ring %d i %d skb_linked %p dma_mapping_addr %08x\n", sdr_compatible_str,
287 			ring_idx, i, (void*)(ring->bds[i].skb_linked), (unsigned int)(ring->bds[i].dma_mapping_addr));
288 
289 		ring->bds[i].skb_linked=0;
290 		ring->bds[i].dma_mapping_addr = 0;
291 		ring->bds[i].seq_no = 0;
292 	}
293 	if (ring->bds)
294 		kfree(ring->bds);
295 	ring->bds = NULL;
296 }
297 
298 static int openwifi_init_rx_ring(struct openwifi_priv *priv)
299 {
300 	int i;
301 	u8 *pdata_tmp;
302 
303 	priv->rx_cyclic_buf = dma_alloc_coherent(priv->rx_chan->device->dev,RX_BD_BUF_SIZE*NUM_RX_BD,&priv->rx_cyclic_buf_dma_mapping_addr,GFP_KERNEL);
304 	if (!priv->rx_cyclic_buf) {
305 		printk("%s openwifi_init_rx_ring: WARNING dma_alloc_coherent failed!\n", sdr_compatible_str);
306 		dma_free_coherent(priv->rx_chan->device->dev,RX_BD_BUF_SIZE*NUM_RX_BD,priv->rx_cyclic_buf,priv->rx_cyclic_buf_dma_mapping_addr);
307 		return(-1);
308 	}
309 
310 	// Set tsft_low and tsft_high to 0. If they are not zero, it means there is a packet in the buffer by DMA
311 	for (i=0; i<NUM_RX_BD; i++) {
312 		pdata_tmp = priv->rx_cyclic_buf + i*RX_BD_BUF_SIZE; // our header insertion is at the beginning
313 		(*((u32*)(pdata_tmp+0 ))) = 0;
314 		(*((u32*)(pdata_tmp+4 ))) = 0;
315 	}
316 	printk("%s openwifi_init_rx_ring: tsft_low and tsft_high are cleared!\n", sdr_compatible_str);
317 
318 	return 0;
319 }
320 
321 static void openwifi_free_rx_ring(struct openwifi_priv *priv)
322 {
323 	if (priv->rx_cyclic_buf)
324 		dma_free_coherent(priv->rx_chan->device->dev,RX_BD_BUF_SIZE*NUM_RX_BD,priv->rx_cyclic_buf,priv->rx_cyclic_buf_dma_mapping_addr);
325 
326 	priv->rx_cyclic_buf_dma_mapping_addr = 0;
327 	priv->rx_cyclic_buf = 0;
328 }
329 
330 static int rx_dma_setup(struct ieee80211_hw *dev){
331 	struct openwifi_priv *priv = dev->priv;
332 	struct dma_device *rx_dev = priv->rx_chan->device;
333 
334 	priv->rxd = rx_dev->device_prep_dma_cyclic(priv->rx_chan,priv->rx_cyclic_buf_dma_mapping_addr,RX_BD_BUF_SIZE*NUM_RX_BD,RX_BD_BUF_SIZE,DMA_DEV_TO_MEM,DMA_CTRL_ACK|DMA_PREP_INTERRUPT);
335 	if (!(priv->rxd)) {
336 		openwifi_free_rx_ring(priv);
337 		printk("%s rx_dma_setup: WARNING rx_dev->device_prep_dma_cyclic %p\n", sdr_compatible_str, (void*)(priv->rxd));
338 		return(-1);
339 	}
340 	priv->rxd->callback = 0;
341 	priv->rxd->callback_param = 0;
342 
343 	priv->rx_cookie = priv->rxd->tx_submit(priv->rxd);
344 
345 	if (dma_submit_error(priv->rx_cookie)) {
346 		printk("%s rx_dma_setup: WARNING dma_submit_error(rx_cookie) %d\n", sdr_compatible_str, (u32)(priv->rx_cookie));
347 		return(-1);
348 	}
349 
350 	dma_async_issue_pending(priv->rx_chan);
351 	return(0);
352 }
353 
354 static irqreturn_t openwifi_rx_interrupt(int irq, void *dev_id)
355 {
356 	struct ieee80211_hw *dev = dev_id;
357 	struct openwifi_priv *priv = dev->priv;
358 	struct ieee80211_rx_status rx_status = {0};
359 	struct sk_buff *skb;
360 	struct ieee80211_hdr *hdr;
361 	u32 addr1_low32=0, addr2_low32=0, addr3_low32=0, len, rate_idx, tsft_low, tsft_high, loop_count=0;//, fc_di;
362 	bool ht_flag, short_gi, ht_aggr, ht_aggr_last;
363 	// u32 dma_driver_buf_idx_mod;
364 	u8 *pdata_tmp, fcs_ok;//, target_buf_idx;//, phy_rx_sn_hw;
365 	s8 signal;
366 	u16 agc_status_and_pkt_exist_flag, rssi_val, addr1_high16=0, addr2_high16=0, addr3_high16=0, sc=0;
367 	bool content_ok = false, len_overflow = false;
368 
369 #ifdef USE_NEW_RX_INTERRUPT
370 	int i;
371 	spin_lock(&priv->lock);
372 	for (i=0; i<NUM_RX_BD; i++) {
373 		pdata_tmp = priv->rx_cyclic_buf + i*RX_BD_BUF_SIZE;
374 		agc_status_and_pkt_exist_flag = (*((u16*)(pdata_tmp+10))); //check rx_intf_pl_to_m_axis.v. FPGA TODO: add pkt exist 1bit flag next to gpio_status_lock_by_sig_valid
375 		if ( agc_status_and_pkt_exist_flag==0 ) // no packet in the buffer
376 			continue;
377 #else
378 	static u8 target_buf_idx_old = 0;
379 	spin_lock(&priv->lock);
380 	while(1) { // loop all rx buffers that have new rx packets
381 		pdata_tmp = priv->rx_cyclic_buf + target_buf_idx_old*RX_BD_BUF_SIZE; // our header insertion is at the beginning
382 		agc_status_and_pkt_exist_flag = (*((u16*)(pdata_tmp+10)));
383 		if ( agc_status_and_pkt_exist_flag==0 ) // no packet in the buffer
384 			break;
385 #endif
386 
387 		tsft_low =     (*((u32*)(pdata_tmp+0 )));
388 		tsft_high =    (*((u32*)(pdata_tmp+4 )));
389 		rssi_val =     (*((u16*)(pdata_tmp+8 )));
390 		len =          (*((u16*)(pdata_tmp+12)));
391 
392 		len_overflow = (len>(RX_BD_BUF_SIZE-16)?true:false);
393 
394 		rate_idx =     (*((u16*)(pdata_tmp+14)));
395 		ht_flag  =     ((rate_idx&0x10)!=0);
396 		short_gi =     ((rate_idx&0x20)!=0);
397 		ht_aggr  =     (ht_flag & ((rate_idx&0x40)!=0));
398 		ht_aggr_last = (ht_flag & ((rate_idx&0x80)!=0));
399 		rate_idx =     (rate_idx&0x1F);
400 
401 		fcs_ok = ( len_overflow?0:(*(( u8*)(pdata_tmp+16+len-1))) );
402 
403 		//phy_rx_sn_hw = (fcs_ok&(NUM_RX_BD-1));
404 		// phy_rx_sn_hw = (fcs_ok&0x7f);//0x7f is FPGA limitation
405 		// dma_driver_buf_idx_mod = (state.residue&0x7f);
406 		fcs_ok = ((fcs_ok&0x80)!=0);
407 
408 		if ( (len>=14 && (!len_overflow)) && (rate_idx>=8 && rate_idx<=23)) {
409 			// if ( phy_rx_sn_hw!=dma_driver_buf_idx_mod) {
410 			// 	printk("%s openwifi_rx_interrupt: WARNING sn %d next buf_idx %d!\n", sdr_compatible_str,phy_rx_sn_hw,dma_driver_buf_idx_mod);
411 			// }
412 			content_ok = true;
413 		} else {
414 			printk("%s openwifi_rx_interrupt: WARNING content!\n", sdr_compatible_str);
415 			content_ok = false;
416 		}
417 
418 		rssi_val = (rssi_val>>1);
419 		if ( (rssi_val+128)<priv->rssi_correction )
420 			signal = -128;
421 		else
422 			signal = rssi_val - priv->rssi_correction;
423 
424 		// fc_di =        (*((u32*)(pdata_tmp+16)));
425 		// addr1_high16 = (*((u16*)(pdata_tmp+16+4)));
426 		// addr1_low32  = (*((u32*)(pdata_tmp+16+4+2)));
427 		// addr2_high16 = (*((u16*)(pdata_tmp+16+6+4)));
428 		// addr2_low32  = (*((u32*)(pdata_tmp+16+6+4+2)));
429 		// addr3_high16 = (*((u16*)(pdata_tmp+16+12+4)));
430 		// addr3_low32  = (*((u32*)(pdata_tmp+16+12+4+2)));
431 		if ( (priv->drv_rx_reg_val[DRV_RX_REG_IDX_PRINT_CFG]&2) || ( (priv->drv_rx_reg_val[DRV_RX_REG_IDX_PRINT_CFG]&1) && fcs_ok==0 ) ) {
432 			hdr = (struct ieee80211_hdr *)(pdata_tmp+16);
433 			addr1_low32  = *((u32*)(hdr->addr1+2));
434 			addr1_high16 = *((u16*)(hdr->addr1));
435 			if (len>=20) {
436 				addr2_low32  = *((u32*)(hdr->addr2+2));
437 				addr2_high16 = *((u16*)(hdr->addr2));
438 			}
439 			if (len>=26) {
440 				addr3_low32  = *((u32*)(hdr->addr3+2));
441 				addr3_high16 = *((u16*)(hdr->addr3));
442 			}
443 			if (len>=28)
444 				sc = hdr->seq_ctrl;
445 
446 			if ( (addr1_low32!=0xffffffff || addr1_high16!=0xffff) || (priv->drv_rx_reg_val[DRV_RX_REG_IDX_PRINT_CFG]&4) )
447 				printk("%s openwifi_rx_interrupt:%4dbytes ht%d aggr%d/%d sgi%d %3dM FC%04x DI%04x addr1/2/3:%04x%08x/%04x%08x/%04x%08x SC%04x fcs%d buf_idx%d %ddBm\n", sdr_compatible_str,
448 					len, ht_flag, ht_aggr, ht_aggr_last, short_gi, wifi_rate_table[rate_idx], hdr->frame_control, hdr->duration_id,
449 					reverse16(addr1_high16), reverse32(addr1_low32), reverse16(addr2_high16), reverse32(addr2_low32), reverse16(addr3_high16), reverse32(addr3_low32),
450 #ifdef USE_NEW_RX_INTERRUPT
451 					sc, fcs_ok, i, signal);
452 #else
453 					sc, fcs_ok, target_buf_idx_old, signal);
454 #endif
455 		}
456 
457 		// priv->phy_rx_sn_hw_old = phy_rx_sn_hw;
458 		if (content_ok) {
459 			skb = dev_alloc_skb(len);
460 			if (skb) {
461 				skb_put_data(skb,pdata_tmp+16,len);
462 
463 				rx_status.antenna = priv->runtime_rx_ant_cfg;
464 				// def in ieee80211_rate openwifi_rates 0~11. 0~3 11b(1M~11M), 4~11 11a/g(6M~54M)
465 				rx_status.rate_idx = wifi_rate_table_mapping[rate_idx];
466 				rx_status.signal = signal;
467 				rx_status.freq = dev->conf.chandef.chan->center_freq;
468 				rx_status.band = dev->conf.chandef.chan->band;
469 				rx_status.mactime = ( ( (u64)tsft_low ) | ( ((u64)tsft_high)<<32 ) );
470 				rx_status.flag |= RX_FLAG_MACTIME_START;
471 				if (!fcs_ok)
472 					rx_status.flag |= RX_FLAG_FAILED_FCS_CRC;
473 				if (rate_idx <= 15)
474 					rx_status.encoding = RX_ENC_LEGACY;
475 				else
476 					rx_status.encoding = RX_ENC_HT;
477 				rx_status.bw = RATE_INFO_BW_20;
478 				if (short_gi)
479 					rx_status.enc_flags |= RX_ENC_FLAG_SHORT_GI;
480 				if(ht_aggr)
481 				{
482 					rx_status.ampdu_reference = priv->ampdu_reference;
483 					rx_status.flag |= RX_FLAG_AMPDU_DETAILS | RX_FLAG_AMPDU_LAST_KNOWN;
484 					if (ht_aggr_last)
485 						rx_status.flag |= RX_FLAG_AMPDU_IS_LAST;
486 				}
487 
488 				memcpy(IEEE80211_SKB_RXCB(skb), &rx_status, sizeof(rx_status)); // put rx_status into skb->cb, from now on skb->cb is not dma_dsts any more.
489 				ieee80211_rx_irqsafe(dev, skb); // call mac80211 function
490 			} else
491 				printk("%s openwifi_rx_interrupt: WARNING dev_alloc_skb failed!\n", sdr_compatible_str);
492 
493 			if(ht_aggr_last)
494 				priv->ampdu_reference++;
495 		}
496 		(*((u16*)(pdata_tmp+10))) = 0; // clear the field (set by rx_intf_pl_to_m_axis.v) to indicate the packet has been processed
497 		loop_count++;
498 #ifndef USE_NEW_RX_INTERRUPT
499 		target_buf_idx_old=((target_buf_idx_old+1)&(NUM_RX_BD-1));
500 #endif
501 	}
502 
503 	if ( loop_count!=1 && (priv->drv_rx_reg_val[DRV_RX_REG_IDX_PRINT_CFG]&1) )
504 		printk("%s openwifi_rx_interrupt: WARNING loop_count %d\n", sdr_compatible_str,loop_count);
505 
506 // openwifi_rx_interrupt_out:
507 	spin_unlock(&priv->lock);
508 	return IRQ_HANDLED;
509 }
510 
511 static irqreturn_t openwifi_tx_interrupt(int irq, void *dev_id)
512 {
513 	struct ieee80211_hw *dev = dev_id;
514 	struct openwifi_priv *priv = dev->priv;
515 	struct openwifi_ring *ring;
516 	struct sk_buff *skb;
517 	struct ieee80211_tx_info *info;
518 	u32 reg_val1, hw_queue_len, reg_val2, prio, queue_idx, dma_fifo_no_room_flag, num_slot_random, cw, loop_count=0;
519 	u16 seq_no, pkt_cnt, blk_ack_ssn, start_idx;
520 	u8 nof_retx=-1, last_bd_rd_idx, i;
521 	u64 blk_ack_bitmap;
522 	// u16 prio_rd_idx_store[64]={0};
523 	bool tx_fail=false;
524 
525 	spin_lock(&priv->lock);
526 
527 	while(1) { // loop all packets that have been sent by FPGA
528 		reg_val1 = tx_intf_api->TX_INTF_REG_PKT_INFO1_read();
529         reg_val2 = tx_intf_api->TX_INTF_REG_PKT_INFO2_read();
530 		blk_ack_bitmap = (tx_intf_api->TX_INTF_REG_PKT_INFO3_read() | ((u64)tx_intf_api->TX_INTF_REG_PKT_INFO4_read())<<32);
531 
532 		if (reg_val1!=0xFFFFFFFF) {
533 			nof_retx = (reg_val1&0xF);
534 			last_bd_rd_idx = ((reg_val1>>5)&(NUM_TX_BD-1));
535 			prio = ((reg_val1>>17)&0x3);
536 			num_slot_random = ((reg_val1>>19)&0x1FF);
537 			//num_slot_random = ((0xFF80000 &reg_val1)>>(2+5+NUM_BIT_MAX_PHY_TX_SN+NUM_BIT_MAX_NUM_HW_QUEUE));
538 			cw = ((reg_val1>>28)&0xF);
539 			//cw = ((0xF0000000 & reg_val1) >> 28);
540 			if(cw > 10) {
541 				cw = 10 ;
542 				num_slot_random += 512 ;
543 			}
544 			pkt_cnt = (reg_val2&0x3F);
545 			blk_ack_ssn = ((reg_val2>>6)&0xFFF);
546 
547 			ring = &(priv->tx_ring[prio]);
548 
549 			if ( ring->stop_flag == 1) {
550 				// Wake up Linux queue if FPGA and driver ring have room
551 				queue_idx = ((reg_val1>>15)&(MAX_NUM_HW_QUEUE-1));
552 				dma_fifo_no_room_flag = tx_intf_api->TX_INTF_REG_S_AXIS_FIFO_NO_ROOM_read();
553 				hw_queue_len = tx_intf_api->TX_INTF_REG_QUEUE_FIFO_DATA_COUNT_read();
554 
555 				if ( ((dma_fifo_no_room_flag>>queue_idx)&1)==0 && (NUM_TX_BD-((hw_queue_len>>(queue_idx*8))&0xFF))>=RING_ROOM_THRESHOLD ) {
556 					// printk("%s openwifi_tx_interrupt: WARNING ieee80211_wake_queue loop %d call %d\n", sdr_compatible_str, loop_count, priv->call_counter);
557 					printk("%s openwifi_tx_interrupt: WARNING ieee80211_wake_queue prio %d queue %d no room flag %x hw queue len %08x wr %d rd %d\n", sdr_compatible_str,
558 					prio, queue_idx, dma_fifo_no_room_flag, hw_queue_len, ring->bd_wr_idx, last_bd_rd_idx);
559 					ieee80211_wake_queue(dev, prio);
560 					ring->stop_flag = 0;
561 				}
562 			}
563 
564 			for(i = 1; i <= pkt_cnt; i++)
565 			{
566 				ring->bd_rd_idx = (last_bd_rd_idx + i - pkt_cnt + 64)%64;
567 				seq_no = ring->bds[ring->bd_rd_idx].seq_no;
568 				skb = ring->bds[ring->bd_rd_idx].skb_linked;
569 
570 				dma_unmap_single(priv->tx_chan->device->dev,ring->bds[ring->bd_rd_idx].dma_mapping_addr,
571 						skb->len, DMA_MEM_TO_DEV);
572 
573 				info = IEEE80211_SKB_CB(skb);
574 				ieee80211_tx_info_clear_status(info);
575 
576 				// Aggregation packet
577 				if(pkt_cnt > 1)
578 				{
579 					start_idx = (seq_no>=blk_ack_ssn) ? (seq_no-blk_ack_ssn) : (seq_no+((~blk_ack_ssn+1)&0x0FFF));
580 					tx_fail = (((blk_ack_bitmap>>start_idx)&0x1)==0);
581 					info->flags |= IEEE80211_TX_STAT_AMPDU;
582 					info->status.ampdu_len = 1;
583 					info->status.ampdu_ack_len = (tx_fail == true) ? 0 : 1;
584 
585 					skb_pull(skb, LEN_MPDU_DELIM);
586 					//skb_trim(skb, num_byte_pad_skb);
587 				}
588 				// Normal packet
589 				else
590 				{
591 					tx_fail = ((blk_ack_bitmap&0x1)==0);
592 					info->flags &= (~IEEE80211_TX_CTL_AMPDU);
593 				}
594 
595 				if (tx_fail == false)
596 					info->flags |= IEEE80211_TX_STAT_ACK;
597 
598 				info->status.rates[0].count = nof_retx + 1; //according to our test, the 1st rate is the most important. we only do retry on the 1st rate
599 				info->status.rates[1].idx = -1;
600 				info->status.rates[2].idx = -1;
601 				info->status.rates[3].idx = -1;//in mac80211.h: #define IEEE80211_TX_MAX_RATES	4
602 				info->status.antenna = priv->runtime_tx_ant_cfg;
603 
604 				if ( tx_fail && ((priv->drv_tx_reg_val[DRV_TX_REG_IDX_PRINT_CFG])&1) )
605 					printk("%s openwifi_tx_interrupt: WARNING pkt_no %d/%d tx_result [nof_retx %d pass %d] prio%d wr%d rd%d\n", sdr_compatible_str, i, pkt_cnt, nof_retx+1, !tx_fail, prio, ring->bd_wr_idx, ring->bd_rd_idx);
606 				if ( ( (!(info->flags & IEEE80211_TX_CTL_NO_ACK))||(priv->drv_tx_reg_val[DRV_TX_REG_IDX_PRINT_CFG]&4) ) && ((priv->drv_tx_reg_val[DRV_TX_REG_IDX_PRINT_CFG])&2) )
607 					printk("%s openwifi_tx_interrupt: tx_result [nof_retx %d pass %d] prio%d wr%d rd%d num_rand_slot %d cw %d \n", sdr_compatible_str, nof_retx+1, !tx_fail, prio, ring->bd_wr_idx, ring->bd_rd_idx, num_slot_random, cw);
608 
609 				ieee80211_tx_status_irqsafe(dev, skb);
610 			}
611 
612 			loop_count++;
613 
614 			// printk("%s openwifi_tx_interrupt: loop %d prio %d rd %d\n", sdr_compatible_str, loop_count, prio, ring->bd_rd_idx);
615 
616 		} else
617 			break;
618 	}
619 	if ( loop_count!=1 && ((priv->drv_tx_reg_val[DRV_TX_REG_IDX_PRINT_CFG])&1) )
620 		printk("%s openwifi_tx_interrupt: WARNING loop_count %d\n", sdr_compatible_str, loop_count);
621 
622 	spin_unlock(&priv->lock);
623 	return IRQ_HANDLED;
624 }
625 
626 u32 crc_table[16] = {0x4DBDF21C, 0x500AE278, 0x76D3D2D4, 0x6B64C2B0, 0x3B61B38C, 0x26D6A3E8, 0x000F9344, 0x1DB88320, 0xA005713C, 0xBDB26158, 0x9B6B51F4, 0x86DC4190, 0xD6D930AC, 0xCB6E20C8, 0xEDB71064, 0xF0000000};
627 u32 gen_mpdu_crc(u8 *data_in, u32 num_bytes)
628 {
629 	u32 i, crc = 0;
630 	u8 idx;
631 	for( i = 0; i < num_bytes; i++)
632 	{
633 		idx = (crc & 0x0F) ^ (data_in[i] & 0x0F);
634 		crc = (crc >> 4) ^ crc_table[idx];
635 
636 		idx = (crc & 0x0F) ^ ((data_in[i] >> 4) & 0x0F);
637 		crc = (crc >> 4) ^ crc_table[idx];
638 	}
639 
640 	return crc;
641 }
642 
643 u8 gen_mpdu_delim_crc(u16 m)
644 {
645 	u8 i, temp, c[8] = {1, 1, 1, 1, 1, 1, 1, 1}, mpdu_delim_crc;
646 
647 	for (i = 0; i < 16; i++)
648 	{
649 		temp = c[7] ^ ((m >> i) & 0x01);
650 
651 		c[7] = c[6];
652 		c[6] = c[5];
653 		c[5] = c[4];
654 		c[4] = c[3];
655 		c[3] = c[2];
656 		c[2] = c[1] ^ temp;
657 		c[1] = c[0] ^ temp;
658 		c[0] = temp;
659 	}
660 	mpdu_delim_crc = ((~c[7] & 0x01) << 0) | ((~c[6] & 0x01) << 1) | ((~c[5] & 0x01) << 2) | ((~c[4] & 0x01) << 3) | ((~c[3] & 0x01) << 4) | ((~c[2] & 0x01) << 5) | ((~c[1] & 0x01) << 6) | ((~c[0] & 0x01) << 7);
661 
662 	return mpdu_delim_crc;
663 }
664 
665 static inline struct gpio_led_data * //please align with the implementation in leds-gpio.c
666 			cdev_to_gpio_led_data(struct led_classdev *led_cdev)
667 {
668 	return container_of(led_cdev, struct gpio_led_data, cdev);
669 }
670 
671 static void openwifi_tx(struct ieee80211_hw *dev,
672 		       struct ieee80211_tx_control *control,
673 		       struct sk_buff *skb)
674 {
675 	struct openwifi_priv *priv = dev->priv;
676 	unsigned long flags;
677 	struct ieee80211_tx_info *info = IEEE80211_SKB_CB(skb);
678 	struct ieee80211_hdr *hdr = (struct ieee80211_hdr *)skb->data;
679 	struct openwifi_ring *ring = NULL;
680 	dma_addr_t dma_mapping_addr;
681 	unsigned int prio=0, i;
682 	u32 num_dma_symbol, len_mpdu = 0, len_mpdu_delim_pad = 0, num_dma_byte, len_psdu, num_byte_pad;
683 	u32 rate_signal_value,rate_hw_value=0,ack_flag;
684 	u32 pkt_need_ack=0, addr1_low32=0, addr2_low32=0, addr3_low32=0, queue_idx=2, tx_config, cts_reg, phy_hdr_config;//, openofdm_state_history;
685 	u16 addr1_high16=0, addr2_high16=0, addr3_high16=0, sc=0, cts_duration=0, cts_rate_hw_value=0, cts_rate_signal_value=0, sifs, ack_duration=0, traffic_pkt_duration;
686 	u8 fc_flag,fc_type,fc_subtype,retry_limit_raw=0,use_short_gi=0,*dma_buf,retry_limit_hw_value,rc_flags,*qos_hdr;
687 	bool use_rts_cts, use_cts_protect=false, ht_aggr_start=false, use_ht_rate=false, use_ht_aggr=false, addr_flag, cts_use_traffic_rate=false, force_use_cts_protect=false;
688 	__le16 frame_control,duration_id;
689 	u32 dma_fifo_no_room_flag, hw_queue_len;
690 	enum dma_status status;
691 
692 	static u32 addr1_low32_prev = -1, rate_hw_value_prev = -1, pkt_need_ack_prev = -1;
693 	static u16 addr1_high16_prev = -1;
694 	static __le16 duration_id_prev = -1;
695 	static unsigned int prio_prev = -1;
696 	static u8 retry_limit_raw_prev = -1;
697 	static u8 use_short_gi_prev = -1;
698 
699 	// static bool led_status=0;
700 	// struct gpio_led_data *led_dat = cdev_to_gpio_led_data(priv->led[3]);
701 
702 	// if ( (priv->phy_tx_sn&7) ==0 ) {
703 	// 	openofdm_state_history = openofdm_rx_api->OPENOFDM_RX_REG_STATE_HISTORY_read();
704 	// 	if (openofdm_state_history!=openofdm_state_history_old){
705 	// 		led_status = (~led_status);
706 	// 		openofdm_state_history_old = openofdm_state_history;
707 	// 		gpiod_set_value(led_dat->gpiod, led_status);
708 	// 	}
709 	// }
710 
711 	if (test_mode==1){
712 		printk("%s openwifi_tx: WARNING test_mode==1\n", sdr_compatible_str);
713 		goto openwifi_tx_early_out;
714 	}
715 
716 	if (skb->data_len>0) {// more data are not in linear data area skb->data
717 		printk("%s openwifi_tx: WARNING skb->data_len>0\n", sdr_compatible_str);
718 		goto openwifi_tx_early_out;
719 	}
720 
721 	len_mpdu = skb->len;
722 
723 	// get Linux priority/queue setting info and target mac address
724 	prio = skb_get_queue_mapping(skb);
725 	addr1_low32  = *((u32*)(hdr->addr1+2));
726 	ring = &(priv->tx_ring[prio]);
727 
728 	// -------------- DO your idea here! Map Linux/SW "prio" to hardware "queue_idx" -----------
729 	if (priv->slice_idx == 0xFFFFFFFF) {// use Linux default prio setting, if there isn't any slice config
730 		queue_idx = prio;
731 	} else {// customized prio to queue_idx mapping
732 		//if (fc_type==2 && fc_subtype==0 && (!addr_flag)) { // for unicast data packet only
733 		// check current packet belonging to which slice/hw-queue
734 			for (i=0; i<MAX_NUM_HW_QUEUE; i++) {
735 				if ( priv->dest_mac_addr_queue_map[i] == addr1_low32 ) {
736 					break;
737 				}
738 			}
739 		//}
740 		queue_idx = (i>=MAX_NUM_HW_QUEUE?2:i); // if no address is hit, use FPGA queue 2. because the queue 2 is the longest.
741 	}
742 	// -------------------- end of Map Linux/SW "prio" to hardware "queue_idx" ------------------
743 	// get other info from packet header
744 	addr1_high16 = *((u16*)(hdr->addr1));
745 	if (len_mpdu>=20) {
746 		addr2_low32  = *((u32*)(hdr->addr2+2));
747 		addr2_high16 = *((u16*)(hdr->addr2));
748 	}
749 	if (len_mpdu>=26) {
750 		addr3_low32  = *((u32*)(hdr->addr3+2));
751 		addr3_high16 = *((u16*)(hdr->addr3));
752 	}
753 
754 	duration_id = hdr->duration_id;
755 	frame_control=hdr->frame_control;
756 	ack_flag = (info->flags&IEEE80211_TX_CTL_NO_ACK);
757 	fc_type = ((frame_control)>>2)&3;
758 	fc_subtype = ((frame_control)>>4)&0xf;
759 	fc_flag = ( fc_type==2 || fc_type==0 || (fc_type==1 && (fc_subtype==8 || fc_subtype==9 || fc_subtype==10) ) );
760 	//if it is broadcasting or multicasting addr
761 	addr_flag = ( (addr1_low32==0 && addr1_high16==0) ||
762 	              (addr1_low32==0xFFFFFFFF && addr1_high16==0xFFFF) ||
763 				  (addr1_high16==0x3333) ||
764 				  (addr1_high16==0x0001 && hdr->addr1[2]==0x5E)  );
765 	if ( fc_flag && ( !addr_flag ) && (!ack_flag) ) { // unicast data frame
766 		pkt_need_ack = 1; //FPGA need to wait ACK after this pkt sent
767 	} else {
768 		pkt_need_ack = 0;
769 	}
770 
771 	// get Linux rate (MCS) setting
772 	rate_hw_value = ieee80211_get_tx_rate(dev, info)->hw_value;
773 	//rate_hw_value = 10; //4:6M, 5:9M, 6:12M, 7:18M, 8:24M, 9:36M, 10:48M, 11:54M
774 	if (priv->drv_tx_reg_val[DRV_TX_REG_IDX_RATE]>0 && fc_type==2 && (!addr_flag)) //rate override command
775 		rate_hw_value = priv->drv_tx_reg_val[DRV_TX_REG_IDX_RATE];
776 
777 	retry_limit_raw = info->control.rates[0].count;
778 
779 	rc_flags = info->control.rates[0].flags;
780 	use_rts_cts = ((rc_flags&IEEE80211_TX_RC_USE_RTS_CTS)!=0);
781 	use_cts_protect = ((rc_flags&IEEE80211_TX_RC_USE_CTS_PROTECT)!=0);
782 	use_ht_rate = ((rc_flags&IEEE80211_TX_RC_MCS)!=0);
783 	use_short_gi = ((rc_flags&IEEE80211_TX_RC_SHORT_GI)!=0);
784 	use_ht_aggr = ((info->flags&IEEE80211_TX_CTL_AMPDU)!=0);
785 
786 	if (use_rts_cts)
787 		printk("%s openwifi_tx: WARNING sn %d use_rts_cts is not supported!\n", sdr_compatible_str, ring->bd_wr_idx);
788 
789 	if (use_cts_protect) {
790 		cts_rate_hw_value = ieee80211_get_rts_cts_rate(dev, info)->hw_value;
791 		cts_duration = le16_to_cpu(ieee80211_ctstoself_duration(dev,info->control.vif,len_mpdu,info));
792 	} else if (force_use_cts_protect) { // could override mac80211 setting here.
793 		cts_rate_hw_value = 4; //wifi_mcs_table_11b_force_up[] translate it to 1011(6M)
794 		sifs = (priv->actual_rx_lo<2500?10:16);
795 		if (pkt_need_ack)
796 			ack_duration = 44;//assume the ack we wait use 6Mbps: 4*ceil((22+14*8)/24) + 20(preamble+SIGNAL)
797 		traffic_pkt_duration = 20 + 4*(((22+len_mpdu*8)/wifi_n_dbps_table[rate_hw_value])+1);
798 		cts_duration = traffic_pkt_duration + sifs + pkt_need_ack*(sifs+ack_duration);
799 	}
800 
801 // this is 11b stuff
802 //	if (info->flags&IEEE80211_TX_RC_USE_SHORT_PREAMBLE)
803 //		printk("%s openwifi_tx: WARNING IEEE80211_TX_RC_USE_SHORT_PREAMBLE\n", sdr_compatible_str);
804 
805 	if (len_mpdu>=28) {
806 		if (info->flags & IEEE80211_TX_CTL_ASSIGN_SEQ) {
807 			if (info->flags & IEEE80211_TX_CTL_FIRST_FRAGMENT)
808 				priv->seqno += 0x10;
809 			hdr->seq_ctrl &= cpu_to_le16(IEEE80211_SCTL_FRAG);
810 			hdr->seq_ctrl |= cpu_to_le16(priv->seqno);
811 		}
812 		sc = hdr->seq_ctrl;
813 	}
814 
815 	if ( ( (!addr_flag)||(priv->drv_tx_reg_val[DRV_TX_REG_IDX_PRINT_CFG]&4) ) && (priv->drv_tx_reg_val[DRV_TX_REG_IDX_PRINT_CFG]&2) )
816 		printk("%s openwifi_tx: %4dbytes ht%d aggr%d %3dM FC%04x DI%04x addr1/2/3:%04x%08x/%04x%08x/%04x%08x SC%04x flag%08x retr%d ack%d prio%d q%d wr%d rd%d\n", sdr_compatible_str,
817 			len_mpdu, (use_ht_rate == false ? 0 : 1), (use_ht_aggr == false ? 0 : 1), (use_ht_rate == false ? wifi_rate_all[rate_hw_value] : wifi_rate_all[rate_hw_value + 12]),frame_control,duration_id,
818 			reverse16(addr1_high16), reverse32(addr1_low32), reverse16(addr2_high16), reverse32(addr2_low32), reverse16(addr3_high16), reverse32(addr3_low32),
819 			sc, info->flags, retry_limit_raw, pkt_need_ack, prio, queue_idx,
820 			// use_rts_cts,use_cts_protect|force_use_cts_protect,wifi_rate_all[cts_rate_hw_value],cts_duration,
821 			ring->bd_wr_idx,ring->bd_rd_idx);
822 
823 		// printk("%s openwifi_tx: rate&try: %d %d %03x; %d %d %03x; %d %d %03x; %d %d %03x\n", sdr_compatible_str,
824 		// 	info->status.rates[0].idx,info->status.rates[0].count,info->status.rates[0].flags,
825 		// 	info->status.rates[1].idx,info->status.rates[1].count,info->status.rates[1].flags,
826 		// 	info->status.rates[2].idx,info->status.rates[2].count,info->status.rates[2].flags,
827 		// 	info->status.rates[3].idx,info->status.rates[3].count,info->status.rates[3].flags);
828 
829 	// -----------end of preprocess some info from header and skb----------------
830 
831 	// /* HW will perform RTS-CTS when only RTS flags is set.
832 	//  * HW will perform CTS-to-self when both RTS and CTS flags are set.
833 	//  * RTS rate and RTS duration will be used also for CTS-to-self.
834 	//  */
835 	// if (rc_flags & IEEE80211_TX_RC_USE_RTS_CTS) {
836 	// 	tx_flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
837 	// 	rts_duration = ieee80211_rts_duration(dev, priv->vif[0], // assume all vif have the same config
838 	// 					len_mpdu, info);
839 	// 	printk("%s openwifi_tx: rc_flags & IEEE80211_TX_RC_USE_RTS_CTS\n", sdr_compatible_str);
840 	// } else if (rc_flags & IEEE80211_TX_RC_USE_CTS_PROTECT) {
841 	// 	tx_flags |= ieee80211_get_rts_cts_rate(dev, info)->hw_value << 19;
842 	// 	rts_duration = ieee80211_ctstoself_duration(dev, priv->vif[0], // assume all vif have the same config
843 	// 					len_mpdu, info);
844 	// 	printk("%s openwifi_tx: rc_flags & IEEE80211_TX_RC_USE_CTS_PROTECT\n", sdr_compatible_str);
845 	// }
846 
847 	if(use_ht_aggr)
848 	{
849 		qos_hdr = ieee80211_get_qos_ctl(hdr);
850 		if(ieee80211_is_data_qos(frame_control) == false || qos_hdr[0] != priv->tid)
851 		{
852 			printk("%s openwifi_tx: WARNING packet is either not qos or tid %u does not match registered tid %u\n", sdr_compatible_str, qos_hdr[0], priv->tid);
853 			goto openwifi_tx_early_out;
854 		}
855 
856 		// psdu = [ MPDU DEL | MPDU | CRC | MPDU padding ]
857 		len_mpdu_delim_pad = ((len_mpdu + LEN_PHY_CRC)%4 == 0) ? 0 :(4 - (len_mpdu + LEN_PHY_CRC)%4);
858 		len_psdu = LEN_MPDU_DELIM + len_mpdu + LEN_PHY_CRC + len_mpdu_delim_pad;
859 
860 		if( (addr1_low32 != addr1_low32_prev) || (addr1_high16 != addr1_high16_prev) || (duration_id != duration_id_prev) ||
861 			(rate_hw_value != rate_hw_value_prev) || (use_short_gi != use_short_gi_prev) ||
862 			(prio != prio_prev) || (retry_limit_raw != retry_limit_raw_prev) || (pkt_need_ack != pkt_need_ack_prev) )
863 		{
864 			addr1_low32_prev = addr1_low32;
865 			addr1_high16_prev = addr1_high16;
866 			duration_id_prev = duration_id;
867 			rate_hw_value_prev = rate_hw_value;
868 			use_short_gi_prev = use_short_gi;
869 			prio_prev = prio;
870 			retry_limit_raw_prev = retry_limit_raw;
871 			pkt_need_ack_prev = pkt_need_ack;
872 
873 			ht_aggr_start = true;
874 		}
875 	}
876 	else
877 	{
878 		// psdu = [ MPDU ]
879 		len_psdu = len_mpdu;
880 
881 		addr1_low32_prev = -1;
882 		addr1_high16_prev = -1;
883 		duration_id_prev = -1;
884 		use_short_gi_prev = -1;
885 		rate_hw_value_prev = -1;
886 		prio_prev = -1;
887 		retry_limit_raw_prev = -1;
888 		pkt_need_ack_prev = -1;
889 	}
890 	num_dma_symbol = (len_psdu>>TX_INTF_NUM_BYTE_PER_DMA_SYMBOL_IN_BITS) + ((len_psdu&(TX_INTF_NUM_BYTE_PER_DMA_SYMBOL-1))!=0);
891 
892 	// check whether the packet is bigger than DMA buffer size
893 	num_dma_byte = (num_dma_symbol<<TX_INTF_NUM_BYTE_PER_DMA_SYMBOL_IN_BITS);
894 	if (num_dma_byte > TX_BD_BUF_SIZE) {
895 		printk("%s openwifi_tx: WARNING sn %d num_dma_byte > TX_BD_BUF_SIZE\n", sdr_compatible_str, ring->bd_wr_idx);
896 		goto openwifi_tx_early_out;
897 	}
898 
899 	// Copy MPDU delimiter and padding into sk_buff
900 	if(use_ht_aggr)
901 	{
902 		// when skb does not have enough headroom, skb_push will cause kernel panic. headroom needs to be extended if necessary
903 		if (skb_headroom(skb)<LEN_MPDU_DELIM) {
904 			struct sk_buff *skb_new; // in case original skb headroom is not enough to host MPDU delimiter
905 			printk("%s openwifi_tx: WARNING sn %d skb_headroom(skb)<LEN_MPDU_DELIM\n", sdr_compatible_str, ring->bd_wr_idx);
906 			if ((skb_new = skb_realloc_headroom(skb, LEN_MPDU_DELIM)) == NULL) {
907 				printk("%s openwifi_tx: WARNING sn %d skb_realloc_headroom failed!\n", sdr_compatible_str, ring->bd_wr_idx);
908 				goto openwifi_tx_early_out;
909 			}
910 			if (skb->sk != NULL)
911 				skb_set_owner_w(skb_new, skb->sk);
912 			dev_kfree_skb(skb);
913 			skb = skb_new;
914 		}
915 		skb_push( skb, LEN_MPDU_DELIM );
916 		dma_buf = skb->data;
917 
918 		// fill in MPDU delimiter
919 		*((u16*)(dma_buf+0)) = ((u16)(len_mpdu+LEN_PHY_CRC) << 4) & 0xFFF0;
920 		*((u8 *)(dma_buf+2)) = gen_mpdu_delim_crc(*((u16 *)dma_buf));
921 		*((u8 *)(dma_buf+3)) = 0x4e;
922 
923 		// Extend sk_buff to hold CRC + MPDU padding + empty MPDU delimiter
924 		num_byte_pad = num_dma_byte - (LEN_MPDU_DELIM + len_mpdu);
925 		if (skb_tailroom(skb)<num_byte_pad) {
926 			printk("%s openwifi_tx: WARNING sn %d skb_tailroom(skb)<num_byte_pad!\n", sdr_compatible_str, ring->bd_wr_idx);
927 			goto openwifi_tx_early_out;
928 		}
929 		skb_put( skb, num_byte_pad );
930 
931 		// fill in MPDU CRC
932 		*((u32*)(dma_buf+LEN_MPDU_DELIM+len_mpdu)) = gen_mpdu_crc(dma_buf+LEN_MPDU_DELIM, len_mpdu);
933 
934 		// fill in MPDU delimiter padding
935 		memset(dma_buf+LEN_MPDU_DELIM+len_mpdu+LEN_PHY_CRC, 0, len_mpdu_delim_pad);
936 
937 		// num_dma_byte is on 8-byte boundary and len_psdu is on 4 byte boundary.
938 		// If they have different lengths, add "empty MPDU delimiter" for alignment
939 		if(num_dma_byte == len_psdu + 4)
940 		{
941 			*((u32*)(dma_buf+len_psdu)) = 0x4e140000;
942 			len_psdu = num_dma_byte;
943 		}
944 	}
945 	else
946 	{
947 		// Extend sk_buff to hold padding
948 		num_byte_pad = num_dma_byte - len_mpdu;
949 		if (skb_tailroom(skb)<num_byte_pad) {
950 			printk("%s openwifi_tx: WARNING sn %d skb_tailroom(skb)<num_byte_pad!\n", sdr_compatible_str, ring->bd_wr_idx);
951 			goto openwifi_tx_early_out;
952 		}
953 		skb_put( skb, num_byte_pad );
954 
955 		dma_buf = skb->data;
956 	}
957 //	for(i = 0; i <= num_dma_symbol; i++)
958 //		printk("%16llx\n", (*(u64*)(&(dma_buf[i*8]))));
959 
960 	rate_signal_value = (use_ht_rate ? rate_hw_value : wifi_mcs_table_11b_force_up[rate_hw_value]);
961 
962 	retry_limit_hw_value = ( retry_limit_raw==0?0:((retry_limit_raw - 1)&0xF) );
963 
964 	cts_rate_signal_value = wifi_mcs_table_11b_force_up[cts_rate_hw_value];
965 	cts_reg = ((use_cts_protect|force_use_cts_protect)<<31 | cts_use_traffic_rate<<30 | cts_duration<<8 | cts_rate_signal_value<<4 | rate_signal_value);
966 	tx_config = ( prio<<26 | ring->bd_wr_idx<<20 | queue_idx<<18 | retry_limit_hw_value<<14 | pkt_need_ack<<13 | (len_mpdu+LEN_PHY_CRC) );
967 	phy_hdr_config = ( ht_aggr_start<<20 | rate_hw_value<<16 | use_ht_rate<<15 | use_short_gi<<14 | use_ht_aggr<<13 | len_psdu );
968 
969 	/* We must be sure that tx_flags is written last because the HW
970 	 * looks at it to check if the rest of data is valid or not
971 	 */
972 	//wmb();
973 	// entry->flags = cpu_to_le32(tx_flags);
974 	/* We must be sure this has been written before following HW
975 	 * register write, because this write will make the HW attempts
976 	 * to DMA the just-written data
977 	 */
978 	//wmb();
979 
980 	spin_lock_irqsave(&priv->lock, flags); // from now on, we'd better avoid interrupt because ring->stop_flag is shared with interrupt
981 
982 	// -------------check whether FPGA dma fifo and queue (queue_idx) has enough room-------------
983 	dma_fifo_no_room_flag = tx_intf_api->TX_INTF_REG_S_AXIS_FIFO_NO_ROOM_read();
984 	hw_queue_len = tx_intf_api->TX_INTF_REG_QUEUE_FIFO_DATA_COUNT_read();
985 	if ( ((dma_fifo_no_room_flag>>queue_idx)&1) || ((NUM_TX_BD-((hw_queue_len>>(queue_idx*8))&0xFF))<RING_ROOM_THRESHOLD)  || ring->stop_flag==1 ) {
986 		ieee80211_stop_queue(dev, prio); // here we should stop those prio related to the queue idx flag set in TX_INTF_REG_S_AXIS_FIFO_NO_ROOM_read
987 		printk("%s openwifi_tx: WARNING ieee80211_stop_queue prio %d queue %d no room flag %x hw queue len %08x request %d wr %d rd %d\n", sdr_compatible_str,
988 		prio, queue_idx, dma_fifo_no_room_flag, hw_queue_len, num_dma_symbol, ring->bd_wr_idx, ring->bd_rd_idx);
989 		ring->stop_flag = 1;
990 		goto openwifi_tx_early_out_after_lock;
991 	}
992 	// --------end of check whether FPGA fifo (queue_idx) has enough room------------
993 
994 	status = dma_async_is_tx_complete(priv->tx_chan, priv->tx_cookie, NULL, NULL);
995 	if (status!=DMA_COMPLETE) {
996 		printk("%s openwifi_tx: WARNING status!=DMA_COMPLETE\n", sdr_compatible_str);
997 		goto openwifi_tx_early_out_after_lock;
998 	}
999 
1000 //-------------------------fire skb DMA to hardware----------------------------------
1001 	dma_mapping_addr = dma_map_single(priv->tx_chan->device->dev, dma_buf,
1002 				 num_dma_byte, DMA_MEM_TO_DEV);
1003 
1004 	if (dma_mapping_error(priv->tx_chan->device->dev,dma_mapping_addr)) {
1005 		// dev_err(priv->tx_chan->device->dev, "sdr,sdr openwifi_tx: WARNING TX DMA mapping error\n");
1006 		printk("%s openwifi_tx: WARNING sn %d TX DMA mapping error\n", sdr_compatible_str, ring->bd_wr_idx);
1007 		goto openwifi_tx_early_out_after_lock;
1008 	}
1009 
1010 	sg_init_table(&(priv->tx_sg), 1); // only need to be initialized once in openwifi_start
1011 	sg_dma_address( &(priv->tx_sg) ) = dma_mapping_addr;
1012 	sg_dma_len( &(priv->tx_sg) ) = num_dma_byte;
1013 
1014 	tx_intf_api->TX_INTF_REG_CTS_TOSELF_CONFIG_write(cts_reg);
1015 	tx_intf_api->TX_INTF_REG_TX_CONFIG_write(tx_config);
1016 	tx_intf_api->TX_INTF_REG_PHY_HDR_CONFIG_write(phy_hdr_config);
1017 	priv->txd = priv->tx_chan->device->device_prep_slave_sg(priv->tx_chan, &(priv->tx_sg),1,DMA_MEM_TO_DEV, DMA_CTRL_ACK | DMA_PREP_INTERRUPT, NULL);
1018 	if (!(priv->txd)) {
1019 		printk("%s openwifi_tx: WARNING sn %d device_prep_slave_sg %p\n", sdr_compatible_str, ring->bd_wr_idx, (void*)(priv->txd));
1020 		goto openwifi_tx_after_dma_mapping;
1021 	}
1022 
1023 	priv->tx_cookie = priv->txd->tx_submit(priv->txd);
1024 
1025 	if (dma_submit_error(priv->tx_cookie)) {
1026 		printk("%s openwifi_tx: WARNING sn %d dma_submit_error(tx_cookie) %d\n", sdr_compatible_str, ring->bd_wr_idx, (u32)(priv->tx_cookie));
1027 		goto openwifi_tx_after_dma_mapping;
1028 	}
1029 
1030 	// seems everything is ok. let's mark this pkt in bd descriptor ring
1031 	ring->bds[ring->bd_wr_idx].seq_no = (sc&IEEE80211_SCTL_SEQ)>>4;
1032 	ring->bds[ring->bd_wr_idx].skb_linked = skb;
1033 	ring->bds[ring->bd_wr_idx].dma_mapping_addr = dma_mapping_addr;
1034 
1035 	ring->bd_wr_idx = ((ring->bd_wr_idx+1)&(NUM_TX_BD-1));
1036 
1037 	dma_async_issue_pending(priv->tx_chan);
1038 
1039 	spin_unlock_irqrestore(&priv->lock, flags);
1040 
1041 	return;
1042 
1043 openwifi_tx_after_dma_mapping:
1044 	dma_unmap_single(priv->tx_chan->device->dev, dma_mapping_addr, num_dma_byte, DMA_MEM_TO_DEV);
1045 
1046 openwifi_tx_early_out_after_lock:
1047 	dev_kfree_skb(skb);
1048 	spin_unlock_irqrestore(&priv->lock, flags);
1049 	// printk("%s openwifi_tx: WARNING openwifi_tx_after_dma_mapping phy_tx_sn %d queue %d\n", sdr_compatible_str,priv->phy_tx_sn,queue_idx);
1050 	return;
1051 
1052 openwifi_tx_early_out:
1053 	dev_kfree_skb(skb);
1054 	// printk("%s openwifi_tx: WARNING openwifi_tx_early_out phy_tx_sn %d queue %d\n", sdr_compatible_str,priv->phy_tx_sn,queue_idx);
1055 }
1056 
1057 static int openwifi_set_antenna(struct ieee80211_hw *dev, u32 tx_ant, u32 rx_ant)
1058 {
1059 	struct openwifi_priv *priv = dev->priv;
1060 	u8 fpga_tx_ant_setting, target_rx_ant;
1061 	u32 atten_mdb_tx0, atten_mdb_tx1;
1062 	struct ctrl_outs_control ctrl_out;
1063 	int ret;
1064 
1065 	printk("%s openwifi_set_antenna: tx_ant%d rx_ant%d\n",sdr_compatible_str,tx_ant,rx_ant);
1066 
1067 	if (tx_ant >= 4 || tx_ant == 0) {
1068 		return -EINVAL;
1069 	} else if (rx_ant >= 3 || rx_ant == 0) {
1070 		return -EINVAL;
1071 	}
1072 
1073 	fpga_tx_ant_setting = ((tx_ant<=2)?(tx_ant):(tx_ant+16));
1074 	target_rx_ant = ((rx_ant&1)?0:1);
1075 
1076 	// try rf chip setting firstly, only update internal state variable when rf chip succeed
1077 	atten_mdb_tx0 = ((tx_ant&1)?(AD9361_RADIO_ON_TX_ATT+priv->rf_reg_val[RF_TX_REG_IDX_ATT]):AD9361_RADIO_OFF_TX_ATT);
1078 	atten_mdb_tx1 = ((tx_ant&2)?(AD9361_RADIO_ON_TX_ATT+priv->rf_reg_val[RF_TX_REG_IDX_ATT]):AD9361_RADIO_OFF_TX_ATT);
1079 	ret = ad9361_set_tx_atten(priv->ad9361_phy, atten_mdb_tx0, true, false, true);
1080 	if (ret < 0) {
1081 		printk("%s openwifi_set_antenna: WARNING ad9361_set_tx_atten ant0 %d FAIL!\n",sdr_compatible_str, atten_mdb_tx0);
1082 		return -EINVAL;
1083 	} else {
1084 		printk("%s openwifi_set_antenna: ad9361_set_tx_atten ant0 %d OK\n",sdr_compatible_str, atten_mdb_tx0);
1085 	}
1086 	ret = ad9361_set_tx_atten(priv->ad9361_phy, atten_mdb_tx1, false, true, true);
1087 	if (ret < 0) {
1088 		printk("%s openwifi_set_antenna: WARNING ad9361_set_tx_atten ant1 %d FAIL!\n",sdr_compatible_str, atten_mdb_tx1);
1089 		return -EINVAL;
1090 	} else {
1091 		printk("%s openwifi_set_antenna: ad9361_set_tx_atten ant1 %d OK\n",sdr_compatible_str, atten_mdb_tx1);
1092 	}
1093 
1094 	ctrl_out.en_mask = priv->ctrl_out.en_mask;
1095 	ctrl_out.index = (target_rx_ant==0?AD9361_CTRL_OUT_INDEX_ANT0:AD9361_CTRL_OUT_INDEX_ANT1);
1096 	ret = ad9361_ctrl_outs_setup(priv->ad9361_phy, &(ctrl_out));
1097 	if (ret < 0) {
1098 		printk("%s openwifi_set_antenna: WARNING ad9361_ctrl_outs_setup en_mask 0x%02x index 0x%02x FAIL!\n",sdr_compatible_str, ctrl_out.en_mask, ctrl_out.index);
1099 		return -EINVAL;
1100 	} else {
1101 		printk("%s openwifi_set_antenna: ad9361_ctrl_outs_setup en_mask 0x%02x index 0x%02x\n",sdr_compatible_str, ctrl_out.en_mask, ctrl_out.index);
1102 	}
1103 
1104 	tx_intf_api->TX_INTF_REG_ANT_SEL_write(fpga_tx_ant_setting);
1105 	ret = tx_intf_api->TX_INTF_REG_ANT_SEL_read();
1106 	if (ret != fpga_tx_ant_setting) {
1107 		printk("%s openwifi_set_antenna: WARNING TX_INTF_REG_ANT_SEL_write target %d read back %d\n",sdr_compatible_str, fpga_tx_ant_setting, ret);
1108 		return -EINVAL;
1109 	} else {
1110 		printk("%s openwifi_set_antenna: TX_INTF_REG_ANT_SEL_write value %d\n",sdr_compatible_str, ret);
1111 	}
1112 
1113 	rx_intf_api->RX_INTF_REG_ANT_SEL_write(target_rx_ant);
1114 	ret = rx_intf_api->RX_INTF_REG_ANT_SEL_read();
1115 	if (ret != target_rx_ant) {
1116 		printk("%s openwifi_set_antenna: WARNING RX_INTF_REG_ANT_SEL_write target %d read back %d\n",sdr_compatible_str, target_rx_ant, ret);
1117 		return -EINVAL;
1118 	} else {
1119 		printk("%s openwifi_set_antenna: RX_INTF_REG_ANT_SEL_write value %d\n",sdr_compatible_str, ret);
1120 	}
1121 
1122 	// update internal state variable
1123 	priv->runtime_tx_ant_cfg = tx_ant;
1124 	priv->runtime_rx_ant_cfg = rx_ant;
1125 
1126 	if (TX_OFFSET_TUNING_ENABLE)
1127 		priv->tx_intf_cfg = ((tx_ant&1)?TX_INTF_BW_20MHZ_AT_N_10MHZ_ANT0:TX_INTF_BW_20MHZ_AT_N_10MHZ_ANT1);//NO USE
1128 	else {
1129 		if (tx_ant == 3)
1130 			priv->tx_intf_cfg = TX_INTF_BW_20MHZ_AT_0MHZ_ANT_BOTH;
1131 		else
1132 			priv->tx_intf_cfg = ((tx_ant&1)?TX_INTF_BW_20MHZ_AT_0MHZ_ANT0:TX_INTF_BW_20MHZ_AT_0MHZ_ANT1);
1133 	}
1134 
1135 	priv->rx_intf_cfg = (target_rx_ant==0?RX_INTF_BW_20MHZ_AT_0MHZ_ANT0:RX_INTF_BW_20MHZ_AT_0MHZ_ANT1);
1136 	priv->ctrl_out.index=ctrl_out.index;
1137 
1138 	priv->tx_freq_offset_to_lo_MHz = tx_intf_fo_mapping[priv->tx_intf_cfg];
1139 	priv->rx_freq_offset_to_lo_MHz = rx_intf_fo_mapping[priv->rx_intf_cfg];
1140 
1141 	return 0;
1142 }
1143 static int openwifi_get_antenna(struct ieee80211_hw *dev, u32 *tx_ant, u32 *rx_ant)
1144 {
1145 	struct openwifi_priv *priv = dev->priv;
1146 
1147 	*tx_ant = priv->runtime_tx_ant_cfg;
1148 	*rx_ant = priv->runtime_rx_ant_cfg;
1149 
1150 	printk("%s openwifi_get_antenna: tx_ant%d rx_ant%d\n",sdr_compatible_str, *tx_ant, *rx_ant);
1151 
1152 	printk("%s openwifi_get_antenna: drv tx cfg %d offset %d drv rx cfg %d offset %d drv ctrl_out sel %x\n",sdr_compatible_str,
1153 	priv->tx_intf_cfg, priv->tx_freq_offset_to_lo_MHz, priv->rx_intf_cfg, priv->rx_freq_offset_to_lo_MHz, priv->ctrl_out.index);
1154 
1155 	printk("%s openwifi_get_antenna: fpga tx sel %d rx sel %d\n", sdr_compatible_str,
1156 	tx_intf_api->TX_INTF_REG_ANT_SEL_read(), rx_intf_api->RX_INTF_REG_ANT_SEL_read());
1157 
1158 	printk("%s openwifi_get_antenna: rf tx att0 %d tx att1 %d ctrl_out sel %x\n", sdr_compatible_str,
1159 	ad9361_get_tx_atten(priv->ad9361_phy, 1), ad9361_get_tx_atten(priv->ad9361_phy, 2), ad9361_spi_read(priv->ad9361_phy->spi, REG_CTRL_OUTPUT_POINTER));
1160 
1161 	return 0;
1162 }
1163 
1164 static int openwifi_start(struct ieee80211_hw *dev)
1165 {
1166 	struct openwifi_priv *priv = dev->priv;
1167 	int ret, i, rssi_half_db_offset, agc_gain_delay;//rssi_half_db_th,
1168 	u32 reg;
1169 
1170 	for (i=0; i<MAX_NUM_VIF; i++) {
1171 		priv->vif[i] = NULL;
1172 	}
1173 
1174 	// //keep software registers persistent between NIC down and up for multiple times
1175 	/*memset(priv->drv_tx_reg_val, 0, sizeof(priv->drv_tx_reg_val));
1176 	memset(priv->drv_rx_reg_val, 0, sizeof(priv->drv_rx_reg_val));
1177 	memset(priv->drv_xpu_reg_val, 0, sizeof(priv->drv_xpu_reg_val));
1178 	memset(priv->rf_reg_val,0,sizeof(priv->rf_reg_val));
1179 	priv->drv_xpu_reg_val[DRV_XPU_REG_IDX_GIT_REV] = GIT_REV;*/
1180 
1181 	//turn on radio
1182 	openwifi_set_antenna(dev, priv->runtime_tx_ant_cfg, priv->runtime_rx_ant_cfg);
1183 	reg = ad9361_get_tx_atten(priv->ad9361_phy, ((priv->runtime_tx_ant_cfg==1 || priv->runtime_tx_ant_cfg==3)?1:2));
1184 	if (reg == (AD9361_RADIO_ON_TX_ATT+priv->rf_reg_val[RF_TX_REG_IDX_ATT])) {
1185 		priv->rfkill_off = 1;// 0 off, 1 on
1186 		printk("%s openwifi_start: rfkill radio on\n",sdr_compatible_str);
1187 	}
1188 	else
1189 		printk("%s openwifi_start: WARNING rfkill radio on failed. tx att read %d require %d\n",sdr_compatible_str, reg, AD9361_RADIO_ON_TX_ATT+priv->rf_reg_val[RF_TX_REG_IDX_ATT]);
1190 
1191 	rx_intf_api->hw_init(priv->rx_intf_cfg,8,8);
1192 	tx_intf_api->hw_init(priv->tx_intf_cfg,8,8,priv->fpga_type);
1193 	openofdm_tx_api->hw_init(priv->openofdm_tx_cfg);
1194 	openofdm_rx_api->hw_init(priv->openofdm_rx_cfg);
1195 	xpu_api->hw_init(priv->xpu_cfg);
1196 
1197 	agc_gain_delay = 50; //samples
1198 	rssi_half_db_offset = 150; // to be consistent
1199 	xpu_api->XPU_REG_RSSI_DB_CFG_write(0x80000000|((rssi_half_db_offset<<16)|agc_gain_delay) );
1200 	xpu_api->XPU_REG_RSSI_DB_CFG_write((~0x80000000)&((rssi_half_db_offset<<16)|agc_gain_delay) );
1201 
1202 	openofdm_rx_api->OPENOFDM_RX_REG_POWER_THRES_write(0);
1203 	// rssi_half_db_th = 87<<1; // -62dBm // will setup in runtime in _rf_set_channel
1204 	// xpu_api->XPU_REG_LBT_TH_write(rssi_half_db_th); // set IQ rssi th step .5dB to xxx and enable it
1205 	xpu_api->XPU_REG_FORCE_IDLE_MISC_write(75); //control the duration to force ch_idle after decoding a packet due to imperfection of agc and signals
1206 
1207 	//xpu_api->XPU_REG_SEND_ACK_WAIT_TOP_write( ((40)<<16)|0 );//high 16bit 5GHz; low 16 bit 2.4GHz (Attention, current tx core has around 1.19us starting delay that makes the ack fall behind 10us SIFS in 2.4GHz! Need to improve TX in 2.4GHz!)
1208 	//xpu_api->XPU_REG_SEND_ACK_WAIT_TOP_write( ((51)<<16)|0 );//now our tx send out I/Q immediately
1209 	xpu_api->XPU_REG_SEND_ACK_WAIT_TOP_write( ((51+23)<<16)|(0+23) );//we have more time when we use FIR in AD9361
1210 
1211 	xpu_api->XPU_REG_RECV_ACK_COUNT_TOP0_write( (1<<31) | (((45+2+2)*10 + 15)<<16) | 10 );//2.4GHz. extra 300 clocks are needed when rx core fall into fake ht detection phase (rx mcs 6M)
1212 	xpu_api->XPU_REG_RECV_ACK_COUNT_TOP1_write( (1<<31) | (((51+2+2)*10 + 15)<<16) | 10 );//5GHz. extra 300 clocks are needed when rx core fall into fake ht detection phase (rx mcs 6M)
1213 
1214 	tx_intf_api->TX_INTF_REG_CTS_TOSELF_WAIT_SIFS_TOP_write( ((16*10)<<16)|(10*10) );//high 16bit 5GHz; low 16 bit 2.4GHz. counter speed 10MHz is assumed
1215 
1216 	// //xpu_api->XPU_REG_BB_RF_DELAY_write(51); // fine tuned value at 0.005us. old: dac-->ant port: 0.6us, 57 taps fir at 40MHz: 1.425us; round trip: 2*(0.6+1.425)=4.05us; 4.05*10=41
1217 	// xpu_api->XPU_REG_BB_RF_DELAY_write(47);//add .5us for slightly longer fir -- already in xpu.c
1218 	xpu_api->XPU_REG_MAC_ADDR_write(priv->mac_addr);
1219 
1220 	// setup time schedule of 4 slices
1221 	// slice 0
1222 	xpu_api->XPU_REG_SLICE_COUNT_TOTAL_write(50000-1); // total 50ms
1223 	xpu_api->XPU_REG_SLICE_COUNT_START_write(0); //start 0ms
1224 	xpu_api->XPU_REG_SLICE_COUNT_END_write(50000-1); //end 50ms
1225 
1226 	// slice 1
1227 	xpu_api->XPU_REG_SLICE_COUNT_TOTAL_write((1<<20)|(50000-1)); // total 50ms
1228 	xpu_api->XPU_REG_SLICE_COUNT_START_write((1<<20)|(0)); //start 0ms
1229 	//xpu_api->XPU_REG_SLICE_COUNT_END_write((1<<20)|(20000-1)); //end 20ms
1230 	xpu_api->XPU_REG_SLICE_COUNT_END_write((1<<20)|(50000-1)); //end 20ms
1231 
1232 	// slice 2
1233 	xpu_api->XPU_REG_SLICE_COUNT_TOTAL_write((2<<20)|(50000-1)); // total 50ms
1234 	//xpu_api->XPU_REG_SLICE_COUNT_START_write((2<<20)|(20000)); //start 20ms
1235 	xpu_api->XPU_REG_SLICE_COUNT_START_write((2<<20)|(0)); //start 20ms
1236 	//xpu_api->XPU_REG_SLICE_COUNT_END_write((2<<20)|(40000-1)); //end 20ms
1237 	xpu_api->XPU_REG_SLICE_COUNT_END_write((2<<20)|(50000-1)); //end 20ms
1238 
1239 	// slice 3
1240 	xpu_api->XPU_REG_SLICE_COUNT_TOTAL_write((3<<20)|(50000-1)); // total 50ms
1241 	//xpu_api->XPU_REG_SLICE_COUNT_START_write((3<<20)|(40000)); //start 40ms
1242 	xpu_api->XPU_REG_SLICE_COUNT_START_write((3<<20)|(0)); //start 40ms
1243 	//xpu_api->XPU_REG_SLICE_COUNT_END_write((3<<20)|(50000-1)); //end 20ms
1244 	xpu_api->XPU_REG_SLICE_COUNT_END_write((3<<20)|(50000-1)); //end 20ms
1245 
1246 	// all slice sync rest
1247 	xpu_api->XPU_REG_MULTI_RST_write(1<<7); //bit7 reset the counter for all queues at the same time
1248 	xpu_api->XPU_REG_MULTI_RST_write(0<<7);
1249 
1250 	//xpu_api->XPU_REG_MAC_ADDR_HIGH_write( (*( (u16*)(priv->mac_addr + 4) )) );
1251 	printk("%s openwifi_start: rx_intf_cfg %d openofdm_rx_cfg %d tx_intf_cfg %d openofdm_tx_cfg %d\n",sdr_compatible_str, priv->rx_intf_cfg, priv->openofdm_rx_cfg, priv->tx_intf_cfg, priv->openofdm_tx_cfg);
1252 	printk("%s openwifi_start: rx_freq_offset_to_lo_MHz %d tx_freq_offset_to_lo_MHz %d\n",sdr_compatible_str, priv->rx_freq_offset_to_lo_MHz, priv->tx_freq_offset_to_lo_MHz);
1253 
1254 	tx_intf_api->TX_INTF_REG_INTERRUPT_SEL_write(0x30004); //disable tx interrupt
1255 	rx_intf_api->RX_INTF_REG_INTERRUPT_TEST_write(0x100); // disable rx interrupt by interrupt test mode
1256 	rx_intf_api->RX_INTF_REG_M_AXIS_RST_write(1); // hold M AXIS in reset status
1257 
1258 	if (test_mode==1) {
1259 		printk("%s openwifi_start: test_mode==1\n",sdr_compatible_str);
1260 		goto normal_out;
1261 	}
1262 
1263 	priv->rx_chan = dma_request_slave_channel(&(priv->pdev->dev), "rx_dma_s2mm");
1264 	if (IS_ERR(priv->rx_chan) || priv->rx_chan==NULL) {
1265 		ret = PTR_ERR(priv->rx_chan);
1266 		pr_err("%s openwifi_start: No Rx channel ret %d priv->rx_chan 0x%p\n",sdr_compatible_str, ret, priv->rx_chan);
1267 		goto err_dma;
1268 	}
1269 
1270 	priv->tx_chan = dma_request_slave_channel(&(priv->pdev->dev), "tx_dma_mm2s");
1271 	if (IS_ERR(priv->tx_chan) || priv->tx_chan==NULL) {
1272 		ret = PTR_ERR(priv->tx_chan);
1273 		pr_err("%s openwifi_start: No Tx channel ret %d priv->tx_chan 0x%p\n",sdr_compatible_str, ret, priv->tx_chan);
1274 		goto err_dma;
1275 	}
1276 	printk("%s openwifi_start: DMA channel setup successfully. priv->rx_chan 0x%p priv->tx_chan 0x%p\n",sdr_compatible_str, priv->rx_chan, priv->tx_chan);
1277 
1278 	ret = openwifi_init_rx_ring(priv);
1279 	if (ret) {
1280 		printk("%s openwifi_start: openwifi_init_rx_ring ret %d\n", sdr_compatible_str,ret);
1281 		goto err_free_rings;
1282 	}
1283 
1284 	priv->seqno=0;
1285 	for (i=0; i<MAX_NUM_SW_QUEUE; i++) {
1286 		if ((ret = openwifi_init_tx_ring(priv, i))) {
1287 			printk("%s openwifi_start: openwifi_init_tx_ring %d ret %d\n", sdr_compatible_str, i, ret);
1288 			goto err_free_rings;
1289 		}
1290 	}
1291 
1292 	if ( (ret = rx_dma_setup(dev)) ) {
1293 		printk("%s openwifi_start: rx_dma_setup ret %d\n", sdr_compatible_str,ret);
1294 		goto err_free_rings;
1295 	}
1296 
1297 	priv->irq_rx = irq_of_parse_and_map(priv->pdev->dev.of_node, 1);
1298 	ret = request_irq(priv->irq_rx, openwifi_rx_interrupt,
1299 			IRQF_SHARED, "sdr,rx_pkt_intr", dev);
1300 	if (ret) {
1301 		wiphy_err(dev->wiphy, "openwifi_start:failed to register IRQ handler openwifi_rx_interrupt\n");
1302 		goto err_free_rings;
1303 	} else {
1304 		printk("%s openwifi_start: irq_rx %d\n", sdr_compatible_str, priv->irq_rx);
1305 	}
1306 
1307 	priv->irq_tx = irq_of_parse_and_map(priv->pdev->dev.of_node, 3);
1308 	ret = request_irq(priv->irq_tx, openwifi_tx_interrupt,
1309 			IRQF_SHARED, "sdr,tx_itrpt", dev);
1310 	if (ret) {
1311 		wiphy_err(dev->wiphy, "openwifi_start: failed to register IRQ handler openwifi_tx_interrupt\n");
1312 		goto err_free_rings;
1313 	} else {
1314 		printk("%s openwifi_start: irq_tx %d\n", sdr_compatible_str, priv->irq_tx);
1315 	}
1316 
1317 	rx_intf_api->RX_INTF_REG_INTERRUPT_TEST_write(0x000); // enable rx interrupt get normal fcs valid pass through ddc to ARM
1318 	tx_intf_api->TX_INTF_REG_INTERRUPT_SEL_write(0x4); //enable tx interrupt
1319 	rx_intf_api->RX_INTF_REG_M_AXIS_RST_write(0); // release M AXIS
1320 	xpu_api->XPU_REG_TSF_LOAD_VAL_write(0,0); // reset tsf timer
1321 
1322 	//ieee80211_wake_queue(dev, 0);
1323 
1324 normal_out:
1325 	printk("%s openwifi_start: normal end\n", sdr_compatible_str);
1326 	return 0;
1327 
1328 err_free_rings:
1329 	openwifi_free_rx_ring(priv);
1330 	for (i=0; i<MAX_NUM_SW_QUEUE; i++)
1331 		openwifi_free_tx_ring(priv, i);
1332 
1333 err_dma:
1334 	ret = -1;
1335 	printk("%s openwifi_start: abnormal end ret %d\n", sdr_compatible_str, ret);
1336 	return ret;
1337 }
1338 
1339 static void openwifi_stop(struct ieee80211_hw *dev)
1340 {
1341 	struct openwifi_priv *priv = dev->priv;
1342 	u32 reg, reg1;
1343 	int i;
1344 
1345 	if (test_mode==1){
1346 		pr_info("%s openwifi_stop: test_mode==1\n", sdr_compatible_str);
1347 		goto normal_out;
1348 	}
1349 
1350 	//turn off radio
1351 	#if 1
1352 	ad9361_tx_mute(priv->ad9361_phy, 1);
1353 	reg = ad9361_get_tx_atten(priv->ad9361_phy, 2);
1354 	reg1 = ad9361_get_tx_atten(priv->ad9361_phy, 1);
1355 	if (reg == AD9361_RADIO_OFF_TX_ATT && reg1 == AD9361_RADIO_OFF_TX_ATT ) {
1356 		priv->rfkill_off = 0;// 0 off, 1 on
1357 		printk("%s openwifi_stop: rfkill radio off\n",sdr_compatible_str);
1358 	}
1359 	else
1360 		printk("%s openwifi_stop: WARNING rfkill radio off failed. tx att read %d %d require %d\n",sdr_compatible_str, reg, reg1, AD9361_RADIO_OFF_TX_ATT);
1361 	#endif
1362 
1363 	//ieee80211_stop_queue(dev, 0);
1364 	tx_intf_api->TX_INTF_REG_INTERRUPT_SEL_write(0x30004); //disable tx interrupt
1365 	rx_intf_api->RX_INTF_REG_INTERRUPT_TEST_write(0x100); // disable fcs_valid by interrupt test mode
1366 	rx_intf_api->RX_INTF_REG_M_AXIS_RST_write(1); // hold M AXIS in reset status
1367 
1368 	for (i=0; i<MAX_NUM_VIF; i++) {
1369 		priv->vif[i] = NULL;
1370 	}
1371 
1372 	openwifi_free_rx_ring(priv);
1373 	for (i=0; i<MAX_NUM_SW_QUEUE; i++)
1374 		openwifi_free_tx_ring(priv, i);
1375 
1376 	pr_info("%s openwifi_stop: dropped channel %s\n", sdr_compatible_str, dma_chan_name(priv->rx_chan));
1377 	dmaengine_terminate_all(priv->rx_chan);
1378 	dma_release_channel(priv->rx_chan);
1379 	pr_info("%s openwifi_stop: dropped channel %s\n", sdr_compatible_str, dma_chan_name(priv->tx_chan));
1380 	dmaengine_terminate_all(priv->tx_chan);
1381 	dma_release_channel(priv->tx_chan);
1382 
1383 	//priv->rf->stop(dev);
1384 
1385 	free_irq(priv->irq_rx, dev);
1386 	free_irq(priv->irq_tx, dev);
1387 
1388 normal_out:
1389 	printk("%s openwifi_stop\n", sdr_compatible_str);
1390 }
1391 
1392 static u64 openwifi_get_tsf(struct ieee80211_hw *dev,
1393 			   struct ieee80211_vif *vif)
1394 {
1395 	u32 tsft_low, tsft_high;
1396 
1397 	tsft_low = xpu_api->XPU_REG_TSF_RUNTIME_VAL_LOW_read();
1398 	tsft_high = xpu_api->XPU_REG_TSF_RUNTIME_VAL_HIGH_read();
1399 	//printk("%s openwifi_get_tsf: %08x%08x\n", sdr_compatible_str,tsft_high,tsft_low);
1400 	return( ( (u64)tsft_low ) | ( ((u64)tsft_high)<<32 ) );
1401 }
1402 
1403 static void openwifi_set_tsf(struct ieee80211_hw *hw, struct ieee80211_vif *vif, u64 tsf)
1404 {
1405 	u32 tsft_high = ((tsf >> 32)&0xffffffff);
1406 	u32 tsft_low  = (tsf&0xffffffff);
1407 	xpu_api->XPU_REG_TSF_LOAD_VAL_write(tsft_high,tsft_low);
1408 	printk("%s openwifi_set_tsf: %08x%08x\n", sdr_compatible_str,tsft_high,tsft_low);
1409 }
1410 
1411 static void openwifi_reset_tsf(struct ieee80211_hw *hw, struct ieee80211_vif *vif)
1412 {
1413 	xpu_api->XPU_REG_TSF_LOAD_VAL_write(0,0);
1414 	printk("%s openwifi_reset_tsf\n", sdr_compatible_str);
1415 }
1416 
1417 static int openwifi_set_rts_threshold(struct ieee80211_hw *hw, u32 value)
1418 {
1419 	printk("%s openwifi_set_rts_threshold WARNING value %d\n", sdr_compatible_str,value);
1420 	return(0);
1421 }
1422 
1423 static void openwifi_beacon_work(struct work_struct *work)
1424 {
1425 	struct openwifi_vif *vif_priv =
1426 		container_of(work, struct openwifi_vif, beacon_work.work);
1427 	struct ieee80211_vif *vif =
1428 		container_of((void *)vif_priv, struct ieee80211_vif, drv_priv);
1429 	struct ieee80211_hw *dev = vif_priv->dev;
1430 	struct ieee80211_mgmt *mgmt;
1431 	struct sk_buff *skb;
1432 
1433 	/* don't overflow the tx ring */
1434 	if (ieee80211_queue_stopped(dev, 0))
1435 		goto resched;
1436 
1437 	/* grab a fresh beacon */
1438 	skb = ieee80211_beacon_get(dev, vif);
1439 	if (!skb)
1440 		goto resched;
1441 
1442 	/*
1443 	 * update beacon timestamp w/ TSF value
1444 	 * TODO: make hardware update beacon timestamp
1445 	 */
1446 	mgmt = (struct ieee80211_mgmt *)skb->data;
1447 	mgmt->u.beacon.timestamp = cpu_to_le64(openwifi_get_tsf(dev, vif));
1448 
1449 	/* TODO: use actual beacon queue */
1450 	skb_set_queue_mapping(skb, 0);
1451 	openwifi_tx(dev, NULL, skb);
1452 
1453 resched:
1454 	/*
1455 	 * schedule next beacon
1456 	 * TODO: use hardware support for beacon timing
1457 	 */
1458 	schedule_delayed_work(&vif_priv->beacon_work,
1459 			usecs_to_jiffies(1024 * vif->bss_conf.beacon_int));
1460 }
1461 
1462 static int openwifi_add_interface(struct ieee80211_hw *dev,
1463 				 struct ieee80211_vif *vif)
1464 {
1465 	int i;
1466 	struct openwifi_priv *priv = dev->priv;
1467 	struct openwifi_vif *vif_priv;
1468 
1469 	switch (vif->type) {
1470 	case NL80211_IFTYPE_AP:
1471 	case NL80211_IFTYPE_STATION:
1472 	case NL80211_IFTYPE_ADHOC:
1473 	case NL80211_IFTYPE_MONITOR:
1474 	case NL80211_IFTYPE_MESH_POINT:
1475 		break;
1476 	default:
1477 		return -EOPNOTSUPP;
1478 	}
1479 	// let's support more than 1 interface
1480 	for (i=0; i<MAX_NUM_VIF; i++) {
1481 		if (priv->vif[i] == NULL)
1482 			break;
1483 	}
1484 
1485 	printk("%s openwifi_add_interface start. vif for loop result %d\n", sdr_compatible_str, i);
1486 
1487 	if (i==MAX_NUM_VIF)
1488 		return -EBUSY;
1489 
1490 	priv->vif[i] = vif;
1491 
1492 	/* Initialize driver private area */
1493 	vif_priv = (struct openwifi_vif *)&vif->drv_priv;
1494 	vif_priv->idx = i;
1495 
1496 	vif_priv->dev = dev;
1497 	INIT_DELAYED_WORK(&vif_priv->beacon_work, openwifi_beacon_work);
1498 	vif_priv->enable_beacon = false;
1499 
1500 	printk("%s openwifi_add_interface end with vif idx %d\n", sdr_compatible_str,vif_priv->idx);
1501 
1502 	return 0;
1503 }
1504 
1505 static void openwifi_remove_interface(struct ieee80211_hw *dev,
1506 				     struct ieee80211_vif *vif)
1507 {
1508 	struct openwifi_vif *vif_priv;
1509 	struct openwifi_priv *priv = dev->priv;
1510 
1511 	vif_priv = (struct openwifi_vif *)&vif->drv_priv;
1512 	priv->vif[vif_priv->idx] = NULL;
1513 	printk("%s openwifi_remove_interface vif idx %d\n", sdr_compatible_str, vif_priv->idx);
1514 }
1515 
1516 static int openwifi_config(struct ieee80211_hw *dev, u32 changed)
1517 {
1518 	struct openwifi_priv *priv = dev->priv;
1519 	struct ieee80211_conf *conf = &dev->conf;
1520 
1521 	if (changed & IEEE80211_CONF_CHANGE_CHANNEL)
1522 		priv->rf->set_chan(dev, conf);
1523 	else
1524 		printk("%s openwifi_config changed flag %08x\n", sdr_compatible_str, changed);
1525 
1526 	return 0;
1527 }
1528 
1529 static void openwifi_bss_info_changed(struct ieee80211_hw *dev,
1530 				     struct ieee80211_vif *vif,
1531 				     struct ieee80211_bss_conf *info,
1532 				     u32 changed)
1533 {
1534 	struct openwifi_priv *priv = dev->priv;
1535 	struct openwifi_vif *vif_priv;
1536 	u32 bssid_low, bssid_high;
1537 
1538 	vif_priv = (struct openwifi_vif *)&vif->drv_priv;
1539 
1540 	//be careful: we don have valid chip, so registers addresses in priv->map->BSSID[0] are not valid! should not print it!
1541 	//printk("%s openwifi_bss_info_changed map bssid %02x%02x%02x%02x%02x%02x\n",sdr_compatible_str,priv->map->BSSID[0],priv->map->BSSID[1],priv->map->BSSID[2],priv->map->BSSID[3],priv->map->BSSID[4],priv->map->BSSID[5]);
1542 	if (changed & BSS_CHANGED_BSSID) {
1543 		printk("%s openwifi_bss_info_changed BSS_CHANGED_BSSID %02x%02x%02x%02x%02x%02x\n",sdr_compatible_str,info->bssid[0],info->bssid[1],info->bssid[2],info->bssid[3],info->bssid[4],info->bssid[5]);
1544 		// write new bssid to our HW, and do not change bssid filter
1545 		//u32 bssid_filter_high = xpu_api->XPU_REG_BSSID_FILTER_HIGH_read();
1546 		bssid_low = ( *( (u32*)(info->bssid) ) );
1547 		bssid_high = ( *( (u16*)(info->bssid+4) ) );
1548 
1549 		//bssid_filter_high = (bssid_filter_high&0x80000000);
1550 		//bssid_high = (bssid_high|bssid_filter_high);
1551 		xpu_api->XPU_REG_BSSID_FILTER_LOW_write(bssid_low);
1552 		xpu_api->XPU_REG_BSSID_FILTER_HIGH_write(bssid_high);
1553 	}
1554 
1555 	if (changed & BSS_CHANGED_BEACON_INT) {
1556 		printk("%s openwifi_bss_info_changed WARNING BSS_CHANGED_BEACON_INT %x\n",sdr_compatible_str,info->beacon_int);
1557 	}
1558 
1559 	if (changed & BSS_CHANGED_TXPOWER)
1560 		printk("%s openwifi_bss_info_changed WARNING BSS_CHANGED_TXPOWER %x\n",sdr_compatible_str,info->txpower);
1561 
1562 	if (changed & BSS_CHANGED_ERP_CTS_PROT)
1563 		printk("%s openwifi_bss_info_changed WARNING BSS_CHANGED_ERP_CTS_PROT %x\n",sdr_compatible_str,info->use_cts_prot);
1564 
1565 	if (changed & BSS_CHANGED_BASIC_RATES)
1566 		printk("%s openwifi_bss_info_changed WARNING BSS_CHANGED_BASIC_RATES %x\n",sdr_compatible_str,info->basic_rates);
1567 
1568 	if (changed & (BSS_CHANGED_ERP_SLOT | BSS_CHANGED_ERP_PREAMBLE)) {
1569 		printk("%s openwifi_bss_info_changed WARNING BSS_CHANGED_ERP_SLOT %d BSS_CHANGED_ERP_PREAMBLE %d short slot %d\n",sdr_compatible_str,
1570 		changed&BSS_CHANGED_ERP_SLOT,changed&BSS_CHANGED_ERP_PREAMBLE,info->use_short_slot);
1571 		if (info->use_short_slot && priv->use_short_slot==false) {
1572 			priv->use_short_slot=true;
1573 			xpu_api->XPU_REG_BAND_CHANNEL_write( (priv->use_short_slot<<24)|(priv->band<<16) );
1574 		} else if ((!info->use_short_slot) && priv->use_short_slot==true) {
1575 			priv->use_short_slot=false;
1576 			xpu_api->XPU_REG_BAND_CHANNEL_write( (priv->use_short_slot<<24)|(priv->band<<16) );
1577 		}
1578 	}
1579 
1580 	if (changed & BSS_CHANGED_BEACON_ENABLED) {
1581 		printk("%s openwifi_bss_info_changed WARNING BSS_CHANGED_BEACON_ENABLED\n",sdr_compatible_str);
1582 		vif_priv->enable_beacon = info->enable_beacon;
1583 	}
1584 
1585 	if (changed & (BSS_CHANGED_BEACON_ENABLED | BSS_CHANGED_BEACON)) {
1586 		cancel_delayed_work_sync(&vif_priv->beacon_work);
1587 		if (vif_priv->enable_beacon)
1588 			schedule_work(&vif_priv->beacon_work.work);
1589 		printk("%s openwifi_bss_info_changed WARNING BSS_CHANGED_BEACON_ENABLED %d BSS_CHANGED_BEACON %d\n",sdr_compatible_str,
1590 		changed&BSS_CHANGED_BEACON_ENABLED,changed&BSS_CHANGED_BEACON);
1591 	}
1592 }
1593 // helper function
1594 u32 log2val(u32 val){
1595 	u32 ret_val = 0 ;
1596 	while(val>1){
1597 		val = val >> 1 ;
1598 		ret_val ++ ;
1599 	}
1600 	return ret_val ;
1601 }
1602 
1603 static int openwifi_conf_tx(struct ieee80211_hw *hw, struct ieee80211_vif *vif, u16 queue,
1604 	      const struct ieee80211_tx_queue_params *params)
1605 {
1606 	u32 reg_val, cw_min_exp, cw_max_exp;
1607 
1608 	printk("%s openwifi_conf_tx: [queue %d], aifs: %d, cw_min: %d, cw_max: %d, txop: %d, aifs and txop ignored\n",
1609 		  sdr_compatible_str,queue,params->aifs,params->cw_min,params->cw_max,params->txop);
1610 
1611 	reg_val=xpu_api->XPU_REG_CSMA_CFG_read();
1612 	cw_min_exp = (log2val(params->cw_min + 1) & 0x0F);
1613 	cw_max_exp = (log2val(params->cw_max + 1) & 0x0F);
1614 	switch(queue){
1615 		case 0: reg_val = ( (reg_val & 0xFFFFFF00) | ((cw_min_exp | (cw_max_exp << 4)) << 0) );  break;
1616 		case 1: reg_val = ( (reg_val & 0xFFFF00FF) | ((cw_min_exp | (cw_max_exp << 4)) << 8) );  break;
1617 		case 2: reg_val = ( (reg_val & 0xFF00FFFF) | ((cw_min_exp | (cw_max_exp << 4)) << 16) ); break;
1618 		case 3: reg_val = ( (reg_val & 0x00FFFFFF) | ((cw_min_exp | (cw_max_exp << 4)) << 24) ); break;
1619 		default: printk("%s openwifi_conf_tx: WARNING queue %d does not exist",sdr_compatible_str, queue); return(0);
1620 	}
1621 	xpu_api->XPU_REG_CSMA_CFG_write(reg_val);
1622 	return(0);
1623 }
1624 
1625 static u64 openwifi_prepare_multicast(struct ieee80211_hw *dev,
1626 				     struct netdev_hw_addr_list *mc_list)
1627 {
1628 	printk("%s openwifi_prepare_multicast\n", sdr_compatible_str);
1629 	return netdev_hw_addr_list_count(mc_list);
1630 }
1631 
1632 static void openwifi_configure_filter(struct ieee80211_hw *dev,
1633 				     unsigned int changed_flags,
1634 				     unsigned int *total_flags,
1635 				     u64 multicast)
1636 {
1637 	u32 filter_flag;
1638 
1639 	(*total_flags) &= SDR_SUPPORTED_FILTERS;
1640 	(*total_flags) |= FIF_ALLMULTI; //because we need to pass all multicast (no matter it is for us or not) to upper layer
1641 
1642 	filter_flag = (*total_flags);
1643 
1644 	filter_flag = (filter_flag|UNICAST_FOR_US|BROADCAST_ALL_ONE|BROADCAST_ALL_ZERO);
1645 	//filter_flag = (filter_flag|UNICAST_FOR_US|BROADCAST_ALL_ONE|BROADCAST_ALL_ZERO|MONITOR_ALL); // all pkt will be delivered to arm
1646 
1647 	//if (priv->vif[0]->type == NL80211_IFTYPE_MONITOR)
1648 	if ((filter_flag&0xf0) == 0xf0) //FIF_BCN_PRBRESP_PROMISC/FIF_CONTROL/FIF_OTHER_BSS/FIF_PSPOLL are set means monitor mode
1649 		filter_flag = (filter_flag|MONITOR_ALL);
1650 	else
1651 		filter_flag = (filter_flag&(~MONITOR_ALL));
1652 
1653 	if ( !(filter_flag&FIF_BCN_PRBRESP_PROMISC) )
1654 		filter_flag = (filter_flag|MY_BEACON);
1655 
1656 	filter_flag = (filter_flag|FIF_PSPOLL);
1657 
1658 	xpu_api->XPU_REG_FILTER_FLAG_write(filter_flag|HIGH_PRIORITY_DISCARD_FLAG);
1659 	//xpu_api->XPU_REG_FILTER_FLAG_write(filter_flag); //do not discard any pkt
1660 
1661 	printk("%s openwifi_configure_filter MON %d M_BCN %d BST0 %d BST1 %d UST %d PB_RQ %d PS_PL %d O_BSS %d CTL %d BCN_PRP %d PCP_FL %d FCS_FL %d ALL_MUT %d\n", sdr_compatible_str,
1662 	(filter_flag>>13)&1,(filter_flag>>12)&1,(filter_flag>>11)&1,(filter_flag>>10)&1,(filter_flag>>9)&1,(filter_flag>>8)&1,(filter_flag>>7)&1,(filter_flag>>6)&1,(filter_flag>>5)&1,(filter_flag>>4)&1,(filter_flag>>3)&1,(filter_flag>>2)&1,(filter_flag>>1)&1);
1663 }
1664 
1665 static int openwifi_ampdu_action(struct ieee80211_hw *hw, struct ieee80211_vif *vif, struct ieee80211_ampdu_params *params)
1666 {
1667 	struct ieee80211_sta *sta = params->sta;
1668 	enum ieee80211_ampdu_mlme_action action = params->action;
1669 	// struct openwifi_priv *priv = hw->priv;
1670 	u16 max_tx_bytes, buf_size;
1671 	u32 ampdu_action_config;
1672 
1673 	if (!AGGR_ENABLE) {
1674 		return -EOPNOTSUPP;
1675 	}
1676 
1677 	switch (action)
1678 	{
1679 		case IEEE80211_AMPDU_TX_START:
1680 			ieee80211_start_tx_ba_cb_irqsafe(vif, sta->addr, params->tid);
1681 			break;
1682 		case IEEE80211_AMPDU_TX_STOP_CONT:
1683 		case IEEE80211_AMPDU_TX_STOP_FLUSH:
1684 		case IEEE80211_AMPDU_TX_STOP_FLUSH_CONT:
1685 			ieee80211_stop_tx_ba_cb_irqsafe(vif, sta->addr, params->tid);
1686 			break;
1687 		case IEEE80211_AMPDU_TX_OPERATIONAL:
1688 			buf_size = 4;
1689 //			buf_size = (params->buf_size) - 1;
1690 			max_tx_bytes = (1 << (IEEE80211_HT_MAX_AMPDU_FACTOR + sta->ht_cap.ampdu_factor)) - 1;
1691 			ampdu_action_config = ( sta->ht_cap.ampdu_density<<24 | buf_size<<16 | max_tx_bytes );
1692 			tx_intf_api->TX_INTF_REG_AMPDU_ACTION_CONFIG_write(ampdu_action_config);
1693 			break;
1694 		case IEEE80211_AMPDU_RX_START:
1695 			printk("%s openwifi_ampdu_action: start RX aggregation. tid %d\n", sdr_compatible_str, params->tid);
1696 			break;
1697 		case IEEE80211_AMPDU_RX_STOP:
1698 			printk("%s openwifi_ampdu_action: stop RX aggregation. tid %d\n", sdr_compatible_str, params->tid);
1699 			break;
1700 		default:
1701 			return -EOPNOTSUPP;
1702 	}
1703 
1704 	return 0;
1705 }
1706 
1707 static const struct ieee80211_ops openwifi_ops = {
1708 	.tx			       = openwifi_tx,
1709 	.start			   = openwifi_start,
1710 	.stop			   = openwifi_stop,
1711 	.add_interface	   = openwifi_add_interface,
1712 	.remove_interface  = openwifi_remove_interface,
1713 	.config			   = openwifi_config,
1714 	.bss_info_changed  = openwifi_bss_info_changed,
1715 	.conf_tx		   = openwifi_conf_tx,
1716 	.prepare_multicast = openwifi_prepare_multicast,
1717 	.configure_filter  = openwifi_configure_filter,
1718 	.rfkill_poll	   = openwifi_rfkill_poll,
1719 	.get_tsf		   = openwifi_get_tsf,
1720 	.set_tsf		   = openwifi_set_tsf,
1721 	.reset_tsf		   = openwifi_reset_tsf,
1722 	.set_rts_threshold = openwifi_set_rts_threshold,
1723 	.ampdu_action      = openwifi_ampdu_action,
1724 	.testmode_cmd	   = openwifi_testmode_cmd,
1725 };
1726 
1727 static const struct of_device_id openwifi_dev_of_ids[] = {
1728 	{ .compatible = "sdr,sdr", },
1729 	{}
1730 };
1731 MODULE_DEVICE_TABLE(of, openwifi_dev_of_ids);
1732 
1733 static int custom_match_spi_dev(struct device *dev, void *data)
1734 {
1735     const char *name = data;
1736 
1737 	bool ret = sysfs_streq(name, dev->of_node->name);
1738 	printk("%s custom_match_spi_dev %s %s %d\n", sdr_compatible_str,name, dev->of_node->name, ret);
1739 	return ret;
1740 }
1741 
1742 static int custom_match_platform_dev(struct device *dev, void *data)
1743 {
1744 	struct platform_device *plat_dev = to_platform_device(dev);
1745 	const char *name = data;
1746 	char *name_in_sys_bus_platform_devices = strstr(plat_dev->name, name);
1747 	bool match_flag = (name_in_sys_bus_platform_devices != NULL);
1748 
1749 	if (match_flag) {
1750 		printk("%s custom_match_platform_dev %s\n", sdr_compatible_str,plat_dev->name);
1751 	}
1752 	return(match_flag);
1753 }
1754 
1755 static int openwifi_dev_probe(struct platform_device *pdev)
1756 {
1757 	struct ieee80211_hw *dev;
1758 	struct openwifi_priv *priv;
1759 	int err=1, rand_val;
1760 	const char *chip_name, *fpga_model;
1761 	u32 reg;//, reg1;
1762 
1763 	struct device_node *np = pdev->dev.of_node;
1764 
1765 	struct device *tmp_dev;
1766 	struct platform_device *tmp_pdev;
1767 	struct iio_dev *tmp_indio_dev;
1768 	// struct gpio_leds_priv *tmp_led_priv;
1769 
1770 	printk("\n");
1771 
1772 	if (np) {
1773 		const struct of_device_id *match;
1774 
1775 		match = of_match_node(openwifi_dev_of_ids, np);
1776 		if (match) {
1777 			printk("%s openwifi_dev_probe: match!\n", sdr_compatible_str);
1778 			err = 0;
1779 		}
1780 	}
1781 
1782 	if (err)
1783 		return err;
1784 
1785 	dev = ieee80211_alloc_hw(sizeof(*priv), &openwifi_ops);
1786 	if (!dev) {
1787 		printk(KERN_ERR "%s openwifi_dev_probe: ieee80211 alloc failed\n",sdr_compatible_str);
1788 		err = -ENOMEM;
1789 		goto err_free_dev;
1790 	}
1791 
1792 	priv = dev->priv;
1793 	priv->pdev = pdev;
1794 
1795 	err = of_property_read_string(of_find_node_by_path("/"), "model", &fpga_model);
1796 	if(err < 0) {
1797 		printk("%s openwifi_dev_probe: WARNING unknown openwifi FPGA model %d\n",sdr_compatible_str, err);
1798 		priv->fpga_type = SMALL_FPGA;
1799 	} else {
1800 		// LARGE FPGAs (i.e. ZCU102, Z7035, ZC706)
1801 		if(strstr(fpga_model, "ZCU102") != NULL || strstr(fpga_model, "Z7035") != NULL || strstr(fpga_model, "ZC706") != NULL)
1802 			priv->fpga_type = LARGE_FPGA;
1803 		// SMALL FPGA: (i.e. ZED, ZC702, Z7020)
1804 		else if(strstr(fpga_model, "ZED") != NULL || strstr(fpga_model, "ZC702") != NULL || strstr(fpga_model, "Z7020") != NULL)
1805 			priv->fpga_type = SMALL_FPGA;
1806 	}
1807 
1808 	// //-------------find ad9361-phy driver for lo/channel control---------------
1809 	priv->actual_rx_lo = 0;
1810 	priv->actual_tx_lo = 0;
1811 	tmp_dev = bus_find_device( &spi_bus_type, NULL, "ad9361-phy", custom_match_spi_dev );
1812 	if (tmp_dev == NULL) {
1813 		printk(KERN_ERR "%s find_dev ad9361-phy failed\n",sdr_compatible_str);
1814 		err = -ENOMEM;
1815 		goto err_free_dev;
1816 	}
1817 	printk("%s bus_find_device ad9361-phy: %s. driver_data pointer %p\n", sdr_compatible_str, ((struct spi_device*)tmp_dev)->modalias, (void*)(((struct spi_device*)tmp_dev)->dev.driver_data));
1818 	if (((struct spi_device*)tmp_dev)->dev.driver_data == NULL) {
1819 		printk(KERN_ERR "%s find_dev ad9361-phy failed. dev.driver_data == NULL\n",sdr_compatible_str);
1820 		err = -ENOMEM;
1821 		goto err_free_dev;
1822 	}
1823 
1824 	priv->ad9361_phy = ad9361_spi_to_phy((struct spi_device*)tmp_dev);
1825 	if (!(priv->ad9361_phy)) {
1826 		printk(KERN_ERR "%s ad9361_spi_to_phy failed\n",sdr_compatible_str);
1827 		err = -ENOMEM;
1828 		goto err_free_dev;
1829 	}
1830 	printk("%s ad9361_spi_to_phy ad9361-phy: %s\n", sdr_compatible_str, priv->ad9361_phy->spi->modalias);
1831 
1832 	priv->ctrl_out.en_mask=0xFF;
1833 	priv->ctrl_out.index=0x16;
1834 	err = ad9361_ctrl_outs_setup(priv->ad9361_phy, &(priv->ctrl_out));
1835 	if (err < 0) {
1836 		printk("%s openwifi_dev_probe: WARNING ad9361_ctrl_outs_setup %d\n",sdr_compatible_str, err);
1837 	} else {
1838 		printk("%s openwifi_dev_probe: ad9361_ctrl_outs_setup en_mask 0x%02x index 0x%02x\n",sdr_compatible_str, priv->ctrl_out.en_mask, priv->ctrl_out.index);
1839 	}
1840 
1841 	reg = ad9361_spi_read(priv->ad9361_phy->spi, REG_CTRL_OUTPUT_POINTER);
1842 	printk("%s openwifi_dev_probe: ad9361_spi_read REG_CTRL_OUTPUT_POINTER 0x%02x\n",sdr_compatible_str, reg);
1843 	reg = ad9361_spi_read(priv->ad9361_phy->spi, REG_CTRL_OUTPUT_ENABLE);
1844 	printk("%s openwifi_dev_probe: ad9361_spi_read REG_CTRL_OUTPUT_ENABLE 0x%02x\n",sdr_compatible_str, reg);
1845 
1846 	// //-------------find driver: axi_ad9361 hdl ref design module, dac channel---------------
1847 	tmp_dev = bus_find_device( &platform_bus_type, NULL, "cf-ad9361-dds-core-lpc", custom_match_platform_dev );
1848 	if (!tmp_dev) {
1849 		printk(KERN_ERR "%s bus_find_device platform_bus_type cf-ad9361-dds-core-lpc failed\n",sdr_compatible_str);
1850 		err = -ENOMEM;
1851 		goto err_free_dev;
1852 	}
1853 
1854 	tmp_pdev = to_platform_device(tmp_dev);
1855 	if (!tmp_pdev) {
1856 		printk(KERN_ERR "%s to_platform_device failed\n",sdr_compatible_str);
1857 		err = -ENOMEM;
1858 		goto err_free_dev;
1859 	}
1860 
1861 	tmp_indio_dev = platform_get_drvdata(tmp_pdev);
1862 	if (!tmp_indio_dev) {
1863 		printk(KERN_ERR "%s platform_get_drvdata failed\n",sdr_compatible_str);
1864 		err = -ENOMEM;
1865 		goto err_free_dev;
1866 	}
1867 
1868 	priv->dds_st = iio_priv(tmp_indio_dev);
1869 	if (!(priv->dds_st)) {
1870 		printk(KERN_ERR "%s iio_priv failed\n",sdr_compatible_str);
1871 		err = -ENOMEM;
1872 		goto err_free_dev;
1873 	}
1874 	printk("%s openwifi_dev_probe: cf-ad9361-dds-core-lpc dds_st->version %08x chip_info->name %s\n",sdr_compatible_str,priv->dds_st->version,priv->dds_st->chip_info->name);
1875 	cf_axi_dds_datasel(priv->dds_st, -1, DATA_SEL_DMA);
1876 	printk("%s openwifi_dev_probe: cf_axi_dds_datasel DATA_SEL_DMA\n",sdr_compatible_str);
1877 
1878 	// //-------------find driver: axi_ad9361 hdl ref design module, adc channel---------------
1879 	// turn off radio by muting tx
1880 	// ad9361_tx_mute(priv->ad9361_phy, 1);
1881 	// reg = ad9361_get_tx_atten(priv->ad9361_phy, 2);
1882 	// reg1 = ad9361_get_tx_atten(priv->ad9361_phy, 1);
1883 	// if (reg == AD9361_RADIO_OFF_TX_ATT && reg1 == AD9361_RADIO_OFF_TX_ATT ) {
1884 	// 	priv->rfkill_off = 0;// 0 off, 1 on
1885 	// 	printk("%s openwifi_dev_probe: rfkill radio off\n",sdr_compatible_str);
1886 	// }
1887 	// else
1888 	// 	printk("%s openwifi_dev_probe: WARNING rfkill radio off failed. tx att read %d %d require %d\n",sdr_compatible_str, reg, reg1, AD9361_RADIO_OFF_TX_ATT);
1889 
1890 	// //-----------------------------parse the test_mode input--------------------------------
1891 	if (test_mode&1)
1892 		AGGR_ENABLE = true;
1893 
1894 	// if (test_mode&2)
1895 	// 	TX_OFFSET_TUNING_ENABLE = false;
1896 
1897 	priv->last_auto_fpga_lbt_th = 134;//just to avoid uninitialized
1898 	priv->rssi_correction = 43;//this will be set in real-time by _rf_set_channel()
1899 
1900 	//priv->rf_bw = 20000000; // Signal quality issue! NOT use for now. 20MHz or 40MHz. 40MHz need ddc/duc. 20MHz works in bypass mode
1901 	priv->rf_bw = 40000000; // 20MHz or 40MHz. 40MHz need ddc/duc. 20MHz works in bypass mode
1902 
1903 	priv->xpu_cfg = XPU_NORMAL;
1904 
1905 	priv->openofdm_tx_cfg = OPENOFDM_TX_NORMAL;
1906 	priv->openofdm_rx_cfg = OPENOFDM_RX_NORMAL;
1907 
1908 	printk("%s openwifi_dev_probe: priv->rf_bw == %dHz. bool for 20000000 %d, 40000000 %d\n",sdr_compatible_str, priv->rf_bw, (priv->rf_bw==20000000) , (priv->rf_bw==40000000) );
1909 	if (priv->rf_bw == 20000000) {
1910 		priv->rx_intf_cfg = RX_INTF_BYPASS;
1911 		priv->tx_intf_cfg = TX_INTF_BYPASS;
1912 		//priv->rx_freq_offset_to_lo_MHz = 0;
1913 		//priv->tx_freq_offset_to_lo_MHz = 0;
1914 	} else if (priv->rf_bw == 40000000) {
1915 		//priv->rx_intf_cfg = RX_INTF_BW_20MHZ_AT_P_10MHZ; //work
1916 		//priv->tx_intf_cfg = TX_INTF_BW_20MHZ_AT_N_10MHZ_ANT1; //work
1917 
1918 		// // test ddc at central, duc at central+10M. It works. And also change rx BW from 40MHz to 20MHz in rf_init.sh. Rx sampling rate is still 40Msps
1919 		priv->rx_intf_cfg = RX_INTF_BW_20MHZ_AT_0MHZ_ANT0;
1920 		priv->tx_intf_cfg = TX_INTF_BW_20MHZ_AT_N_10MHZ_ANT0; // Let's use rx0 tx0 as default mode, because it works for both 9361 and 9364
1921 		// // try another antenna option
1922 		//priv->rx_intf_cfg = RX_INTF_BW_20MHZ_AT_0MHZ_ANT1;
1923 		//priv->tx_intf_cfg = TX_INTF_BW_20MHZ_AT_N_10MHZ_ANT0;
1924 
1925 		#if 0
1926 		if (priv->rx_intf_cfg == DDC_BW_20MHZ_AT_N_10MHZ) {
1927 			priv->rx_freq_offset_to_lo_MHz = -10;
1928 		} else if (priv->rx_intf_cfg == DDC_BW_20MHZ_AT_P_10MHZ) {
1929 			priv->rx_freq_offset_to_lo_MHz = 10;
1930 		} else if (priv->rx_intf_cfg == DDC_BW_20MHZ_AT_0MHZ) {
1931 			priv->rx_freq_offset_to_lo_MHz = 0;
1932 		} else {
1933 			printk("%s openwifi_dev_probe: Warning! priv->rx_intf_cfg == %d\n",sdr_compatible_str,priv->rx_intf_cfg);
1934 		}
1935 		#endif
1936 	} else {
1937 		printk("%s openwifi_dev_probe: Warning! priv->rf_bw == %dHz (should be 20000000 or 40000000)\n",sdr_compatible_str, priv->rf_bw);
1938 	}
1939 
1940 	printk("%s openwifi_dev_probe: test_mode %d AGGR_ENABLE %d TX_OFFSET_TUNING_ENABLE %d init_tx_att %d\n", sdr_compatible_str, test_mode, AGGR_ENABLE, TX_OFFSET_TUNING_ENABLE, init_tx_att);
1941 
1942 	priv->runtime_tx_ant_cfg = ((priv->tx_intf_cfg==TX_INTF_BW_20MHZ_AT_0MHZ_ANT0 || priv->tx_intf_cfg==TX_INTF_BW_20MHZ_AT_N_10MHZ_ANT0)?1:(priv->tx_intf_cfg==TX_INTF_BW_20MHZ_AT_0MHZ_ANT_BOTH?3:2));
1943 	priv->runtime_rx_ant_cfg = (priv->rx_intf_cfg==RX_INTF_BW_20MHZ_AT_0MHZ_ANT0?1:2);
1944 
1945 	priv->ctrl_out.en_mask=AD9361_CTRL_OUT_EN_MASK;
1946 	priv->ctrl_out.index  =(priv->rx_intf_cfg==RX_INTF_BW_20MHZ_AT_0MHZ_ANT0?AD9361_CTRL_OUT_INDEX_ANT0:AD9361_CTRL_OUT_INDEX_ANT1);
1947 
1948 	memset(priv->drv_rx_reg_val,0,sizeof(priv->drv_rx_reg_val));
1949 	memset(priv->drv_tx_reg_val,0,sizeof(priv->drv_tx_reg_val));
1950 	memset(priv->drv_xpu_reg_val,0,sizeof(priv->drv_xpu_reg_val));
1951 	memset(priv->rf_reg_val,0,sizeof(priv->rf_reg_val));
1952 
1953 	priv->rf_reg_val[RF_TX_REG_IDX_ATT] = init_tx_att;
1954 
1955 	//let's by default turn radio on when probing
1956 	err = openwifi_set_antenna(dev, priv->runtime_tx_ant_cfg, priv->runtime_rx_ant_cfg);
1957 	if (err) {
1958 		printk("%s openwifi_dev_probe: WARNING openwifi_set_antenna FAIL %d\n",sdr_compatible_str, err);
1959 		err = -EIO;
1960 		goto err_free_dev;
1961 	}
1962 	reg = ad9361_spi_read(priv->ad9361_phy->spi, REG_CTRL_OUTPUT_POINTER);
1963 	printk("%s openwifi_dev_probe: ad9361_spi_read REG_CTRL_OUTPUT_POINTER 0x%02x\n",sdr_compatible_str, reg);
1964 	reg = ad9361_spi_read(priv->ad9361_phy->spi, REG_CTRL_OUTPUT_ENABLE);
1965 	printk("%s openwifi_dev_probe: ad9361_spi_read REG_CTRL_OUTPUT_ENABLE 0x%02x\n",sdr_compatible_str, reg);
1966 
1967 	reg = ad9361_get_tx_atten(priv->ad9361_phy, ((priv->runtime_tx_ant_cfg==1 || priv->runtime_tx_ant_cfg==3)?1:2));
1968 	if (reg == (AD9361_RADIO_ON_TX_ATT+priv->rf_reg_val[RF_TX_REG_IDX_ATT])) {
1969 		priv->rfkill_off = 1;// 0 off, 1 on
1970 		printk("%s openwifi_dev_probe: rfkill radio on\n",sdr_compatible_str);
1971 	} else
1972 		printk("%s openwifi_dev_probe: WARNING rfkill radio on failed. tx att read %d require %d\n",sdr_compatible_str, reg, AD9361_RADIO_ON_TX_ATT+priv->rf_reg_val[RF_TX_REG_IDX_ATT]);
1973 
1974 	priv->drv_xpu_reg_val[DRV_XPU_REG_IDX_GIT_REV] = GIT_REV;
1975 
1976 	// //set ad9361 in certain mode
1977 	#if 0
1978 	err = ad9361_set_trx_clock_chain_freq(priv->ad9361_phy,priv->rf_bw);
1979 	printk("%s openwifi_dev_probe: ad9361_set_trx_clock_chain_freq %dHz err %d\n",sdr_compatible_str, priv->rf_bw,err);
1980 	err = ad9361_update_rf_bandwidth(priv->ad9361_phy,priv->rf_bw,priv->rf_bw);
1981 	printk("%s openwifi_dev_probe: ad9361_update_rf_bandwidth %dHz err %d\n",sdr_compatible_str, priv->rf_bw,err);
1982 
1983 	rx_intf_api->hw_init(priv->rx_intf_cfg,8,8);
1984 	tx_intf_api->hw_init(priv->tx_intf_cfg,8,8,priv->fpga_type);
1985 	openofdm_tx_api->hw_init(priv->openofdm_tx_cfg);
1986 	openofdm_rx_api->hw_init(priv->openofdm_rx_cfg);
1987 	printk("%s openwifi_dev_probe: rx_intf_cfg %d openofdm_rx_cfg %d tx_intf_cfg %d openofdm_tx_cfg %d\n",sdr_compatible_str, priv->rx_intf_cfg, priv->openofdm_rx_cfg, priv->tx_intf_cfg, priv->openofdm_tx_cfg);
1988 	printk("%s openwifi_dev_probe: rx_freq_offset_to_lo_MHz %d tx_freq_offset_to_lo_MHz %d\n",sdr_compatible_str, priv->rx_freq_offset_to_lo_MHz, priv->tx_freq_offset_to_lo_MHz);
1989 	#endif
1990 
1991 	dev->max_rates = 1; //maximum number of alternate rate retry stages the hw can handle.
1992 
1993 	SET_IEEE80211_DEV(dev, &pdev->dev);
1994 	platform_set_drvdata(pdev, dev);
1995 
1996 	BUILD_BUG_ON(sizeof(priv->rates_2GHz) != sizeof(openwifi_2GHz_rates));
1997 	BUILD_BUG_ON(sizeof(priv->rates_5GHz) != sizeof(openwifi_5GHz_rates));
1998 	BUILD_BUG_ON(sizeof(priv->channels_2GHz) != sizeof(openwifi_2GHz_channels));
1999 	BUILD_BUG_ON(sizeof(priv->channels_5GHz) != sizeof(openwifi_5GHz_channels));
2000 
2001 	memcpy(priv->rates_2GHz, openwifi_2GHz_rates, sizeof(openwifi_2GHz_rates));
2002 	memcpy(priv->rates_5GHz, openwifi_5GHz_rates, sizeof(openwifi_5GHz_rates));
2003 	memcpy(priv->channels_2GHz, openwifi_2GHz_channels, sizeof(openwifi_2GHz_channels));
2004 	memcpy(priv->channels_5GHz, openwifi_5GHz_channels, sizeof(openwifi_5GHz_channels));
2005 
2006 	priv->band = BAND_5_8GHZ; //this can be changed by band _rf_set_channel() (2.4GHz ERP(OFDM)) (5GHz OFDM)
2007 	priv->channel = 44;  //currently useless. this can be changed by band _rf_set_channel()
2008 	priv->use_short_slot = false; //this can be changed by openwifi_bss_info_changed: BSS_CHANGED_ERP_SLOT
2009 	priv->ampdu_reference = 0;
2010 
2011 	priv->band_2GHz.band = NL80211_BAND_2GHZ;
2012 	priv->band_2GHz.channels = priv->channels_2GHz;
2013 	priv->band_2GHz.n_channels = ARRAY_SIZE(priv->channels_2GHz);
2014 	priv->band_2GHz.bitrates = priv->rates_2GHz;
2015 	priv->band_2GHz.n_bitrates = ARRAY_SIZE(priv->rates_2GHz);
2016 	priv->band_2GHz.ht_cap.ht_supported = true;
2017 	priv->band_2GHz.ht_cap.cap = IEEE80211_HT_CAP_SGI_20;
2018 	if (AGGR_ENABLE) {
2019 		priv->band_2GHz.ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_8K;
2020 		priv->band_2GHz.ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_2;
2021 	}
2022 	memset(&priv->band_2GHz.ht_cap.mcs, 0, sizeof(priv->band_2GHz.ht_cap.mcs));
2023 	priv->band_2GHz.ht_cap.mcs.rx_mask[0] = 0xff;
2024 	priv->band_2GHz.ht_cap.mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
2025 	dev->wiphy->bands[NL80211_BAND_2GHZ] = &(priv->band_2GHz);
2026 
2027 	priv->band_5GHz.band = NL80211_BAND_5GHZ;
2028 	priv->band_5GHz.channels = priv->channels_5GHz;
2029 	priv->band_5GHz.n_channels = ARRAY_SIZE(priv->channels_5GHz);
2030 	priv->band_5GHz.bitrates = priv->rates_5GHz;
2031 	priv->band_5GHz.n_bitrates = ARRAY_SIZE(priv->rates_5GHz);
2032 	priv->band_5GHz.ht_cap.ht_supported = true;
2033 	priv->band_5GHz.ht_cap.cap = IEEE80211_HT_CAP_SGI_20;
2034 	if (AGGR_ENABLE) {
2035 		priv->band_5GHz.ht_cap.ampdu_factor = IEEE80211_HT_MAX_AMPDU_8K;
2036 		priv->band_5GHz.ht_cap.ampdu_density = IEEE80211_HT_MPDU_DENSITY_2;
2037 	}
2038 	memset(&priv->band_5GHz.ht_cap.mcs, 0, sizeof(priv->band_5GHz.ht_cap.mcs));
2039 	priv->band_5GHz.ht_cap.mcs.rx_mask[0] = 0xff;
2040 	priv->band_5GHz.ht_cap.mcs.tx_params = IEEE80211_HT_MCS_TX_DEFINED;
2041 	dev->wiphy->bands[NL80211_BAND_5GHZ] = &(priv->band_5GHz);
2042 
2043 	printk("%s openwifi_dev_probe: band_2GHz.n_channels %d n_bitrates %d band_5GHz.n_channels %d n_bitrates %d\n",sdr_compatible_str,
2044 	priv->band_2GHz.n_channels,priv->band_2GHz.n_bitrates,priv->band_5GHz.n_channels,priv->band_5GHz.n_bitrates);
2045 
2046 	ieee80211_hw_set(dev, HOST_BROADCAST_PS_BUFFERING);
2047 	ieee80211_hw_set(dev, RX_INCLUDES_FCS);
2048 	ieee80211_hw_set(dev, BEACON_TX_STATUS);
2049 	if (AGGR_ENABLE) {
2050 		ieee80211_hw_set(dev, AMPDU_AGGREGATION);
2051 	}
2052 
2053 
2054 	dev->vif_data_size = sizeof(struct openwifi_vif);
2055 	dev->wiphy->interface_modes =
2056 			BIT(NL80211_IFTYPE_MONITOR)|
2057 			BIT(NL80211_IFTYPE_P2P_GO) |
2058 			BIT(NL80211_IFTYPE_P2P_CLIENT) |
2059 			BIT(NL80211_IFTYPE_AP) |
2060 			BIT(NL80211_IFTYPE_STATION) |
2061 			BIT(NL80211_IFTYPE_ADHOC) |
2062 			BIT(NL80211_IFTYPE_MESH_POINT) |
2063 			BIT(NL80211_IFTYPE_OCB);
2064 	dev->wiphy->iface_combinations = &openwifi_if_comb;
2065 	dev->wiphy->n_iface_combinations = 1;
2066 
2067 	dev->wiphy->available_antennas_tx = NUM_TX_ANT_MASK;
2068 	dev->wiphy->available_antennas_rx = NUM_RX_ANT_MASK;
2069 
2070 	dev->wiphy->regulatory_flags = (REGULATORY_STRICT_REG|REGULATORY_CUSTOM_REG); // use our own config within strict regulation
2071 	//dev->wiphy->regulatory_flags = REGULATORY_CUSTOM_REG; // use our own config
2072 	wiphy_apply_custom_regulatory(dev->wiphy, &sdr_regd);
2073 
2074 	chip_name = "ZYNQ";
2075 
2076 	/* we declare to MAC80211 all the queues except for beacon queue
2077 	 * that will be eventually handled by DRV.
2078 	 * TX rings are arranged in such a way that lower is the IDX,
2079 	 * higher is the priority, in order to achieve direct mapping
2080 	 * with mac80211, however the beacon queue is an exception and it
2081 	 * is mapped on the highst tx ring IDX.
2082 	 */
2083 	dev->queues = MAX_NUM_HW_QUEUE;
2084 	//dev->queues = 1;
2085 
2086 	ieee80211_hw_set(dev, SIGNAL_DBM);
2087 
2088 	wiphy_ext_feature_set(dev->wiphy, NL80211_EXT_FEATURE_CQM_RSSI_LIST);
2089 
2090 	priv->rf = &ad9361_rf_ops;
2091 
2092 	memset(priv->dest_mac_addr_queue_map,0,sizeof(priv->dest_mac_addr_queue_map));
2093 	priv->slice_idx = 0xFFFFFFFF;
2094 
2095 	sg_init_table(&(priv->tx_sg), 1);
2096 
2097 	get_random_bytes(&rand_val, sizeof(rand_val));
2098     rand_val%=250;
2099 	priv->mac_addr[0]=0x66;	priv->mac_addr[1]=0x55;	priv->mac_addr[2]=0x44;	priv->mac_addr[3]=0x33;	priv->mac_addr[4]=0x22;
2100 	priv->mac_addr[5]=rand_val+1;
2101 	//priv->mac_addr[5]=0x11;
2102 	if (!is_valid_ether_addr(priv->mac_addr)) {
2103 		printk(KERN_WARNING "%s openwifi_dev_probe: WARNING Invalid hwaddr! Using randomly generated MAC addr\n",sdr_compatible_str);
2104 		eth_random_addr(priv->mac_addr);
2105 	} else {
2106 		printk("%s openwifi_dev_probe: mac_addr %02x:%02x:%02x:%02x:%02x:%02x\n",sdr_compatible_str,priv->mac_addr[0],priv->mac_addr[1],priv->mac_addr[2],priv->mac_addr[3],priv->mac_addr[4],priv->mac_addr[5]);
2107 	}
2108 	SET_IEEE80211_PERM_ADDR(dev, priv->mac_addr);
2109 
2110 	spin_lock_init(&priv->lock);
2111 
2112 	err = ieee80211_register_hw(dev);
2113 	if (err) {
2114 		pr_err(KERN_ERR "%s openwifi_dev_probe: WARNING Cannot register device\n",sdr_compatible_str);
2115 		goto err_free_dev;
2116 	} else {
2117 		printk("%s openwifi_dev_probe: ieee80211_register_hw %d\n",sdr_compatible_str, err);
2118 	}
2119 
2120 	// // //--------------------hook leds (not complete yet)--------------------------------
2121 	// tmp_dev = bus_find_device( &platform_bus_type, NULL, "leds", custom_match_platform_dev ); //leds is the name in devicetree, not "compatible" field
2122 	// if (!tmp_dev) {
2123 	// 	printk(KERN_ERR "%s bus_find_device platform_bus_type leds-gpio failed\n",sdr_compatible_str);
2124 	// 	err = -ENOMEM;
2125 	// 	goto err_free_dev;
2126 	// }
2127 
2128 	// tmp_pdev = to_platform_device(tmp_dev);
2129 	// if (!tmp_pdev) {
2130 	// 	printk(KERN_ERR "%s to_platform_device failed for leds-gpio\n",sdr_compatible_str);
2131 	// 	err = -ENOMEM;
2132 	// 	goto err_free_dev;
2133 	// }
2134 
2135 	// tmp_led_priv = platform_get_drvdata(tmp_pdev);
2136 	// if (!tmp_led_priv) {
2137 	// 	printk(KERN_ERR "%s platform_get_drvdata failed for leds-gpio\n",sdr_compatible_str);
2138 	// 	err = -ENOMEM;
2139 	// 	goto err_free_dev;
2140 	// }
2141 	// printk("%s openwifi_dev_probe: leds-gpio detect %d leds!\n",sdr_compatible_str, tmp_led_priv->num_leds);
2142 	// if (tmp_led_priv->num_leds!=4){
2143 	// 	printk(KERN_ERR "%s WARNING we expect 4 leds, but actual %d leds\n",sdr_compatible_str,tmp_led_priv->num_leds);
2144 	// 	err = -ENOMEM;
2145 	// 	goto err_free_dev;
2146 	// }
2147 	// gpiod_set_value(tmp_led_priv->leds[0].gpiod, 1);//light it
2148 	// gpiod_set_value(tmp_led_priv->leds[3].gpiod, 0);//black it
2149 	// priv->num_led = tmp_led_priv->num_leds;
2150 	// priv->led[0] = &(tmp_led_priv->leds[0].cdev);
2151 	// priv->led[1] = &(tmp_led_priv->leds[1].cdev);
2152 	// priv->led[2] = &(tmp_led_priv->leds[2].cdev);
2153 	// priv->led[3] = &(tmp_led_priv->leds[3].cdev);
2154 
2155 	// snprintf(priv->led_name[0], OPENWIFI_LED_MAX_NAME_LEN, "openwifi-%s::radio", wiphy_name(dev->wiphy));
2156 	// snprintf(priv->led_name[1], OPENWIFI_LED_MAX_NAME_LEN, "openwifi-%s::assoc", wiphy_name(dev->wiphy));
2157 	// snprintf(priv->led_name[2], OPENWIFI_LED_MAX_NAME_LEN, "openwifi-%s::tx", wiphy_name(dev->wiphy));
2158 	// snprintf(priv->led_name[3], OPENWIFI_LED_MAX_NAME_LEN, "openwifi-%s::rx", wiphy_name(dev->wiphy));
2159 
2160 	wiphy_info(dev->wiphy, "hwaddr %pm, %s + %s\n",
2161 		   priv->mac_addr, chip_name, priv->rf->name);
2162 
2163 	openwifi_rfkill_init(dev);
2164 	return 0;
2165 
2166  err_free_dev:
2167 	ieee80211_free_hw(dev);
2168 
2169 	return err;
2170 }
2171 
2172 static int openwifi_dev_remove(struct platform_device *pdev)
2173 {
2174 	struct ieee80211_hw *dev = platform_get_drvdata(pdev);
2175 
2176 	if (!dev) {
2177 		pr_info("%s openwifi_dev_remove: dev %p\n", sdr_compatible_str, (void*)dev);
2178 		return(-1);
2179 	}
2180 
2181 	openwifi_rfkill_exit(dev);
2182 	ieee80211_unregister_hw(dev);
2183 	ieee80211_free_hw(dev);
2184 	return(0);
2185 }
2186 
2187 static struct platform_driver openwifi_dev_driver = {
2188 	.driver = {
2189 		.name = "sdr,sdr",
2190 		.owner = THIS_MODULE,
2191 		.of_match_table = openwifi_dev_of_ids,
2192 	},
2193 	.probe = openwifi_dev_probe,
2194 	.remove = openwifi_dev_remove,
2195 };
2196 
2197 module_platform_driver(openwifi_dev_driver);
2198