Přeložit do češtiny pomocí Google Translate ...

Labs: 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14.

In this lab we will do a quick refresh of the principles of asymmetric cryptography and then start using SSH: a way to work on a remote Linux machine in the shell.

Note about asymmetric cryptography

Before diving into details about SSH, we need to make a brief refresh of some cryptography-related topics.

In this lab we will be talking a lot about asymmetric cryptography. In general, it is a method of encryption/decryption where the user needs a different key for decryption of the message than the one that was used for message encryption.

For example, the well known Caesar cipher is an example of a symmetric cryptography: the key used for encryption (i.e., the alphabet shift size) is the same one as key used for decryption (only applied in reverse direction).

Asymmetric ciphers require use of two keys. Usually they are called a private and a public key (often, these ciphers are referred to as public/private key encryption). The sender of the message uses a public key to encrypt the message and the receiver decrypts it with the private key. Because it is impossible (or rather very difficult) to derive the private (deciphering) key from the public one, the message is considered safe.

Note that asymmetric cryptography has an advantage that the users do not have to protect many keys: they need to know the public keys of the recipients (but these are, by definition, public and in no need for protection) and guard their private key for decryption.

Unlike symmetric cryptography, asymmetric cryptography is much more complex and there is no “asymmetric” equivalent to the Caesar cipher that represents the simples form of a symmetric cipher. The simplest thing to imagine is that the user randomly selects two large primes as his private key. The public key is then their multiplication. The safety of this approach is based on the belief that deriving the private keys from the public one is rather difficult. As a matter of fact, RSA is based on this assumption but it has several extra steps to make the system actually useful.

Please, refer to a real material about cryptography if you want to learn more. The above serves as a refresher to ensure we are on the same page for the rest of this lab.

Two uses for asymmetric cryptography

Asymmetric cryptography has two main uses. The first one is obvious: if we know the public key of the receiver of the message, we can use it to encrypt the message and send it over unprotected medium (and without fear that anyone else would be able to read it).

But it can be used also in reverse to authenticate the owner of the private key. We assume we are able to distribute the public keys safely here.

The mini-protocol is then able to authenticate (i.e., verify) that the other party is who he claims to be by proving the ownership of the private key (i.e., we assume that private keys were not stolen).

The method is very simple – the sender generates a random text and encrypts it with the public key of the receiver (the one we wish to verify). If the receiver is the real owner, he would be able to decrypt the random text and send it back to us. Inability to decrypt the text means the receiver is not the owner of the private key.

Public & private key authentication

Typically a user authenticates to a service with a login and a password. While this method is quite natural and common for human users, it has several drawbacks.

The most obvious problem is password strength: people have rarely long passwords and not many people use any form of password manager. Using same passwords on multiple places also allows administrator (or hacker) of one service to act as you in other services.

Instead, some services allows the user to authenticate with his public key. The user uploads the public key to the server (using login and password for authenticating that operation) and when he wants to log-in, server challenges him with a random secret encrypted with his public key. As he is the sole owner of the private key (and hence the only one able to decrypt) he can decrypt the secret and confirm his identity. Operation then continue as with any other authenticated user.

Useful rules

For the public key authentication to work correctly, the following is highly recommended (note that most of the rules apply to any other type of authentication too).

The private key is like the password – it must not leak. Because the private key is usually a file, you must protect this file. Having an encrypted hard-drive is a typical option for portable machines.

It is possible to protect the key itself with a passphrase (basically, another password). Then even a leaked private key file is not an immediate threat to identity theft. Note that there are helpers, such as ssh-agent(1) that can store the passphrase for some time so you do not have to enter it every time you use the key.

Usually, private/public key is local to a machine. While it is possible to copy it both to another machine, prefer not to do it. It is similar to using the same password on multiple sites.

SSH

SSH – that stands for Secure Shell – is a protocol for connecting to a different machine and running a shell there.

From a user perspective, after you SSH from a Linux machine into a different Linux machine, the shell may look the same and some commands would behave completely the same. Except they might be running on a different computer.

Note that this is intentional: remote (and secure) shell is a natural way to control a Linux machine. No need to make it different from controlling it through a local shell.

Using SSH

