@@ -20,9 +20,9 @@ extern "C"
20
20
#include "rcutils/time.h"
21
21
22
22
#include <inttypes.h>
23
- #include <stdint.h>
24
23
#include <stdio.h>
25
24
#include <stdlib.h>
25
+ #include <time.h>
26
26
27
27
#include "rcutils/allocator.h"
28
28
#include "rcutils/error_handling.h"
@@ -46,6 +46,61 @@ rcutils_time_point_value_as_nanoseconds_string(
46
46
return RCUTILS_RET_OK ;
47
47
}
48
48
49
+ rcutils_ret_t
50
+ rcutils_time_point_value_as_date_string (
51
+ const rcutils_time_point_value_t * time_point ,
52
+ char * str ,
53
+ size_t str_size )
54
+ {
55
+ RCUTILS_CHECK_ARGUMENT_FOR_NULL (time_point , RCUTILS_RET_INVALID_ARGUMENT );
56
+ RCUTILS_CHECK_ARGUMENT_FOR_NULL (str , RCUTILS_RET_INVALID_ARGUMENT );
57
+ if (0 == str_size ) {
58
+ return RCUTILS_RET_OK ;
59
+ }
60
+ // best to abs it to avoid issues with negative values in C89, see:
61
+ // https://stackoverflow.com/a/3604984/671658
62
+ uint64_t abs_time_point = (uint64_t )llabs (* time_point );
63
+ // break into two parts to avoid floating point error
64
+ uint64_t seconds = abs_time_point / (1000u * 1000u * 1000u );
65
+ uint64_t nanoseconds = abs_time_point % (1000u * 1000u * 1000u );
66
+ // Make sure the buffer is large enough to hold the largest possible uint64_t
67
+ char nanoseconds_str [21 ];
68
+
69
+ if (rcutils_snprintf (nanoseconds_str , sizeof (nanoseconds_str ), "%" PRIu64 , nanoseconds ) < 0 ) {
70
+ RCUTILS_SET_ERROR_MSG ("failed to format time point nanoseconds into string" );
71
+ return RCUTILS_RET_ERROR ;
72
+ }
73
+
74
+ time_t now_t = (time_t )(seconds );
75
+ struct tm ptm = {.tm_year = 0 , .tm_mday = 0 };
76
+ #ifdef _WIN32
77
+ if (localtime_s (& ptm , & now_t ) != 0 ) {
78
+ RCUTILS_SET_ERROR_MSG ("failed to get localtime" );
79
+ return RCUTILS_RET_ERROR ;
80
+ }
81
+ #else
82
+ if (localtime_r (& now_t , & ptm ) == NULL ) {
83
+ RCUTILS_SET_ERROR_MSG ("failed to get localtime" );
84
+ return RCUTILS_RET_ERROR ;
85
+ }
86
+ #endif
87
+
88
+ if (str_size < 32 || strftime (str , 32 , "%Y-%m-%d %H:%M:%S" , & ptm ) == 0 ) {
89
+ RCUTILS_SET_ERROR_MSG ("failed to format time point into string as iso8601_date" );
90
+ return RCUTILS_RET_ERROR ;
91
+ }
92
+ static const int date_end_position = 19 ;
93
+ if (rcutils_snprintf (
94
+ & str [date_end_position ], str_size - date_end_position , ".%.3s" ,
95
+ nanoseconds_str ) < 0 )
96
+ {
97
+ RCUTILS_SET_ERROR_MSG ("failed to format time point into string as date_time_with_ms" );
98
+ return RCUTILS_RET_ERROR ;
99
+ }
100
+
101
+ return RCUTILS_RET_OK ;
102
+ }
103
+
49
104
rcutils_ret_t
50
105
rcutils_time_point_value_as_seconds_string (
51
106
const rcutils_time_point_value_t * time_point ,
0 commit comments