• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1#!/vendor/bin/sh
2
3# Do all the setup required for WiFi.
4# The kernel driver mac80211_hwsim has already created two virtual wifi devices
5# us. These devices are connected so that everything that's sent on one device
6# is recieved on the other and vice versa. This allows us to create a fake
7# WiFi network with an access point running inside the guest. Here is the setup
8# for that and the basics of how it works.
9#
10# Create a namespace named router and move eth0 to it. Create a virtual ethernet
11# pair of devices and move both one virtual ethernet interface and one virtual
12# wifi interface into the router namespace. Then set up NAT networking for those
13# interfaces so that traffic flowing through them reach eth0 and eventually the
14# host and the internet. The main network namespace will now only see the other
15# ends of those pipes and send traffic on them depending on if WiFi or radio is
16# used.  Finally run hostapd in the network namespace to create an access point
17# for the guest to connect to and dnsmasq to serve as a DHCP server for the WiFi
18# connection.
19#
20#          main namespace                     router namespace
21#       -------       ----------   |    ---------------
22#       | ril |<----->| radio0 |<--+--->| radio0-peer |<-------+
23#       -------       ----------   |    ---------------        |
24#                                  |            ^              |
25#                                  |            |              |
26#                                  |            v              v
27#                                  |      *************     --------
28#                                  |      * ipv6proxy *<--->| eth0 |<--+
29#                                  |      *************     --------   |
30#                                  |            ^              ^       |
31#                                  |            |              |       |
32#                                  |            v              |       |
33# ------------------   ---------   |        ---------          |       |
34# | wpa_supplicant |<->| wlan0 |<--+------->| wlan1 |<---------+       |
35# ------------------   ---------   |        ---------                  |
36#                                  |         ^     ^                   |
37#                                  |         |     |                   v
38#                                  |         v     v                --------
39#                                  | ***********  ***********       | host |
40#                                  | * hostapd *  * dnsmasq *       --------
41#                                  | ***********  ***********
42#
43
44NAMESPACE="router"
45rm -rf /data/vendor/var/run/netns/${NAMESPACE}
46rm -rf /data/vendor/var/run/netns/${NAMESPACE}.pid
47# Lower the MTU of the WiFi interface to prevent issues with packet injection.
48# The MTU of the WiFi monitor interface cannot be higher than 1500 but injection
49# requires extra space for injection headers which count against the MTU. So if
50# a 1500 byte payload needs to be injected it will fail because with the
51# additional headers the total amount of data will exceed 1500 bytes. This way
52# the payload is restricted to a smaller size that should leave room for the
53# injection headers.
54/system/bin/ip link set wlan0 mtu 1400
55
56createns ${NAMESPACE}
57
58# If this is a clean boot we need to copy the hostapd configuration file to the
59# data partition where netmgr can change it if needed. If it already exists we
60# need to preserve the existing settings.
61if [ ! -f /data/vendor/wifi/hostapd/hostapd.conf ]; then
62    cp /vendor/etc/simulated_hostapd.conf /data/vendor/wifi/hostapd/hostapd.conf
63    chown wifi:wifi /data/vendor/wifi/hostapd/hostapd.conf
64    chmod 660 /data/vendor/wifi/hostapd/hostapd.conf
65fi
66
67# createns will have created a file that contains the process id (pid) of a
68# process running in the network namespace. This pid is needed for some commands
69# to access the namespace.
70PID=$(cat /data/vendor/var/run/netns/${NAMESPACE}.pid)
71
72# Move the WiFi monitor interface to the other namespace and bring it up. This
73# is what we use for injecting WiFi frames from the outside world.
74/system/bin/ip link set hwsim0 netns ${PID}
75execns ${NAMESPACE} /system/bin/ip link set hwsim0 up
76
77# Start the network manager as soon as possible after the namespace is available.
78# This ensures that anything that follows is properly managed and monitored.
79setprop ctl.start netmgr
80
81/system/bin/ip link set eth0 netns ${PID}
82/system/bin/ip link add radio0 type veth peer name radio0-peer
83/system/bin/ip link set radio0-peer netns ${PID}
84# Enable privacy addresses for radio0, this is done by the framework for wlan0
85sysctl -wq net.ipv6.conf.radio0.use_tempaddr=2
86/system/bin/ip addr add 192.168.200.2/24 broadcast 192.168.200.255 dev radio0
87execns ${NAMESPACE} /system/bin/ip addr add 192.168.200.1/24 dev radio0-peer
88execns ${NAMESPACE} sysctl -wq net.ipv6.conf.all.forwarding=1
89execns ${NAMESPACE} /system/bin/ip link set radio0-peer up
90# Start the dhcp client for eth0 to acquire an address
91setprop ctl.start dhcpclient_rtr
92# Create iptables entries. -w will cause an indefinite wait for the exclusive
93# lock. Without this flag iptables can sporadically fail if something else is
94# modifying the iptables at the same time. -W indicates the number of micro-
95# seconds between each retry. The default is one second which seems like a long
96# time. Keep this short so we don't slow down startup too much.
97execns ${NAMESPACE} /system/bin/iptables -w -W 50000 -t nat -A POSTROUTING -s 192.168.232.0/21 -o eth0 -j MASQUERADE
98execns ${NAMESPACE} /system/bin/iptables -w -W 50000 -t nat -A POSTROUTING -s 192.168.200.0/24 -o eth0 -j MASQUERADE
99/vendor/bin/iw phy phy1 set netns $PID
100
101execns ${NAMESPACE} /system/bin/ip addr add 192.168.232.1/21 dev wlan1
102execns ${NAMESPACE} /system/bin/ip link set wlan1 mtu 1400
103execns ${NAMESPACE} /system/bin/ip link set wlan1 up
104# Start the IPv6 proxy that will enable use of IPv6 in the main namespace
105setprop ctl.start ipv6proxy
106execns ${NAMESPACE} sysctl -wq net.ipv4.ip_forward=1
107# Start hostapd, the access point software
108setprop ctl.start emu_hostapd
109# Start DHCP server for the wifi interface
110setprop ctl.start dhcpserver
111/system/bin/ip link set radio0 up
112