Using SSH is very simple (but can be configured to be very complex too). To SSH to a remote machine, you need to know your credentials (i.e., username and a password) and, of course, name of the remote machine.

To SSH to the machine, simply execute the following.

ssh YOUR_LOGIN@REMOTE_MACHINE_NAME

Note that the command ssh is often called SSH client as it connect to the SSH server (similar to curl or wget being web clients connecting to a webserver).

We have set-up a remote machine for you on linux.ms.mff.cuni.cz. You will be using your GitLab (SIS/CAS) login and also the same password.

ssh YOUR_SIS_LOGIN@linux.ms.mff.cuni.cz

The first login to the machine is a bit more complicated. SSH client wants from you a verification that you trust the remote server. It shows you a so-called server fingerprint.

The authenticity of host 'linux.ms.mff.cuni.cz (195.113.20.170)' can't be established.
ECDSA key fingerprint is SHA256:ltoc1TjoYhCZk6b8qSTAL6wFsRv7blw6u3h6NqCcYvI.
Are you sure you want to continue connecting (yes/no/[fingerprint])?

Based on your configuration, RSA or ED25519 key may be used instead:

RSA: SHA256:Z11Qbd6nN6mVmCSY57Y6WmxIJzqEFHFm47ZGiH4QQ9Y
ED25519: SHA256:/CVwDW388z6Z5VlhLJT0JX+o1UzakyQ+S01+34BI0BA

You should have received this fingerprint in a secure way before connecting to the server (for example, printed from your employer etc.). In this case, we hope that a potential attacked would not be able to attack both this web server and the SSH server at once and we consider HTTPS protocol used here as secure to verify the server.

The program then continues to ask your for a password and also informs you that the fingerprint was stored.

On following logins, SSH client checks that the fingerprint has not changed. A changed fingerprint belonging to the same machine (i.e., with the same DNS name) could indicate a man-in-the-middle attack. Do not connect when fingerprint was changed. Always contact the admin (e.g., the teachers in this particular case) and check with him what is happening.

If you were able to log-in, you will see an (almost) empty $HOME and otherwise a normal Linux machine, this time without any graphical applications installed.

Note that this machine is shared for all students of this course. Use it to solve graded tasks or to experiment with commands we show in the labs. Do not use it for computationally intensive tasks or other tasks that are not related to this course. If we encounter any form of abusive use, we will block the offending account.

Using machines in Rotunda

Apart from the machine linux.ms.mff.cuni.cz there is also a full lab of machines available in the Rotunda computer lab on Malostranské náměstí.

All the GNU/Linux machines are also reachable via SSH. Again, use your SIS credentials to log-in. Note that all machines in Rotunda (but not linux.ms.mff.cuni.cz!) share the same $HOME, i.e., it does not matter to which you physically connect. Your files will be available on all machines.

Unfortunately, the used file system and authentication mechanism does not allow to use public key authentication for Rotunda machines. You need to always specify your password. (linux.ms.mff.cuni.cz does not have this limitation and we expect you will use public key authentication there.)

Following machines are available.

  • Lab SU1
    • u1-1.ms.mff.cuni.cz
    • u1-2.ms.mff.cuni.cz
    • u1-14.ms.mff.cuni.cz
  • Lab SU2
    • u2-1.ms.mff.cuni.cz
    • u2-2.ms.mff.cuni.cz
    • u2-25.ms.mff.cuni.cz
  • Rotunda
    • u-pl1.ms.mff.cuni.cz
    • u-pl2.ms.mff.cuni.cz
    • u-pl23.ms.mff.cuni.cz

Using SSH to run one command

The command ssh is actually quite powerful and configurable. One important feature is that you can specify a command after the hostname and run this command directly. In this case, SSH never starts interactive shell on the remote machine but executes the command only and returns.

Following commands prints uname -r on the remote machine.

ssh user@hostname uname -r

Investigate how (and why) the following command behaves differently.

ssh user@hostname uname -r >local_file.txt
ssh user@hostname "uname -r >remote_file.txt"

Sidenote: uname and hostname

To verify that you are on a different machine, run on both uname -a and hostname -f.

uname identifies the current machine (kernel version, CPU architecture etc.) while hostname provides details about DNS name of the current machine.

Can you see the differences?

You can also trying checking free -h or uptime.

SSH and passwordless authentication

