| FILE(9) | Kernel Developer's Manual | FILE(9) | 
file, closef,
  ffree, FILE_IS_USABLE,
  FILE_USE, FILE_UNUSE,
  FILE_SET_MATURE —
#include <sys/file.h>
int
  
  closef(struct
    file *fp, struct lwp
    *l);
void
  
  ffree(struct
    file *fp);
int
  
  FILE_IS_USABLE(struct
    file *fp);
void
  
  FILE_USE(struct
    file *fp);
void
  
  FILE_UNUSE(struct
    file *fp, struct lwp
    *l);
void
  
  FILE_SET_MATURE(struct
    file *fp);
struct file {
        LIST_ENTRY(file) f_list;        /* list of active files */
        int             f_flag;
        int             f_iflags;       /* internal flags */
        int             f_type;         /* descriptor type */
        u_int           f_count;        /* reference count */
        u_int           f_msgcount;     /* message queue references */
        int             f_usecount;     /* number active users */
        kauth_cred_t    f_cred;         /* creds associated with descriptor */
        struct fileops {
                int (*fo_read)(struct file *fp, off_t *offset,
			struct uio *uio, kauth_cred_t cred, int flags);
                int (*fo_write)(struct file *fp, off_t *offset,
                        struct uio *uio, kauth_cred_t cred, int flags);
                int (*fo_ioctl)(struct file *fp, u_long com, void *data,
			struct lwp *l);
                int (*fo_fcntl)(struct file *fp, u_int com, void *data,
			struct lwp *l);
                int (*fo_poll)(struct file *fp, int events,
			struct lwp *l);
                int (*fo_stat)(struct file *fp, struct stat *sp,
			struct lwp *l);
                int (*fo_close)(struct file *fp, struct lwp *l);
        } *f_ops;
        off_t           f_offset;
        void         *f_data;         /* descriptor data */
};
NetBSD treats file entries in an
    object-oriented fashion after they are created. Each entry specifies the
    object type, f_type, which can have the values
    DTYPE_VNODE, DTYPE_SOCKET,
    DTYPE_PIPE and DTYPE_MISC.
    The file entry also has a pointer to a data structure,
    f_data, that contains information specific to the instance
    of the underlying object. The data structure is opaque to the routines that
    manipulate the file entry. Each entry also contains an array of function
    pointers, f_ops, that translate the generic operations on
    a file descriptor into the specific action associated with its type. A
    reference to the data structure is passed as the first parameter to a
    function that implements a file operation. The operations that must be
    implemented for each descriptor type are read, write, ioctl, fcntl, poll,
    stat, and close. See
    vnfileops(9) for an
    overview of the vnode file operations. All state associated with an instance
    of an object must be stored in that instance's data structure; the
    underlying objects are not permitted to manipulate the file entry
    themselves.
For data files, the file entry points to a vnode(9) structure. Pipes and sockets do not have data blocks allocated on the disk and are handled by the special-device filesystem that calls appropriate drivers to handle I/O for them. For pipes, the file entry points to a system block that is used during data transfer. For sockets, the file entry points to a system block that is used in doing interprocess communications.
The descriptor table of a process (and thus access to the objects to which the descriptors refer) is inherited from its parent, so several different processes may reference the same file entry. Thus, each file entry has a reference count, f_count. Each time a new reference is created, the reference count is incremented. When a descriptor is closed, the reference count is decremented. When the reference count drops to zero, the file entry is freed.
Some file descriptor semantics can be altered through the flags argument to the open(2) system call. These flags are recorded in f_flags member of the file entry. For example, the flags record whether the descriptor is open for reading, writing, or both reading and writing. The following flags and their corresponding open(2) flags are:
O_APPENDO_ASYNCO_SYNCO_NONBLOCKO_NONBLOCKO_NONBLOCKO_SYNCO_DSYNCO_RSYNCO_ALT_IOSome additional state-specific flags are recorded in the f_iflags member. Valid values include:
FIF_WANTCLOSEFIF_LARVALThe read(2) and write(2) system calls do not take an offset in the file as an argument. Instead, each read or write updates the current file offset, f_offset in the file according to the number of bytes transferred. Since more than one process may open the same file and each needs its own offset in the file, the offset cannot be stored in the per-object data structure.
closef(fp,
    l)closef() function
      release all locks on the file owned by lwp l,
      decrements the reference count on the file entry, and invokes
      ffree() to free the file entry.ffree(struct file *fp)FILE_IS_USABLE(fp)FIF_WANTCLOSE flag nor the
      FIF_LARVAL flag is set in
      f_iflags.FILE_USE(fp)FILE_UNUSE(fp,
    l)FIF_WANTCLOSE flag is set in
      f_iflags, the file entry is freed.FILE_SET_MATURE(fp)FIF_LARVAL flag in
    f_iflags.| May 17, 2009 | NetBSD 9.4 |