Browse code

Keep pre-existing tun/tap devices around on *BSD

This amends commit 62c613d46dc49 to check whether a named tun/tap
device ("--dev tunX" instead of "--dev tun") exists before OpenVPN
started - if yes, keep around at program end. If no, destroy.

Also has a spelling fix, and changes clear_tuntap() to be "static"
(only ever called from within tun.c).

Tested on FreeBSD 7.4, FreeBSD 9.0, NetBSD 5.1, OpenBSD 4.9

Signed-off-by: Gert Doering <gert@greenie.muc.de>
Acked-by: Eric Crist <ecrist@secure-computing.net>
Signed-off-by: David Sommerseth <davids@redhat.com>

Gert Doering authored on 2012/08/17 03:09:09
Showing 2 changed files
... ...
@@ -890,7 +890,7 @@ do_ifconfig (struct tuntap *tt,
890 890
 #elif defined(TARGET_OPENBSD)
891 891
 
892 892
       /*
893
-       * On OpenBSD, tun interfaces are persistant if created with
893
+       * On OpenBSD, tun interfaces are persistent if created with
894 894
        * "ifconfig tunX create", and auto-destroyed if created by
895 895
        * opening "/dev/tunX" (so we just use the /dev/tunX)
896 896
        */
... ...
@@ -1235,7 +1235,7 @@ do_ifconfig (struct tuntap *tt,
1235 1235
   gc_free (&gc);
1236 1236
 }
1237 1237
 
1238
-void
1238
+static void
1239 1239
 clear_tuntap (struct tuntap *tuntap)
1240 1240
 {
1241 1241
   CLEAR (*tuntap);
... ...
@@ -1344,6 +1344,13 @@ open_tun_generic (const char *dev, const char *dev_type, const char *dev_node,
1344 1344
 
1345 1345
       if (!dynamic_opened)
1346 1346
 	{
1347
+	  /* has named device existed before? if so, don't destroy at end */
1348
+	  if ( if_nametoindex( dev ) > 0 )
1349
+	    {
1350
+	      msg (M_INFO, "TUN/TAP device %s exists previously, keep at program end", dev );
1351
+	      tt->persistent_if = true;
1352
+	    }
1353
+
1347 1354
 	  if ((tt->fd = open (tunname, O_RDWR)) < 0)
1348 1355
 	    msg (M_ERR, "Cannot open TUN/TAP dev %s", tunname);
1349 1356
 	}
... ...
@@ -2030,7 +2037,7 @@ close_tun (struct tuntap* tt)
2030 2030
 {
2031 2031
   /* only *TAP* devices need destroying, tun devices auto-self-destruct
2032 2032
    */
2033
-  if (tt && tt->type == DEV_TYPE_TUN )
2033
+  if (tt && (tt->type == DEV_TYPE_TUN || tt->persistent_if ) )
2034 2034
     {
2035 2035
       close_tun_generic (tt);
2036 2036
       free(tt);
... ...
@@ -2165,7 +2172,7 @@ close_tun (struct tuntap *tt)
2165 2165
 {
2166 2166
   /* only tun devices need destroying, tap devices auto-self-destruct
2167 2167
    */
2168
-  if (tt && tt->type != DEV_TYPE_TUN )
2168
+  if (tt && ( tt->type != DEV_TYPE_TUN || tt->persistent_if ) )
2169 2169
     {
2170 2170
       close_tun_generic (tt);
2171 2171
       free(tt);
... ...
@@ -2303,7 +2310,12 @@ open_tun (const char *dev, const char *dev_type, const char *dev_node, struct tu
2303 2303
 void
2304 2304
 close_tun (struct tuntap *tt)
2305 2305
 {
2306
-  if (tt)
2306
+  if (tt && tt->persistent_if )		/* keep pre-existing if around */
2307
+    {
2308
+      close_tun_generic (tt);
2309
+      free (tt);
2310
+    }
2311
+  else if (tt)				/* close and destroy */
2307 2312
     {
2308 2313
       struct gc_arena gc = gc_new ();
2309 2314
       struct argv argv;
... ...
@@ -137,6 +137,8 @@ struct tuntap
137 137
 
138 138
   bool ipv6;
139 139
 
140
+  bool persistent_if;		/* if existed before, keep on program end */
141
+
140 142
   struct tuntap_options options; /* options set on command line */
141 143
 
142 144
   char *actual_name; /* actual name of TUN/TAP dev, usually including unit number */
... ...
@@ -201,7 +203,7 @@ tuntap_defined (const struct tuntap *tt)
201 201
  * Function prototypes
202 202
  */
203 203
 
204
-void clear_tuntap (struct tuntap *tuntap);
204
+static void clear_tuntap (struct tuntap *tuntap);
205 205
 
206 206
 void open_tun (const char *dev, const char *dev_type, const char *dev_node,
207 207
 	       struct tuntap *tt);