To enable authentication with public key over SSH, we need to perform two steps. Generate the public-private key pair and copy the public key to the remote machine.

To generate the public key we need to run the following command.

ssh-keygen -t ed25519 -C "your_email@example.com"

The program would ask us where to store the generated private and public key. Keep the defaults. Then check that directory ~/.ssh contains id_ed25519 and id_ed25519.pub. Choose if you want a passphrase or not (it is more secure to have one but the use is a bit more cumbersome).

Feel free to inspect their content. Surprised that they are text files?

Once we have the key ready, we need to upload it to the remote machine. If you have multiple key pairs, read about -i switch.

ssh-copy-id LOGIN@REMOTE_MACHINE

If you log-in to the remote machine again, the SSH client should use the key pair and log you in without asking for a password. If not, run SSH with -vvv to debug the issue.

Note that the public key was stored into ~/.ssh/authorized_keys file on the remote machine. You can copy it there manually but using ssh-copy-id is easier.

Update if the copying fails with cryptic message about warning: here-document at line 251 delimited by end-of-file (wanted EOF), try upgrading SSH client first. If you use the image from us, simple sudo dnf upgrade openssh-clients should work.

Disabling login/password

Note that some services actually require that you authenticate using a key-pair instead of a password as it is considered more secure.

The advantage is that any random attackers could keep guessing your password and still never get access to your machine.

Typically, the server is also configured to ban any client that tries to login without success several times in a row. Our server does that too.

SSH configuration

The SSH client is configured via the ~/.ssh/config file. Review the syntax of this file via man 5 ssh_config.

The file is divided into sections. Each section is related to one or more remote hosts. The section header is in the format Host pattern, where pattern might use wildcards.

The syntax is mostly self explanatory, so we will only provide an example.

Host *
  	IdentityFile ~/.ssh/id_ed25519

Host intro
	Hostname linux.ms.mff.cuni.cz
	User YOUR_SIS_LOGIN

Host mff1
    Hostname u-pl6.ms.mff.cuni.cz
    User YOUR_SIS_LOGIN

Host mff2
    Hostname u-pl17.ms.mff.cuni.cz
    User YOUR_SIS_LOGIN

With this ~/.ssh/config, we can type ssh intro and the ssh will start connection equivalent to

ssh YOUR_SIS-LOGIN@linux.ms.mff.cuni.cz

We recommend to use different u-pl* hostnames in your config to distribute the load across multiple machines. Note that the Rotunda machines may be unevenly loaded so it is a good idea to bookmark several of them and relogin if the first one is too slow.

SCP

In order to copy files between two Linux machines, we can use scp. Like SSH, it is a secure variant of rcp(1), i.e. a remote copying tool.

The syntax is very simple and follows the semantics of a normal cp.

scp local_source_file.txt user@remote_machine:remote_destination_file.txt
scp user@remote_machine:remote_source_file.txt local_destination_file.txt

Note that many file managers allows you to open SCP-style connection transparently and copy between machines with the same ease as when working with local files.

For example, in mc, select Shell connection either in left or right panel and specify SSH connection. One of the panels will show the files on the remote machine. Try using F5 to copy files interactively.

SCP issues

For those who care about security we should note that that the SCP protocol has some security vulnerabilities. These can be used to attack your “local” computer while connecting to a malicious server. There are some replacements for the scp utility, namely sftp(1) (don’t confuse with ftps) or rsync(1). Sadly none of these is a drop in replacement or provides the simplicity of the scp command.

The rsync tool requires plenty of command line options even for simple copy operations. It’s benefit is that it is so smart that it can transfer only files that differ on remote and local computer.

The sftp(1) command on the other hand often requires using an interactive mode, which is inappropriate in automated scenarios.

More information on this topic can be found on LWN.net.

Git over SSH

So far, we have used Git over HTTPS. Git can be used over SSH too. Then, the traffic is basically tunneled through an SSH connection and Git relies on the SSH wrapper for security as well as for (partial) authentication.

Virtually all Git servers (GitLab, GitHub, Bitbucket…) will require you to upload your public key if you want to use Git over SSH.

GitLab and SSH keys

Copy your public key to GitLab. Navigate to right-top menu with your avatar, select Preferences and then SSH keys or visit this link.

