Re: Multihomed server issue

2017-09-20 Thread Jason A. Donenfeld
Hey again,

It turns out that our new semantics -- of rejecting only if the src IP
doesn't belong to _any_ interface, as opposed to the specific
interface -- nicely map to Linux's PKTINFO interface for userspace. In
working with Mathias on the Go implementation, I produced the
following code snippet that shows this sticky-socket technique using
pure-userspace facilities:

https://git.zx2c4.com/WireGuard/tree/contrib/examples/sticky-sockets/sticky-sockets.c

Just FYI, if anybody is curious.

Jason
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-09-09 Thread Wang Jian
2017-09-08 5:28 GMT+08:00 Jason A. Donenfeld :
> Hey there,
>
> This all should be fixed and working well in the latest snapshot. Can
> you test this and confirm that it behaves the way you were hoping?
>

Hi Jason,

It works as expected now. Thanks a lot.

--
Wang Jian
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-09-07 Thread Jason A. Donenfeld
Hey there,

This all should be fixed and working well in the latest snapshot. Can
you test this and confirm that it behaves the way you were hoping?

Thanks,
Jason
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-12 Thread Wang Jian
2017-08-10 22:29 GMT+08:00 Jason A. Donenfeld :
> Hi Wang,
>
> Did you have any luck reproducing this with the netns.sh script?

I managed to test with dummy interface but things are not as expected.
I think it's because my test case patch is not equvalent to my real setup.

I was building a more complex test case that mimics my real setup, but
got stuck on other things and got no progress by now.

It seems that you have figured out what the scenario is and how to deal
with it.

IMHO, you have several options
1. Use request's destination address as reply source address, inject
the packet, then let kernel routing code do the left work, because a
policy route is installed anyway
2. like 1, but your code lookup routing table and search best route for
reply source address
3. provide config option that ListenAddress can be specified. You just
use it/them to check against request packet's dest address, and inject
the reply packet.

(Disclaimer: I haven't looked into your code related to routing due to
time constraint, so my opinions may be totally wrong)

I understand that you prefer 0.0.0.0 for most flexible, thus option 3
is not convicing.

BTW: finished test case is attached anyway.


netns.dummy.patch
Description: Binary data
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-11 Thread Jason A. Donenfeld
Work in progress of last email from airplane:
https://git.zx2c4.com/WireGuard/commit/?id=afca9ef9ce88e8ef026e9c9deca98600c19c502e
If you'd like to test or play with the code.

(Will refine further when I'm home.)
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-10 Thread Jason A. Donenfeld
Hey Baptiste,

On Fri, Aug 11, 2017 at 12:16 AM, Baptiste Jonglez
 wrote:
> This is essentially a difference of weak vs. strong host model, see
> https://tools.ietf.org/html/rfc1122#page-61
>
> The RFC is quite clear:

Wow, thank you so much for knowing about this / finding this. Exactly
the kind of "actual knowledge" I was hoping would emerge on the
thread. Super appreciated.

> However, a system with a strong host model would drop the incoming packets
> in the first place, still from the RFC:
> But Linux has adopted the weak host model, see for instance the documentation
> for "arp_filter" and "arp_announce" in Documentation/networking/ip-sysctl.txt.

That's a useful way of distinguishing it. WireGuard's external
endpoint has always aimed to be as _weak_ as possible, always
listening on ::/0 and 0.0.0.0/0, and always accepting the most packets
in the most permissive way, because it can rely on solid
cryptographically verified authenticators to verify that the packet is
legitimate, and because it stays silent anyway in response to
illegitimate packets. For this reason, in terms of ingress, I think
following the weak model makes sense.

It's therefore useful to know that the egress decision can directly
follow from the ingress decision, according to your reasoning and that
of the RFC.

> So I think your proposed change makes sense, you should use the
> destination address of the request as source address, even if this address
> is not assigned to the outgoing interface.

Okay, I'll most likely roll with that. I will still check, however,
that the source address belongs to one of the interfaces in general.
If the source address belongs to no interfaces, it will then use the
default one from the routing table. Otherwise, the socket won't react
to changes at all, what I've been calling "overly sticky" in the test
suite and commits, and connections won't gracefully resume when
changing interfaces around. Doing it this way has the added benefit
that I can check for address interface inclusion before doing a
routing lookup, rather than after and then retrying, which is a nice
optimization.

There is one thing, though, that occurred to me. The reason it was
like this originally -- checking to see if the outgoing source address
belonged to the interface it was going out on -- was because I very
frequently change between wifi and ethernet on my laptop, and each
interface has a different IP address. When I'm on wifi, and then I
connect to ethernet, the ethernet's default route gets a lower (higher
priority) metric than the wifi, and so packets that were formerly on
wifi now go through ethernet. I wanted this same change-over to happen
with wireguard too -- where changing to ethernet would result in
ongoing wireguard packets now having the source address of the
ethernet interface. However, this wasn't happening, since wireguard
was "remembering" the previous source address of the wifi, from the
ingress. Therefore, I added the check to see if that source address
was still on the routed egress interface, and if it wasn't, resetting
it to 0 (choose the default) and trying again.

