NetBSD Problem Report #39233

From riastradh@smalltalk.localdomain  Mon Jul 28 01:58:17 2008
Return-Path: <riastradh@smalltalk.localdomain>
Received: from mail.netbsd.org (mail.netbsd.org [204.152.190.11])
	by narn.NetBSD.org (Postfix) with ESMTP id B494063B91E
	for <gnats-bugs@gnats.NetBSD.org>; Mon, 28 Jul 2008 01:58:16 +0000 (UTC)
Message-Id: <20080726022706.D5F455A@smalltalk.localdomain>
Date: Sat, 26 Jul 2008 02:27:06 +0000 (UTC)
From: Taylor R Campbell <campbell@mumble.net>
Reply-To: campbell@mumble.net
To: gnats-bugs@gnats.NetBSD.org
Subject: OpenSSH fails to initialize tun(4) tunnels correctly
X-Send-Pr-Version: 3.95

>Number:         39233
>Category:       bin
>Synopsis:       OpenSSH fails to initialize tun(4) tunnels correctly
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    bin-bug-people
>State:          closed
>Class:          sw-bug
>Submitter-Id:   net
>Arrival-Date:   Mon Jul 28 02:00:01 +0000 2008
>Closed-Date:    Tue Dec 13 08:43:37 +0000 2011
>Last-Modified:  Tue Dec 13 08:43:37 +0000 2011
>Originator:     Taylor R Campbell <campbell@mumble.net>
>Release:        NetBSD 4.0_STABLE
>Organization:
>Environment:
System: NetBSD smalltalk 4.0_STABLE NetBSD 4.0_STABLE (RIAXEN3_DOM0) #2: Fri Jul 18 23:32:56 UTC 2008 riastradh@smalltalk:/home/riastradh/netbsd/4/obj/sys/arch/i386/compile/RIAXEN3_DOM0 i386
Architecture: i386
Machine: i386
>Description:

	After running `ssh -w 0:1' (the numbers don't matter; they just
	help me to keep from getting mixed up) to create a tun(4)
	tunnel over ssh, and after configuring the tun(4) interfaces
	appropriately on both machines, no packets actually get through
	the tunnel.

	`ssh -vvv' on NetBSD 4.99.70 (i.e. with OpenSSH 5.0) reveals
	from debugging messages that packets are being transmitted
	between the ssh end-points, but no packets get through the
	tun(4) interfaces.  I checked the routes for the end-points'
	point-to-point IP addresses, and they correctly indicate using
	the tun(4) interfaces.

	Ethernet tunnels, with `ssh -o Tunnel=ethernet', also don't
	work.  I believe in this case, the code in ssh/misc.c's
	tun_open will not correctly turn the tunnel interface into a
	broadcast interface from a point-to-point interface, since it
	doesn't use the TUNSIFMODE ioctl command described in the
	tun(4) man page.  It is not immediately obvious to me, however,
	why the point-to-point tunnels don't work.

	I tried creating tunnels between NetBSD 4.0_STABLE and NetBSD
	4.99.70, between NetBSD 4.0_STABLE and OpenBSD 4.3, and between
	NetBSD 4.0_STABLE and FreeBSD 7.0.  Also, I tried recompiling
	the kernel with `options GATEWAY' and setting the sysctl
	`net.inet.ip.forwarding' to 1, doubting whether these would
	have any effect.  None of these pairs or configurations worked.
	By contrast, I was able to successfully create tun(4) tunnels
	with ssh between OpenBSD 4.3 and FreeBSD 7.0.

	(My 4.0_STABLE kernel is currently configured as in XEN3_DOM0
	from netbsd-4, with cgd(4), VND_COMPRESSION, FFS_EI, and
	APPLE_UFS enabled.  My 4.99.70 kernel is currently configured
	as in XEN3_DOMU from -current (as of last week) with the same
	options enabled, and also putter(4) & PUFFS.  I can't imagine
	that any of these would affect tunnels, and I also initially
	tried the tunnels without any of these options set, but didn't
	get around to submitting a PR until now.)

>How-To-Repeat:

	In the local machine's sshd_config, set PermitTunnels to yes.
	In the remote machine's sshd_config, set PermitTunnels and
	PermitRootLogin to yes.  As root, ssh to root at the remote
	machine with

	  local# ssh -w 0:1 <remote hostname>

	Then

	  local# ifconfig tun0 10.0.2.2 10.0.2.1 netmask 0xffffff00
	  remote# ifconfig tun1 10.0.2.1 10.0.2.2 netmask 0xffffff00

	Check the interface configurations:

	  local# ifconfig tun0
	  tun0: flags=51<UP,POINTOPOINT,RUNNING> mtu 1500
	          inet 10.0.2.2 -> 10.0.2.1 netmask 0xffffff00

	[Remote machine running OpenBSD]
	  remote# ifconfig tun1
	  tun1: flags=51<UP,POINTOPOINT,RUNNING> mtu 1500
	          groups: tun
	          inet 10.0.2.1 --> 10.0.2.2 netmask 0xffffff00

	Check that the routes are correct:

	  local# route get 10.0.2.1
	     route to: 10.0.2.1
	  destination: 10.0.2.1
	   local addr: 10.0.2.2
	    interface: tun0
	        flags: <UP,HOST,DONE>
	   recvpipe  sendpipe  ssthresh  rtt,msec    rttvar  hopcount      mtu     expire
	         0         0         0         0         0         0         0         0 

	  remote# route get 10.0.2.2
	     route to: 10.0.2.2
	  destination: 10.0.2.2
	    interface: tun1
	   if address: 10.0.2.1
	        flags: <UP,HOST,DONE>
	       use  hopcount       mtu    expire
	         0         0         0         0 

	Then watch no pings, or packets of any sort, get through.

>Fix:

	I haven't yet been able to test changes or debug this
	thoroughly, and sha'n't be able to until I figure out the
	NetBSD build system well enough to build locally modified
	OpenSSH subtrees.

>Release-Note:

>Audit-Trail:
From: Quentin Garnier <cube@cubidou.net>
To: gnats-bugs@NetBSD.org
Cc: campbell@mumble.net
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 16:25:07 +0200

 --LQksG6bCIzRHxTLp
 Content-Type: text/plain; charset=us-ascii
 Content-Disposition: inline
 Content-Transfer-Encoding: quoted-printable

 On Mon, Jul 28, 2008 at 02:00:01AM +0000, Taylor R Campbell wrote:
 > >Number:         39233
 > >Category:       bin
 > >Synopsis:       OpenSSH fails to initialize tun(4) tunnels correctly
 [...]
 > >Description:
 >=20
 > 	After running `ssh -w 0:1' (the numbers don't matter; they just
 > 	help me to keep from getting mixed up) to create a tun(4)
 > 	tunnel over ssh, and after configuring the tun(4) interfaces
 > 	appropriately on both machines, no packets actually get through
 > 	the tunnel.

 I think this is because OpenSSH's code is specific to OpenBSD.  Their
 tun(4) covers both our tun(4) and our tap(4), and has a different
 interface.  The fact that it compiles is actually the main bug.

 Now, it'd probably be good to add support for that in NetBSD, and it
 shouldn't be too difficult, given it's mostly the initialisation of
 devices that matters.  Well, the code might also be expecting a header
 or something on read packets, or even try to prepend one on written
 ones.

 --=20
 Quentin Garnier - cube@cubidou.net - cube@NetBSD.org
 "See the look on my face from staying too long in one place
 [...] every time the morning breaks I know I'm closer to falling"
 KT Tunstall, Saving My Face, Drastic Fantastic, 2007.

 --LQksG6bCIzRHxTLp
 Content-Type: application/pgp-signature
 Content-Disposition: inline

 -----BEGIN PGP SIGNATURE-----
 Version: GnuPG v1.4.9 (NetBSD)

 iQEcBAEBAgAGBQJIjdbDAAoJENgoQloHrPno2D4H/jDnDbOztKlACQHktaA+GY1G
 KSqA8amwf+ddIw50IX2TbYoyuDLVRrfcTDQJI8o31eA09fsLRF8VRN+mKyx95Rk/
 gmfi4bYBkI5/xkQcCCL8JMl7fep4UKdUYY2/PXSk78YwCH9tslhs3VAqMll4ZbJi
 uSRnRu/7vIAQdl8mWNxSbKxIQFkEv1RlCkbDlBWlDMkn7+OkRBgYEC1VcKwyCEMp
 X9mFzMWVsBxHsPY/TH3P8bra3/OtWcmtTA5QqwglBl0jizpHiLi4GriZVZBYkJH9
 mSJZlmoMtCtn3doYv+p/U7GWMndo1GHWRLEzatGP2BxZM26EfTjQW0grUX3RReE=
 =WxZo
 -----END PGP SIGNATURE-----

 --LQksG6bCIzRHxTLp--

