diff options
| author | Hungming Chen <nuccachen@google.com> | 2020-02-14 20:24:16 +0800 |
|---|---|---|
| committer | Maciej Żenczykowski <maze@google.com> | 2020-02-18 05:49:40 +0000 |
| commit | 1da9008a49dd7acf9ab1f1a5f727ad541c487756 (patch) | |
| tree | 957d3e32a1ee9e0a3eb7bb8042410b0c24fbe88f /server/TetherController.cpp | |
| parent | ec203383d2eb81c735677a63d888fb24a94f69aa (diff) | |
TetherController: attach/detach tether bpf program to upstream interface
Test: build, atest
Manual test steps:
1. Connect to FarEastone mobile
2. Enable WiFi hotspot
3. Get the upstream interface via logcat
I netd : ipfwdAddInterfaceForward("wlan1", "rmnet_data1")
4. Check the tether BPF program attaching on upstream interface
$ adb shell tc filter show dev rmnet_data1 ingress
filter protocol ipv6 pref 1 bpf
filter protocol ipv6 pref 1 bpf handle 0x1
prog_offload_schedcls_ingress_tether_rawip:[*fsobj] direct-action
5. Disable WiFi hotspot
6. Check the tether BPF program detaching on upstream interface by
logcat
Change-Id: I2acca0220a660fbaa235f8863237d526828c2af8
Diffstat (limited to 'server/TetherController.cpp')
| -rw-r--r-- | server/TetherController.cpp | 49 |
1 files changed, 49 insertions, 0 deletions
diff --git a/server/TetherController.cpp b/server/TetherController.cpp index b56480a9..a62d7746 100644 --- a/server/TetherController.cpp +++ b/server/TetherController.cpp @@ -42,6 +42,7 @@ #include <android-base/unique_fd.h> #include <cutils/properties.h> #include <log/log.h> +#include <net/if.h> #include <netdutils/DumpWriter.h> #include <netdutils/StatusOr.h> @@ -50,6 +51,7 @@ #include "InterfaceController.h" #include "NetdConstants.h" #include "NetworkController.h" +#include "OffloadUtils.h" #include "Permission.h" #include "TetherController.h" @@ -598,6 +600,7 @@ int TetherController::enableNat(const char* intIface, const char* extIface) { return -ENODEV; } + maybeStartBpf(extIface); return 0; } @@ -784,6 +787,8 @@ int TetherController::disableNat(const char* intIface, const char* extIface) { if (!isAnyForwardingPairEnabled()) { setDefaults(); } + + maybeStopBpf(extIface); return 0; } @@ -922,6 +927,50 @@ StatusOr<TetherController::TetherStatsList> TetherController::getTetherStats() { return statsList; } +void TetherController::maybeStartBpf(const char* extIface) { + // TODO: perhaps ignore IPv4-only interface because IPv4 traffic downstream is not supported. + int ifIndex = if_nametoindex(extIface); + if (!ifIndex) { + ALOGE("Fail to get index for interface %s", extIface); + return; + } + + auto isEthernet = android::net::isEthernet(extIface); + if (!isEthernet.ok()) { + ALOGE("isEthernet(%s[%d]) failure: %s", extIface, ifIndex, + isEthernet.error().message().c_str()); + return; + } + + int rv = getTetherIngressProgFd(isEthernet.value()); + if (rv < 0) { + ALOGE("getTetherIngressProgFd(%d) failure: %s", isEthernet.value(), strerror(-rv)); + return; + } + unique_fd tetherProgFd(rv); + + rv = tcFilterAddDevIngressTether(ifIndex, tetherProgFd, isEthernet.value()); + if (rv) { + ALOGE("tcFilterAddDevIngressTether(%d[%s], %d) failure: %s", ifIndex, extIface, + isEthernet.value(), strerror(-rv)); + return; + } +} + +void TetherController::maybeStopBpf(const char* extIface) { + // TODO: perhaps ignore IPv4-only interface because IPv4 traffic downstream is not supported. + int ifIndex = if_nametoindex(extIface); + if (!ifIndex) { + ALOGE("Fail to get index for interface %s", extIface); + return; + } + + int rv = tcFilterDelDevIngressTether(ifIndex); + if (rv < 0) { + ALOGE("tcFilterDelDevIngressTether(%d[%s]) failure: %s", ifIndex, extIface, strerror(-rv)); + } +} + void TetherController::dumpIfaces(DumpWriter& dw) { dw.println("Interface pairs:"); |