So, if I'm going to go the route of the weak model, I'll need a
different check to see when I should drop the source address to 0.
Perhaps comparing the ingress device with the routed egress device is
in fact the proper way to do it. The "remembered" source address would
only be used if the egress packet is going out of the same interface
as the ingress packet, and otherwise the default source address would
be used. This seems superior to what we have now. What do you think?

In any case, coding this will likely wait until I'm back from holiday
in a few weeks, so there's plenty of time to think carefully about it.

Jason
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-10 Thread Baptiste Jonglez
Hi Jason,

On Thu, Aug 10, 2017 at 04:29:54PM +0200, Jason A. Donenfeld wrote:
> 1. Packet from peer P arrives from src:A dst:B
> 2. WireGuard records that it should contact P at src:B dst:A
> 3. When sending an encrypted packet to P, it asks for which interface
> to use for src:B dst:A. The routing API returns interface I.
> 4. We ask whether interface I has an address B assigned to it. If yes,
> we transmit the packet as src:B dst:A using interface I, and return.
> If no, we move to step 5:
> 5. We ask which interface and src IP we should use for src:default
> dst:A. The routing API returns interface I' (which may be the same as
> I or perhaps not) and a default src address, B', for interface I'.
> 6. We transmit the packet as src:B' dst:A using interface I'.
> 
> In the past, this has been sufficient for handling issues with
> multihomed servers, while still dealing gracefully with IP address
> changes.
> 
> It seems like the problem you're facing is that B does not belong to
> I, because B belongs to an unrouted dummy0 interface. The solution
> would be to change the question of step 4 to instead ask if _any_
> interface contains B, not just the returned interface I. While this is
> essentially what's done for IPv6, I'm not certain this is the correct
> behavior for IPv4. Do you know of any relevant RFCs for your use of v4
> dummy interfaces and RTS routing? Or some other reference?

This is essentially a difference of weak vs. strong host model, see
https://tools.ietf.org/html/rfc1122#page-61

The RFC is quite clear:

If the datagram is sent in response to a received datagram, the source
address for the response SHOULD be the specific-destination address of
the request.

However, a system with a strong host model would drop the incoming packets
in the first place, still from the RFC:

A host MAY silently discard an incoming datagram whose destination
address does not correspond to the physical interface through which it
is received.

A host MAY restrict itself to sending (non-source-routed) IP datagrams
only through the physical interface that corresponds to the IP source
address of the datagrams.

But Linux has adopted the weak host model, see for instance the documentation
for "arp_filter" and "arp_announce" in Documentation/networking/ip-sysctl.txt.

So I think your proposed change makes sense, you should use the
destination address of the request as source address, even if this address
is not assigned to the outgoing interface.

Baptiste


signature.asc
Description: PGP signature
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-10 Thread Jan De Landtsheer
indeed, this looks the same


On Thu, Aug 10, 2017 at 8:43 PM Jason A. Donenfeld  wrote:

> On Thu, Aug 10, 2017 at 4:29 PM, Jason A. Donenfeld 
> wrote:
> > It seems like the problem you're facing is that B does not belong to
> > I, because B belongs to an unrouted dummy0 interface. The solution
> > would be to change the question of step 4 to instead ask if _any_
> > interface contains B, not just the returned interface I. While this is
> > essentially what's done for IPv6, I'm not certain this is the correct
> > behavior for IPv4.
>
> This looks like http://ix.io/z3d if you want to try it and report back.
>
> Jason
>
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-10 Thread Jason A. Donenfeld
On Thu, Aug 10, 2017 at 4:29 PM, Jason A. Donenfeld  wrote:
> It seems like the problem you're facing is that B does not belong to
> I, because B belongs to an unrouted dummy0 interface. The solution
> would be to change the question of step 4 to instead ask if _any_
> interface contains B, not just the returned interface I. While this is
> essentially what's done for IPv6, I'm not certain this is the correct
> behavior for IPv4.

This looks like http://ix.io/z3d if you want to try it and report back.

Jason
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-10 Thread Jason A. Donenfeld
Hi Wang,

Did you have any luck reproducing this with the netns.sh script?

Here's what's happening here:

1. Packet from peer P arrives from src:A dst:B
2. WireGuard records that it should contact P at src:B dst:A
3. When sending an encrypted packet to P, it asks for which interface
to use for src:B dst:A. The routing API returns interface I.
4. We ask whether interface I has an address B assigned to it. If yes,
we transmit the packet as src:B dst:A using interface I, and return.
If no, we move to step 5:
5. We ask which interface and src IP we should use for src:default
dst:A. The routing API returns interface I' (which may be the same as
I or perhaps not) and a default src address, B', for interface I'.
6. We transmit the packet as src:B' dst:A using interface I'.

In the past, this has been sufficient for handling issues with
multihomed servers, while still dealing gracefully with IP address
changes.

It seems like the problem you're facing is that B does not belong to
I, because B belongs to an unrouted dummy0 interface. The solution
would be to change the question of step 4 to instead ask if _any_
interface contains B, not just the returned interface I. While this is
essentially what's done for IPv6, I'm not certain this is the correct
behavior for IPv4. Do you know of any relevant RFCs for your use of v4
dummy interfaces and RTS routing? Or some other reference?

Please do let me know whether the above is an accurate representation
of the problem you're facing.

Jason
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-03 Thread Wang Jian
2017-08-03 20:59 GMT+08:00 Jason A. Donenfeld :
> Hi Wang,
>
> I understand your inquiry and I see what you're trying to accomplish
> with your use of ip rule and fwmark. However, *WireGuard already does
> this automatically*. We _do_ support reply-to-sender. We _do_
> supported multihomed servers. You wrote, "But I do wish that server
> can deduce public address which the client connects to, and use the
> public address to response to the client, then the configuration will
> be simple and straightforward." WireGuard _does_ do this.
>
> To demonstrate that, I've added a more explicit test of this to the test 
> suite:
> https://git.zx2c4.com/WireGuard/commit/?id=bf44c07a805a5e40408059ac60dfc526196a3797
>
> If this is not working for you, then you're either doing something
> wrong, or you've uncovered a bug in either WireGuard or the kernel. In
> case it's the latter, would you send me a patch for netns.sh that
> demonstrated the problem in a clear way?

Your test case is straightforward. And I am confident that you're right in this
kind of setup.

But there's significant difference. In your test case, the endpoint
addresses are configured
directly on attached link. In my case, the wireguard server's endpoint
address is configured on
dummy interface, not attached link.

I reproduce the problem while using tcpdump to get some clues,

1. server can receives client's packet
2. server 'wg' output shows client's endpoint addr:port correctly
3. tcpdump on client only captures outgoing request packets, no
response from server
4. tcpdump on server only captures incoming request packets, no
response (on all physical interfaces)

I was wrong. Response is not routed via default gateway, or other
interfaces. There is NO response at all.
Very sorry for misleading.

I am not familiar with test in namespace. I will look into it.
Hopefully I can come back
with a patch.
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-03 Thread Jason A. Donenfeld
Hi Wang,

I understand your inquiry and I see what you're trying to accomplish
with your use of ip rule and fwmark. However, *WireGuard already does
this automatically*. We _do_ support reply-to-sender. We _do_
supported multihomed servers. You wrote, "But I do wish that server
can deduce public address which the client connects to, and use the
public address to response to the client, then the configuration will
be simple and straightforward." WireGuard _does_ do this.

To demonstrate that, I've added a more explicit test of this to the test suite:
https://git.zx2c4.com/WireGuard/commit/?id=bf44c07a805a5e40408059ac60dfc526196a3797

If this is not working for you, then you're either doing something
wrong, or you've uncovered a bug in either WireGuard or the kernel. In
case it's the latter, would you send me a patch for netns.sh that
demonstrated the problem in a clear way?

Thanks,
Jason
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-02 Thread Wang Jian
2017-08-01 19:28 GMT+08:00 Wang Jian :
> 2017-08-01 11:06 GMT+08:00 Jason A. Donenfeld :
>> On Tue, Aug 1, 2017 at 4:01 AM, Wang Jian  wrote:
>>> 2017-07-31 23:34 GMT+08:00 Jason A. Donenfeld :
 On Fri, Jul 28, 2017 at 2:51 AM, Wang Jian  wrote:
> The solution can be one of:
>
> 1. server can RTS (response to source), or can bind to arbitary
> address for outgoing

 The server does already respond to source.
>>>
>>> Sorry, I didn't make it clear. By saying RTS, I mean response to
>>> source link, that is,
>>> using called address and incoming link.
>>
>> You're still unclear to me. What?
>
> Let's say server has multiple interfaces, eth0, eth1, ... ethN, with
> IP0, IP1, ... IPn,
> If an incoming request is to eth1, to IP1, then the server's response
> packet will go out from eth1, and source is IP1.
>
> In some cases, it can be done using policy routing, but other cases not. I 
> know
> a FreeBSD based VPN implements so called RTS.
>
> In my case, the server looks like
>
> eth0 = 10.1.1.2/24(default route, via 10.1.1.1/24)
> eth1.100 = 172.16.1.2/30 (policy routing: when source address
> is 111.111.1.0/24,  route via 172.16.1.1/30)
> eth1.200 = 172.16.2.2/30 (policy routing: when source address
> is 111.111.2.0/24,  route via 172.16.2.1/30)
> dummy0 = 111.111.1.2/24
> dummy1 = 111.111.2.2/24
>
> When a wireguard client contacts 111.111.1.2, the server responses UDP packet
> with source address 10.1.1.2 but not the desired 111.111.1.2, because
> of default route.
>
> I have mailed you my network setup privately. Sorry for inconvenience.

