Always call res_init() before getaddrinfo().
authorGuus Sliepen <guus@tinc-vpn.org>
Sun, 12 Apr 2015 13:42:48 +0000 (15:42 +0200)
committerGuus Sliepen <guus@tinc-vpn.org>
Sun, 12 Apr 2015 13:42:48 +0000 (15:42 +0200)
Unfortunately, glibc assumes that /etc/resolv.conf is a static file that
never changes. Even on servers, /etc/resolv.conf might be a dynamically
generated file, and we never know when it changes. So just call
res_init() every time, so glibc uses up-to-date nameserver information.

Conflicts:
src/have.h
src/net.c
src/net_setup.c

1  2 
doc/tinc.conf.5.in
doc/tinc.texi
src/net_packet.c
src/net_setup.c

diff --combined doc/tinc.conf.5.in
@@@ -464,10 -464,10 +464,10 @@@ an
  .Ev REMOTEPORT
  are available.
  .El
- .It Va ReplayWindow Li = Ar bytes Pq 16
+ .It Va ReplayWindow Li = Ar bytes Pq 32
  This is the size of the replay tracking window for each remote node, in bytes.
  The window is a bitfield which tracks 1 packet per bit, so for example
- the default setting of 16 will track up to 128 packets in the window. In high
+ the default setting of 32 will track up to 256 packets in the window. In high
  bandwidth scenarios, setting this to a higher value can reduce packet loss from
  the interaction of replay tracking with underlying real packet loss and/or
  reordering. Setting this to zero will disable replay tracking completely and
@@@ -500,14 -500,14 +500,16 @@@ The minimum amount of time between send
  .It Va UDPDiscoveryTimeout Li = Ar seconds Pq 30
  If tinc doesn't receive any UDP ping replies over the specified interval,
  it will assume UDP communication is broken and will fall back to TCP.
- .It Va UDPRcvBuf Li = Ar bytes Pq OS default
 +.It Va UDPInfoInterval Li = Ar seconds Pq 5
 +The minimum amount of time between sending periodic updates about UDP addresses, which are mostly useful for UDP hole punching.
+ .It Va UDPRcvBuf Li = Ar bytes Pq 1048576
  Sets the socket receive buffer size for the UDP socket, in bytes.
- If unset, the default buffer size will be used by the operating system.
- .It Va UDPSndBuf Li = Ar bytes Pq OS default
+ If set to zero, the default buffer size will be used by the operating system.
+ Note: this setting can have a significant impact on performance, especially raw throughput.
+ .It Va UDPSndBuf Li = Ar bytes Pq 1048576
  Sets the socket send buffer size for the UDP socket, in bytes.
- If unset, the default buffer size will be used by the operating system.
+ If set to zero, the default buffer size will be used by the operating system.
+ Note: this setting can have a significant impact on performance, especially raw throughput.
  .El
  .Sh HOST CONFIGURATION FILES
  The host configuration files contain all information needed
@@@ -571,8 -571,6 +573,8 @@@ This option controls the initial path M
  .It Va PMTUDiscovery Li = yes | no Po yes Pc
  When this option is enabled, tinc will try to discover the path MTU to this node.
  After the path MTU has been discovered, it will be enforced on the VPN.
 +.It Va MTUInfoInterval Li = Ar seconds Pq 5
 +The minimum amount of time between sending periodic updates about relay path MTU. Useful for quickly determining MTU to indirect nodes.
  .It Va Port Li = Ar port Pq 655
  The port number on which this tinc daemon is listening for incoming connections,
  which is used if no port number is specified in an
diff --combined doc/tinc.texi
@@@ -1207,10 -1207,10 +1207,10 @@@ The environment variables @env{NAME}, @
  @end table
  
  @cindex ReplayWindow
- @item ReplayWindow = <bytes> (16)
+ @item ReplayWindow = <bytes> (32)
  This is the size of the replay tracking window for each remote node, in bytes.
  The window is a bitfield which tracks 1 packet per bit, so for example
- the default setting of 16 will track up to 128 packets in the window. In high
+ the default setting of 32 will track up to 256 packets in the window. In high
  bandwidth scenarios, setting this to a higher value can reduce packet loss from
  the interaction of replay tracking with underlying real packet loss and/or
  reordering. Setting this to zero will disable replay tracking completely and
@@@ -1253,19 -1253,17 +1253,21 @@@ The minimum amount of time between send
  If tinc doesn't receive any UDP ping replies over the specified interval,
  it will assume UDP communication is broken and will fall back to TCP.
  
 +@cindex UDPInfoInterval
 +@item UDPInfoInterval = <seconds> (5)
 +The minimum amount of time between sending periodic updates about UDP addresses, which are mostly useful for UDP hole punching.
 +
  @cindex UDPRcvBuf
- @item UDPRcvBuf = <bytes> (OS default)
+ @item UDPRcvBuf = <bytes> (1048576)
  Sets the socket receive buffer size for the UDP socket, in bytes.
- If unset, the default buffer size will be used by the operating system.
+ If set to zero, the default buffer size will be used by the operating system.
+ Note: this setting can have a significant impact on performance, especially raw throughput.
  
  @cindex UDPSndBuf
- @item UDPSndBuf = <bytes> Pq OS default
+ @item UDPSndBuf = <bytes> (1048576)
  Sets the socket send buffer size for the UDP socket, in bytes.
- If unset, the default buffer size will be used by the operating system.
+ If set to zero, the default buffer size will be used by the operating system.
+ Note: this setting can have a significant impact on performance, especially raw throughput.
  
  @end table
  
