From charlesreid1

Handy SSH Tricks

SSH File System (SSHFS)

SSHFS ( allows you to mount remote directories and see them/treat them as local directories. It comes built-in to pretty much any Unix or Linux distro, but unfortunately it doesn't come stock on a Mac.

If you want to use SSHFS on a Mac, you need to install MacFUSE:

And if you want a nice GUI for MacFUSE, you can install MacFusion:

Otherwise, it's literally as easy to mount a remote directory as a local disk as it is to brush your teeth:

[MachineB] $ sshfs /path/to/mount/locally

And if you don't want it to take forever, you can use a faster cipher:

[MachineB] $ sshfs -o Cipher="arcfour" /path/to/mount/locally


Some of the tricks mentioned below and above for ssh and sshfs can also be applied to scp. It has the -o flag, which allows you to set options in the same form as options set in the ssh_config file. For example, you can tell scp which cipher to use by using the Cipher or Ciphers option:

scp -o 'Ciphers arcfour,blowfish-cbc' 

Alternatively, you can specify which ssh command scp should use, by using the ProxyCommand option:

scp -o 'ProxyCommand ssh -c user1@remote1' filetocopy user2@remote2:/path/to/target/file

And, of course, one of the user@remote can be local, i.e. you can use this to copy a file from a remote server to your local computer.

SSH Tunnels

SSH can be used to create tunnels between ports on two computers. This comes in handy if, for example, you want to use a protocol that shares information between two computers, but the protocol is completely and hopelessly insecure. A perfect example is file sharing, or remote desktop sharing. Another situation where this comes in handy is if you're trying to run a service (like the above) through a computer that has a firewall blocking most ports. It is possible to route traffic to a port on your local machine, which won't have a firewall issue, through the SSH port (port 22).

An SSH tunnel works like this: normally, two computers would communicate to each other. Machine A, acting as the server, would open a port, perhaps port 4000, and Machine B would connect to port 4000 of Machine A to send and receive information. However, if the connection between Machine A and Machine B is not encrypted, someone could sit on the network and see everything that's passing between Machine A and Machine B.

Alternatively, MachineB can create an encrypted SSH tunnel between itself and MachineA. The power of SSH tunnels is, they can be made between any ports. So MachineB can create an SSH tunnel that forwards all information coming from port 4000 on MachineA through the encrypted tunnel to port 4000 on the local machine. Or, it could forward all information to port 4001 on the local machine, or port 5000 on the local machine - you get the idea.

To create a tunnel from port XXXX on MachineA to port YYYY on MachineB,

[MachineB] $ ssh -L XXXX:localhost:YYYY

The SSH tunnel will stay alive for as long as this SSH session remains open. If you don't want to have to keep this window open, you can create the SSH tunnel and run it in the background:

[MachineB] $ ssh -L XXXX:localhost:YYYY -f -N

The -f argument runs SSH in the background, and -N runs no commands.

Killing Background SSH Tunnels

You can kill all those background SSH tunnels and other SSH processes cluttering up your list of running programs by running the command:

$ ps -A | /bin/grep ssh

Then you can either run

$ kill -9 <PID>

or the slightly easier

$ killall <PROCESS NAME>

Tunneling AFP over SSH

AFP, or Apple File Protocol, is the built-in filesharing protocol on Mac. AFP uses port 548, but you can actually forward AFP to any port number you want. So, if you're already using AFP from another Mac (through an SSH tunnel, right?), and port 548 is already occupied, that's OK - you can tunnel the new AFP connection through port 549, or 550, or... whatever.

If you want to take an AFP-shared directory that is on MachineA port 548, and mount it/see it on MachineB (just for kicks) port 15548, you'll do the following:

[MachineB] $ ssh -L 548:localhost:15548 -f -N

Then you can mount the (now LOCAL) AFP directory:

$ mount afp://localhost:15548 /Volumes/AFP_DRIVE

Tunneling Remote Desktop Connections over SSH

Since remote desktop shares such valuable information (i.e. graphical interaction plus complete remote control over the computer, plus viewing any sensitive information), it is important to take necessary security measures. One such measure is tunneling the remote desktop connection through an SSH tunnel, encrypting all remote desktop traffic. This can be done as described on the SSH page, using the command (run from the client computer):

ssh -f -N -L 5900:localhost:5900

One of the problems with tunneling the remote desktop connection through an SSH tunnel is that it's very slow. The reason for this is, SSH is encrypting all outgoing traffic and decrypting all incoming traffic - a time-consuming and slow process, added to the fact that remote desktop is sending and receiving a large amount of information. This makes the response time and graphics quality of remote desktop windows very poor.

SSH can be tweaked, however, to use a faster (albeit less secure) cipher called Arcfour (see wikipedia:RC4 for details). This is done by using the -c flag for the SSH command:

ssh -c arcfour -f -N -L 5900:localhost:5900

If you run the command man ssh you can see all of the different options you have for the -c flag. Arcfour is almost assured to be the fastest.

Cypher Selection

As mentioned in the above section, sometimes you want to use a faster and less secure cypher; other times you want to trade speed for higher security. The -c flag allows you to select the cypher used by SSH. From the ssh man page:

     -c cipher_spec
             Selects the cipher specification for encrypting the session.

             Protocol version 1 allows specification of a single cipher.  The sup-
             ported values are ``3des'', ``blowfish'', and ``des''.  3des (triple-
             des) is an encrypt-decrypt-encrypt triple with three different keys.
             It is believed to be secure.  blowfish is a fast block cipher; it
             appears very secure and is much faster than 3des.  des is only sup-
             ported in the ssh client for interoperability with legacy protocol 1
             implementations that do not support the 3des cipher.  Its use is
             strongly discouraged due to cryptographic weaknesses.  The default is

             For protocol version 2, cipher_spec is a comma-separated list of
             ciphers listed in order of preference.  The supported ciphers are:
             3des-cbc, aes128-cbc, aes192-cbc, aes256-cbc, aes128-ctr, aes192-ctr,
             aes256-ctr, arcfour128, arcfour256, arcfour, blowfish-cbc, and
             cast128-cbc.  The default is:


Unless you're using an ancient version of SSH, you'll be using version 2 (if you're not, you need to be, because version 1 has security flaws! For example, see, The Matrix Reloaded section, and for more information).

Passwordless Login

These instructions will enable you to log in to MachineB from MachineA without entering your password.

MachineA is the machine you are sitting in front of.


Generate a public and private key. Use the DSA encryption algorithm. To do this, execute the command:

[MachineA] $ ssh-keygen -t rsa

You'll be prompted for a passphrase that must be entered every time you use your public key. This operation will create two files, ~/.ssh/{id_dsa,}.

The file id_rsa is your private key - DO NOT SHARE YOUR PRIVATE KEY WITH ANYONE!

First, print the public key for MachineA into a terminal on MachineA:

cat ~/.ssh/

Now copy the public key.

Remote-login to MachineB and paste the public key for MachineA into MachineB's list of authorized keys, using your favorite (er, my favorite) text editor:

[MachineB] $ vi ~/.ssh/authorized_keys

and paste the contents of MachineA's public key.


To login to MachineB from MachineA without entering your password, perform the following steps:

Start the SSH agent in the background:

[MachineA] $ eval "$(ssh-agent -s)"
[MachineA] $ ssh-add -K ~/.ssh/id_rsa

You will be prompted for your public key passphrase once per session, and once you enter it, you will have passwordless access to MachineB from MachineA.

These steps are somewhat cumbersome, and can be shortened to a much more convenient bash function as follows. I want to create a bash function on MachineA so that when I type:

[MachineA] $ MachineB

I will instantaneously be logged in to MachineB. To do this, I will create a function in my ~/.bashrc (or somewhere similar, I use a ~/.aliases file). This will look as follows:

alias MachineB="MachineB"
function MachineB() {
  eval "$(ssh-agent -s)"
  ssh-add -K ~/.ssh/id_rsa

  # ssh to MachineB
  ssh -Y

And now you can log in to MachineB by simply typing:

$ MachineB

How hard is that???

Note that this trick will leave an ssh-agent process lying around each time you use that function, but you can fix that by running killall ssh-agent as described above: Killing Background SSH Tunnels/Processes

SSH Man-In-The-Middle Attacks and SSH Fingerprints

Occasionally you might see a message that looks something like this:

$ ssh hostname
Someone could be eavesdropping on you right now (man-in-the-middle attack)!
It is also possible that the RSA host key has just been changed.
The fingerprint for the RSA key sent by the remote host is
Please contact your system administrator.
Add correct host key in /home/username/.ssh/known_hosts to get rid of this message.
Offending key in /home/username/.ssh/known_hosts:13
RSA host key for hostname has changed and you have requested strict checking.
Host key verification failed.

If this happens, you should contact the administrator of the remote machine and ask them why this might have happened. If there is nothing on the remote machine that has changed, this should raise a big red flag.

The administrator of the remote machine can check their RSA host key (and communicate it to you via a SECURE means, i.e., not via email) by running this command on the remote server:

cat /etc/ssh/

(or, alternatively, the system administrator should know where their RSA keys are. If they don't, they are oblivious to security ad you should find a new system administrator).

The administrator of the remote machine can generate a new RSA host key by running the command

$ ssh-keygen -l -f /etc/ssh/

or, if the machine is a Mac (or a similarly BSD-based OS),

$ ssh-keygen -l -f /etc/

SSH Shortcuts

If you ssh into hosts with nonstandard ports, long hostnames, or different usernames, it gets annoying to type them all out. You can create host profiles in your ~/.ssh/config file that can help shorten those.

Let's say you SSH into a machine like this:

$ ssh -p9999 

You can shorten this by adding the following into your ssh config file:

Host machine1
User my_username
Port 9999

Now, the ssh command can be shortened to:

$ ssh machine1

Port Knocking

Port knocking is the idea that, in order to remotely connect to a machine via SSH, you can require a certain port-knocking pattern - kind of like if you had 65,536 front doors, and you would only open door number 22 if, FIRST, a person knocked on door 5000, then on door 4000, then on door 3000, then on door 2000, then on door 1000.

Port knocking is security through obfuscation, which is a weak form of security on its own (since, once your secret port knocking pattern is known, it is trivial to bypass), but can lead to hackers giving up and moving on to find some other, easier machine.

Fart Knocker vulnhub box:


wikipedia:Apple Filing Protocol

Tunneling AFP through SSH -

How to create a self signed certificate -