From: Taylor R Campbell <campbell@mumble.net>
To: cube@cubidou.net
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 12:34:49 -0400

    Date: Mon, 28 Jul 2008 16:25:07 +0200
    From: Quentin Garnier <cube@cubidou.net>

    I think this is because OpenSSH's code is specific to OpenBSD.  Their
    tun(4) covers both our tun(4) and our tap(4), and has a different
    interface.  The fact that it compiles is actually the main bug.

    Now, it'd probably be good to add support for that in NetBSD, and it
    shouldn't be too difficult, given it's mostly the initialisation of
    devices that matters.  Well, the code might also be expecting a header
    or something on read packets, or even try to prepend one on written
    ones.

 I'm working on this -- no wonder the code in ssh/misc.c made no sense.
 I'm entirely new to NetBSD, however; can you suggest how I might
 rebuild libssh and usr.bin/ssh without running `build.sh -u build',
 which takes ten minutes rather than the ten seconds I'd hope for?

From: Quentin Garnier <cube@cubidou.net>
To: Taylor R Campbell <campbell@mumble.net>
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 18:41:52 +0200

 --YToU2i3Vx8H2dn7O
 Content-Type: text/plain; charset=us-ascii
 Content-Disposition: inline
 Content-Transfer-Encoding: quoted-printable

 On Mon, Jul 28, 2008 at 12:34:49PM -0400, Taylor R Campbell wrote:
 >    Date: Mon, 28 Jul 2008 16:25:07 +0200
 >    From: Quentin Garnier <cube@cubidou.net>
 >=20
 >    I think this is because OpenSSH's code is specific to OpenBSD.  Their
 >    tun(4) covers both our tun(4) and our tap(4), and has a different
 >    interface.  The fact that it compiles is actually the main bug.
 >=20
 >    Now, it'd probably be good to add support for that in NetBSD, and it
 >    shouldn't be too difficult, given it's mostly the initialisation of
 >    devices that matters.  Well, the code might also be expecting a header
 >    or something on read packets, or even try to prepend one on written
 >    ones.
 >=20
 > I'm working on this -- no wonder the code in ssh/misc.c made no sense.
 > I'm entirely new to NetBSD, however; can you suggest how I might
 > rebuild libssh and usr.bin/ssh without running `build.sh -u build',
 > which takes ten minutes rather than the ten seconds I'd hope for?

 Locate your ${TOOLSDIR}, and use ${TOOLSDIR}/bin/nbmake-${ARCH} in
 place of make, and do nbmake-lalala dependall install in libssh and
 then the same in usr.bin/ssh.  I don't remember if ssh uses a shared
 libssh, but in that case you can probably get away with just rebuilding
 and reisntalling libssh.  Then you can play with LD_LIBRARY_PATH to make
 sure ssh picks up the correct libssh.so.

 Alternatively you can also use make directly in those directories but
 that tend to leave files behind.  Of course you can set OBJDIRPREFIX or
 MAKEOBJDIRPREFIX so that files get built elsewhere but don't forget to
 do "make obj" first.

 I hope I don't sound too confusing :-)

 --=20
 Quentin Garnier - cube@cubidou.net - cube@NetBSD.org
 "See the look on my face from staying too long in one place
 [...] every time the morning breaks I know I'm closer to falling"
 KT Tunstall, Saving My Face, Drastic Fantastic, 2007.

 --YToU2i3Vx8H2dn7O
 Content-Type: application/pgp-signature
 Content-Disposition: inline

 -----BEGIN PGP SIGNATURE-----
 Version: GnuPG v1.4.9 (NetBSD)

 iQEcBAEBAgAGBQJIjfbQAAoJENgoQloHrPnoJBwH/AqUGZ+VFoEYCrc4w8/0HYUW
 LCZq/bmqpinTZzguLxMD4jkhx5tBiCMsY7wG6LLJcbesWcaTdz0P0ebjA2B6YUl1
 WGCvcui93xBbDwqVPFNKX31NKTdOfC/Ni3/7iwP9jECyla80QW/cf4omFrGUFfsv
 mqjQ0IL3hqIx7FDCC/WuI818kX6GNU7T6kUEe1ewMmiTa4X6J4XvhXRDMndHICWS
 eluRthFlNJQIvV8qKZlJJL1evy9QjDjeuqrNuMrpCCz+t3DGfV95HkT9QqBi/zHN
 basvbuSSoxZxaIeqCXLWkO4bQlAkgWKIcRbveh0i9YwfJ5BFe6dtj0QqdZvk2gE=
 =UTO3
 -----END PGP SIGNATURE-----

 --YToU2i3Vx8H2dn7O--

