Mike Mike - 6 days ago 4x
Linux Question

How much information is actually stored in a file descriptor?

This may sound like an odd question, but when I go and open a file:

int fd;
fd = open("/dev/somedevice", O_RDWR);

What exactly am I getting back? I can see the man page says:

The open() function shall return a file descriptor for the named file that is the lowest file descriptor not currently open for that process

But is that it? Is it just an
or is there data attached to it behind the scenes? The reason I'm asking is I found some code (Linux/C) where we're opening the file from user space:

//User space code:
int fdC;

if ((fdC = open(DEVICE, O_RDWR)) < 0) {
printf("Error opening device %s (%s)\n", DEVICE, strerror(errno));
goto error_exit;
while (!fQuit) {
if ((nRet = read(fdC, &rx_message, 1)) > 0) {

then on the kernel end, the file operations for this module (which supplies the fd) map reads to the

struct file_operations can_fops = {
lseek: NULL,
read: n_read,

Then the file descriptor is used in the
, but it's being accessed to get data:

int n_read(struct file *file, char *buffer, size_t count, loff_t *loff)
data_t * dev;

dev = (data_t*)file->private_data;

So... I figure what's happening here is either:

A) a file descriptor returned from
contains more data than just a descriptive integer value


B)The mapping between a call to "read" in the user space isn't as simple as I'm making it out to be and there's some code missing in this equation.

Any input that might help direct me?


File descriptor is just an int. The kernel uses it as an index to a table containing all the related information, including file position, file ops (kernel functions that provide the read(), write(), mmap() etc. syscalls), and so on.

When you open() a file or device, the kernel creates a new file descriptor entry for your process, and populates the internal data, including the file ops.

When you use read(), write(), mmap(), etc. with a valid file descriptor, the kernel simply looks up the correct in-kernel function to call based on the file ops in the file descriptor table it has (and which the file descriptor indexes). It really is that simple.