Copy your public key there and name it. Typically, the name should mention your username and your machine. Note that GitLab will send you an e-mail informing you about a new key. Why? Hint. Answer.

Go to your project and clone it again. This time, use the Clone with SSH URL.

git clone git@gitlab.mff.cuni.cz:teaching/nswi177/2021-summer/student-LOGIN.git

Have you noticed that this looks like SSH/SCP address? It actually is exactly that. The first part identifies the machine and the user (git) and after a colon is a local path.

You can clone this way a Git directory from any SSH server by specifying its remote path there (here, GitLab does some mangling but the principle holds).

Note that the user we clone with is git – not you. This way, GitLab needs only one physical user account for handling Git requests and distinguishes the users via their public keys. How? Answer.

By the way, what happens if you try to run the following?

ssh git@gitlab.mff.cuni.cz

Note that you should use the SSH protocol for working with Git as it is much more comfortable for use. Note that Git on other platforms also offers generation of an SSH key but often the key is usable only by one application (different applications have incompatible key formats), while on Linux a single key is a generally usable for Git, other machines, and other services.

SSH forced command

There are situations when you want to give a user access to a machine over SSH but limit the operations they can perform. One of the ways is to use the so-called SSH forced command where you can specify that user with given SSH public key will always execute a specific script. Inside this script you can perform any checks you need.

To test this, generate another SSH key (and ensure you do not overwrite your existing one). Copy this key to the linux.ms.mff.cuni.cz machine too.

Log in to the remote machine and open ~/.ssh/authorized_keys in an editor. In front of the second key add the following

command="uname -r",no-port-forwarding,no-X11-forwarding,no-pty

The whole line would thus look like this:

command="uname -r",no-port-forwarding,no-X11-forwarding,no-pty ssh-ed25519 ALOTOFCHARACTERS intro@localhost

Use the -i parameter of ssh to log-in to the remote machine using your other key.

You should see the following output.

PTY allocation request failed on channel 0
NUMBERS.fc33.x86_64
Connection to lab.d3s.mff.cuni.cz closed.

The error messages on first and last line informs us that we do not have access to an interactive shell and that the connection was closed after the command terminated.

Using this technique, you can allow execution of a specific command for a specific user without giving full access to the machine.

Note that the extra options no-port-forwarding,no-X11-forwarding,no-pty ensure that the user cannot do much mischief.

The original command specified on the command-line is available as $SSH_ORIGINAL_COMMAND inside the executed script.

What to try when you are locked-out…

If you managed to break your ~/.ssh/authorized_keys, following commands may get you back on track.

First of all, adding -o PreferredAuthentications=password and/or -o PubkeyAuthentication=no should revert you to the password authentication, bypassing any SSH keys (what will work depends on the state of your authorized_keys).

Another option is to try to log-in via a different machine where you do not have any SSH keys (e.g. machine in Rotunda lab).

Finally, when you believe your SSH client picks the wrong key, try adding -o IdentitiesOnly=yes.

If none of the above helps, try to investigate the reasons by adding -vvv to your ssh command. If that does not help, contact us.

Unix-style access rights

So far we have silently ignored the fact that there are different user accounts on any Linux machine. And that users cannot access all files on the machine. In this section we will explain the basics of Unix-style access rights and how to interpret them.

Recall what we said about /etc/passwd – it contains list of user accounts on that particular machine (technically, it is not the only source of user list but it is good enough approximation for us at the moment).

Every running application, i.e. a process, is owned by one of the users from /etc/passwd (again, this contains small simplifications but these are not important for us at the moment). We also say that the process is running under a specific user.

And every file in the filesystem (including both real files such as ~/.bashrc or virtual ones such as /dev/sda or /proc/uptime) has some owner.

The ability to read or modify a file is then determined by the combination of the owner of the file, owner of the process and actual access rights.

In simplest case, if the owner of the process is the same as the owner of the file, it can virtually do anything with it. This is checked by the operating system and if the process tries to perform a prohibited operation, the error is usually propagated as a raised exception in the programming language.

Note that ownership of the executable script is not relevant here once the program was started (i.e., once the passive entity of an executable file becomes the active entity of a running process). For example, /usr/bin/mc is owned by root, yet it can be launched by any user and the running process is then owned by the user that launched it.