I managed to handle this issue for one public address

--
[Interface]
FwMark = 600
PostUp = ip rule add pref 2 fwmark 600 table 600; ip route add
table 600 default via 172.16.1.1 src 111.111.1.2
--

With this workaround, for a wireguard interface, only one public address can
be used. We do need multiple public addresses for a reason: some clients
connect to one public address while other clients connect to another public
address.

We can use multple wg interfaces to address the limitation. But I do wish that
server can deduce public address which the client connects to, and use the
public address to response to the client, then the configuration will be
simple and straightforward.
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-08-01 Thread Wang Jian
2017-08-01 11:06 GMT+08:00 Jason A. Donenfeld :
> On Tue, Aug 1, 2017 at 4:01 AM, Wang Jian  wrote:
>> 2017-07-31 23:34 GMT+08:00 Jason A. Donenfeld :
>>> On Fri, Jul 28, 2017 at 2:51 AM, Wang Jian  wrote:
 The solution can be one of:

 1. server can RTS (response to source), or can bind to arbitary
 address for outgoing
>>>
>>> The server does already respond to source.
>>
>> Sorry, I didn't make it clear. By saying RTS, I mean response to
>> source link, that is,
>> using called address and incoming link.
>
> You're still unclear to me. What?

Let's say server has multiple interfaces, eth0, eth1, ... ethN, with
IP0, IP1, ... IPn,
If an incoming request is to eth1, to IP1, then the server's response
packet will go out from eth1, and source is IP1.

In some cases, it can be done using policy routing, but other cases not. I know
a FreeBSD based VPN implements so called RTS.

In my case, the server looks like

eth0 = 10.1.1.2/24(default route, via 10.1.1.1/24)
eth1.100 = 172.16.1.2/30 (policy routing: when source address
is 111.111.1.0/24,  route via 172.16.1.1/30)
eth1.200 = 172.16.2.2/30 (policy routing: when source address
is 111.111.2.0/24,  route via 172.16.2.1/30)
dummy0 = 111.111.1.2/24
dummy1 = 111.111.2.2/24

When a wireguard client contacts 111.111.1.2, the server responses UDP packet
with source address 10.1.1.2 but not the desired 111.111.1.2, because
of default route.

I have mailed you my network setup privately. Sorry for inconvenience.
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-07-31 Thread Jason A. Donenfeld
On Tue, Aug 1, 2017 at 4:01 AM, Wang Jian  wrote:
> 2017-07-31 23:34 GMT+08:00 Jason A. Donenfeld :
>> On Fri, Jul 28, 2017 at 2:51 AM, Wang Jian  wrote:
>>> The solution can be one of:
>>>
>>> 1. server can RTS (response to source), or can bind to arbitary
>>> address for outgoing
>>
>> The server does already respond to source.
>
> Sorry, I didn't make it clear. By saying RTS, I mean response to
> source link, that is,
> using called address and incoming link.

You're still unclear to me. What?
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-07-31 Thread Wang Jian
2017-07-31 23:34 GMT+08:00 Jason A. Donenfeld :
> On Fri, Jul 28, 2017 at 2:51 AM, Wang Jian  wrote:
>> The solution can be one of:
>>
>> 1. server can RTS (response to source), or can bind to arbitary
>> address for outgoing
>
> The server does already respond to source.

Sorry, I didn't make it clear. By saying RTS, I mean response to
source link, that is,
using called address and incoming link.

>
> Can you send me a TCP dump and the output of `ip route` indicating
> that WireGuard is doing otherwise?

For security reason, I will send you privately.
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard


Re: Multihomed server issue

2017-07-31 Thread Jason A. Donenfeld
On Fri, Jul 28, 2017 at 2:51 AM, Wang Jian  wrote:
> The solution can be one of:
>
> 1. server can RTS (response to source), or can bind to arbitary
> address for outgoing

The server does already respond to source.

Can you send me a TCP dump and the output of `ip route` indicating
that WireGuard is doing otherwise?

Thanks,
Jason
___
WireGuard mailing list
WireGuard@lists.zx2c4.com
https://lists.zx2c4.com/mailman/listinfo/wireguard