Lab - 3 - File capabilities and files' extended attributes

Introduction

The goal of these exercises is to explore the programmatic functionalities of Linux capabilities and files’ extended attributes.

This work requires a Linux host, which can be virtualized.

Resources required: capabilities.zip

Goal

The purpose is to implement a simple file ownership take-grant mechanism. Actually, only the super-user of a process with the CAP_CHOWN capability can change the ownership of a file. Furthermore, there is no mechanism to request, or allow, an ownership modification.

In the Windows NTFS it is possible to indicate, for a given file, that a set of targets can take its ownership. Given that permission, those targets may effectively take its ownership, but on a voluntary basis. The goal is to do something similar in Linux, while not allowing a list of targets (which NTFS supports).

The code to implement this guide is provided in the course Web page.

Software installation

This guide requires the installation of the tools that manipulate files’ extended attributes:

sudo apt install attr

Give ownership}

To give a file ownership to another pair UID / GID, we will develop a program give that uses the extended attributes of a file to express that desire. We will used the attribute user.new-owner to provide the UID of the new owner, and the attribute user.new-group to provide the GID of the new group owner.

The file give_ownership.c contains most of the code necessary to implement a give application. You can compile it with the provided Makefile, using the make command.

Take ownership

To take a file ownership, to which we previously signaled the identity of the new UID / GID using the command give, we will use a program take that uses the previously referred extended attributes of a file to check if we where granted the right to take its ownership. That can only happen if the expressed UID equals ours, or the expressed GID equals our main GID. In all other cases, the ownership is not changed.

The file take_ownership.c contains most of the code necessary to implement a take application. You can compile it with the provided Makefile, using the make command.

The Makefile already sets the file’s capabilities to add the CAP_CHOWN capability the the process’ set of effective capabilities. This way, the take_ownership will be able to change the ownership of a file without running as super-user. You can check those capabilities with the command: getcap take_ownership

Experimentation

Create two sessions, one for a user (say, user1), and another for another user (say, user2).

With user1, create a file (say, abc) in a common directory (say, /tmp). With that file, use give to express your will to give the file ownership to root (UID 0, GID 0). Check the file’s extended attributes with the command getfattr:

give_ownership 0:0 /tmp/abc
getfattr /tmp/abc
getfattr -n user.new-owner /tmp/abc
getfattr -n user.new-group /tmp/abc

With user2, try to get the file’s ownership with take. Check that it fails, since you are not the target for the ownership transfer.

ls -la /tmp/abc

With user1 again, use give to express your will to give the file ownership to user2 UID and GID.

give_ownership user2_uid:user2_gid /tmp/abc
getfattr /tmp/abc
getfattr -n user.new-owner /tmp/abc
getfattr -n user.new-group /tmp/abc

With user2, try to get the file’s ownership with take. Check that it succeeds, since you are now the target for the ownership transfer: ls -la /tmp/abc.

Observe now the extended attributes of the file manipulated. Check they were gone.

Try this sequence of commands using only only a UID or a GID, or using a UID / GID combination that does not belong to the same user. Check what happens to the file which ownership changes and try to explain what happens from the code of the programs provided.

Previous
Next