| #!/vendor/bin/sh |
| |
| # Do all the setup required for WiFi. |
| # The kernel driver mac80211_hwsim has already created two virtual wifi devices |
| # us. These devices are connected so that everything that's sent on one device |
| # is recieved on the other and vice versa. This allows us to create a fake |
| # WiFi network with an access point running inside the guest. Here is the setup |
| # for that and the basics of how it works. |
| # |
| # Create a namespace named router and move eth0 to it. Create a virtual ethernet |
| # pair of devices and move both one virtual ethernet interface and one virtual |
| # wifi interface into the router namespace. Then set up NAT networking for those |
| # interfaces so that traffic flowing through them reach eth0 and eventually the |
| # host and the internet. The main network namespace will now only see the other |
| # ends of those pipes and send traffic on them depending on if WiFi or radio is |
| # used. Finally run hostapd in the network namespace to create an access point |
| # for the guest to connect to and dnsmasq to serve as a DHCP server for the WiFi |
| # connection. |
| # |
| # main namespace router namespace |
| # ------- ---------- | --------------- |
| # | ril |<----->| radio0 |<--+--->| radio0-peer |<-------+ |
| # ------- ---------- | --------------- | |
| # | ^ | |
| # | | | |
| # | v v |
| # | ************* -------- |
| # | * ipv6proxy *<--->| eth0 |<--+ |
| # | ************* -------- | |
| # | ^ ^ | |
| # | | | | |
| # | v | | |
| # ------------------ --------- | --------- | | |
| # | wpa_supplicant |<->| wlan0 |<--+------->| wlan1 |<---------+ | |
| # ------------------ --------- | --------- | |
| # | ^ ^ | |
| # | | | v |
| # | v v -------- |
| # | *********** *********** | host | |
| # | * hostapd * * dnsmasq * -------- |
| # | *********** *********** |
| # |
| |
| NAMESPACE="router" |
| rm -rf /data/vendor/var/run/netns/${NAMESPACE} |
| rm -rf /data/vendor/var/run/netns/${NAMESPACE}.pid |
| # We need to fake a mac address to pass CTS |
| # And the kernel only accept mac addresses with some special format |
| # (Like, begin with 02) |
| /system/bin/ip link set dev wlan0 address 02:00:00:44:55:66 |
| |
| createns ${NAMESPACE} |
| # createns will have created a file that contains the process id (pid) of a |
| # process running in the network namespace. This pid is needed for some commands |
| # to access the namespace. |
| PID=$(cat /data/vendor/var/run/netns/${NAMESPACE}.pid) |
| /system/bin/ip link set eth0 netns ${PID} |
| /system/bin/ip link add radio0 type veth peer name radio0-peer |
| /system/bin/ip link set radio0-peer netns ${PID} |
| # Enable privacy addresses for radio0, this is done by the framework for wlan0 |
| sysctl -wq net.ipv6.conf.radio0.use_tempaddr=2 |
| /system/bin/ip addr add 192.168.200.2/24 broadcast 192.168.200.255 dev radio0 |
| execns ${NAMESPACE} /system/bin/ip addr add 192.168.200.1/24 dev radio0-peer |
| execns ${NAMESPACE} sysctl -wq net.ipv6.conf.all.forwarding=1 |
| execns ${NAMESPACE} /system/bin/ip link set radio0-peer up |
| # Start the dhcp client for eth0 to acquire an address |
| setprop ctl.start dhcpclient_rtr |
| # Create iptables entries. -w will cause an indefinite wait for the exclusive |
| # lock. Without this flag iptables can sporadically fail if something else is |
| # modifying the iptables at the same time. -W indicates the number of micro- |
| # seconds between each retry. The default is one second which seems like a long |
| # time. Keep this short so we don't slow down startup too much. |
| execns ${NAMESPACE} /system/bin/iptables -w -W 50000 -t nat -A POSTROUTING -s 192.168.232.0/21 -o eth0 -j MASQUERADE |
| execns ${NAMESPACE} /system/bin/iptables -w -W 50000 -t nat -A POSTROUTING -s 192.168.200.0/24 -o eth0 -j MASQUERADE |
| /vendor/bin/iw phy phy1 set netns $PID |
| |
| execns ${NAMESPACE} /system/bin/ip addr add 192.168.232.1/21 dev wlan1 |
| execns ${NAMESPACE} /system/bin/ip link set wlan1 up |
| # Start the IPv6 proxy that will enable use of IPv6 in the main namespace |
| setprop ctl.start ipv6proxy |
| execns ${NAMESPACE} sysctl -wq net.ipv4.ip_forward=1 |
| # Start hostapd, the access point software |
| setprop ctl.start emu_hostapd |
| # Start DHCP server for the wifi interface |
| setprop ctl.start dhcpserver |
| /system/bin/ip link set radio0 up |