Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[question] "server" on the local system, "client" on the remote system? #421

Open
brianthelion opened this issue Apr 9, 2020 · 8 comments

Comments

@brianthelion
Copy link

If I understand the implementation correctly, the data flow starting from the CLI works as follows:

Local system Remote system
1. Set up firewall 5. Instantiate "server"
2. Instantiate a "client"
3. Copy code to remote system
4. Execute code on remote system

Furthermore, the main difference between client and server the following:

  • Client receives new connection requests pushed to it by the firewall, accepts those connections, and multiplexes them over the ssh socket by wrapping them in a lightweight application protocol.

  • Server reads bytes from the ssh socket, interprets those bytes according to the application protocol, and demultiplexes the requests appropriately to get the data to the their intended destinations in their original form.

From a review of the code, it would appear that "local" and "remote" are agnostic to whether or not they're "client" or "server". It's just that that happens to be how the code is written.

Question

Is there any hard technical reason that the actions performed by the local system and remote system couldn't be reversed? Ie, the remote system runs the firewall and the client; the local system runs the server?

@brianmay
Copy link
Member

Not 100% sure I understand. Nothing stopping you though from running the client on the remote system, if the remote system can connect to ssh on your local system.

@brianthelion
Copy link
Author

brianthelion commented Apr 10, 2020

@brianmay Unfortunately, no, in the case in front of me the local system is unreachable from the remote system. But otherwise, based on my reading of the sshuttle application protocol, nothing should prevent them from being swapped -- it just happens to be "hard-coded" that the local system does # 2 (above) instead of # 5. Is that correct?

@brianmay
Copy link
Member

I think I understand your requirements now. I don't think there is any technical reason why this can't happen, apart from the fact the current code base is very much based on the assumption that the server code will run on the remote system. Also the process on the remote system will need to be able to obtain root access somehow in order to configure the firewall.

@ferfebles
Copy link

Doing that with a reverse ssh tunnel.

First I create a ssh tunnel from the remote system to my computer. Something like this:

ssh -p local_ssh_port -fN -R 31416:localhost:22 local_host_user@local_host_public_ip

I use '-p local_ssh_port' because I configured my ADSL router to redirect a non_standard port (p.e. 7777) to my laptop ssh port (22). You probably don't need that if you use the standard port.

Then i connect from my local computer to the remote system using the 'localhost:31416' tunnel:

sshuttle --dns --verbose --disable-ipv6 --no-latency-control --remote remote_host_user@localhost:31416 10.0.0.0/8 172.0.0.0/8

With the previous command I only redirect the 10 and 172 networks.

@HakuG
Copy link

HakuG commented May 27, 2020

How did this end up working out? I'm thinking of doing something similar.

@ferfebles
Copy link

I'm remote working with this every day.

A bit slow, even with latency control disabled, but it's the best thing I've found.

Perhaps https://tailscale.com/ could be easier and faster. I think that @apenwarr (the one that started this project) is working there now.

@juliusl
Copy link

juliusl commented Mar 29, 2022

You can customize the ssh command in sshuttle, so you would add:

sshuttle -e 'ssh -R <remote-port>:<local-host>:<local-port>' ...

Which means that the remote will forward traffic it receives from <remote-port> to <local-host>:<local-port>.

There are some ports that are blocked from forwarding like this, for example port 80, and you could mess with ssh config to override that, but I would suggest to pick a different port and setup up a proxy on the local remote. For example, you'll probably want a reverse proxy, to forward traffic from the remote to the client.

A simple example is to:

  1. Install nginx apt install nginx
  2. Edit /etc/nginx/sites-enabled/default
  3. Within the server config add a location config like this:
server {
...
         location / {
                # First attempt to serve request as file, then
                # as directory, then fall back to displaying a 404.
                # try_files $uri $uri/ =404;

                proxy_pass http://localhost:<remote-port>;
        }
...
}
  1. Restart nginx sudo service nginx restart

I've tested this setup with WSL2/Windows 11 as my local and an Azure VM running on UbuntuLTS as my remote.

@boombatower
Copy link

I am not sure if the above aligns with my use-case or is different.

Assuming one wants to route traffic from a home machine to a remote machine, but the remote machine is not accessible via ssh, but other roudabout means. One can ssh out of said remote machine to the home machine.

One can setup a reverse ssh tunnel from the remote machine to home machine, but since sshd is not running on the remote machine there would be nothing to connect back to from the home machine.

That said effectively I have an ssh tunnel through which I can send data. Would it be feasible (perhaps with some code tweaks) to start remote end of sshuttle on the remote machine directly using the source and listing on a port to which the reverse tunnel routes. Then on the home machine one could run sshuttle client side bits to route all traffic through the tunnel and effectively create the normal setup, but without requiring ssh access to the remote machine? Still only need root on the home (client) machine.

If the code is structured such that it wouldn't take too many tweaks I'd be willing to take a stab at it, but figured I'd ask if this seems feasible. From an outside perspective it feels like all the same things, expect cut out the ssh command from client side and just expect the server to be there.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

6 participants