Working with JFS i-nodes

Files in the journaled file system (JFS) are represented internally as index nodes (i-nodes). JFS i-nodes exist in a static form on disk and contain access information for the file, as well as pointers to the real disk addresses of the file's data blocks.

The number of disk i-nodes available to a file system is dependent on the size of the file system, the allocation group size (8 MB by default), and the number of bytes per i-node ratio (4096 by default). These parameters are given to the mkfs command at file system creation. When enough files have been created to use all the available i-nodes, no more files can be created, even if the file system has free space.

To determine the number of available i-nodes, use the df -v command. Disk i-nodes are defined in the /usr/include/jfs/ino.h file.

Disk i-node structure for JFS

Each disk i-node in JFS is a 128-byte structure. The offset of a particular i-node within the i-node list of the file system produces the unique number (i-number) by which the operating system identifies the i-node. A bit map, known as the i-node map, tracks the availability of free disk i-nodes for the file system.

Disk i-nodes include the following information:

Field Contents
i_mode Type of file and access permission mode bits
i_size Size of file in bytes
i_uid Access permissions for the user ID
i_gid Access permissions for the group ID
i_nblocks Number of blocks allocated to the file
i_mtime Last time the file was modified
i_atime Last time the file was accessed
i_ctime Last time the i-node was modified
i_nlink Number of hard links to the file
i_rdaddr[8] Real disk addresses of the data
i_rindirect Real disk address of the indirect block, if any

You cannot change file data without changing the i-node, but it is possible to change the i-node without changing the contents of the file. For example, when permission is changed, the information within the i-node (i_mode) is modified, but the data in the file remains the same.

The i_rdaddr field within the disk i-node contains 8 disk addresses. These addresses point to the first 8 data blocks assigned to the file. The i_rindirect field address points to an indirect block. Indirect blocks are either single indirect or double indirect. Thus, there are three possible geometries of block allocation for a file: direct, indirect, or double indirect.

Disk i-nodes do not contain file or path name information. Directory entries are used to link file names to i-nodes. Any i-node can be linked to many file names by creating additional directory entries with the link or symlink subroutine. To determine the i-node number assigned to a file, use the ls -i command.

The i-nodes that represent files that define devices contain slightly different information from i-nodes for regular files. Files associated with devices are called special files. There are no data block addresses in special device files, but the major and minor device numbers are included in the i_rdev field.

A disk i-node is released when the link count (i_nlink) to the i-node equals 0. Links represent the file names associated with the i-node. When the link count to the disk i-node is 0, all the data blocks associated with the i-node are released to the bit map of free data blocks for the file system. The i-node is then placed on the free i-node map.

JFS In-core i-node structure

When a file is opened, the operating system creates an in-core i-node. The in-core i-node contains a copy of all the fields defined in the disk i-node, plus additional fields for tracking and managing access to the in-core i-node. When a file is opened, the information in the disk i-node is copied into an in-core i-node for easier access. In-core i-nodes are defined in the /usr/include/jfs/inode.h file. Some of the additional information tracked by the in-core i-node is as follows:
  • Status of the in-core i-node, including flags that indicate:
    • An i-node lock
    • A process waiting for the i-node to unlock
    • Changes to the file's i-node information
    • Changes to the file's data
  • Logical device number of the file system that contains the file
  • i-number used to identify the i-node
  • Reference count. When the reference count field equals 0, the in-core i-node is released.

When an in-core i-node is released (for example, with the close subroutine), the in-core i-node reference count is reduced by 1. If this reduction results in the reference count to the in-core i-node becoming 0, the i-node is released from the in-core i-node table, and the contents of the in-core i-node are written to the disk copy of the i-node (if the two versions differ).