clatd: change to pass in tun filedescriptor via command line
Test: atest clatd_test, built and installed on aosp_blueline device
connected to ipv6-only wifi network: ping 8.8.8.8 still works
and it is via v4-wlan0 clat tun interface
Bug: 65674744
Signed-off-by: Maciej Żenczykowski <maze@google.com>
Change-Id: I8c9e235e9a5bf1a1436e8dc3af8d0aa86f6dc1a5
diff --git a/main.c b/main.c
index 54d12d1..9e796fd 100644
--- a/main.c
+++ b/main.c
@@ -46,6 +46,7 @@
printf("-6 [IPv6 address]\n");
printf("-n [NetId]\n");
printf("-m [socket mark]\n");
+ printf("-t [tun file descriptor number]\n");
}
/* function: main
@@ -55,12 +56,12 @@
struct tun_data tunnel;
int opt;
char *uplink_interface = NULL, *plat_prefix = NULL, *net_id_str = NULL, *mark_str = NULL;
- char *v4_addr = NULL, *v6_addr = NULL;
+ char *v4_addr = NULL, *v6_addr = NULL, *tunfd_str = NULL;
unsigned net_id = NETID_UNSET;
uint32_t mark = MARK_UNSET;
unsigned len;
- while ((opt = getopt(argc, argv, "i:p:4:6:n:m:h")) != -1) {
+ while ((opt = getopt(argc, argv, "i:p:4:6:n:m:t:h")) != -1) {
switch (opt) {
case 'i':
uplink_interface = optarg;
@@ -80,6 +81,9 @@
case 'm':
mark_str = optarg;
break;
+ case 't':
+ tunfd_str = optarg;
+ break;
case 'h':
print_help();
exit(0);
@@ -104,6 +108,15 @@
exit(1);
}
+ if (tunfd_str != NULL && !parse_int(tunfd_str, &tunnel.fd4)) {
+ logmsg(ANDROID_LOG_FATAL, "invalid tunfd %s", tunfd_str);
+ exit(1);
+ }
+ if (!tunnel.fd4) {
+ logmsg(ANDROID_LOG_FATAL, "no tunfd specified on commandline.");
+ exit(1);
+ }
+
len = snprintf(tunnel.device4, sizeof(tunnel.device4), "%s%s", DEVICEPREFIX, uplink_interface);
if (len >= sizeof(tunnel.device4)) {
logmsg(ANDROID_LOG_FATAL, "interface name too long '%s'", tunnel.device4);
@@ -124,13 +137,6 @@
// keeps only admin capability
set_capability(1 << CAP_NET_ADMIN);
- // we can create tun devices as non-root because we're in the VPN group.
- tunnel.fd4 = tun_open();
- if (tunnel.fd4 < 0) {
- logmsg(ANDROID_LOG_FATAL, "tun_open4 failed: %s", strerror(errno));
- exit(1);
- }
-
// When run from netd, the environment variable ANDROID_DNS_MODE is set to
// "local", but that only works for the netd process itself. Removing the
// following line causes XLAT failure in permissive mode.