#include "utils.h"
#include "defaults.h"
+#include "time.h"
/*
* Return a partial realpath(3) of the path even if the full path does not
}
static
-char *expand_double_slashes_dot_and_dotdot(char *path)
+int expand_double_slashes_dot_and_dotdot(char *path)
{
size_t expanded_path_len, path_len;
const char *curr_char, *path_last_char, *next_slash, *prev_slash;
path_last_char = &path[path_len];
if (path_len == 0) {
- path = NULL;
goto error;
}
}
path[expanded_path_len] = '\0';
-
+ return 0;
error:
- return path;
+ return -1;
}
/*
int ret;
char *absolute_path = NULL;
char *last_token;
- int is_dot, is_dotdot;
+ bool is_dot, is_dotdot;
/* Safety net */
if (path == NULL) {
absolute_path, LTTNG_PATH_MAX);
}
- absolute_path = expand_double_slashes_dot_and_dotdot(absolute_path);
- if (!absolute_path) {
+ ret = expand_double_slashes_dot_and_dotdot(absolute_path);
+ if (ret) {
goto error;
}
end:
return ret;
}
+
+LTTNG_HIDDEN
+int timespec_to_ms(struct timespec ts, unsigned long *ms)
+{
+ unsigned long res, remain_ms;
+
+ if (ts.tv_sec > ULONG_MAX / MSEC_PER_SEC) {
+ errno = EOVERFLOW;
+ return -1; /* multiplication overflow */
+ }
+ res = ts.tv_sec * MSEC_PER_SEC;
+ remain_ms = ULONG_MAX - res;
+ if (ts.tv_nsec / NSEC_PER_MSEC > remain_ms) {
+ errno = EOVERFLOW;
+ return -1; /* addition overflow */
+ }
+ res += ts.tv_nsec / NSEC_PER_MSEC;
+ *ms = res;
+ return 0;
+}
+
+LTTNG_HIDDEN
+struct timespec timespec_abs_diff(struct timespec t1, struct timespec t2)
+{
+ uint64_t ts1 = (uint64_t) t1.tv_sec * (uint64_t) NSEC_PER_SEC +
+ (uint64_t) t1.tv_nsec;
+ uint64_t ts2 = (uint64_t) t2.tv_sec * (uint64_t) NSEC_PER_SEC +
+ (uint64_t) t2.tv_nsec;
+ uint64_t diff = max(ts1, ts2) - min(ts1, ts2);
+ struct timespec res;
+
+ res.tv_sec = diff / (uint64_t) NSEC_PER_SEC;
+ res.tv_nsec = diff % (uint64_t) NSEC_PER_SEC;
+ return res;
+}