The kit arrived just in time and I have worked on setting up the environment for the Command Center, based on the Raspberry Pi 3. In this post I cover the initial Command Center setup, securing SSH with SSH keys, installing and tunneling VNC through SSH, a post focused mostly on security. But first an index to my previous posts for reference - thanks mcb1 for your suggestion last time - and the project status view.
Initial Setup of the Command Center
Let's start setting up the new RPI3 just received from Element14 Although it is not required, I like to make an initial backup of the SD card. To do so, after inserting the SD card in the adapter I put it in my Mac. Please note, that all of the commands will be for Mac (sorry about this limitation...) and will be using the Terminal app. The command I'm using for the backup is:
sudo dd if=/dev/rdisk1 bs=1m | gzip > ~/Desktop/pi.gz
A couple of comments on this, the /dev/rdisk1 is the device (SD card) I just inserted, to find yours, you can use the app in Mac "Disk Utility" and locate the SD card on the left hand side menu. You will find it without the "r", that is "disk1". By using /dev/rdisk1 with the command, you access the disk in a raw mode making the data transfer much faster. Another note, you need to be super user - or log with an account with these rights - to execute the dd command. Last comment, I send it through gzip (| gzip in the command line) to avoid storing 16Gb, the final file goes up to 2.5 Gb. This process will take long, it will take looong, in my computer took me 20 something mins… You can check the progress by pressing Control-T every now and then. But… be patient… I insist, this step is not necessary as you can always obtain the lastest NOOBS from the here, but I prefer doing so and storing this in my home server. Whenever you want to restore this image, you can do it with the command below and same comments as above.
gzip -dc ~/Desktop/pi.gz | sudo dd of=/dev/rdisk1 bs=1m
In any case, backing up the SD is a healthy thing to do from time to time.
After plugging the RPI to my TV via HDMI and connecting an external keyboard and mouse to the USB ports, it is time to start it up and continue configuring the RPI. I have realized that the NOOBS that came with the SD directly starts the graphical interface, which I personally prefer for the first steps. The first key step is to change the password, better now than to forget about this later and expose your RPI and your whole home network on the Internet. Just go to Menu->Preferences->Raspberry pi Configuration and you can change it there. While we are here, I change the Hostname to DomPi, a bit of customization for the project
Wifi Setup - what I find great in the RPI3 is that the Wifi module is already built in, no need of any dongle which makes this much easier. One important thing is that the RPI gets always the same IP address, otherwise, each time you boot it up, it may change and you will need to find out the IP before being able to connect. You can configure a static IP via the RPI configuration, but I prefer to put enforce the IP address on the router instead. I let my router manage all of the IP's. This also makes it easier if I ever take the RPI to another home/network, as it will continue to use the DHCP to get the address. All in all, I obtain the MAC address of the Wifi interface in a Terminal and with the ifconfig command.
A note on security and SSH Keys
As said above, security on devices connected to the Internet is a must, and I learned it via "almost" the bad way. The first time I had a RPI I installed the VNC to be able to control the Desktop in another computer and avoiding to have to connect it always to the TV. Since I wanted to access VNC from a remote location, I opened the ports in the router and went on vacations. After a couple of days, I wanted to log on to the VNC to work something out and... I could not enter. Luckily enough I did put a "difficult" password and the effect all in all is that I could not log into my own RPI but neither could the intruder. I was so surprised that somebody is even interested in breaking into my network - I mean, I'm just yet another home in the Internet...
My lesson learned from that project and that will apply here is to configure the SSH server in the RPI to request a 4096bit shared key. This should be better than any password I can create, hehe, and remember. Let´s start generating the public and private keys in my Mac. To do so, I typed:
ssh-keygen -b 4096
and changed the name of the files to "id_rsa_dompi_cx", and left the default folder. When asked for the passphrase, I typed a phrase I can remember and is long enough. This passphrase will encrypt the key to be generated. The next step is to copy the public key just generated in the Mac into the RPI. From a Terminal window in the Mac I typed:
scp .ssh/id_rsa_dompi_cx.pub email@example.com:/home/pi/.ssh/id_rsa_dompi.pub
You can modify the IP address to fit yours. The next step is to add the public key just copied to the authorized key file in the Raspberry Pi. To do so, I did ssh to the RPI (or just type the following directly on a bash window on the RPI) and typed:
chmod 700 .ssh cat .ssh/id_rsa_dompi_cx.pub >> .ssh/authorized_keys chmod 600 .ssh
With this, the RPI is already accepting a SSH request from my Mac if it is encrypted with the private key. In this way, I don't need to type any password. To test the connection you can execute this command on the Mac Terminal:
ssh -i .ssh/id_rsa_dompi_cx firstname.lastname@example.org
It should ask for the passphrase. If you allow that it is included in the key chain, you will not need to type any password any more when ssh´ing into the RPI To make it easier and faster I have created an alias:
And added this line:
alias sshdompi='ssh -i .ssh/id_rsa_dompi_cx email@example.com'
After relaunching the Terminal, I just need to type sshdompi and I will be ssh´d into the RPI without any password typing or remembering any other command.
The final step is to configure the SSH to only accept connections that are based on public keys. For that in the RPI I edit the following file:
sudo nano /etc/ssh/sshd_config
And I checked that it had these lines in it:
PasswordAuthentication no RSAAuthentication yes PubkeyAuthentication yes
and I relaunched it by: sudo /etc/init.d/ssh reload
I am conscious I just briefly touched upon security and there are many more points to take into account, but this is not the objective of this post. There is an interesting post SSH Keys.and I would recommend this web for
To get the VNC server in the Command Center I followed the instructions in here: https://www.raspberrypi.org/documentation/remote-access/vnc/ There is no special call out rather than I did set it up to run at boot.
Tunneling VNC over SSH
As said above, it can't be strengthened enough the importance of securing devices exposed to the Internet. The tightvnc version says it transmit between devices without encryption. So the best I can do is to tunnel the VNC over SSH and achieve two goals at the same time:
- the data will be encrypted between my Mac and the RPI - specially important when I communicate to it over the Internet
- instead of only using a password to connect to VNC, this solution uses first the private-public key encryption as per above and then the VNC password, limiting brute force attacks - as I wrote in the first paragraphs, I learned this the hard way...
There are two parts, on my Mac and on the RPI.
Mac VNC over SSH setup
Starting by the Mac, there are as well two steps, first is a sort of ssh forwarding a local port to the correct RPI port and second is launching the VNC client against the local port instead of the RPI remote port. The ssh command looks like (and an explanation of the parameters can be found here):
ssh -L 5901:127.0.0.1:5900 -N -f -l pi 192.168.1.11
alias sshvncint='ssh -L 5901:localhost:5900 -N -f -l pi 192.168.1.11'
Actually I created two alias, the internal one (above) and yet an external one that I use when not at the home network - just modifying the ip address and entering the router WAN´s (remember to configure the routers´ports). When launching VNC, the address of the VNC server to enter is no longer the RPI IP address, but "localhost:5901" or "localhost:1" if you modify the VNC config and specify there the port to use in the Mac.
Force VNC to accept only SSH
In principle avoiding somebody from the Internet to access my VNC server without a SSH tunnel and the right private key should already be protected just by not opening the VNCserver port on the router. However, it does not harm to quickly setup the VNC to just accept sessions originated in the RPI or localhost and ignore the rest. To do so I edit again the file
/etc/init.d/vncboot (see again this link ) and modify the appropriate line by:
su - $USER -c "/usr/bin/vncserver :1 -geometry 1280x800 -depth 16 -pixelformat rgb565 -localhost -nolisten tcp"
the -localhost parameter makes VNC to only listen to the port on the local interface and the -nolisten tcp disables the port 6001. Further info here.
To sum up, we have now a VNC server that only listens to connections on the local host, these connections can come from the RPI or from the outside. If coming from the outside, they have to arrive via the SSH tunnel. To connect to the SSH tunnel, the client has to have the appropriate private key that the RPI will confirm against the public key. Besides that, once the connection with the VNC server is established, the server will ask yet for the VNC password. All in all, I'd say quite a secure communication to avoid exposing our network on the internet. This can still be improved by modifying the default ports of the SSH and VNC if you wish to.