From: Quentin Garnier <cube@cubidou.net>
To: Taylor R Campbell <campbell@mumble.net>
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 18:52:17 +0200

 --n+lFg1Zro7sl44OB
 Content-Type: text/plain; charset=us-ascii
 Content-Disposition: inline
 Content-Transfer-Encoding: quoted-printable

 On Mon, Jul 28, 2008 at 12:49:37PM -0400, Taylor R Campbell wrote:
 >    Date: Mon, 28 Jul 2008 18:41:52 +0200
 >    From: Quentin Garnier <cube@cubidou.net>
 >=20
 >    Locate your ${TOOLSDIR}, and use ${TOOLSDIR}/bin/nbmake-${ARCH} in
 >    place of make, and do nbmake-lalala dependall install in libssh and
 >    then the same in usr.bin/ssh.  I don't remember if ssh uses a shared
 >    libssh, but in that case you can probably get away with just rebuilding
 >    and reisntalling libssh.  Then you can play with LD_LIBRARY_PATH to ma=
 ke
 >    sure ssh picks up the correct libssh.so.
 >=20
 >    Alternatively you can also use make directly in those directories but
 >    that tend to leave files behind.  Of course you can set OBJDIRPREFIX or
 >    MAKEOBJDIRPREFIX so that files get built elsewhere but don't forget to
 >    do "make obj" first.
 >=20
 >    I hope I don't sound too confusing :-)
 >=20
 > That was helpful -- thanks!  To install the newly built binaries in a
 > NetBSD system (a Xen domU intended for the purposes of testing), would
 > it suffice to copy $DESTDIR/usr/lib/libssh.* and $DESTDIR/usr/bin/ssh
 > into /usr/lib/ and /usr/bin/ of the target system?

 That's my recollection from my the last time I played with ssh.  You
 have to be careful though;  always keep a root shell somewhere so you
 don't lock yourself out.

 --=20
 Quentin Garnier - cube@cubidou.net - cube@NetBSD.org
 "See the look on my face from staying too long in one place
 [...] every time the morning breaks I know I'm closer to falling"
 KT Tunstall, Saving My Face, Drastic Fantastic, 2007.

 --n+lFg1Zro7sl44OB
 Content-Type: application/pgp-signature
 Content-Disposition: inline

 -----BEGIN PGP SIGNATURE-----
 Version: GnuPG v1.4.9 (NetBSD)

 iQEcBAEBAgAGBQJIjflBAAoJENgoQloHrPnoAqwIAJIIjk3IigSQHpg39Zo6CRn6
 0IxFkwQ36iuFtpcYiEkO/CLraLJMNm7HjzxwYZhAaCHoOtxBhAUE8YPbgc88m5lD
 M4/KTiTo+fMsIyurE0PqUg494QSdJSFNFcWmCOn8cqZ/2AsK+mamaf2B7OAhnh5j
 UiPBLRdlOWtgD7Mb6ifOwFkIl6I8fmTrwBl8F886OHwKSeDJse8G71sAcxyyJ6zJ
 ANQYVHWAzVnTzfbuBsmwEnyA+IVolruHXHKpYlzL05UVqHGT0NitfNCbWU0H5geh
 bdwgUAOrohJ2/Y1ohR89u/Jqk8WRAEdlqCNei1tVDmnbHi/DlxVO3ZhleICEDNY=
 =yZBi
 -----END PGP SIGNATURE-----

 --n+lFg1Zro7sl44OB--

