LCOV - code coverage report
Current view: top level - drivers/input - input-poller.c (source / functions) Hit Total Coverage
Test: coverage.info Lines: 0 82 0.0 %
Date: 2023-08-24 13:40:31 Functions: 0 15 0.0 %

          Line data    Source code
       1             : // SPDX-License-Identifier: GPL-2.0-only
       2             : /*
       3             :  * Support for polling mode for input devices.
       4             :  */
       5             : 
       6             : #include <linux/device.h>
       7             : #include <linux/input.h>
       8             : #include <linux/jiffies.h>
       9             : #include <linux/mutex.h>
      10             : #include <linux/slab.h>
      11             : #include <linux/types.h>
      12             : #include <linux/workqueue.h>
      13             : #include "input-poller.h"
      14             : 
      15             : struct input_dev_poller {
      16             :         void (*poll)(struct input_dev *dev);
      17             : 
      18             :         unsigned int poll_interval; /* msec */
      19             :         unsigned int poll_interval_max; /* msec */
      20             :         unsigned int poll_interval_min; /* msec */
      21             : 
      22             :         struct input_dev *input;
      23             :         struct delayed_work work;
      24             : };
      25             : 
      26           0 : static void input_dev_poller_queue_work(struct input_dev_poller *poller)
      27             : {
      28             :         unsigned long delay;
      29             : 
      30           0 :         delay = msecs_to_jiffies(poller->poll_interval);
      31           0 :         if (delay >= HZ)
      32           0 :                 delay = round_jiffies_relative(delay);
      33             : 
      34           0 :         queue_delayed_work(system_freezable_wq, &poller->work, delay);
      35           0 : }
      36             : 
      37           0 : static void input_dev_poller_work(struct work_struct *work)
      38             : {
      39           0 :         struct input_dev_poller *poller =
      40           0 :                 container_of(work, struct input_dev_poller, work.work);
      41             : 
      42           0 :         poller->poll(poller->input);
      43           0 :         input_dev_poller_queue_work(poller);
      44           0 : }
      45             : 
      46           0 : void input_dev_poller_finalize(struct input_dev_poller *poller)
      47             : {
      48           0 :         if (!poller->poll_interval)
      49           0 :                 poller->poll_interval = 500;
      50           0 :         if (!poller->poll_interval_max)
      51           0 :                 poller->poll_interval_max = poller->poll_interval;
      52           0 : }
      53             : 
      54           0 : void input_dev_poller_start(struct input_dev_poller *poller)
      55             : {
      56             :         /* Only start polling if polling is enabled */
      57           0 :         if (poller->poll_interval > 0) {
      58           0 :                 poller->poll(poller->input);
      59           0 :                 input_dev_poller_queue_work(poller);
      60             :         }
      61           0 : }
      62             : 
      63           0 : void input_dev_poller_stop(struct input_dev_poller *poller)
      64             : {
      65           0 :         cancel_delayed_work_sync(&poller->work);
      66           0 : }
      67             : 
      68           0 : int input_setup_polling(struct input_dev *dev,
      69             :                         void (*poll_fn)(struct input_dev *dev))
      70             : {
      71             :         struct input_dev_poller *poller;
      72             : 
      73           0 :         poller = kzalloc(sizeof(*poller), GFP_KERNEL);
      74           0 :         if (!poller) {
      75             :                 /*
      76             :                  * We want to show message even though kzalloc() may have
      77             :                  * printed backtrace as knowing what instance of input
      78             :                  * device we were dealing with is helpful.
      79             :                  */
      80           0 :                 dev_err(dev->dev.parent ?: &dev->dev,
      81             :                         "%s: unable to allocate poller structure\n", __func__);
      82           0 :                 return -ENOMEM;
      83             :         }
      84             : 
      85           0 :         INIT_DELAYED_WORK(&poller->work, input_dev_poller_work);
      86           0 :         poller->input = dev;
      87           0 :         poller->poll = poll_fn;
      88             : 
      89           0 :         dev->poller = poller;
      90           0 :         return 0;
      91             : }
      92             : EXPORT_SYMBOL(input_setup_polling);
      93             : 
      94             : static bool input_dev_ensure_poller(struct input_dev *dev)
      95             : {
      96           0 :         if (!dev->poller) {
      97           0 :                 dev_err(dev->dev.parent ?: &dev->dev,
      98             :                         "poller structure has not been set up\n");
      99             :                 return false;
     100             :         }
     101             : 
     102             :         return true;
     103             : }
     104             : 
     105           0 : void input_set_poll_interval(struct input_dev *dev, unsigned int interval)
     106             : {
     107           0 :         if (input_dev_ensure_poller(dev))
     108           0 :                 dev->poller->poll_interval = interval;
     109           0 : }
     110             : EXPORT_SYMBOL(input_set_poll_interval);
     111             : 
     112           0 : void input_set_min_poll_interval(struct input_dev *dev, unsigned int interval)
     113             : {
     114           0 :         if (input_dev_ensure_poller(dev))
     115           0 :                 dev->poller->poll_interval_min = interval;
     116           0 : }
     117             : EXPORT_SYMBOL(input_set_min_poll_interval);
     118             : 
     119           0 : void input_set_max_poll_interval(struct input_dev *dev, unsigned int interval)
     120             : {
     121           0 :         if (input_dev_ensure_poller(dev))
     122           0 :                 dev->poller->poll_interval_max = interval;
     123           0 : }
     124             : EXPORT_SYMBOL(input_set_max_poll_interval);
     125             : 
     126           0 : int input_get_poll_interval(struct input_dev *dev)
     127             : {
     128           0 :         if (!dev->poller)
     129             :                 return -EINVAL;
     130             : 
     131           0 :         return dev->poller->poll_interval;
     132             : }
     133             : EXPORT_SYMBOL(input_get_poll_interval);
     134             : 
     135             : /* SYSFS interface */
     136             : 
     137           0 : static ssize_t input_dev_get_poll_interval(struct device *dev,
     138             :                                            struct device_attribute *attr,
     139             :                                            char *buf)
     140             : {
     141           0 :         struct input_dev *input = to_input_dev(dev);
     142             : 
     143           0 :         return sprintf(buf, "%d\n", input->poller->poll_interval);
     144             : }
     145             : 
     146           0 : static ssize_t input_dev_set_poll_interval(struct device *dev,
     147             :                                            struct device_attribute *attr,
     148             :                                            const char *buf, size_t count)
     149             : {
     150           0 :         struct input_dev *input = to_input_dev(dev);
     151           0 :         struct input_dev_poller *poller = input->poller;
     152             :         unsigned int interval;
     153             :         int err;
     154             : 
     155           0 :         err = kstrtouint(buf, 0, &interval);
     156           0 :         if (err)
     157           0 :                 return err;
     158             : 
     159           0 :         if (interval < poller->poll_interval_min)
     160             :                 return -EINVAL;
     161             : 
     162           0 :         if (interval > poller->poll_interval_max)
     163             :                 return -EINVAL;
     164             : 
     165           0 :         mutex_lock(&input->mutex);
     166             : 
     167           0 :         poller->poll_interval = interval;
     168             : 
     169           0 :         if (input_device_enabled(input)) {
     170           0 :                 cancel_delayed_work_sync(&poller->work);
     171           0 :                 if (poller->poll_interval > 0)
     172           0 :                         input_dev_poller_queue_work(poller);
     173             :         }
     174             : 
     175           0 :         mutex_unlock(&input->mutex);
     176             : 
     177           0 :         return count;
     178             : }
     179             : 
     180             : static DEVICE_ATTR(poll, 0644,
     181             :                    input_dev_get_poll_interval, input_dev_set_poll_interval);
     182             : 
     183           0 : static ssize_t input_dev_get_poll_max(struct device *dev,
     184             :                                       struct device_attribute *attr, char *buf)
     185             : {
     186           0 :         struct input_dev *input = to_input_dev(dev);
     187             : 
     188           0 :         return sprintf(buf, "%d\n", input->poller->poll_interval_max);
     189             : }
     190             : 
     191             : static DEVICE_ATTR(max, 0444, input_dev_get_poll_max, NULL);
     192             : 
     193           0 : static ssize_t input_dev_get_poll_min(struct device *dev,
     194             :                                      struct device_attribute *attr, char *buf)
     195             : {
     196           0 :         struct input_dev *input = to_input_dev(dev);
     197             : 
     198           0 :         return sprintf(buf, "%d\n", input->poller->poll_interval_min);
     199             : }
     200             : 
     201             : static DEVICE_ATTR(min, 0444, input_dev_get_poll_min, NULL);
     202             : 
     203           0 : static umode_t input_poller_attrs_visible(struct kobject *kobj,
     204             :                                           struct attribute *attr, int n)
     205             : {
     206           0 :         struct device *dev = kobj_to_dev(kobj);
     207           0 :         struct input_dev *input = to_input_dev(dev);
     208             : 
     209           0 :         return input->poller ? attr->mode : 0;
     210             : }
     211             : 
     212             : static struct attribute *input_poller_attrs[] = {
     213             :         &dev_attr_poll.attr,
     214             :         &dev_attr_max.attr,
     215             :         &dev_attr_min.attr,
     216             :         NULL
     217             : };
     218             : 
     219             : struct attribute_group input_poller_attribute_group = {
     220             :         .is_visible     = input_poller_attrs_visible,
     221             :         .attrs          = input_poller_attrs,
     222             : };

Generated by: LCOV version 1.14