1// SPDX-License-Identifier: GPL-2.0-or-later
2/*
3 * PPS dummy generator
4 *
5 * Copyright (C) 2024 Rodolfo Giometti <giometti@enneenne.com>
6 */
7
8#include <linux/kernel.h>
9#include <linux/module.h>
10#include <linux/init.h>
11#include <linux/time.h>
12#include <linux/timer.h>
13#include <linux/random.h>
14#include <linux/pps_gen_kernel.h>
15
16static struct pps_gen_device *pps_gen;
17static struct timer_list ktimer;
18
19static unsigned int get_random_delay(void)
20{
21 unsigned int delay = get_random_u8() & 0x0f;
22
23 return (delay + 1) * HZ;
24}
25
26/*
27 * The kernel timer
28 */
29
30static void pps_gen_ktimer_event(struct timer_list *unused)
31{
32 pps_gen_event(pps_gen, PPS_GEN_EVENT_MISSEDPULSE, NULL);
33}
34
35/*
36 * PPS Generator methods
37 */
38
39static int pps_gen_dummy_get_time(struct pps_gen_device *pps_gen,
40 struct timespec64 *time)
41{
42 struct system_time_snapshot snap;
43
44 ktime_get_snapshot(systime_snapshot: &snap);
45 *time = ktime_to_timespec64(snap.real);
46
47 return 0;
48}
49
50static int pps_gen_dummy_enable(struct pps_gen_device *pps_gen, bool enable)
51{
52 if (enable)
53 mod_timer(timer: &ktimer, expires: jiffies + get_random_delay());
54 else
55 timer_delete_sync(timer: &ktimer);
56
57 return 0;
58}
59
60/*
61 * The PPS info struct
62 */
63
64static const struct pps_gen_source_info pps_gen_dummy_info = {
65 .use_system_clock = true,
66 .get_time = pps_gen_dummy_get_time,
67 .enable = pps_gen_dummy_enable,
68};
69
70/*
71 * Module staff
72 */
73
74static void __exit pps_gen_dummy_exit(void)
75{
76 timer_delete_sync(timer: &ktimer);
77 pps_gen_unregister_source(pps_gen);
78}
79
80static int __init pps_gen_dummy_init(void)
81{
82 pps_gen = pps_gen_register_source(info: &pps_gen_dummy_info);
83 if (IS_ERR(ptr: pps_gen))
84 return PTR_ERR(ptr: pps_gen);
85
86 timer_setup(&ktimer, pps_gen_ktimer_event, 0);
87
88 return 0;
89}
90
91module_init(pps_gen_dummy_init);
92module_exit(pps_gen_dummy_exit);
93
94MODULE_AUTHOR("Rodolfo Giometti <giometti@enneenne.com>");
95MODULE_DESCRIPTION("LinuxPPS dummy generator");
96MODULE_LICENSE("GPL");
97

source code of linux/drivers/pps/generators/pps_gen-dummy.c