From: Taylor R Campbell <campbell@mumble.net>
To: cube@cubidou.net
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 12:49:37 -0400

    Date: Mon, 28 Jul 2008 18:41:52 +0200
    From: Quentin Garnier <cube@cubidou.net>

    Locate your ${TOOLSDIR}, and use ${TOOLSDIR}/bin/nbmake-${ARCH} in
    place of make, and do nbmake-lalala dependall install in libssh and
    then the same in usr.bin/ssh.  I don't remember if ssh uses a shared
    libssh, but in that case you can probably get away with just rebuilding
    and reisntalling libssh.  Then you can play with LD_LIBRARY_PATH to make
    sure ssh picks up the correct libssh.so.

    Alternatively you can also use make directly in those directories but
    that tend to leave files behind.  Of course you can set OBJDIRPREFIX or
    MAKEOBJDIRPREFIX so that files get built elsewhere but don't forget to
    do "make obj" first.

    I hope I don't sound too confusing :-)

 That was helpful -- thanks!  To install the newly built binaries in a
 NetBSD system (a Xen domU intended for the purposes of testing), would
 it suffice to copy $DESTDIR/usr/lib/libssh.* and $DESTDIR/usr/bin/ssh
 into /usr/lib/ and /usr/bin/ of the target system?

From: Taylor R Campbell <campbell@mumble.net>
To: cube@cubidou.net
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 14:53:27 -0400

 Attached is a patch that applies cleanly to HEAD and to netbsd-4 (as
 of a couple weeks ago).  I'm a little equivocal about the use of
 tap(4), considering PR kern/39237, which I just reproduced a few
 minutes ago.  I'll try it in a dom0 and then in a non-Xen situation
 as soon as I get a chance.

