arm64: dts: msm8996: add support blsp2_uart2
[deliverable/linux.git] / arch / um / os-Linux / time.c
CommitLineData
cff65c4f 1/*
2eb5f31b
AI
2 * Copyright (C) 2015 Anton Ivanov (aivanov@{brocade.com,kot-begemot.co.uk})
3 * Copyright (C) 2015 Thomas Meyer (thomas@m3y3r.de)
4 * Copyright (C) 2012-2014 Cisco Systems
4c9e1385 5 * Copyright (C) 2000 - 2007 Jeff Dike (jdike{addtoit,linux.intel}.com)
cff65c4f
GS
6 * Licensed under the GPL
7 */
8
4c9e1385
JD
9#include <stddef.h>
10#include <errno.h>
11#include <signal.h>
cff65c4f 12#include <time.h>
1da177e4 13#include <sys/time.h>
37185b33
AV
14#include <kern_util.h>
15#include <os.h>
2eb5f31b
AI
16#include <string.h>
17#include <timer-internal.h>
cff65c4f 18
2eb5f31b 19static timer_t event_high_res_timer = 0;
537ae946 20
2eb5f31b
AI
21static inline long long timeval_to_ns(const struct timeval *tv)
22{
23 return ((long long) tv->tv_sec * UM_NSEC_PER_SEC) +
24 tv->tv_usec * UM_NSEC_PER_USEC;
cff65c4f
GS
25}
26
2eb5f31b 27static inline long long timespec_to_ns(const struct timespec *ts)
d2753a6d 28{
2eb5f31b
AI
29 return ((long long) ts->tv_sec * UM_NSEC_PER_SEC) +
30 ts->tv_nsec;
31}
d2753a6d 32
2eb5f31b
AI
33long long os_persistent_clock_emulation (void) {
34 struct timespec realtime_tp;
d2753a6d 35
2eb5f31b
AI
36 clock_gettime(CLOCK_REALTIME, &realtime_tp);
37 return timespec_to_ns(&realtime_tp);
d2753a6d
JD
38}
39
5f734614 40/**
2eb5f31b 41 * os_timer_create() - create an new posix (interval) timer
5f734614 42 */
2eb5f31b
AI
43int os_timer_create(void* timer) {
44
45 timer_t* t = timer;
46
47 if(t == NULL) {
48 t = &event_high_res_timer;
49 }
50
51 if (timer_create(
52 CLOCK_MONOTONIC,
53 NULL,
54 t) == -1) {
55 return -1;
56 }
57 return 0;
5f734614
JD
58}
59
2eb5f31b 60int os_timer_set_interval(void* timer, void* i)
cff65c4f 61{
2eb5f31b
AI
62 struct itimerspec its;
63 unsigned long long nsec;
64 timer_t* t = timer;
65 struct itimerspec* its_in = i;
4c9e1385 66
2eb5f31b
AI
67 if(t == NULL) {
68 t = &event_high_res_timer;
69 }
181bde80 70
2eb5f31b 71 nsec = UM_NSEC_PER_SEC / UM_HZ;
fe2cc53e 72
2eb5f31b
AI
73 if(its_in != NULL) {
74 its.it_value.tv_sec = its_in->it_value.tv_sec;
75 its.it_value.tv_nsec = its_in->it_value.tv_nsec;
76 } else {
77 its.it_value.tv_sec = 0;
78 its.it_value.tv_nsec = nsec;
79 }
1da177e4 80
2eb5f31b
AI
81 its.it_interval.tv_sec = 0;
82 its.it_interval.tv_nsec = nsec;
1da177e4 83
2eb5f31b
AI
84 if(timer_settime(*t, 0, &its, NULL) == -1) {
85 return -errno;
86 }
1da177e4 87
0a765329 88 return 0;
364e3a3d 89}
fe2cc53e 90
2eb5f31b
AI
91/**
92 * os_timer_remain() - returns the remaining nano seconds of the given interval
93 * timer
94 * Because this is the remaining time of an interval timer, which correspondends
95 * to HZ, this value can never be bigger than one second. Just
96 * the nanosecond part of the timer is returned.
97 * The returned time is relative to the start time of the interval timer.
98 * Return an negative value in an error case.
99 */
100long os_timer_remain(void* timer)
fe2cc53e 101{
2eb5f31b
AI
102 struct itimerspec its;
103 timer_t* t = timer;
fe2cc53e 104
2eb5f31b
AI
105 if(t == NULL) {
106 t = &event_high_res_timer;
107 }
fe2cc53e 108
2eb5f31b
AI
109 if(timer_gettime(t, &its) == -1) {
110 return -errno;
111 }
fe2cc53e 112
2eb5f31b
AI
113 return its.it_value.tv_nsec;
114}
fe2cc53e 115
2eb5f31b
AI
116int os_timer_one_shot(int ticks)
117{
118 struct itimerspec its;
119 unsigned long long nsec;
120 unsigned long sec;
06e1e4ff 121
2eb5f31b
AI
122 nsec = (ticks + 1);
123 sec = nsec / UM_NSEC_PER_SEC;
124 nsec = nsec % UM_NSEC_PER_SEC;
fe2cc53e 125
2eb5f31b
AI
126 its.it_value.tv_sec = nsec / UM_NSEC_PER_SEC;
127 its.it_value.tv_nsec = nsec;
fe2cc53e 128
2eb5f31b
AI
129 its.it_interval.tv_sec = 0;
130 its.it_interval.tv_nsec = 0; // we cheat here
fe2cc53e 131
2eb5f31b
AI
132 timer_settime(event_high_res_timer, 0, &its, NULL);
133 return 0;
fe2cc53e
JD
134}
135
2eb5f31b
AI
136/**
137 * os_timer_disable() - disable the posix (interval) timer
138 * Returns the remaining interval timer time in nanoseconds
139 */
140long long os_timer_disable(void)
fe2cc53e 141{
2eb5f31b 142 struct itimerspec its;
fe2cc53e 143
2eb5f31b
AI
144 memset(&its, 0, sizeof(struct itimerspec));
145 timer_settime(event_high_res_timer, 0, &its, &its);
146
147 return its.it_value.tv_sec * UM_NSEC_PER_SEC + its.it_value.tv_nsec;
364e3a3d
JD
148}
149
2eb5f31b 150long long os_vnsecs(void)
364e3a3d 151{
2eb5f31b 152 struct timespec ts;
06e1e4ff 153
2eb5f31b
AI
154 clock_gettime(CLOCK_PROCESS_CPUTIME_ID,&ts);
155 return timespec_to_ns(&ts);
156}
364e3a3d 157
2eb5f31b
AI
158long long os_nsecs(void)
159{
160 struct timespec ts;
364e3a3d 161
2eb5f31b
AI
162 clock_gettime(CLOCK_MONOTONIC,&ts);
163 return timespec_to_ns(&ts);
364e3a3d 164}
364e3a3d 165
2eb5f31b
AI
166/**
167 * os_idle_sleep() - sleep for a given time of nsecs
168 * @nsecs: nanoseconds to sleep
169 */
170void os_idle_sleep(unsigned long long nsecs)
cff65c4f 171{
364e3a3d
JD
172 struct timespec ts;
173
2eb5f31b
AI
174 if (nsecs <= 0) {
175 return;
176 }
fe2cc53e 177
2eb5f31b
AI
178 ts = ((struct timespec) {
179 .tv_sec = nsecs / UM_NSEC_PER_SEC,
180 .tv_nsec = nsecs % UM_NSEC_PER_SEC
181 });
cff65c4f 182
2eb5f31b
AI
183 /*
184 * Relay the signal if clock_nanosleep is interrupted.
185 */
186 if (clock_nanosleep(CLOCK_MONOTONIC, 0, &ts, NULL)) {
fe2cc53e 187 deliver_alarm();
2eb5f31b 188 }
cff65c4f 189}
This page took 0.827331 seconds and 5 git commands to generate.