xref: /openwifi/README.md (revision 2a1e074623b8c736e0474cf32293701b6e7cd77b)
1# openwifi
2<img src="./openwifi-arch.jpg" width="900">
3
4**openwifi:** Linux mac80211 compatible full-stack IEEE802.11/Wi-Fi design based on SDR (Software Defined Radio).
5
6This repository includes Linux driver and software. [openwifi-hw](https://github.com/open-sdr/openwifi-hw) repository has the FPGA design. [[Detailed document](https://github.com/open-sdr/openwifi/tree/master/doc)]
7
8[Demo [video](https://youtu.be/NpjEaszd5u4) and video [download](https://users.ugent.be/~xjiao/openwifi-low-aac.mp4)]   [openwifi [maillist](https://lists.ugent.be/wws/subscribe/openwifi)] [[Cite openwifi project](#cite-openwifi-project)]
9
10Openwifi code has dual licenses. AGPLv3 is the opensource license. For non-opensource license, please contact [email protected]. Openwifi project also leverages some 3rd party modules. It is user's duty to check and follow licenses of those modules according to the purpose/usage. You can find [an example explanation from Analog Devices](https://github.com/analogdevicesinc/hdl/blob/master/LICENSE) for this compound license conditions.
11
12Openwifi was born in [ORCA project](https://www.orca-project.eu/) (EU's Horizon2020 programme under agreement number 732174).
13
14**Features:**
15
16* 802.11a/g
17* 802.11n MCS 0~7 (Only PHY rx for now. Full system support of 802.11n will come soon)
18* 20MHz bandwidth; 70 MHz to 6 GHz frequency range
19* Mode tested: Ad-hoc; Station; AP, Monitor
20* DCF (CSMA/CA) low MAC layer in FPGA (10us SIFS is achieved)
21* Configurable channel access priority parameters:
22  * duration of RTS/CTS, CTS-to-self
23  * SIFS/DIFS/xIFS/slot-time/CW/etc
24* Time slicing based on MAC address
25* Easy to change bandwidth and frequency:
26  * 2MHz for 802.11ah in sub-GHz
27  * 10MHz for 802.11p/vehicle in 5.9GHz
28* On roadmap: **802.11ax**
29
30**Performance (AP: openwifi at channel 44, client: TL-WDN4200 N900 Wireless Dual Band USB Adapter. iperf test):**
31* AP --> client: 30.6Mbps(TCP), 38.8Mbps(UDP)
32* client --> AP: 17.0Mbps(TCP), 21.5Mbps(UDP)
33
34**Supported SDR platforms:**
35
36* zc706 (Xilinx) + fmcomms2/fmcomms4 (Analog Devices)
37* On roadmap: ADRV9361-Z7035/ADRV9364-Z7020 + ADRV1CRR-BOB (Analog Devices)
38* On roadmap: zcu102 (Xilinx) + fmcomms2/fmcomms4/ADRV9371 (Analog Devices)
39* Don't have any boards? Or you like JTAG boot instead of SD card? Check our test bed [w-iLab.t](https://doc.ilabt.imec.be/ilabt/wilab/tutorials/openwifi.html) tutorial.
40
41**Quick start:** (Example instructions are verified on Ubuntu 16/18)
42
43* Download pre-built [openwifi Linux img file](https://users.ugent.be/~xjiao/openwifi-1.0.0-ghent.zip). Burn the img file to a 16G SD card:
44
45```
46sudo dd bs=4M if=openwifi-1.0.0-ghent.img of=/dev/mmcblk0
47(mmcblk0 is the dev name of sdcard in Linux. Make sure you use the correct one in your situation!)
48(Above command takes a while)
49```
50* Connect RX/TX antenna to RX1A/TX2A ports of your zc706+fmcomms2 platform, and make two antennas orthogonal to each other for good isolation. Config zc706 to SD card boot mode by switches (Read zc706 board spec on internet). Insert the SD card to zc706. (For fmcomms4/ad9364, you may connect antennas to TXA/RXA)
51
52* Connect the board to PC. (PC IP address should be 192.168.10.1). Power on the board. Then from PC:
53
54```
55ssh [email protected]
56(password: openwifi)
57cd openwifi
58service network-manager stop
59./wgd.sh
60(For fmcomms4, you need an extra command: ./set_ant.sh rx1 tx1)
61ifconfig sdr0 up
62iwlist sdr0 scan
63(you should see the Wi-Fi scan result)
64```
65* Setup openwifi hotspot over topology: client -- (sdr0)|board|(eth0) -- (***ethX***)|PC|(***ethY***) -- internet
66  * Enable IPv4 **IP forwarding** on both **board** and **PC**
67  * Then, on board:
68
69        ifconfig sdr0 192.168.13.1
70        route add default gw 192.168.10.1
71        service isc-dhcp-server restart
72        hostapd hostapd-openwifi.conf
73  * Then, on PC:
74
75        sudo iptables -t nat -A POSTROUTING -o ethY -j MASQUERADE
76        sudo ip route add 192.168.13.0/24 via 192.168.10.122 dev ethX
77  * Now you can connect openwifi by your devices (phone, laptop, etc)
78* Connect openwifi to another hotspot. Terminate hostapd, edit wpa-connect.conf properly, then:
79
80        ./wgd.sh
81        (For fmcomms4, you need an extra command: ./set_ant.sh rx1 tx1)
82        route del default gw 192.168.10.1
83        wpa_supplicant -i sdr0 -c wpa-connect.conf
84        (Wait for connection done, then open another ssh terminal)
85        dhclient sdr0
86        (Wait for its done, then you should have connection)
87
88* Real-time control/config via sdrctl (time slice config, etc), please go to openwifi/doc.
89
90* ***Note***: The files (BOOT.BIN, drivers, etc) in pre-built SD card img might not have the latest bug-fixes/features. Check related section in this README on how to generate them and update them if needed.
91
92* ***Note***: If openwifi stops working after ~2 hours, it means the evaluation license of Xilinx Viterbi decoder has expired. You need to power cycle the board. Run this command several times on board to confirm:
93
94        root@analog:~/openwifi# ./sdrctl dev sdr0 get reg rx 20
95        SENDaddr: 00040050
96        reg  val: 34be0123
97        (If the last number of reg val is always 3, that means the Viterbi decoder stops working)
98
99**Build openwifi Linux img based on openwifi FPGA and driver:**
100
101* Install Vivado/SDK 2017.4.1 (If you don't need to re-compile FPGA, WebPack version without license is enough)
102* Get pre-built FPGA files from openwifi-hw repository.
103
104```
105git submodule init openwifi-hw
106git submodule update openwifi-hw
107cd openwifi-hw
108git checkout master
109git pull
110```
111* Build Linux kernel and modules:
112
113```
114export XILINX_DIR=your_Xilinx_directory
115cd openwifi
116git submodule init adi-linux
117git submodule update adi-linux
118(Will take a while)
119cd adi-linux
120git reset --hard 4220d5d24c6c7589fc702db4f941f0632b5ad767
121cp ../kernel_boot/kernel_config ./.config
122source $XILINX_DIR/SDK/2017.4/settings64.sh
123export ARCH=arm
124export CROSS_COMPILE=arm-linux-gnueabihf-
125make -j12 UIMAGE_LOADADDR=0x8000 uImage
126(Answer "y" to Xilinx DMA Engines (XILINX_DMA_ENGINES) [N/y/?] (NEW))
127make modules
128```
129* Build openwifi Linux driver modules:
130
131```
132export OPENWIFI_DIR=your_openwifi_directory
133cd $OPENWIFI_DIR/driver
134./make_all.sh $XILINX_DIR/SDK/2017.4/ $OPENWIFI_DIR/adi-linux/
135```
136* Build openwifi Linux devicetree:
137
138```
139cd $OPENWIFI_DIR/kernel_boot
140dtc -I dts -O dtb -o devicetree.dtb devicetree.dts
141```
142* Build openwifi BOOT.BIN based on FPGA files generated in openwifi-hw:
143
144```
145cd $OPENWIFI_DIR/kernel_boot
146source $XILINX_DIR/SDK/2017.4/settings64.sh
147./build_boot_bin.sh ../openwifi-hw/zc706_fmcs2/sdk/system_top_hw_platform_0/system.hdf u-boot-zc70x.elf
148(u-boot-zc70x.elf is included in the original Analog Devices Linux img)
149```
150* Download [2017_R1-2018_01_29.img.xz](http://swdownloads.analog.com/cse/2017_R1-2018_01_29.img.xz) from [Analog Devices Wiki](https://wiki.analog.com/resources/tools-software/linux-software/zynq_images). Burn it into a SD card via your PC.
151* Mount SD card BOOT/rootfs partitions to SDCARD_DIR directory of your PC (If it is mounted automatically, find the directory). Then copy built files to SD card via your PC. (You can also update files over ftp/ssh after your full system runs. Please check next section. Read carefully user_space/sdcard_boot_update.sh and set your ftp root directory to $OPENWIFI_DIR in your PC):
152
153```
154export SDCARD_DIR=sdcard_mount_point
155cp $OPENWIFI_DIR/kernel_boot/devicetree.dtb $SDCARD_DIR/BOOT
156cp $OPENWIFI_DIR/kernel_boot/output_boot_bin/BOOT.BIN $SDCARD_DIR/BOOT
157cp $OPENWIFI_DIR/adi-linux/arch/arm/boot/uImage $SDCARD_DIR/BOOT
158cd $SDCARD_DIR/BOOT
159sync
160
161sudo mkdir $SDCARD_DIR/rootfs/root/openwifi
162sudo find $OPENWIFI_DIR/driver -name \*.ko -exec cp {} $SDCARD_DIR/rootfs/root/openwifi/ \;
163sudo cp $OPENWIFI_DIR/user_space/* $SDCARD_DIR/rootfs/root/openwifi/
164
165sudo mkdir $SDCARD_DIR/rootfs/lib/modules
166sudo mkdir $SDCARD_DIR/rootfs/lib/modules/4.14.0-g4220d5d24c6c
167sudo find $OPENWIFI_DIR/adi-linux -name \*.ko -exec cp {} $SDCARD_DIR/rootfs/lib/modules/4.14.0-g4220d5d24c6c/ \;
168sudo rm $SDCARD_DIR/rootfs/lib/modules/4.14.0-g4220d5d24c6c/{axidmatest.ko,xilinx_dma.ko,adi_axi_hdmi.ko,ad9361_drv.ko} -f
169
170sudo rm $SDCARD_DIR/rootfs/etc/udev/rules.d/70-persistent-net.rules
171sudo cp $OPENWIFI_DIR/kernel_boot/70-persistent-net.rules $SDCARD_DIR/rootfs/etc/udev/rules.d/
172(Above rule will auto-rename wlan0 to sdr0 which is the openwifi NIC name)
173cd $SDCARD_DIR/rootfs
174sync
175```
176**Run Linux and do some post-config:**
177
178* Insert the SD card to the board, power on and run serial console (such as minicom) from a PC via USB-UART cable to the board. After booting completes, in the PC serial console:
179
180```
181depmod
182(Ignore the error messages)
183modprobe mac80211
184(if you get error like: could not open moddep file 'lib/modules/4.14.0XXXYYYZZZ/modules.dep.bin', you could make a symbol link and modprobe again)
185ln -s /lib/modules/4.14.0-g4220d5d24c6c /lib/modules/4.14.0XXXYYYZZZ
186depmod
187modprobe mac80211
188
189cd openwifi
190./wgd.sh
191(For fmcomms4, you need an extra command: ./set_ant.sh rx1 tx1)
192(Wait for the completion)
193ifconfig
194(You should see sdr0 interface)
195iwlist sdr0 scan
196(You should see the Wi-Fi scan results)
197```
198* Config ssh server and ethernet IP address of the board. In the PC serial console:
199
200```
201passwd
202(ssh server needs a password, such as "openwifi")
203Add "UseDNS no" to /etc/ssh/sshd_config, otherwise ssh login takes too long time
204Set static IP to board (If you have DHCP server on PC, you can skip this step)
205Add following content to /etc/network/interfaces
206  auto lo eth0
207  iface lo inet loopback
208  iface eth0 inet static
209          address 192.168.10.122
210          netmask 255.255.255.0
211Add following content to /etc/resolv.conf
212  nameserver 8.8.8.8
213  nameserver 4.4.4.4
214
215Disable update (long time hang) on boot or ssh session:
216  sudo chmod -x /etc/update-motd.d/90-updates-available
217  sudo chmod -x /etc/update-motd.d/91-release-upgrade
218
219reboot the board, and set proper IP (192.168.10.1) of the connected PC, then from the PC:
220ssh [email protected]
221(password: openwifi)
222```
223* Make on board file update easier:
224  * Option 1: Access the board disk/rootfs from Ubuntu PC: "File manager --> Connect to Server...", input: sftp://[email protected]/root . Then you can operate files on board like normal files on your disk. To update files that need to be in boot partition (BOOT.BIN, uImage and devicetree.dtb), you can transfer those files to rootfs firstly, then on board:
225
226         mount /dev/mmcblk0p1 /sdcard
227         (Create /sdcard directory firstly if it doesn't exist)
228         cp file /sdcard
229         cd /sdcard
230         sync
231         cd /
232         umount /sdcard
233         (Remember to power cycle the board)
234  * Option 2: Setup [ftp server](https://help.ubuntu.com/lts/serverguide/ftp-server.html) on PC, allow anonymous and change ftp root directory to $OPENWIFI_DIR. Then on board:
235
236        ./sdcard_boot_update.sh
237        (Above command downloads uImage, BOOT.BIN and devicetree.dtb, then copy them into boot partition. Remember to power cycle)
238        ./wgd.sh remote
239        (Above command downloads driver files, and brings up sdr0)
240        (For fmcomms4, you need an extra command: ./set_ant.sh rx1 tx1)
241
242**Compile sdrctl on the board** ("On the board" means that you login to the board via ssh)
243
244```
245sudo apt-get install libnl-3-dev
246sudo apt-get install libnl-genl-3-dev
247(Please find the next section to see how to connect board to the internet via your PC)
248(or find out .deb files by above commands and copy .deb to the board, if you do not have internet)
249
250copy $OPENWIFI_DIR/user_space/sdrctl_src to the board, then on the board:
251cd sdrctl_src
252chmod +x version.sh
253make
254```
255**Internet config**
256* Connect board to internet. Topology: board|(eth0) -- (***ethX***)|PC|(***ethY***) -- internet
257  * Enable IPv4 **IP forwarding** on both **board** and **PC**
258  * On board:
259  ```
260  route add default gw 192.168.10.1
261  ```
262  * On PC. After this your board should have internet via NAT through your PC.
263
264  ```
265  sudo iptables -t nat -A POSTROUTING -o ethY -j MASQUERADE
266  ```
267* Setup AP for Wi-Fi client. Topology: client -- (sdr0)|board|(eth0) -- (***ethX***)|PC|(***ethY***) -- internet
268  * On board: Install dhcp server preparing for serving your openwifi clients via hostapd.
269
270  ```
271  sudo apt-get install isc-dhcp-server
272  sudo apt-get install Haveged
273  sudo apt-get install hostapd
274  ```
275  * Put user_space/dhcpd.conf into (overwrite) /etc/dhcp/dhcpd.conf on board.
276  * On board:
277
278  ```
279  cd openwifi
280  service network-manager stop
281  ./wgd.sh
282  (For fmcomms4, you need an extra command: ./set_ant.sh rx1 tx1)
283  ifconfig sdr0 up
284  ifconfig sdr0 192.168.13.1
285  route add default gw 192.168.10.1
286  service isc-dhcp-server restart
287  hostapd hostapd-openwifi.conf
288  ```
289  * On PC:
290
291  ```
292  sudo ip route add 192.168.13.0/24 via 192.168.10.122 dev ethX
293  ```
294  * Now you can connect openwifi hotspot from your phone/laptop and access the internet.
295
296## cite openwifi project
297
298Any use of openwifi project which results in a publication should include a citation via (bibtex example):
299```
300@electronic{openwifigithub,
301            author = {Xianjun, Jiao and Wei, Liu and Michael, Mehari},
302            title = {open-source IEEE802.11/Wi-Fi baseband chip/FPGA design},
303            url = {https://github.com/open-sdr/openwifi},
304            year = {2019},
305}
306```
307