From: Taylor R Campbell <campbell@mumble.net>
To: cube@cubidou.net
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 15:45:06 -0400

 Looks like the issue affects only Xen domU kernels, so I'm no longer
 (as) worried about it.  Both tun(4) and tap(4) interfaces appear to
 work for me with this patch, on NetBSD 4.0_STABLE and on NetBSD
 4.99.70.  It may be worth adding a comment above the ioctl TUNSIFHEAD
 line in the new function `tun_set_if_mode':

    /* Prepend the address family to each packet delivered through the
       tun(4) interface, which is what OpenBSD's tun(4) expects. */

From: Taylor R Campbell <campbell@mumble.net>
To: cube@cubidou.net
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 28 Jul 2008 16:06:38 -0400

 This is a multi-part message in MIME format.
 --=_i07pdvDj0yTsQ9jeHFVr2rwrkkBRyGtP

 ..actually attached this time.

 --=_i07pdvDj0yTsQ9jeHFVr2rwrkkBRyGtP
 Content-Type: text/plain; charset="iso-8859-1"; name="ssh-tun"
 Content-Transfer-Encoding: quoted-printable
 Content-Disposition: attachment; filename="ssh-tun.patch"

 Index: misc.c
 =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
 =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
 =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
 RCS file: /cvsroot/src/crypto/dist/ssh/misc.c,v
 retrieving revision 1.21
 diff -u -r1.21 misc.c
 --- misc.c	6 Apr 2008 23:38:19 -0000	1.21
 +++ misc.c	28 Jul 2008 17:41:32 -0000
 @@ -35,6 +35,9 @@
  #include <net/if.h>
  #include <netinet/in.h>
  #include <netinet/tcp.h>
 +#ifdef __NetBSD__
 +# include <net/if_tun.h>
 +#endif
 =20
  #include <errno.h>
  #include <fcntl.h>
 @@ -636,20 +639,62 @@
  	return -1;
  }
 =20
 +#if defined(__NetBSD__)
 +
 +# define TUN_POINTOPOINT_DEVICE "tun"
 +# define TUN_ETHERNET_DEVICE "tap"
 +
 +static int
 +tun_set_if_mode(int tun, int mode, int fd, int sock, struct ifreq *ifr)
 +{
 +	if (mode =3D=3D SSH_TUNMODE_POINTOPOINT) {
 +		int one =3D 1;
 +		return ioctl(fd, TUNSIFHEAD, &one);
 +	}
 +	return 0;
 +}
 +
 +#elif defined(__OpenBSD__) || defined(__FreeBSD__)
 +
 +# define TUN_POINTOPOINT_DEVICE "tun"
 +# define TUN_ETHERNET_DEVICE "tun"
 +
 +static int
 +tun_set_if_mode(int tun, int mode, int fd, int sock, struct ifreq *ifr)
 +{
 +	ifr->ifr_flags &=3D ~IFF_IP;
 +	if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 +		ifr->ifr_flags |=3D IFF_LINK0;
 +	else
 +		ifr->ifr_flags &=3D ~IFF_LINK0;
 +	return ioctl(sock, SIOCSIFFLAGS, ifr);
 +}
 +
 +#endif
 +
  int
  tun_open(int tun, int mode)
  {
  	struct ifreq ifr;
 -	char name[100];
 +	char name[100], *device;
  	int fd =3D -1, sock;
 =20
 +	if (mode =3D=3D SSH_TUNMODE_POINTOPOINT)
 +		device =3D TUN_POINTOPOINT_DEVICE;
 +	else if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 +		device =3D TUN_ETHERNET_DEVICE;
 +	else {
 +		debug("%s: invalid tunnel mode %d", __func__, tun);
 +		return (-1);
 +	}
 +
  	/* Open the tunnel device */
  	if (tun <=3D SSH_TUNID_MAX) {
 -		snprintf(name, sizeof(name), "/dev/tun%d", tun);
 +		snprintf(name, sizeof(name), "/dev/%s%d", device, tun);
  		fd =3D open(name, O_RDWR);
  	} else if (tun =3D=3D SSH_TUNID_ANY) {
  		for (tun =3D 100; tun >=3D 0; tun--) {
 -			snprintf(name, sizeof(name), "/dev/tun%d", tun);
 +			snprintf(name, sizeof(name), "/dev/%s%d", device, tun);
  			if ((fd =3D open(name, O_RDWR)) >=3D 0)
  				break;
  		}
 @@ -666,7 +711,7 @@
  	debug("%s: %s mode %d fd %d", __func__, name, mode, fd);
 =20
  	/* Set the tunnel device operation mode */
 -	snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "tun%d", tun);
 +	snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s%d", device, tun);
  	if ((sock =3D socket(PF_UNIX, SOCK_STREAM, 0)) =3D=3D -1)
  		goto failed;
 =20
 @@ -674,12 +719,7 @@
  		goto failed;
 =20
  	/* Set interface mode */
 -	ifr.ifr_flags &=3D ~IFF_UP;
 -	if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 -		ifr.ifr_flags |=3D IFF_LINK0;
 -	else
 -		ifr.ifr_flags &=3D ~IFF_LINK0;
 -	if (ioctl(sock, SIOCSIFFLAGS, &ifr) =3D=3D -1)
 +	if (tun_set_if_mode(tun, mode, fd, sock, &ifr) =3D=3D -1)
  		goto failed;
 =20
  	/* Bring interface up */

 --=_i07pdvDj0yTsQ9jeHFVr2rwrkkBRyGtP--

From: Taylor R Campbell <campbell@mumble.net>
To: cube@cubidou.net
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Tue, 29 Jul 2008 10:36:31 -0400

 This is a multi-part message in MIME format.
 --=_CcgIGg4diOwClHzD+65up5YYtGiWa47p

 Sorry, that was a terrible patch.  Here's a better one (also actually
 attached this time).

 --=_CcgIGg4diOwClHzD+65up5YYtGiWa47p
 Content-Type: text/plain; charset="iso-8859-1"; name="ssh-tun"
 Content-Transfer-Encoding: quoted-printable
 Content-Disposition: attachment; filename="ssh-tun.patch"

 Index: misc.c
 =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
 =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=
 =3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D=3D
 RCS file: /cvsroot/src/crypto/dist/ssh/misc.c,v
 retrieving revision 1.21
 diff -u -r1.21 misc.c
 --- misc.c	6 Apr 2008 23:38:19 -0000	1.21
 +++ misc.c	28 Jul 2008 23:36:35 -0000
 @@ -35,6 +35,9 @@
  #include <net/if.h>
  #include <netinet/in.h>
  #include <netinet/tcp.h>
 +#ifdef __NetBSD__
 +# include <net/if_tun.h>
 +#endif
 =20
  #include <errno.h>
  #include <fcntl.h>
 @@ -636,20 +639,90 @@
  	return -1;
  }
 =20
 +#if defined(__NetBSD__)
 +
 +static ssize_t
 +tun_get_device_name(int tun, int mode, char *buf, size_t buflen)
 +{
 +        if (mode =3D=3D SSH_TUNMODE_POINTOPOINT)
 +                return strlcpy(buf, "tun", buflen);
 +        else if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 +                return strlcpy(buf, "tap", buflen);
 +        else
 +                return (-1);
 +}
 +
 +static int
 +tun_set_if_mode(int tun, int mode, int fd, int sock, struct ifreq *ifr)
 +{
 +	if (mode =3D=3D SSH_TUNMODE_POINTOPOINT) {
 +		int one =3D 1;
 +                /* Request the tun(4) interface to prepend four bytes
 +                   of address family to each packet delivered, which is
 +                   what OpenBSD's tun(4) expects. */
 +		return ioctl(fd, TUNSIFHEAD, &one);
 +	}
 +	return 0;
 +}
 +
 +#elif defined(__OpenBSD__) || defined(__FreeBSD__)
 +
 +static ssize_t
 +tun_get_device_name(int tun, int mode, char *buf, size_t buflen)
 +{
 +        if (mode =3D=3D SSH_TUNMODE_POINTOPOINT ||
 +            mode =3D=3D SSH_TUNMODE_ETHERNET)
 +                return strlcpy(buf, "tun", buflen);
 +        else
 +                return (-1);
 +}
 +
 +static int
 +tun_set_if_mode(int tun, int mode, int fd, int sock, struct ifreq *ifr)
 +{
 +	ifr->ifr_flags &=3D ~IFF_IP;
 +	if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 +		ifr->ifr_flags |=3D IFF_LINK0;
 +	else
 +		ifr->ifr_flags &=3D ~IFF_LINK0;
 +	return ioctl(sock, SIOCSIFFLAGS, ifr);
 +}
 +
 +#else
 +
 +static ssize_t
 +tun_get_device_name(int tun, int mode, char *buf, size_t buflen)
 +{
 +        return (-1);
 +}
 +
 +static int
 +tun_set_if_mode(int tun, int mode, int fd, int sock, struct ifreq *ifr)
 +{
 +        return (-1);
 +}
 +
 +#endif
 +
  int
  tun_open(int tun, int mode)
  {
  	struct ifreq ifr;
 -	char name[100];
 +	char name[100], device[100];
  	int fd =3D -1, sock;
 =20
 +        if (tun_get_device_name(tun, mode, device, sizeof(device)) =3D=3D =
 -1) {
 +                debug("%s: no tunnel %d for mode %u", __func__, tun, mode);
 +		return (-1);
 +	}
 +
  	/* Open the tunnel device */
  	if (tun <=3D SSH_TUNID_MAX) {
 -		snprintf(name, sizeof(name), "/dev/tun%d", tun);
 +		snprintf(name, sizeof(name), "/dev/%s%d", device, tun);
  		fd =3D open(name, O_RDWR);
  	} else if (tun =3D=3D SSH_TUNID_ANY) {
  		for (tun =3D 100; tun >=3D 0; tun--) {
 -			snprintf(name, sizeof(name), "/dev/tun%d", tun);
 +			snprintf(name, sizeof(name), "/dev/%s%d", device, tun);
  			if ((fd =3D open(name, O_RDWR)) >=3D 0)
  				break;
  		}
 @@ -666,7 +739,7 @@
  	debug("%s: %s mode %d fd %d", __func__, name, mode, fd);
 =20
  	/* Set the tunnel device operation mode */
 -	snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "tun%d", tun);
 +	snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s%d", device, tun);
  	if ((sock =3D socket(PF_UNIX, SOCK_STREAM, 0)) =3D=3D -1)
  		goto failed;
 =20
 @@ -674,12 +747,7 @@
  		goto failed;
 =20
  	/* Set interface mode */
 -	ifr.ifr_flags &=3D ~IFF_UP;
 -	if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 -		ifr.ifr_flags |=3D IFF_LINK0;
 -	else
 -		ifr.ifr_flags &=3D ~IFF_LINK0;
 -	if (ioctl(sock, SIOCSIFFLAGS, &ifr) =3D=3D -1)
 +	if (tun_set_if_mode(tun, mode, fd, sock, &ifr) =3D=3D -1)
  		goto failed;
 =20
  	/* Bring interface up */

 --=_CcgIGg4diOwClHzD+65up5YYtGiWa47p--

From: Quentin Garnier <cube@cubidou.net>
To: Taylor R Campbell <campbell@mumble.net>
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Tue, 29 Jul 2008 16:58:59 +0200

 --SLfjTIIQuAzj8yil
 Content-Type: text/plain; charset=us-ascii
 Content-Disposition: inline
 Content-Transfer-Encoding: quoted-printable

 On Tue, Jul 29, 2008 at 10:36:31AM -0400, Taylor R Campbell wrote:
 [...]
 > @@ -636,20 +639,90 @@
 >  	return -1;
 >  }
 > =20
 > +#if defined(__NetBSD__)
 > +
 > +static ssize_t
 > +tun_get_device_name(int tun, int mode, char *buf, size_t buflen)

 Why do you pass "tun" to that function?  I don't see the point.

 Well, there would be a point in the SSH_TUNMODE_ETHERNET case for
 SSH_TUNID_ANY, but you don't use that feature of tap(4).

 [...]
 > +#elif defined(__OpenBSD__) || defined(__FreeBSD__)

 Is FreeBSD's tun(4) really compatible with OpenBSD's?

 I think (although I'm not 100% certain) we use the OpenBSD version of
 OpenSSH.  The so-called portable version has code that deals with Linux
 and FreeBSD's specificities for tunnel interface handling, so I don't
 think you have to bother here.

 As a matter of fact, I don't think you have to bother at all with
 ifdefs, unless it makes dealing with conflicts for later imports easier,
 but I'm not entirely sure it will be the case.

 But then we have PAM code, so we're probably using a mix of the portable
 and the OpenBSD version...

 [...]
 > +        if (tun_get_device_name(tun, mode, device, sizeof(device)) =3D=
 =3D -1) {
 > +                debug("%s: no tunnel %d for mode %u", __func__, tun, mod=
 e);
 > +		return (-1);
 > +	}

 I really don't see why device can't be a const char * and
 tun_get_device_name would return either something correct or NULL.

 Otherwise it's looking fine.

 --=20
 Quentin Garnier - cube@cubidou.net - cube@NetBSD.org
 "See the look on my face from staying too long in one place
 [...] every time the morning breaks I know I'm closer to falling"
 KT Tunstall, Saving My Face, Drastic Fantastic, 2007.

 --SLfjTIIQuAzj8yil
 Content-Type: application/pgp-signature
 Content-Disposition: inline

 -----BEGIN PGP SIGNATURE-----
 Version: GnuPG v1.4.9 (NetBSD)

 iQEcBAEBAgAGBQJIjzAzAAoJENgoQloHrPnojr0H/14HHO1hHz1obxLQqQQ0auI8
 9EdqwXAd+H94KQf3vO3Msn4MPXlItazACPz5uNhRzdan3VNyzcixBP7zl8go8YHv
 OGZ0eARTY6dA0x+1SYrVXkVKzwFK9RSCjVy6hKzzD6HhmDq6PbfYDqpOxCp5qNrC
 FwRRDNn219nafr8nUPKc/vxOXwJR/SCHVVylW+ZCQtrsKqoCCJz3OG5rRCvudZbY
 5t2emhnYFZ6JYktKqQO/a6WfdD/xZPVmEQqZCiWoJ23FzqFSfOd0x0L/nXSo377Z
 49s/HLoxnbpJYCy+6R4bEPlesvb/VOG+bx5k6tdZS/875NDM+1X4EiklJWx2Z54=
 =WWOp
 -----END PGP SIGNATURE-----

 --SLfjTIIQuAzj8yil--

From: Taylor R Campbell <campbell@mumble.net>
To: cube@cubidou.net
Cc: gnats-bugs@NetBSD.org
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Tue, 29 Jul 2008 11:48:56 -0400

    Date: Tue, 29 Jul 2008 16:58:59 +0200
    From: Quentin Garnier <cube@cubidou.net>

    On Tue, Jul 29, 2008 at 10:36:31AM -0400, Taylor R Campbell wrote:
    [...]
    > @@ -636,20 +639,90 @@
    >  	return -1;
    >  }
    >  
    > +#if defined(__NetBSD__)
    > +
    > +static ssize_t
    > +tun_get_device_name(int tun, int mode, char *buf, size_t buflen)

    Why do you pass "tun" to that function?  I don't see the point.

    Well, there would be a point in the SSH_TUNMODE_ETHERNET case for
    SSH_TUNID_ANY, but you don't use that feature of tap(4).

 That was the idea.  It did not fully materialize.

    [...]
    > +#elif defined(__OpenBSD__) || defined(__FreeBSD__)

    Is FreeBSD's tun(4) really compatible with OpenBSD's?

 Nope -- I had not carefully enough looked at this.  Turns out FreeBSD
 has pretty much the same interface as NetBSD.

    I think (although I'm not 100% certain) we use the OpenBSD version of
    OpenSSH.  The so-called portable version has code that deals with Linux
    and FreeBSD's specificities for tunnel interface handling, so I don't
    think you have to bother here.

 Yep.  I had forgotten about that.  It already supports NetBSD, too.

From: Taylor R Campbell <campbell@mumble.net>
To: gnats-bugs@NetBSD.org
Cc: 
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 15 Sep 2008 11:52:32 -0400

 Is this bug waiting for someone (e.g., me) to prepare a patch based on
 the portable OpenSSH code, rather than the confused patches I
 hand-crufted before?

From: christos@zoulas.com (Christos Zoulas)
To: gnats-bugs@NetBSD.org, gnats-admin@netbsd.org, netbsd-bugs@netbsd.org, 
	campbell@mumble.net
Cc: 
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Mon, 15 Sep 2008 13:05:48 -0400

 On Sep 15,  3:55pm, campbell@mumble.net (Taylor R Campbell) wrote:
 -- Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correct

 | The following reply was made to PR bin/39233; it has been noted by GNATS.
 | 
 | From: Taylor R Campbell <campbell@mumble.net>
 | To: gnats-bugs@NetBSD.org
 | Cc: 
 | Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
 | Date: Mon, 15 Sep 2008 11:52:32 -0400
 | 
 |  Is this bug waiting for someone (e.g., me) to prepare a patch based on
 |  the portable OpenSSH code, rather than the confused patches I
 |  hand-crufted before?

 That'd be nice.

 christos

From: Taylor R Campbell <campbell@mumble.net>
To: gnats-bugs@NetBSD.org
Cc: gnats-admin@netbsd.org, netbsd-bugs@netbsd.org, christos@zoulas.com
Subject: Re: bin/39233: OpenSSH fails to initialize tun(4) tunnels correctly
Date: Tue, 16 Sep 2008 19:26:38 -0400

 This is a multi-part message in MIME format.
 --=_hd56iJmxf5ahDF81HRbAgCxJgXvYAdCd

 Attached is a patch that slightly adapts of the code one finds in
 portable OpenSSH's openbsd-compat/port-tun.c into misc.c.  I have
 lightly tested both point-to-point and bridge tunnels on a machine
 running NetBSD 4.0_STABLE talking with a machine running OpenBSD 4.3,
 and the patch applies to both netbsd-4 and HEAD.  The only difference
 from my last patch, really, is that there are no confused cpp feature
 conditionals and no auxiliary routines.

 --=_hd56iJmxf5ahDF81HRbAgCxJgXvYAdCd
 Content-Type: text/plain; charset="iso-8859-1"; name="ssh-tun"
 Content-Transfer-Encoding: quoted-printable
 Content-Disposition: attachment; filename="ssh-tun.patch"

 --- misc.c	15 Jun 2008 01:35:37 +0000	1.21
 +++ misc.c	16 Sep 2008 22:25:22 +0000=09
 @@ -33,6 +33,7 @@
  #include <sys/param.h>
 =20
  #include <net/if.h>
 +#include <net/if_tun.h>
  #include <netinet/in.h>
  #include <netinet/tcp.h>
 =20
 @@ -641,15 +642,20 @@
  {
  	struct ifreq ifr;
  	char name[100];
 -	int fd =3D -1, sock;
 +	int fd =3D -1, sock, flag;
 +	const char *tunbase =3D "tun";
 +
 +	if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 +		tunbase =3D "tap";
 =20
  	/* Open the tunnel device */
  	if (tun <=3D SSH_TUNID_MAX) {
 -		snprintf(name, sizeof(name), "/dev/tun%d", tun);
 +		snprintf(name, sizeof(name), "/dev/%s%d", tunbase, tun);
  		fd =3D open(name, O_RDWR);
  	} else if (tun =3D=3D SSH_TUNID_ANY) {
  		for (tun =3D 100; tun >=3D 0; tun--) {
 -			snprintf(name, sizeof(name), "/dev/tun%d", tun);
 +			snprintf(name, sizeof(name), "/dev/%s%d",
 +			    tunbase, tun);
  			if ((fd =3D open(name, O_RDWR)) >=3D 0)
  				break;
  		}
 @@ -663,26 +669,24 @@
  		return (-1);
  	}
 =20
 +	/* Turn on tunnel headers */
 +	flag =3D 1;
 +	if (mode !=3D SSH_TUNMODE_ETHERNET &&
 +	    ioctl(fd, TUNSIFHEAD, &flag) =3D=3D -1) {
 +		debug("%s: ioctl(%d, TUNSIFHEAD, 1): %s", __func__, fd,
 +		    strerror(errno));
 +		close(fd);
 +	}
 +
  	debug("%s: %s mode %d fd %d", __func__, name, mode, fd);
 =20
  	/* Set the tunnel device operation mode */
 -	snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "tun%d", tun);
 +	snprintf(ifr.ifr_name, sizeof(ifr.ifr_name), "%s%d", tunbase, tun);
  	if ((sock =3D socket(PF_UNIX, SOCK_STREAM, 0)) =3D=3D -1)
  		goto failed;
 =20
  	if (ioctl(sock, SIOCGIFFLAGS, &ifr) =3D=3D -1)
  		goto failed;
 -
 -	/* Set interface mode */
 -	ifr.ifr_flags &=3D ~IFF_UP;
 -	if (mode =3D=3D SSH_TUNMODE_ETHERNET)
 -		ifr.ifr_flags |=3D IFF_LINK0;
 -	else
 -		ifr.ifr_flags &=3D ~IFF_LINK0;
 -	if (ioctl(sock, SIOCSIFFLAGS, &ifr) =3D=3D -1)
 -		goto failed;
 -
 -	/* Bring interface up */
  	ifr.ifr_flags |=3D IFF_UP;
  	if (ioctl(sock, SIOCSIFFLAGS, &ifr) =3D=3D -1)
  		goto failed;

 --=_hd56iJmxf5ahDF81HRbAgCxJgXvYAdCd--

From: Christos Zoulas <christos@netbsd.org>
To: gnats-bugs@gnats.NetBSD.org
Cc: 
Subject: PR/39233 CVS commit: src/crypto/dist/ssh
Date: Wed, 17 Sep 2008 15:45:50 +0000 (UTC)

 Module Name:	src
 Committed By:	christos
 Date:		Wed Sep 17 15:45:50 UTC 2008

 Modified Files:
 	src/crypto/dist/ssh: misc.c

 Log Message:
 PR/39233: Taylor R Campbeel: OpenSSH fails to initialize tun(4) tunnels
 correctly.


 To generate a diff of this commit:
 cvs rdiff -r1.21 -r1.22 src/crypto/dist/ssh/misc.c

 Please note that diffs are not public domain; they are subject to the
 copyright notices on the relevant files.

State-Changed-From-To: open->feedback
State-Changed-By: dholland@NetBSD.org
State-Changed-When: Tue, 24 Mar 2009 22:25:36 +0000
State-Changed-Why:
Can this be closed, or do we need a pullup to netbsd-4?


From: Taylor R Campbell <campbell@mumble.net>
To: gnats-bugs@NetBSD.org
Cc: gnats-admin@netbsd.org, netbsd-bugs@netbsd.org, dholland@NetBSD.org
Subject: Re: bin/39233 (OpenSSH fails to initialize tun(4) tunnels correctly)
Date: Sun, 3 May 2009 13:45:35 -0400

 Sorry for replying so late.  I think this PR can be closed now,
 although a pullup to netbsd-4 wouldn't hurt if it has yet to happen.

State-Changed-From-To: feedback->analyzed
State-Changed-By: dholland@NetBSD.org
State-Changed-When: Wed, 06 May 2009 22:16:35 +0000
State-Changed-Why:
Fixed, but wants pulling up to -4. (Has not been filed yet.)

Thanks for replying... and it wasn't that late either compared to some :-)


State-Changed-From-To: analyzed->closed
State-Changed-By: riastradh@NetBSD.org
State-Changed-When: Tue, 13 Dec 2011 08:43:37 +0000
State-Changed-Why:
Fixed ages ago, and I don't care about a pull-up any more.


>Unformatted:

NetBSD Home
NetBSD PR Database Search

(Contact us) $NetBSD: query-full-pr,v 1.39 2013/11/01 18:47:49 spz Exp $
$NetBSD: gnats_config.sh,v 1.8 2006/05/07 09:23:38 tsutsui Exp $
Copyright © 1994-2007 The NetBSD Foundation, Inc. ALL RIGHTS RESERVED.