1c87c5fbaSopenharmony_ci/*
2c87c5fbaSopenharmony_ci * coap_time.h -- Clock Handling
3c87c5fbaSopenharmony_ci *
4c87c5fbaSopenharmony_ci * Copyright (C) 2010-2023 Olaf Bergmann <bergmann@tzi.org>
5c87c5fbaSopenharmony_ci *
6c87c5fbaSopenharmony_ci * SPDX-License-Identifier: BSD-2-Clause
7c87c5fbaSopenharmony_ci *
8c87c5fbaSopenharmony_ci * This file is part of the CoAP library libcoap. Please see README for terms
9c87c5fbaSopenharmony_ci * of use.
10c87c5fbaSopenharmony_ci */
11c87c5fbaSopenharmony_ci
12c87c5fbaSopenharmony_ci/**
13c87c5fbaSopenharmony_ci * @file coap_time.h
14c87c5fbaSopenharmony_ci * @brief Clock Handling
15c87c5fbaSopenharmony_ci */
16c87c5fbaSopenharmony_ci
17c87c5fbaSopenharmony_ci#ifndef COAP_TIME_H_
18c87c5fbaSopenharmony_ci#define COAP_TIME_H_
19c87c5fbaSopenharmony_ci
20c87c5fbaSopenharmony_ci/**
21c87c5fbaSopenharmony_ci * @ingroup application_api
22c87c5fbaSopenharmony_ci * @defgroup clock Clock Handling
23c87c5fbaSopenharmony_ci * API for internal clock assess
24c87c5fbaSopenharmony_ci * @{
25c87c5fbaSopenharmony_ci */
26c87c5fbaSopenharmony_ci
27c87c5fbaSopenharmony_ci#if defined(WITH_LWIP)
28c87c5fbaSopenharmony_ci
29c87c5fbaSopenharmony_ci#include <stdint.h>
30c87c5fbaSopenharmony_ci#include <lwip/sys.h>
31c87c5fbaSopenharmony_ci
32c87c5fbaSopenharmony_ci/* lwIP provides ms in sys_now */
33c87c5fbaSopenharmony_ci#define COAP_TICKS_PER_SECOND 1000
34c87c5fbaSopenharmony_ci
35c87c5fbaSopenharmony_citypedef uint32_t coap_tick_t;
36c87c5fbaSopenharmony_citypedef uint32_t coap_time_t;
37c87c5fbaSopenharmony_citypedef int32_t coap_tick_diff_t;
38c87c5fbaSopenharmony_ci
39c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE void
40c87c5fbaSopenharmony_cicoap_ticks_impl(coap_tick_t *t) {
41c87c5fbaSopenharmony_ci  *t = sys_now();
42c87c5fbaSopenharmony_ci}
43c87c5fbaSopenharmony_ci
44c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE void
45c87c5fbaSopenharmony_cicoap_clock_init_impl(void) {
46c87c5fbaSopenharmony_ci}
47c87c5fbaSopenharmony_ci
48c87c5fbaSopenharmony_ci#define coap_clock_init coap_clock_init_impl
49c87c5fbaSopenharmony_ci#define coap_ticks coap_ticks_impl
50c87c5fbaSopenharmony_ci
51c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE coap_time_t
52c87c5fbaSopenharmony_cicoap_ticks_to_rt(coap_tick_t t) {
53c87c5fbaSopenharmony_ci  return t / COAP_TICKS_PER_SECOND;
54c87c5fbaSopenharmony_ci}
55c87c5fbaSopenharmony_ci
56c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE uint64_t
57c87c5fbaSopenharmony_cicoap_ticks_to_rt_us(coap_tick_t t) {
58c87c5fbaSopenharmony_ci  return (uint64_t)t * 1000000 / COAP_TICKS_PER_SECOND;
59c87c5fbaSopenharmony_ci}
60c87c5fbaSopenharmony_ci
61c87c5fbaSopenharmony_ci#elif defined(WITH_CONTIKI)
62c87c5fbaSopenharmony_ci
63c87c5fbaSopenharmony_ci#include "clock.h"
64c87c5fbaSopenharmony_ci
65c87c5fbaSopenharmony_citypedef clock_time_t coap_tick_t;
66c87c5fbaSopenharmony_citypedef clock_time_t coap_time_t;
67c87c5fbaSopenharmony_ci
68c87c5fbaSopenharmony_ci/**
69c87c5fbaSopenharmony_ci * This data type is used to represent the difference between two clock_tick_t
70c87c5fbaSopenharmony_ci * values. This data type must have the same size in memory as coap_tick_t to
71c87c5fbaSopenharmony_ci * allow wrapping.
72c87c5fbaSopenharmony_ci */
73c87c5fbaSopenharmony_citypedef int coap_tick_diff_t;
74c87c5fbaSopenharmony_ci
75c87c5fbaSopenharmony_ci#define COAP_TICKS_PER_SECOND CLOCK_SECOND
76c87c5fbaSopenharmony_ci
77c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE void
78c87c5fbaSopenharmony_cicoap_clock_init(void) {
79c87c5fbaSopenharmony_ci  clock_init();
80c87c5fbaSopenharmony_ci}
81c87c5fbaSopenharmony_ci
82c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE void
83c87c5fbaSopenharmony_cicoap_ticks(coap_tick_t *t) {
84c87c5fbaSopenharmony_ci  *t = clock_time();
85c87c5fbaSopenharmony_ci}
86c87c5fbaSopenharmony_ci
87c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE coap_time_t
88c87c5fbaSopenharmony_cicoap_ticks_to_rt(coap_tick_t t) {
89c87c5fbaSopenharmony_ci  return t / COAP_TICKS_PER_SECOND;
90c87c5fbaSopenharmony_ci}
91c87c5fbaSopenharmony_ci
92c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE uint64_t
93c87c5fbaSopenharmony_cicoap_ticks_to_rt_us(coap_tick_t t) {
94c87c5fbaSopenharmony_ci  return (uint64_t)t * 1000000 / COAP_TICKS_PER_SECOND;
95c87c5fbaSopenharmony_ci}
96c87c5fbaSopenharmony_ci
97c87c5fbaSopenharmony_ci#elif defined(RIOT_VERSION)
98c87c5fbaSopenharmony_ci#include <xtimer.h>
99c87c5fbaSopenharmony_ci
100c87c5fbaSopenharmony_ci#ifdef XTIMER_HZ
101c87c5fbaSopenharmony_ci#define COAP_TICKS_PER_SECOND (XTIMER_HZ)
102c87c5fbaSopenharmony_ci#else /* XTIMER_HZ */
103c87c5fbaSopenharmony_ci#define COAP_TICKS_PER_SECOND (1000000U)
104c87c5fbaSopenharmony_ci#endif /* XTIMER_HZ */
105c87c5fbaSopenharmony_ci
106c87c5fbaSopenharmony_citypedef uint64_t coap_tick_t;
107c87c5fbaSopenharmony_citypedef int64_t coap_tick_diff_t;
108c87c5fbaSopenharmony_citypedef uint32_t coap_time_t;
109c87c5fbaSopenharmony_ci
110c87c5fbaSopenharmony_cistatic inline void
111c87c5fbaSopenharmony_cicoap_clock_init(void) {}
112c87c5fbaSopenharmony_ci
113c87c5fbaSopenharmony_cistatic inline void
114c87c5fbaSopenharmony_cicoap_ticks(coap_tick_t *t) {
115c87c5fbaSopenharmony_ci#ifdef MODULE_ZTIMER64_XTIMER_COMPAT
116c87c5fbaSopenharmony_ci  *t = xtimer_now_usec64();
117c87c5fbaSopenharmony_ci#else /* MODULE_ZTIMER64_XTIMER_COMPAT */
118c87c5fbaSopenharmony_ci  *t = xtimer_now_usec();
119c87c5fbaSopenharmony_ci#endif /* MODULE_ZTIMER64_XTIMER_COMPAT */
120c87c5fbaSopenharmony_ci}
121c87c5fbaSopenharmony_ci
122c87c5fbaSopenharmony_cistatic inline coap_time_t
123c87c5fbaSopenharmony_cicoap_ticks_to_rt(coap_tick_t t) {
124c87c5fbaSopenharmony_ci  return t / 1000000UL;
125c87c5fbaSopenharmony_ci}
126c87c5fbaSopenharmony_ci
127c87c5fbaSopenharmony_cistatic inline uint64_t
128c87c5fbaSopenharmony_cicoap_ticks_to_rt_us(coap_tick_t t) {
129c87c5fbaSopenharmony_ci  return t;
130c87c5fbaSopenharmony_ci}
131c87c5fbaSopenharmony_ci
132c87c5fbaSopenharmony_cistatic inline coap_tick_t
133c87c5fbaSopenharmony_cicoap_ticks_from_rt_us(uint64_t t) {
134c87c5fbaSopenharmony_ci  return t / 1000000UL;
135c87c5fbaSopenharmony_ci}
136c87c5fbaSopenharmony_ci#else /* !WITH_LWIP && !WITH_CONTIKI && !RIOT_VERSION */
137c87c5fbaSopenharmony_ci
138c87c5fbaSopenharmony_ci#include <stdint.h>
139c87c5fbaSopenharmony_ci
140c87c5fbaSopenharmony_ci/**
141c87c5fbaSopenharmony_ci * This data type represents internal timer ticks with COAP_TICKS_PER_SECOND
142c87c5fbaSopenharmony_ci * resolution.
143c87c5fbaSopenharmony_ci */
144c87c5fbaSopenharmony_citypedef uint64_t coap_tick_t;
145c87c5fbaSopenharmony_ci
146c87c5fbaSopenharmony_ci/**
147c87c5fbaSopenharmony_ci * CoAP time in seconds since epoch.
148c87c5fbaSopenharmony_ci */
149c87c5fbaSopenharmony_citypedef time_t coap_time_t;
150c87c5fbaSopenharmony_ci
151c87c5fbaSopenharmony_ci/**
152c87c5fbaSopenharmony_ci * This data type is used to represent the difference between two clock_tick_t
153c87c5fbaSopenharmony_ci * values. This data type must have the same size in memory as coap_tick_t to
154c87c5fbaSopenharmony_ci * allow wrapping.
155c87c5fbaSopenharmony_ci */
156c87c5fbaSopenharmony_citypedef int64_t coap_tick_diff_t;
157c87c5fbaSopenharmony_ci
158c87c5fbaSopenharmony_ci/** Use ms resolution on POSIX systems */
159c87c5fbaSopenharmony_ci#define COAP_TICKS_PER_SECOND ((coap_tick_t)(1000U))
160c87c5fbaSopenharmony_ci
161c87c5fbaSopenharmony_ci/**
162c87c5fbaSopenharmony_ci * Initializes the internal clock.
163c87c5fbaSopenharmony_ci */
164c87c5fbaSopenharmony_civoid coap_clock_init(void);
165c87c5fbaSopenharmony_ci
166c87c5fbaSopenharmony_ci/**
167c87c5fbaSopenharmony_ci * Sets @p t to the internal time with COAP_TICKS_PER_SECOND resolution.
168c87c5fbaSopenharmony_ci */
169c87c5fbaSopenharmony_civoid coap_ticks(coap_tick_t *t);
170c87c5fbaSopenharmony_ci
171c87c5fbaSopenharmony_ci/**
172c87c5fbaSopenharmony_ci * Helper function that converts coap ticks to wallclock time. On POSIX, this
173c87c5fbaSopenharmony_ci * function returns the number of seconds since the epoch. On other systems, it
174c87c5fbaSopenharmony_ci * may be the calculated number of seconds since last reboot or so.
175c87c5fbaSopenharmony_ci *
176c87c5fbaSopenharmony_ci * @param t Internal system ticks.
177c87c5fbaSopenharmony_ci *
178c87c5fbaSopenharmony_ci * @return  The number of seconds that has passed since a specific reference
179c87c5fbaSopenharmony_ci *          point (seconds since epoch on POSIX).
180c87c5fbaSopenharmony_ci */
181c87c5fbaSopenharmony_cicoap_time_t coap_ticks_to_rt(coap_tick_t t);
182c87c5fbaSopenharmony_ci
183c87c5fbaSopenharmony_ci/**
184c87c5fbaSopenharmony_ci* Helper function that converts coap ticks to POSIX wallclock time in us.
185c87c5fbaSopenharmony_ci*
186c87c5fbaSopenharmony_ci* @param t Internal system ticks.
187c87c5fbaSopenharmony_ci*
188c87c5fbaSopenharmony_ci* @return  The number of seconds that has passed since a specific reference
189c87c5fbaSopenharmony_ci*          point (seconds since epoch on POSIX).
190c87c5fbaSopenharmony_ci*/
191c87c5fbaSopenharmony_ciuint64_t coap_ticks_to_rt_us(coap_tick_t t);
192c87c5fbaSopenharmony_ci
193c87c5fbaSopenharmony_ci/**
194c87c5fbaSopenharmony_ci* Helper function that converts POSIX wallclock time in us to coap ticks.
195c87c5fbaSopenharmony_ci*
196c87c5fbaSopenharmony_ci* @param t POSIX time is us
197c87c5fbaSopenharmony_ci*
198c87c5fbaSopenharmony_ci* @return  coap ticks
199c87c5fbaSopenharmony_ci*/
200c87c5fbaSopenharmony_cicoap_tick_t coap_ticks_from_rt_us(uint64_t t);
201c87c5fbaSopenharmony_ci#endif
202c87c5fbaSopenharmony_ci
203c87c5fbaSopenharmony_ci/**
204c87c5fbaSopenharmony_ci * Returns @c 1 if and only if @p a is less than @p b where less is defined on a
205c87c5fbaSopenharmony_ci * signed data type.
206c87c5fbaSopenharmony_ci */
207c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE int
208c87c5fbaSopenharmony_cicoap_time_lt(coap_tick_t a, coap_tick_t b) {
209c87c5fbaSopenharmony_ci  return ((coap_tick_diff_t)(a - b)) < 0;
210c87c5fbaSopenharmony_ci}
211c87c5fbaSopenharmony_ci
212c87c5fbaSopenharmony_ci/**
213c87c5fbaSopenharmony_ci * Returns @c 1 if and only if @p a is less than or equal @p b where less is
214c87c5fbaSopenharmony_ci * defined on a signed data type.
215c87c5fbaSopenharmony_ci */
216c87c5fbaSopenharmony_ciCOAP_STATIC_INLINE int
217c87c5fbaSopenharmony_cicoap_time_le(coap_tick_t a, coap_tick_t b) {
218c87c5fbaSopenharmony_ci  return a == b || coap_time_lt(a,b);
219c87c5fbaSopenharmony_ci}
220c87c5fbaSopenharmony_ci
221c87c5fbaSopenharmony_ci/** @} */
222c87c5fbaSopenharmony_ci
223c87c5fbaSopenharmony_ci#endif /* COAP_TIME_H_ */
224