Having only an owner would be too limiting, so every file also has an owning group as well (usually just called group for the file).

The actual access rights are of three types: right (or permission) to read (r), to write (w) and to execute (x).

When a process wants to perform some operation on a file, the operating system performs the following checks.

  1. If the user running the process is the same as the owner of the file, owner access rights are used (sometimes also referred to as user access rights).
  2. If the user running the process is in a group that was set on the file group access rights are used.
  3. Otherwise, the system checks against other access rights which is a third set of access rights that each file has.
  4. As a special condition: if the process is run under root (recall that this is the superuser or administrator of the system), it can perform any operation with the file.

Depending on the requested operation, access rights are checked – always against one of user (i.e., owner), group, or other (i.e., everybody else).

  • Read and write operations on a file (i.e., open(..., "w")) are obvious.

  • Executable right is used when user tries to launch a script (recall that without chmod +x, the error message was in the sense of Permission denied: this is the reason).

    • Note that missing executable bit can be often bypassed by selecting the appropriate interpreter manually.
    • Note that when script is launched, by default the owner of the new process is the same as the owner of the shell that launched it.

The same access rights also apply to directories. Their meaning is a bit different, though.

  • Read right allows the user (technically, to the process running under that particular user) to list files inside a directory.
  • Write right allows the user to create or remove files inside that directory. Note that removing write permission on a file inside a writable directory is pointless as it does not prevent the user from overwriting the file completely with a new one.
  • Executable permission allows the user to change directory to it.

Note that with x permission, the user can cd to a directory but cannot list files there. Opening a particular file is possible (if the permission on the file allows it and the user knows the name of the file).

Viewing and changing the permissions

Looking at the shortcuts of rwx for individual permissions, you may found them familiar.

Execute ls -l. The very first column actually contains three columns of these three permissions. The first three letters refer to owner of the file, middle ones to the group and last to the rest of the world (other). The first denotes type of the file (d for directory and - for a plain file are the most typical ones). The next two columns contain owner and group of the file.

Typically, your personal files in $HOME will have you as the owner together with a group with the same name. That is a default configuration that prevents other users seeing your files.

Note that most of the files are actually world-readable (i.e. anyone can read them).

That is actually quite fine because if you check permissions for your $HOME, you will see that it is typically drwx------. Only the owner can modify and cd to it. Since no one can actually change to your directory, no one will be able to read your files (technically, reading a file means traversing the whole directory and checking access rights on the whole path).

To change the permissions, you can use chmod program. It has the general format of

chmod WHO[+=-]PERMISSION file1 file2 ...

WHO can be empty (for all three of user, group and others) or one of u, g or o. And PERMISSION can be one of r, w or x.

Change permission of some of your scripts to be --x. Try to execute them. What happens? Answer.

Remove writable bit for a file and write to it using stdout redirection. What happens?

Sticky and other bits

Execute the following command and interpret the permissions of the mentioned files.

ls -ld /usr/bin/passwd /tmp/

You should have noticed that /tmp has t in place of an executable bit and passwd has s there.

Those are special variants of the executable bit. The t bit on a directory specifies that user can remove only his own files. The reason is obvious – you shall not be able to remove someone else’s files inside /tmp. Something that is otherwise impossible to specify with traditional (basic) permissions.

The s bit is a bit more tricky. It specifies that no matter who runs the shell, passwd will be running under the user owning the file (i.e., root for this file).

While it may look useless, it is a simple way to allow running certain programs with elevated (higher) permissions. passwd is a typical example. It allows the user to change his password. However, this password is stored in a file that is not readable by any user on the system except root (for obvious reason). Giving s bit to the executable means that the process would be running under root and would be able to modify the user database (i.e., /etc/passwd and /etc/shadow that contains the actual passwords).

Since changing the permissions can be done only by the user of the file, there is not a danger that malicious user would add the s bit to other executables.

There are other nuances regarding Unix permissions and their setting, refer to chmod(1) for details.

Beyond traditional Unix permissions: POSIX ACL

The permission model described above is a rare example of a concept coming from Unix that is considered inflexible for use today. However, it is also considered as a typical example of a simple but well usable security model.

Many programs copied this model and you can encounter it in other places too. It is definitely something worth remembering and understanding.

