4

I am working with the latest Manjaro with the kernel: x86_64 Linux 5.10.15-1-MANJARO.

I am connected to my company network via VPN. For this I use SNX with the build version 800010003.

When I start a Docker container (Docker version 20.10.3, build 48d30b5b32) which should connect to a machine from the company network, I get the following message.

[maurice@laptop ~]$ docker run --rm alpine ping company-server
ping: bad address 'company-server'

Also using the IP from the 'company-server' doesn't work.

A ping outside the container works, no matter using the name or IP.

The resolv.conf looks correct to me.

[maurice@laptop ~]$ docker run --rm alpine cat /etc/resolv.conf
# Generated by NetworkManager
search lan
nameserver 10.1.0.250
nameserver 10.1.0.253
nameserver 192.168.86.1

What I have found out so far.

If I downgrade packages glibc and lib32-glibc to version 2.32-5, the ping out of the container works again. Because of dependencies I have also to downgrade gcc, gcc-libs and lib32-gcc-libs to version 10.2.0-4.

I tried the whole thing with a fresh Pop OS 20.10 installation, same problem. I also did a test with another VPN (OpenVPN) which worked fine. However, this was only a test scenario and cannot be used as an alternative.

I have been looking for a solution for several days but have not found anything. It would be really nice if someone could help me with this.

Maurice
  • 43
  • 5
  • I'm use arch with the same issue you discribe OS: Manjaro 20.2.1 Nibia Kernel: x86_64 Linux 5.10.15-1-MANJARO – JamalMcCrackin Feb 20 '21 at 18:36
  • I have the same problem as described. I also added a comment on the aur.archlinux.org snx package site, but did not get any answer to this yet. The problem seems to appear also on other Linux distributions. – Timz Mar 25 '21 at 15:44

3 Answers3

3

TL;DR: on kernel >5.8 the tunsnx interface is no longer created with global scope and need to be recreated. small script to the rescure https://gist.github.com/Fahl-Design/ec1e066ec2ef8160d101dff96a9b56e8

Longer version:

Here are my findings and the solution to (temp) fix it:

Steps to reproduce:

  • connect your snx tunnel

  • see ping fails to server behind tunnel

    docker run --rm -ti --net=company_net busybox /bin/sh -c "ping 192.168.210.210"
    
  • run this command to check ip and scope of the "tunsnx" interface

    ip -o address show "tunsnx" | awk -F ' +' '{print $4 " " $6 " " $8}'
    

if you get something like

192.168.210.XXX 192.168.210.30/32 247

or (Thx Timz)

192.168.210.XXX 192.168.210.30/32 nowhere

the scope is not set to "global" and no connection can be established

to fix this, like "ronan lanore" suggested, you need to change the scope to global

this can be done with a little helper script like this one:

#!/usr/bin/env bash
#
# Usage: [dry_run=1] [debug=1] [interface=tunsnx] docker-fix-snx
#
# Credits to: https://github.com/docker/for-linwux/issues/288#issuecomment-825580160
#
# Env Variables:
#   interface - Defaults to tunsnx
#   dry_run - Set to 1 to have a dry run, just printing out the iptables command
#   debug   - Set to 1 to see bash substitutions

set -eu

_log_stderr() {
  echo "$*" >&2
}

if [ "${debug:=0}" = 1 ]; then
  set -x
  dry_run=${dry_run:=1}
fi

: ${dry_run:=0}
: ${interface:=tunsnx}

data=($(ip -o address show "$interface" | awk -F ' +' '{print $4 " " $6 " " $8}'))

LOCAL_ADDRESS_INDEX=0
PEER_ADDRESS_INDEX=1
SCOPE_INDEX=2

if [ "$dry_run" = 1 ]; then
  echo "[-] DRY-RUN MODE"
fi

if [ "${data[$SCOPE_INDEX]}" == "global" ]; then
  echo "[+] Interface ${interface} is already set to global scope. Skip!"
  exit 0
else
  echo "[+] Interface ${interface} is set to scope ${data[$SCOPE_INDEX]}."

  tmpfile=$(mktemp --suffix=snxwrapper-routes)
  echo "[+] Saving current IP routing table..."
  if [ "$dry_run" = 0 ]; then
    sudo ip route save >$tmpfile
  fi

  echo "[+] Deleting current interface ${interface}..."
  if [ "$dry_run" = 0 ]; then
    sudo ip address del ${data[$LOCAL_ADDRESS_INDEX]} peer ${data[$PEER_ADDRESS_INDEX]} dev ${interface}
  fi

  echo "[+] Recreating interface ${interface} with global scope..."
  if [ "$dry_run" = 0 ]; then
    sudo ip address add ${data[$LOCAL_ADDRESS_INDEX]} dev ${interface} peer ${data[$PEER_ADDRESS_INDEX]} scope global
  fi

  echo "[+] Restoring routing table..."
  if [ "$dry_run" = 0 ]; then
    sudo ip route restore <$tmpfile 2>/dev/null
  fi

  echo "[+] Cleaning temporary files..."
  rm $tmpfile

  echo "[+] Interface ${interface} is set to global scope. Done!"
  if [ "$dry_run" = 0 ]; then
    echo "[+] Result:"
    ip -o address show "tunsnx" | awk -F ' +' '{print $4 " " $6 " " $8}'
  fi
  exit 0
fi

[ "$debug" = 1 ] && set +x
JamalMcCrackin
  • 620
  • 10
  • 15
  • In my case I get the scope "nowhere" when executing the 'ip -o address show ...' command. But I tested your script and it works fine. Thank you very much! – Timz May 03 '21 at 15:12
1

Same problem for me now. Nothing big change but tunsnx interface scope change from global to 247. Delete it and re create with global scope.

ronan lanore
  • 45
  • 1
  • 6
  • 1
    Can you please explain a little bit more how you solve this problem, respectively how you delete and re-create the interface manually? In my understanding SNX creates the interface automatically and removes it when disconnecting. – Timz Apr 15 '21 at 07:24
  • I use a netwrok-manager script into disptached.d `ip address del ${snxInfo[$LOCAL_ADDRESS_INDEX]} peer ${snxInfo[$PEER_ADDRESS_INDEX]} dev ${iface} ip address add ${snxInfo[$LOCAL_ADDRESS_INDEX]} dev ${iface} peer ${snxInfo[$PEER_ADDRESS_INDEX]} scope global` – ronan lanore Oct 06 '21 at 07:25
1

Just for collection of possible solutions. I had the same problem but found that "tunsnx" interface was configured properly with "global" keyword. In my case the problem was that snx was started after docker daemon and restarting docker service docker restart helped.

Konstantin Smolyanin
  • 17,579
  • 12
  • 56
  • 56