Nested attributes in inotify.

Linux inotify does not have anyhow extensible architecture: it is tied to small fixed structure, which carries information about generated event, watcher’s ID (which is aunique number identifying added IO watch for given object) and magic cookie unused by all but rename events where it is used to bind different move events (move-from and move-to events have the same cookie). It is also possible to attach name of the object in question, for example when some file is created or written into, directory watch which contains given file will fire events with appropriate file name. That’s it.

So, basically, you cann not attach PID/TID of the calling process, IO start/size or anything else you would like to transfer to userspace linked to given file or directory.

So, after my initial extension was massively rejected because of ugliness of the design (I remind, that I reused unused by anything bug rename events cookie field to carry PID information, which indeed is ugly, but does not break anything), I decided to implement things using The Right Way.

So, I spent several hours today to cook up following idea of nested attributes in the inotify. Patch uses

inotify_init1()

to show that new event format should be returned when reading from inotify file descriptor.

Attributes are attached to given inotify instance via TIOCSETD ioctl, where ID of the attribute is transferred. If entry with given ID exists, it is removed and -EEXIST is returned.

There is a set of callbacks indexed by ID (currently 4 attributes are supported: pid, tid, io details (start/size of the written block) and name), which are attached to given inotify device. When new event is created, each callback is executed and may queue some data into event structure, based on its internal details. When event is read from the userspace, first its header is transferred (old inotify_event structure) and then all attributes data in the order of its registration via above ioctl. Nested attributes have following structure:

struct inotify_attribute
{
	unsigned int		id;
	unsigned int		size;
	unsigned char		data[0];
};

where size is nuber of attached bytes for given attribute. inotify_event.len contains number of bytes used to store all attached attributes and data.

Attribute callback can check if mask contains its bits and do some steps based on that information, for example io details attribute does not add own data (and header) if event mask does not contain IN_MODIFY bit.

It is possible to infinitely extend number of attributes processed, so we will be no longer limited by inotify API and ABI.

I will cook up userspace example tomorrow and fix possible bugs if find them during testing and would like to get a feedback on idea and implementation, let’s see how many comments I will get on this proposal. Patch contains just 897 lines.