The inflexibility of the system comes from the fact that allowing a set of users to access a particular file means creating a special group for these users. These groups are defined in /etc/group and require administrator privileges.

With increasing amount of users, the amount of possibly needed groups grows exponentially. On the other hand, for most situations, the basic Unix permissions are sufficient.

To tackle this problem, Linux offers also so-called POSIX access control lists where it is possible to assign an arbitrary list of users to any file to specify the permissions.

We require you to know that getfacl and setfacl are the utilities to control these rights but since these are practically needed rarely, we will leave their knowledge at the level of reading the corresponding manpages.

Miscellaneous

If the above about SSH was not enough for you, you may want to consult SSH section of our Resources page.

Graded tasks

Note that for many subtasks, the files are not created in the GitLab submission repository but on the remote machine.

These files cannot be checked automatically by GitLab so pay attention to correct naming etc.

Remote file ~/LAB06 (20 points)

Create file LAB06 in your home directory on linux.ms.mff.cuni.cz. Make your UKČO (the number from your ISIC) its only content.

NOTE: do not create this file in GitLab, we will check it on the linux.ms.mff.cuni.cz only.

Upload our key (20 points)

Add the following public key to authorized keys on your account at linux.ms.mff.cuni.cz. We will check that you have completed this task by SSHing to linux.ms.mff.cuni.cz with your login and this key.

ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIPuoJJldIS6zOxunFxIFGk6tQlw0qpYSOxHYs57117o/ teachers-nswi177@d3s.mff.cuni.cz

NOTE: do not create this file in GitLab, we will check it on the linux.ms.mff.cuni.cz only.

Forced command (30 points)

Following is a list of pseudo users and their public keys. Note that Bob is using a different schema based on RSA for his key. From the user perspective, there is no difference in handling this key.

Do not forget that each key is on one line.

ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAINKE4OEsqqFtJR91HLxUH9Lq2C820lXHIm/HdzE7Byuv root
ssh-ed25519 AAAAC3NzaC1lZDI1NTE5AAAAIG7s1tksIl7xh5LztR2UOjUteHzhem4DViUHuhBbL++r alice
ssh-rsa AAAAB3NzaC1yc2EAAAADAQABAAACAQCeMKM++p6gJBokA6LCaDVjWIRGu93uuKHWH1Rs0fzIvuSLxnN1yKaCDm5iB8rN3WkNfrLBudLnbHTg0Axm04MisgqPm8IsnbURz7cjG3IhWsbYh8cikgLFq+ShtS670cD4r3aSn1uLtxnCKIzgUl4X5VvdJsrVtGKfkxWezSWhqdeVIEAcohV5/H1jg9NcLGEd10kOEveU2oHx0AbwkB75kZS6+GL+enRC2TWXoz096mv4CmSHhGFBoJYbQOh3TiqiD6FxfPgkCf/k09fyHCVUwx6OTuqk60qiT0YBCAhTMMSNo6jg0QHXe4UlxVn6dOq8G6r9F2bS9yNXRqrruJl7yD4NWX99lxvNAWAA8CFFx3/vsHNK/DACdfSpTeCZnsrwWn5hLIY0pI6ZMimKhlqgni/pOuf7y8WeZnud+R5ojKLJ89uhTcg+lwmWiPn+zKSUDcGfaskl5VZ8SY1psbOLd/bGR2GR5rDetBS3Jbvlvq1mO2WU3cn0AF12Mvs3p99zGKzami2saqZgtmfbsZ3Vz1kkiSI7TqSyhtsAy9H+JdMpV6wi3EKHTufHMJe6YwMzQFO9w8qsO5DvCTV4I+cvvdSRLCFefcAQcQbaAYnOYzUX0BLl6ZTx1SCUg3uylLzhx55PF4FOnU/K1CKrdfn+ydPPtx1HhmU9t4KRuaYTRw== bob

Configure your SSH account on linux.ms.mff.cuni.cz to recognize the following commands for the above users. Note that we will check your authorized_keys file to ensure that you are using a common script for all pseudo users above.

None of the users can log in for an interactive shell but can use the following commands

  • date to print current date in YYYY-MM-DD format.
  • stat to show how many times they have executed date today (i.e. this number would reset after midnight)

