Back to home page

OSCL-LXR

 
 

    


0001 /* SPDX-License-Identifier: GPL-2.0-or-later */
0002 /*
0003  * posix-clock.h - support for dynamic clock devices
0004  *
0005  * Copyright (C) 2010 OMICRON electronics GmbH
0006  */
0007 #ifndef _LINUX_POSIX_CLOCK_H_
0008 #define _LINUX_POSIX_CLOCK_H_
0009 
0010 #include <linux/cdev.h>
0011 #include <linux/fs.h>
0012 #include <linux/poll.h>
0013 #include <linux/posix-timers.h>
0014 #include <linux/rwsem.h>
0015 
0016 struct posix_clock;
0017 
0018 /**
0019  * struct posix_clock_operations - functional interface to the clock
0020  *
0021  * Every posix clock is represented by a character device. Drivers may
0022  * optionally offer extended capabilities by implementing the
0023  * character device methods. The character device file operations are
0024  * first handled by the clock device layer, then passed on to the
0025  * driver by calling these functions.
0026  *
0027  * @owner:          The clock driver should set to THIS_MODULE
0028  * @clock_adjtime:  Adjust the clock
0029  * @clock_gettime:  Read the current time
0030  * @clock_getres:   Get the clock resolution
0031  * @clock_settime:  Set the current time value
0032  * @open:           Optional character device open method
0033  * @release:        Optional character device release method
0034  * @ioctl:          Optional character device ioctl method
0035  * @read:           Optional character device read method
0036  * @poll:           Optional character device poll method
0037  */
0038 struct posix_clock_operations {
0039     struct module *owner;
0040 
0041     int  (*clock_adjtime)(struct posix_clock *pc, struct __kernel_timex *tx);
0042 
0043     int  (*clock_gettime)(struct posix_clock *pc, struct timespec64 *ts);
0044 
0045     int  (*clock_getres) (struct posix_clock *pc, struct timespec64 *ts);
0046 
0047     int  (*clock_settime)(struct posix_clock *pc,
0048                   const struct timespec64 *ts);
0049 
0050     /*
0051      * Optional character device methods:
0052      */
0053     long    (*ioctl)   (struct posix_clock *pc,
0054                 unsigned int cmd, unsigned long arg);
0055 
0056     int     (*open)    (struct posix_clock *pc, fmode_t f_mode);
0057 
0058     __poll_t (*poll)   (struct posix_clock *pc,
0059                 struct file *file, poll_table *wait);
0060 
0061     int     (*release) (struct posix_clock *pc);
0062 
0063     ssize_t (*read)    (struct posix_clock *pc,
0064                 uint flags, char __user *buf, size_t cnt);
0065 };
0066 
0067 /**
0068  * struct posix_clock - represents a dynamic posix clock
0069  *
0070  * @ops:     Functional interface to the clock
0071  * @cdev:    Character device instance for this clock
0072  * @dev:     Pointer to the clock's device.
0073  * @rwsem:   Protects the 'zombie' field from concurrent access.
0074  * @zombie:  If 'zombie' is true, then the hardware has disappeared.
0075  *
0076  * Drivers should embed their struct posix_clock within a private
0077  * structure, obtaining a reference to it during callbacks using
0078  * container_of().
0079  *
0080  * Drivers should supply an initialized but not exposed struct device
0081  * to posix_clock_register(). It is used to manage lifetime of the
0082  * driver's private structure. It's 'release' field should be set to
0083  * a release function for this private structure.
0084  */
0085 struct posix_clock {
0086     struct posix_clock_operations ops;
0087     struct cdev cdev;
0088     struct device *dev;
0089     struct rw_semaphore rwsem;
0090     bool zombie;
0091 };
0092 
0093 /**
0094  * posix_clock_register() - register a new clock
0095  * @clk:   Pointer to the clock. Caller must provide 'ops' field
0096  * @dev:   Pointer to the initialized device. Caller must provide
0097  *         'release' field
0098  *
0099  * A clock driver calls this function to register itself with the
0100  * clock device subsystem. If 'clk' points to dynamically allocated
0101  * memory, then the caller must provide a 'release' function to free
0102  * that memory.
0103  *
0104  * Returns zero on success, non-zero otherwise.
0105  */
0106 int posix_clock_register(struct posix_clock *clk, struct device *dev);
0107 
0108 /**
0109  * posix_clock_unregister() - unregister a clock
0110  * @clk: Clock instance previously registered via posix_clock_register()
0111  *
0112  * A clock driver calls this function to remove itself from the clock
0113  * device subsystem. The posix_clock itself will remain (in an
0114  * inactive state) until its reference count drops to zero, at which
0115  * point it will be deallocated with its 'release' method.
0116  */
0117 void posix_clock_unregister(struct posix_clock *clk);
0118 
0119 #endif