]> git.ipfire.org Git - thirdparty/openvpn.git/commitdiff
Implement search for "first free" tun/tap device on Solaris
authorGert Doering <gert@greenie.muc.de>
Thu, 7 Jun 2012 15:38:17 +0000 (17:38 +0200)
committerDavid Sommerseth <davids@redhat.com>
Wed, 13 Jun 2012 09:12:35 +0000 (11:12 +0200)
Without this patch, Solaris will do "--dev tun3" just fine, but "--dev tun"
will either use "tun0" if that is available, or fail.  With the patch, the
first available device is searched if "--dev tun" or "--dev tap" (without
a number) is specified.

Signed-off-by: Gert Doering <gert@greenie.muc.de>
Acked-by: David Sommerseth <davids@redhat.com>
Message-Id: 20120607174638.GW1059@greenie.muc.de
URL: http://article.gmane.org/gmane.network.openvpn.devel/6705
Signed-off-by: David Sommerseth <davids@redhat.com>
src/openvpn/tun.c

index 633150fe5e3be58df5be44912023b176db72b8e5..c9edbb8e5738591f829d935df05d873c481d0512 100644 (file)
@@ -1711,6 +1711,12 @@ open_tun (const char *dev, const char *dev_type, const char *dev_node, struct tu
       msg (M_FATAL, "I don't recognize device %s as a tun or tap device",
           dev);
     }
+
+  if ((tt->ip_fd = open (ip_node, O_RDWR, 0)) < 0)
+    msg (M_ERR, "Can't open %s", ip_node);
+
+  if ((tt->fd = open (dev_node, O_RDWR, 0)) < 0)
+    msg (M_ERR, "Can't open %s", dev_node);
   
   /* get unit number */
   if (*dev)
@@ -1721,19 +1727,37 @@ open_tun (const char *dev, const char *dev_type, const char *dev_node, struct tu
       ppa = atoi (ptr);
     }
 
-  if ((tt->ip_fd = open (ip_node, O_RDWR, 0)) < 0)
-    msg (M_ERR, "Can't open %s", ip_node);
-
-  if ((tt->fd = open (dev_node, O_RDWR, 0)) < 0)
-    msg (M_ERR, "Can't open %s", dev_node);
-
   /* Assign a new PPA and get its unit number. */
   strioc_ppa.ic_cmd = TUNNEWPPA;
   strioc_ppa.ic_timout = 0;
   strioc_ppa.ic_len = sizeof(ppa);
   strioc_ppa.ic_dp = (char *)&ppa;
-  if ((ppa = ioctl (tt->fd, I_STR, &strioc_ppa)) < 0)
-    msg (M_ERR, "Can't assign new interface");
+
+  if ( *ptr == '\0' )          /* no number given, try dynamic */
+    {
+      bool found_one = false;
+      while( ! found_one && ppa < 64 )
+       {
+         int new_ppa = ioctl (tt->fd, I_STR, &strioc_ppa);
+         if ( new_ppa >= 0 )
+           {
+             msg( M_INFO, "open_tun: got dynamic interface '%s%d'", dev_tuntap_type, new_ppa );
+             ppa = new_ppa;
+             found_one = true;
+             break;
+           }
+         if ( errno != EEXIST )
+           msg (M_ERR, "open_tun: unexpected error trying to find free %s interface", dev_tuntap_type );
+         ppa++;
+       }
+      if ( !found_one )
+       msg (M_ERR, "open_tun: could not find free %s interface, give up.", dev_tuntap_type );
+    }
+  else                         /* try this particular one */
+    {
+      if ((ppa = ioctl (tt->fd, I_STR, &strioc_ppa)) < 0)
+        msg (M_ERR, "Can't assign PPA for new interface (%s%d)", dev_tuntap_type, ppa );
+    }
 
   if ((if_fd = open (dev_node, O_RDWR, 0)) < 0)
     msg (M_ERR, "Can't open %s (2)", dev_node);