User root can also execute command csv to download current day statistics for each user.

You can safely assume that users will never execute their commands concurrently.

Follows a simple session, commands are prefixed with > to distinguish them from command output. SIS_LOGIN is your SIS username.

> ssh -i key_alice SIS_LOGIN@linux.ms.mff.cuni.cz date
2021-03-31
> ssh -i key_alice SIS_LOGIN@linux.ms.mff.cuni.cz date
2021-03-31
> ssh -i key_alice SIS_LOGIN@linux.ms.mff.cuni.cz stat
2
> ssh -i key_bob SIS_LOGIN@linux.ms.mff.cuni.cz date
2021-03-31
> ssh -i key_bob SIS_LOGIN@linux.ms.mff.cuni.cz xdate
Invalid command.
> ssh -i key_bob SIS_LOGIN@linux.ms.mff.cuni.cz stat
1
> ssh -i key_root SIS_LOGIN@linux.ms.mff.cuni.cz csv
user,count
alice,2
bob,1
root,0

HINT: create your own set of keys that would behave as another key for root, alice and bob to test your solution.

HINT #2: store the stats for each user in a file named after this user in some common directory (using ~/.nswi177/06 is certainly an option).

NOTE: do not create this file in GitLab, we will check it on the linux.ms.mff.cuni.cz only.

UPDATE: the ordering inside CSV file does not matter, but keeping it alphabetical is certainly a good option.

06/key.pub (15 points)

Store your public key into this file.

Do not lose the private part for it – we will use it for some other tasks later on.

NOTE: this file must be uploaded to the GitLab repository.

06/machine_status.sh (15 points)

On the linux.ms.mff.cuni.cz machine you will find a file /srv/nswi177/machine.status.

We intentionally do not provide any description of the format – it shall be obvious from the file itself. We expect you will make a reasonable deduction of the format.

This file contains an exported status of several services of several machines in the network (you can imagine that in real situation, this will would be regularly updated). Note that the last column denotes status of the service, 0 means the service is up and running (i.e., okay), any other number denotes a problem.

Your task is to write a shell script that prints an overview of the machine states. Using the provided file, the script shall print the following and terminate with exit code 1.

alpha.example.d3s.mff.cuni.cz: UP
bravo.example.d3s.mff.cuni.cz: DOWN
yankee.example.d3s.mff.cuni.cz: DEGRADED
zulu.example.d3s.mff.cuni.cz: UP

The overview contains only the machine name, state is derived from amount of failing services (all services are okay is UP, all services have some kind of problem is DOWN, otherwise it is DEGRADED).

When some of the services have problems, the script terminates with exit code 1, exit code 0 is used only when all services on the machines are up.

Optional argument can be a regular expression filtering the machine list. For tests, we will be using only the basic parts of regular expressions: matching a substring (e.g., alpha) or matching a set of characters (e.g., worker[0-9][0-9]). These should be the same across all tools and dialects.

06/machine_status.sh alpha

With the above invocation, following is printed with exit code of 0.

alpha.example.d3s.mff.cuni.cz: UP

When no machine matches the filter, exit code 2 is used.

Adding parameter --silent or --quiet or -q suppresses any output, meaning of exit code is unchanged.

Running with --help prints the following help (please, use it verbatim):

Usage: machine_state.sh [options] [machine-filter]
 -h --help            Print this help.
 -i --input FILE      Read state from FILE.
 -q --quiet --silent  No output, only exit code.

When -i or equivalent is used, the machine state is read from the provided file instead of /srv/nswi177/machine.status.

Running with unknown parameters (e.g., -x) must terminate the program with exit code 101. When the input file (-i) does not exist, terminate with exit code 102. Note that there are not GitLab pipeline tests for this behaviour but feel free to write your own.

NOTE: this file must be uploaded to the GitLab repository.

Deadline: April 26, AoE April 28, AoE (extended)

Solutions submitted after the deadline will not be accepted.

Note that at the time of the deadline we will download the contents of your project and start the evaluation. Anything uploaded/modified later on will not be taken into account!

Note that we will be looking only at your master branch (unless explicitly specified otherwise), do not forget to merge from other branches if you are using them.

Changelog

2021-04-29: Clarify which regular expression dialect will be used in 06/machine_status.sh.