@@@ -1333,10 -1331,6 +1335,10 @@@ This option controls the initial path M
  When this option is enabled, tinc will try to discover the path MTU to this node.
  After the path MTU has been discovered, it will be enforced on the VPN.
  
 +@cindex MTUInfoInterval
 +@item MTUInfoInterval = <seconds> (5)
 +The minimum amount of time between sending periodic updates about relay path MTU. Useful for quickly determining MTU to indirect nodes.
 +
  @cindex Port
  @item Port = <@var{port}> (655)
  This is the port this tinc daemon listens on.
diff --combined src/net_packet.c
@@@ -64,7 -64,7 +64,7 @@@ static char lzo_wrkmem[LZO1X_999_MEM_CO
  
  static void send_udppacket(node_t *, vpn_packet_t *);
  
- unsigned replaywin = 16;
+ unsigned replaywin = 32;
  bool localdiscovery = true;
  bool udp_discovery = true;
  int udp_discovery_keepalive_interval = 10;
@@@ -687,7 -687,9 +687,7 @@@ static bool send_sptps_data_priv(node_
        bool relay_supported = (relay->options >> 24) >= 4;
        bool tcponly = (myself->options | relay->options) & OPTION_TCPONLY;
  
 -      /* Send it via TCP if it is a handshake packet, TCPOnly is in use, this is a relay packet that the other node cannot understand, or this packet is larger than the MTU.
 -         TODO: When relaying, the original sender does not know the end-to-end PMTU (it only knows the PMTU of the first hop).
 -               This can lead to scenarios where large packets are sent over UDP to relay, but then relay has no choice but fall back to TCP. */
 +      /* Send it via TCP if it is a handshake packet, TCPOnly is in use, this is a relay packet that the other node cannot understand, or this packet is larger than the MTU. */
  
        if(type == SPTPS_HANDSHAKE || tcponly || (!direct && !relay_supported) || (type != PKT_PROBE && (len - SPTPS_DATAGRAM_OVERHEAD) > relay->minmtu)) {
                char buf[len * 4 / 3 + 5];
@@@ -1135,7 -1137,7 +1135,7 @@@ static void try_tx_sptps(node_t *n, boo
        /* If we do have a static relay, try everything with that one instead. */
  
        if(via != n)
 -              try_tx_sptps(via, mtu);
 +              return try_tx_sptps(via, mtu);
  
        /* Otherwise, try to establish UDP connectivity. */
  
@@@ -1392,17 -1394,6 +1392,17 @@@ skip_harder
                        return;
                }
  
 +              /* The packet is supposed to come from the originator or its static relay
 +                 (i.e. with no dynamic relays in between).
 +                 If it did not, "help" the static relay by sending it UDP info.
 +                 Note that we only do this if we're the destination or the static relay;
 +                 otherwise every hop would initiate its own UDP info message, resulting in elevated chatter. */
 +
 +              if(n != from->via && to->via == myself)
 +                      send_udp_info(myself, from);
 +
 +              /* If we're not the final recipient, relay the packet. */
 +
                if(to != myself) {
                        send_sptps_data_priv(to, n, 0, DATA(&pkt), pkt.len - 2 * sizeof(node_id_t));
                        try_tx_sptps(n, true);
        n->sock = ls - listen_socket;
        if(direct && sockaddrcmp(&addr, &n->address))
                update_node_udp(n, &addr);
 +
 +      /* If the packet went through a relay, help the sender find the appropriate MTU
 +         through the relay path. */
 +
 +      if(!direct)
 +              send_mtu_info(myself, n, MTU);
  }
  
  void handle_device_data(void *data, int flags) {
diff --combined src/net_setup.c
@@@ -518,9 -518,6 +518,9 @@@ bool setup_myself_reloadable(void) 
        get_config_int(lookup_config(config_tree, "UDPDiscoveryInterval"), &udp_discovery_interval);
        get_config_int(lookup_config(config_tree, "UDPDiscoveryTimeout"), &udp_discovery_timeout);
  
 +      get_config_int(lookup_config(config_tree, "MTUInfoInterval"), &mtu_info_interval);
 +      get_config_int(lookup_config(config_tree, "UDPInfoInterval"), &udp_info_interval);
 +
        get_config_bool(lookup_config(config_tree, "DirectOnly"), &directonly);
        get_config_bool(lookup_config(config_tree, "LocalDiscovery"), &localdiscovery);
  
@@@ -667,7 -664,7 +667,7 @@@ static bool add_listen_address(char *ad
        hint.ai_protocol = IPPROTO_TCP;
        hint.ai_flags = AI_PASSIVE;
  
 -#ifdef HAVE_DECL_RES_INIT
 +#if HAVE_DECL_RES_INIT
        res_init();
  #endif
        int err = getaddrinfo(address && *address ? address : NULL, port, &hint, &ai);
@@@ -857,14 -854,14 +857,14 @@@ static bool setup_myself(void) 
        }
  
        if(get_config_int(lookup_config(config_tree, "UDPRcvBuf"), &udp_rcvbuf)) {
-               if(udp_rcvbuf <= 0) {
+               if(udp_rcvbuf < 0) {
                        logger(DEBUG_ALWAYS, LOG_ERR, "UDPRcvBuf cannot be negative!");
                        return false;
                }
        }
  
        if(get_config_int(lookup_config(config_tree, "UDPSndBuf"), &udp_sndbuf)) {
-               if(udp_sndbuf <= 0) {
+               if(udp_sndbuf < 0) {
                        logger(DEBUG_ALWAYS, LOG_ERR, "UDPSndBuf cannot be negative!");
                        return false;
                }