Add RTEMS Test Framework

Update #3199.
This commit is contained in:
Sebastian Huber
2019-03-27 07:15:55 +01:00
parent 6fe01e4b3d
commit cfcc2cbf7a
15 changed files with 5743 additions and 0 deletions
+12
View File
@@ -1837,6 +1837,18 @@ librtemstest_a_SOURCES += libtest/testbusy.c
librtemstest_a_SOURCES += libtest/testextension.c
librtemstest_a_SOURCES += libtest/testparallel.c
librtemstest_a_SOURCES += libtest/testwrappers.c
librtemstest_a_SOURCES += libtest/t-test.c
librtemstest_a_SOURCES += libtest/t-test-checks.c
librtemstest_a_SOURCES += libtest/t-test-checks-eno.c
librtemstest_a_SOURCES += libtest/t-test-checks-psx.c
librtemstest_a_SOURCES += libtest/t-test-hash-sha256.c
librtemstest_a_SOURCES += libtest/t-test-malloc.c
librtemstest_a_SOURCES += libtest/t-test-rtems.c
librtemstest_a_SOURCES += libtest/t-test-rtems-fds.c
librtemstest_a_SOURCES += libtest/t-test-rtems-heap.c
librtemstest_a_SOURCES += libtest/t-test-rtems-measure.c
librtemstest_a_SOURCES += libtest/t-test-rtems-objs.c
librtemstest_a_SOURCES += libtest/t-test-time.c
project_lib_LIBRARIES += libftpd.a
+1
View File
@@ -17,6 +17,7 @@ include_HEADERS += include/poll.h
include_HEADERS += include/rtems.h
include_HEADERS += include/sha256.h
include_HEADERS += include/sha512.h
include_HEADERS += include/t.h
include_HEADERS += include/xz.h
include_HEADERS += include/zconf.h
include_HEADERS += include/zlib.h
+2377
View File
File diff suppressed because it is too large Load Diff
+145
View File
@@ -0,0 +1,145 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <t.h>
#include <errno.h>
#define T_STRERROR_CASE(eno) case eno: return #eno
const char *T_strerror(int eno)
{
switch (eno) {
case 0:
return "0";
T_STRERROR_CASE(E2BIG);
T_STRERROR_CASE(EACCES);
T_STRERROR_CASE(EADDRINUSE);
T_STRERROR_CASE(EADDRNOTAVAIL);
T_STRERROR_CASE(EAFNOSUPPORT);
T_STRERROR_CASE(EAGAIN);
T_STRERROR_CASE(EALREADY);
T_STRERROR_CASE(EBADF);
T_STRERROR_CASE(EBADMSG);
T_STRERROR_CASE(EBUSY);
T_STRERROR_CASE(ECANCELED);
T_STRERROR_CASE(ECHILD);
T_STRERROR_CASE(ECONNABORTED);
T_STRERROR_CASE(ECONNREFUSED);
T_STRERROR_CASE(ECONNRESET);
T_STRERROR_CASE(EDEADLK);
T_STRERROR_CASE(EDESTADDRREQ);
T_STRERROR_CASE(EDOM);
T_STRERROR_CASE(EDQUOT);
T_STRERROR_CASE(EEXIST);
T_STRERROR_CASE(EFAULT);
T_STRERROR_CASE(EFBIG);
T_STRERROR_CASE(EHOSTDOWN);
T_STRERROR_CASE(EHOSTUNREACH);
T_STRERROR_CASE(EIDRM);
T_STRERROR_CASE(EILSEQ);
T_STRERROR_CASE(EINPROGRESS);
T_STRERROR_CASE(EINTR);
T_STRERROR_CASE(EINVAL);
T_STRERROR_CASE(EIO);
T_STRERROR_CASE(EISCONN);
T_STRERROR_CASE(EISDIR);
T_STRERROR_CASE(ELOOP);
T_STRERROR_CASE(EMFILE);
T_STRERROR_CASE(EMLINK);
T_STRERROR_CASE(EMSGSIZE);
T_STRERROR_CASE(EMULTIHOP);
T_STRERROR_CASE(ENAMETOOLONG);
T_STRERROR_CASE(ENETDOWN);
T_STRERROR_CASE(ENETRESET);
T_STRERROR_CASE(ENETUNREACH);
T_STRERROR_CASE(ENFILE);
T_STRERROR_CASE(ENOBUFS);
#ifdef ENODATA
T_STRERROR_CASE(ENODATA);
#endif
T_STRERROR_CASE(ENODEV);
T_STRERROR_CASE(ENOENT);
T_STRERROR_CASE(ENOEXEC);
T_STRERROR_CASE(ENOLCK);
T_STRERROR_CASE(ENOLINK);
T_STRERROR_CASE(ENOMEM);
T_STRERROR_CASE(ENOMSG);
T_STRERROR_CASE(ENOPROTOOPT);
T_STRERROR_CASE(ENOSPC);
#ifdef ENOSR
T_STRERROR_CASE(ENOSR);
#endif
#ifdef ENOSTR
T_STRERROR_CASE(ENOSTR);
#endif
T_STRERROR_CASE(ENOSYS);
T_STRERROR_CASE(ENOTCONN);
T_STRERROR_CASE(ENOTDIR);
T_STRERROR_CASE(ENOTEMPTY);
T_STRERROR_CASE(ENOTRECOVERABLE);
T_STRERROR_CASE(ENOTSOCK);
#if ENOTSUP != EOPNOTSUPP
T_STRERROR_CASE(ENOTSUP);
#endif
T_STRERROR_CASE(ENOTTY);
T_STRERROR_CASE(ENXIO);
T_STRERROR_CASE(EOPNOTSUPP);
T_STRERROR_CASE(EOVERFLOW);
T_STRERROR_CASE(EOWNERDEAD);
T_STRERROR_CASE(EPERM);
T_STRERROR_CASE(EPFNOSUPPORT);
T_STRERROR_CASE(EPIPE);
T_STRERROR_CASE(EPROTO);
T_STRERROR_CASE(EPROTONOSUPPORT);
T_STRERROR_CASE(EPROTOTYPE);
T_STRERROR_CASE(ERANGE);
T_STRERROR_CASE(EROFS);
T_STRERROR_CASE(ESPIPE);
T_STRERROR_CASE(ESRCH);
T_STRERROR_CASE(ESTALE);
#ifdef ETIME
T_STRERROR_CASE(ETIME);
#endif
T_STRERROR_CASE(ETIMEDOUT);
T_STRERROR_CASE(ETOOMANYREFS);
T_STRERROR_CASE(ETXTBSY);
T_STRERROR_CASE(EXDEV);
default:
return "?";
}
}
void T_check_eno(int a, const T_check_context *t, int e)
{
T_check_true(a == e, t, "%s == %s", T_strerror(a), T_strerror(e));
}
void T_check_eno_success(int a, const T_check_context *t)
{
T_check_eno(a, t, 0);
}
+17
View File
@@ -0,0 +1,17 @@
#include <t.h>
#include <errno.h>
void T_check_psx_error(int a, const T_check_context *t, int eeno)
{
int aeno;
aeno = errno;
T_check_true(a == -1 && aeno == eeno, t, "%i == -1, %s == %s", a,
T_strerror(aeno), T_strerror(eeno));
}
void T_check_psx_success(int a, const T_check_context *t)
{
T_check_true(a == 0, t, "%i == 0, %s", a, T_strerror(errno));
}
+328
View File
@@ -0,0 +1,328 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <t.h>
#include <inttypes.h>
void
T_check_eq_ptr(const void *a, const T_check_context_msg *t, const void *e)
{
T_check_true(a == e, &t->base, "%s", t->msg);
}
void
T_check_ne_ptr(const void *a, const T_check_context_msg *t, const void *e)
{
T_check_true(a != e, &t->base, "%s", t->msg);
}
void
T_check_null(const void *a, const T_check_context_msg *t)
{
T_check_true(a == NULL, &t->base, "%s == NULL", t->msg);
}
void
T_check_not_null(const void *a, const T_check_context_msg *t)
{
T_check_true(a != NULL, &t->base, "%s != NULL", t->msg);
}
void
T_check_eq_mem(const void *a, const T_check_context_msg *t, const void *e,
size_t n)
{
T_check_true(memcmp(a, e, n) == 0, &t->base, "%s", t->msg);
}
void
T_check_ne_mem(const void *a, const T_check_context_msg *t, const void *e,
size_t n)
{
T_check_true(memcmp(a, e, n) != 0, &t->base, "%s", t->msg);
}
void
T_check_eq_str(const char *a, const T_check_context *t, const char *e)
{
T_check_true(strcmp(a, e) == 0, t, "\"%s\" == \"%s\"", a, e);
}
void
T_check_ne_str(const char *a, const T_check_context *t, const char *e)
{
T_check_true(strcmp(a, e) != 0, t, "\"%s\" != \"%s\"", a, e);
}
void
T_check_eq_nstr(const char *a, const T_check_context *t, const char *e, size_t n)
{
T_check_true(strncmp(a, e, n) == 0, t, "\"%.*s\" == \"%.*s\"", (int)n, a,
(int)n, e);
}
void
T_check_ne_nstr(const char *a, const T_check_context *t, const char *e, size_t n)
{
T_check_true(strncmp(a, e, n) != 0, t, "\"%.*s\" != \"%.*s\"", (int)n, a,
(int)n, e);
}
void
T_check_eq_char(char a, const T_check_context *t, char e)
{
T_check_true(a == e, t, "'%c' == '%c'", a, e);
}
void
T_check_ne_char(char a, const T_check_context *t, char e)
{
T_check_true(a != e, t, "'%c' != '%c'", a, e);
}
void
T_check_eq_int(int a, const T_check_context *t, int e)
{
T_check_true(a == e, t, "%i == %i", a, e);
}
void
T_check_ne_int(int a, const T_check_context *t, int e)
{
T_check_true(a != e, t, "%i != %i", a, e);
}
void
T_check_ge_int(int a, const T_check_context *t, int e)
{
T_check_true(a >= e, t, "%i >= %i", a, e);
}
void
T_check_gt_int(int a, const T_check_context *t, int e)
{
T_check_true(a > e, t, "%i > %i", a, e);
}
void
T_check_le_int(int a, const T_check_context *t, int e)
{
T_check_true(a <= e, t, "%i <= %i", a, e);
}
void
T_check_lt_int(int a, const T_check_context *t, int e)
{
T_check_true(a < e, t, "%i < %i", a, e);
}
void
T_check_eq_uint(unsigned int a, const T_check_context *t, unsigned int e)
{
T_check_true(a == e, t, "%u == %u", a, e);
}
void
T_check_ne_uint(unsigned int a, const T_check_context *t, unsigned int e)
{
T_check_true(a != e, t, "%u != %u", a, e);
}
void
T_check_ge_uint(unsigned int a, const T_check_context *t, unsigned int e)
{
T_check_true(a >= e, t, "%u >= %u", a, e);
}
void
T_check_gt_uint(unsigned int a, const T_check_context *t, unsigned int e)
{
T_check_true(a > e, t, "%u > %u", a, e);
}
void
T_check_le_uint(unsigned int a, const T_check_context *t, unsigned int e)
{
T_check_true(a <= e, t, "%u <= %u", a, e);
}
void
T_check_lt_uint(unsigned int a, const T_check_context *t, unsigned int e)
{
T_check_true(a < e, t, "%u < %u", a, e);
}
void
T_check_eq_long(long a, const T_check_context *t, long e)
{
T_check_true(a == e, t, "%li == %li", a, e);
}
void
T_check_ne_long(long a, const T_check_context *t, long e)
{
T_check_true(a != e, t, "%li != %li", a, e);
}
void
T_check_ge_long(long a, const T_check_context *t, long e)
{
T_check_true(a >= e, t, "%li >= %li", a, e);
}
void
T_check_gt_long(long a, const T_check_context *t, long e)
{
T_check_true(a > e, t, "%li > %li", a, e);
}
void
T_check_le_long(long a, const T_check_context *t, long e)
{
T_check_true(a <= e, t, "%li <= %li", a, e);
}
void
T_check_lt_long(long a, const T_check_context *t, long e)
{
T_check_true(a < e, t, "%li < %li", a, e);
}
void
T_check_eq_ulong(unsigned long a, const T_check_context *t, unsigned long e)
{
T_check_true(a == e, t, "%lu == %lu", a, e);
}
void
T_check_ne_ulong(unsigned long a, const T_check_context *t, unsigned long e)
{
T_check_true(a != e, t, "%lu != %lu", a, e);
}
void
T_check_ge_ulong(unsigned long a, const T_check_context *t, unsigned long e)
{
T_check_true(a >= e, t, "%lu >= %lu", a, e);
}
void
T_check_gt_ulong(unsigned long a, const T_check_context *t, unsigned long e)
{
T_check_true(a > e, t, "%lu > %lu", a, e);
}
void
T_check_le_ulong(unsigned long a, const T_check_context *t, unsigned long e)
{
T_check_true(a <= e, t, "%lu <= %lu", a, e);
}
void
T_check_lt_ulong(unsigned long a, const T_check_context *t, unsigned long e)
{
T_check_true(a < e, t, "%lu < %lu", a, e);
}
void
T_check_eq_ll(long long a, const T_check_context *t, long long e)
{
T_check_true(a == e, t, "%lli == %lli", a, e);
}
void
T_check_ne_ll(long long a, const T_check_context *t, long long e)
{
T_check_true(a != e, t, "%lli != %lli", a, e);
}
void
T_check_ge_ll(long long a, const T_check_context *t, long long e)
{
T_check_true(a >= e, t, "%lli >= %lli", a, e);
}
void
T_check_gt_ll(long long a, const T_check_context *t, long long e)
{
T_check_true(a > e, t, "%lli > %lli", a, e);
}
void
T_check_le_ll(long long a, const T_check_context *t, long long e)
{
T_check_true(a <= e, t, "%lli <= %lli", a, e);
}
void
T_check_lt_ll(long long a, const T_check_context *t, long long e)
{
T_check_true(a < e, t, "%lli < %lli", a, e);
}
void
T_check_eq_ull(unsigned long long a, const T_check_context *t,
unsigned long long e)
{
T_check_true(a == e, t, "%llu == %llu", a, e);
}
void
T_check_ne_ull(unsigned long long a, const T_check_context *t,
unsigned long long e)
{
T_check_true(a != e, t, "%llu != %llu", a, e);
}
void
T_check_ge_ull(unsigned long long a, const T_check_context *t,
unsigned long long e)
{
T_check_true(a >= e, t, "%llu >= %llu", a, e);
}
void
T_check_gt_ull(unsigned long long a, const T_check_context *t,
unsigned long long e)
{
T_check_true(a > e, t, "%llu > %llu", a, e);
}
void
T_check_le_ull(unsigned long long a, const T_check_context *t,
unsigned long long e)
{
T_check_true(a <= e, t, "%llu <= %llu", a, e);
}
void
T_check_lt_ull(unsigned long long a, const T_check_context *t,
unsigned long long e)
{
T_check_true(a < e, t, "%llu < %llu", a, e);
}
+100
View File
@@ -0,0 +1,100 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2019 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <t.h>
#if defined(__rtems__)
#include <sha256.h>
#else
#include <openssl/sha.h>
#endif
typedef struct {
SHA256_CTX sha256;
T_putchar putchar;
void *putchar_arg;
} T_report_hash_sha256_context;
static T_report_hash_sha256_context T_report_hash_sha256_instance;
static void
T_report_hash_sha256_putchar(int c, void *arg)
{
T_report_hash_sha256_context *ctx;
char cc;
ctx = arg;
cc = (char)c;
SHA256_Update(&ctx->sha256, &cc, sizeof(cc));
(*ctx->putchar)(c, ctx->putchar_arg);
}
static void
T_report_hash_sha256_initialize(void)
{
T_report_hash_sha256_context *ctx;
ctx = &T_report_hash_sha256_instance;
SHA256_Init(&ctx->sha256);
T_set_putchar(T_report_hash_sha256_putchar, ctx, &ctx->putchar,
&ctx->putchar_arg);
}
static void
T_report_hash_sha256_finalize(void)
{
T_report_hash_sha256_context *ctx;
unsigned char hash[32];
size_t i;
ctx = &T_report_hash_sha256_instance;
SHA256_Final(hash, &ctx->sha256);
T_printf("Y:ReportHash:SHA256:");
for (i = 0; i < 32; ++i) {
T_printf("%02x", hash[i]);
}
T_printf("\n");
}
void
T_report_hash_sha256(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_report_hash_sha256_initialize();
break;
case T_EVENT_RUN_FINALIZE:
T_report_hash_sha256_finalize();
break;
default:
break;
};
}
+112
View File
@@ -0,0 +1,112 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <t.h>
#include <stdlib.h>
#ifdef __BIGGEST_ALIGNMENT__
#define T_BIGGEST_ALIGNMENT __BIGGEST_ALIGNMENT__
#else
#define T_BIGGEST_ALIGNMENT sizeof(long long)
#endif
typedef struct __attribute__((__aligned__(T_BIGGEST_ALIGNMENT))) {
T_destructor base;
void (*destroy)(void *);
} T_malloc_destructor;
static void
T_malloc_destroy(T_destructor *base)
{
T_malloc_destructor *dtor;
dtor = (T_malloc_destructor *)(uintptr_t)base;
if (dtor->destroy != NULL) {
(*dtor->destroy)(dtor + 1);
}
free(dtor);
}
static void *
T_do_malloc(size_t size, void (*destroy)(void *))
{
T_malloc_destructor *dtor;
size_t new_size;
new_size = sizeof(*dtor) + size;
if (new_size <= size) {
return NULL;
}
dtor = malloc(new_size);
if (dtor != NULL) {
dtor->destroy = destroy;
T_add_destructor(&dtor->base, T_malloc_destroy);
++dtor;
}
return dtor;
}
void *
T_malloc(size_t size)
{
return T_do_malloc(size, NULL);
}
void *
T_calloc(size_t nelem, size_t elsize)
{
return T_zalloc(nelem * elsize, NULL);
}
void *
T_zalloc(size_t size, void (*destroy)(void *))
{
void *p;
p = T_do_malloc(size, destroy);
if (p != NULL) {
p = memset(p, 0, size);
}
return p;
}
void
T_free(void *ptr)
{
T_malloc_destructor *dtor;
dtor = ptr;
--dtor;
T_remove_destructor(&dtor->base);
free(dtor);
}
+83
View File
@@ -0,0 +1,83 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <t.h>
#include <rtems/libio_.h>
static int T_open_fds;
static int
T_count_open_fds(void)
{
int free_count;
rtems_libio_t *iop;
free_count = 0;
rtems_libio_lock();
iop = rtems_libio_iop_free_head;
while (iop != NULL) {
++free_count;
iop = iop->data1;
}
rtems_libio_unlock();
return (int)rtems_libio_number_iops - free_count;
}
static void
T_check_open_fds(void)
{
int open_fds;
int delta;
open_fds = T_count_open_fds();
delta = open_fds - T_open_fds;
if (delta != 0) {
T_open_fds = open_fds;
T_check_true(NULL, false, "file descriptor leak (%+i)", delta);
}
}
void
T_check_file_descriptors(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_open_fds = T_count_open_fds();
break;
case T_EVENT_CASE_END:
T_check_open_fds();
break;
default:
break;
};
}
+112
View File
@@ -0,0 +1,112 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <t.h>
#include <rtems/score/heapimpl.h>
#include <rtems/score/wkspace.h>
#include <rtems/malloc.h>
typedef struct {
Heap_Information_block heap_info;
Heap_Information_block workspace_info;
} T_resource_heap_context;
static T_resource_heap_context T_resource_heap_instance;
static void
T_get_heap_info(Heap_Control *heap, Heap_Information_block *info)
{
_Heap_Get_information(heap, info);
memset(&info->Stats, 0, sizeof(info->Stats));
}
static void
T_heap_run_initialize(void)
{
T_resource_heap_context *ctx;
ctx = &T_resource_heap_instance;
T_get_heap_info(&_Workspace_Area, &ctx->workspace_info);
if (!rtems_configuration_get_unified_work_area()) {
T_get_heap_info(RTEMS_Malloc_Heap, &ctx->heap_info);
}
}
static void
T_heap_case_end(void)
{
T_resource_heap_context *ctx;
Heap_Information_block info;
bool ok;
ctx = &T_resource_heap_instance;
T_get_heap_info(&_Workspace_Area, &info);
ok = memcmp(&info, &ctx->workspace_info, sizeof(info)) == 0;
if (!ok) {
const char *where;
if (rtems_configuration_get_unified_work_area()) {
where = "workspace or heap";
} else {
where = "workspace";
}
T_check_true(ok, NULL, "memory leak in %s", where);
memcpy(&ctx->workspace_info, &info, sizeof(info));
}
if (!rtems_configuration_get_unified_work_area()) {
T_get_heap_info(RTEMS_Malloc_Heap, &info);
ok = memcmp(&info, &ctx->heap_info, sizeof(info)) == 0;
if (!ok) {
T_check_true(ok, NULL, "memory leak in heap");
memcpy(&ctx->heap_info, &info, sizeof(info));
}
}
}
void
T_check_heap(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_heap_run_initialize();
break;
case T_EVENT_CASE_END:
T_heap_case_end();
break;
default:
break;
};
}
File diff suppressed because it is too large Load Diff
+447
View File
@@ -0,0 +1,447 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#undef __STRICT_ANSI__
#include <t.h>
#include <inttypes.h>
#include <rtems/score/objectimpl.h>
#include <rtems/score/threadimpl.h>
#include <rtems/posix/keyimpl.h>
static Objects_Maximum
T_objects_count(Objects_APIs api, uint16_t cls)
{
const Objects_Information *information;
Objects_Maximum count;
information = _Objects_Get_information(api, cls);
_RTEMS_Lock_allocator();
if (information != NULL) {
count = _Objects_Active_count(information);
} else {
count = 0;
}
_RTEMS_Unlock_allocator();
return count;
}
static void
T_objects_check(Objects_APIs api, uint16_t cls,
Objects_Maximum *expected, const char *name)
{
Objects_Maximum count;
int32_t delta;
count = T_objects_count(api, cls);
delta = (int32_t)count - (int32_t)*expected;
if (delta != 0) {
*expected = count;
T_check_true(NULL, false, "%s leak (%" PRIi32 ")", name, delta);
}
}
static Objects_Maximum T_barrier_count;
static void
T_rtems_barriers_run_initialize(void)
{
T_barrier_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_BARRIERS);
}
static void
T_rtems_barriers_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_BARRIERS,
&T_barrier_count, "RTEMS barrier");
}
void
T_check_rtems_barriers(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_barriers_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_barriers_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_extension_count;
static void
T_rtems_extensions_run_initialize(void)
{
T_extension_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_EXTENSIONS);
}
static void
T_rtems_extensions_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_EXTENSIONS,
&T_extension_count, "RTEMS extension");
}
void
T_check_rtems_extensions(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_extensions_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_extensions_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_mq_count;
static void
T_rtems_message_queues_run_initialize(void)
{
T_mq_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_MESSAGE_QUEUES);
}
static void
T_rtems_message_queues_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_MESSAGE_QUEUES,
&T_mq_count, "RTEMS message queue");
}
void
T_check_rtems_message_queues(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_message_queues_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_message_queues_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_part_count;
static void
T_rtems_partitions_run_initialize(void)
{
T_part_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_PARTITIONS);
}
static void
T_rtems_partitions_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_PARTITIONS,
&T_part_count, "RTEMS partition");
}
void
T_check_rtems_partitions(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_partitions_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_partitions_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_period_count;
static void
T_rtems_periods_run_initialize(void)
{
T_period_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_PERIODS);
}
static void
T_rtems_periods_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_PERIODS,
&T_period_count, "RTEMS period");
}
void
T_check_rtems_periods(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_periods_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_periods_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_region_count;
static void
T_rtems_regions_run_initialize(void)
{
T_region_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_REGIONS);
}
static void
T_rtems_regions_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_REGIONS,
&T_region_count, "RTEMS region");
}
void
T_check_rtems_regions(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_regions_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_regions_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_sema_count;
static void
T_rtems_semaphores_run_initialize(void)
{
T_sema_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_SEMAPHORES);
}
static void
T_rtems_semaphores_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_SEMAPHORES,
&T_sema_count, "RTEMS semaphore");
}
void
T_check_rtems_semaphores(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_semaphores_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_semaphores_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_task_count;
static void
T_rtems_tasks_run_initialize(void)
{
T_task_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_TASKS);
}
static void
T_rtems_tasks_case_end(void)
{
_RTEMS_Lock_allocator();
_Thread_Kill_zombies();
_RTEMS_Unlock_allocator();
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_TASKS,
&T_task_count, "RTEMS task");
}
void
T_check_rtems_tasks(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_tasks_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_tasks_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_timer_count;
static void
T_rtems_timers_run_initialize(void)
{
T_timer_count = T_objects_count(OBJECTS_CLASSIC_API,
OBJECTS_RTEMS_TIMERS);
}
static void
T_rtems_timers_case_end(void)
{
T_objects_check(OBJECTS_CLASSIC_API, OBJECTS_RTEMS_TIMERS,
&T_timer_count, "RTEMS timer");
}
void
T_check_rtems_timers(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_rtems_timers_run_initialize();
break;
case T_EVENT_CASE_END:
T_rtems_timers_case_end();
break;
default:
break;
};
}
static Objects_Maximum T_posix_key_count;
static ssize_t T_posix_key_value_count;
static POSIX_Keys_Control *
T_get_next_posix_key(Objects_Id *id)
{
return (POSIX_Keys_Control *)
_Objects_Get_next(*id, &_POSIX_Keys_Information, id);
}
static ssize_t
T_get_active_posix_key_value_pairs(void)
{
ssize_t count;
Objects_Id id;
POSIX_Keys_Control *the_key;
count = 0;
id = OBJECTS_ID_INITIAL_INDEX;
while ((the_key = T_get_next_posix_key(&id)) != NULL ) {
count += (ssize_t)
_Chain_Node_count_unprotected(&the_key->Key_value_pairs);
_Objects_Allocator_unlock();
}
return count;
}
static void
T_posix_keys_run_initialize(void)
{
T_posix_key_count = T_objects_count(OBJECTS_POSIX_API,
OBJECTS_POSIX_KEYS);
T_posix_key_value_count = T_get_active_posix_key_value_pairs();
}
static void
T_posix_keys_case_end(void)
{
ssize_t count;
ssize_t delta;
T_objects_check(OBJECTS_POSIX_API, OBJECTS_POSIX_KEYS,
&T_posix_key_count, "POSIX key");
count = T_get_active_posix_key_value_pairs();
delta = count - T_posix_key_value_count;
if (delta != 0) {
T_posix_key_value_count = count;
T_check_true(NULL, false, "POSIX key value pair leak (%zi)", delta);
}
}
void
T_check_posix_keys(T_event event, const char *name)
{
(void)name;
switch (event) {
case T_EVENT_RUN_INITIALIZE:
T_posix_keys_run_initialize();
break;
case T_EVENT_CASE_END:
T_posix_keys_case_end();
break;
default:
break;
};
}
+51
View File
@@ -0,0 +1,51 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <t.h>
#include <rtems.h>
#include <rtems/bspIo.h>
void
T_putchar_default(int c, void *arg)
{
(void)arg;
rtems_putc((char)c);
}
void
T_check_rsc(uint32_t a, const T_check_context *t, uint32_t e)
{
T_check_true(a == e, t, "%s == %s", rtems_status_text(a),
rtems_status_text(e));
}
void
T_check_rsc_success(uint32_t a, const T_check_context *t)
{
T_check_rsc(a, t, RTEMS_SUCCESSFUL);
}
+233
View File
@@ -0,0 +1,233 @@
/*
* SPDX-License-Identifier: BSD-2-Clause
*
* Copyright (C) 2018 embedded brains GmbH
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions
* are met:
* 1. Redistributions of source code must retain the above copyright
* notice, this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#undef __STRICT_ANSI__
#include <t.h>
#include <inttypes.h>
#include <stdatomic.h>
#include <stdio.h>
#include <time.h>
#ifdef __rtems__
#include <rtems/counter.h>
#include <rtems/score/timecounter.h>
#endif
#ifdef __rtems__
static T_time
round_sbt(T_time time)
{
/*
* One 1ns consists of 4.30 fractions of 1/2**32. Round up close to
* the middle. This turns the conversion mapping of struct timespec to
* sbintime_t and back into the identity function.
*/
return time + 2;
}
#endif
const char *
T_time_to_string_ns(T_time time, T_time_string string)
{
uint32_t s;
uint32_t f;
#ifdef __rtems__
time = round_sbt(time);
s = (uint32_t)(time >> 32);
f = (uint32_t)(((uint64_t)1000000000 * (uint32_t)time) >> 32);
#else
s = (uint32_t)(time / 1000000000);
f = (uint32_t)(time % 1000000000);
#endif
(void)T_snprintf(string, sizeof(T_time_string),
"%" PRIu32 ".%09" PRIu32, s, f);
return string;
}
const char *
T_time_to_string_us(T_time time, T_time_string string)
{
uint32_t s;
uint32_t f;
#ifdef __rtems__
time = round_sbt(time);
s = (uint32_t)(time >> 32);
f = (uint32_t)(((uint64_t)1000000 * (uint32_t)time) >> 32);
#else
time /= 1000;
s = (uint32_t)(time / 1000000);
f = (uint32_t)(time % 1000000);
#endif
(void)T_snprintf(string, sizeof(T_time_string),
"%" PRIu32 ".%06" PRIu32, s, f);
return string;
}
const char *
T_time_to_string_ms(T_time time, T_time_string string)
{
uint32_t s;
uint32_t f;
#ifdef __rtems__
time = round_sbt(time);
s = (uint32_t)(time >> 32);
f = (uint32_t)(((uint64_t)1000 * (uint32_t)time) >> 32);
#else
time /= 1000000;
s = (uint32_t)(time / 1000);
f = (uint32_t)(time % 1000);
#endif
(void)T_snprintf(string, sizeof(T_time_string),
"%" PRIu32 ".%03" PRIu32, s, f);
return string;
}
const char *
T_time_to_string_s(T_time time, T_time_string string)
{
uint32_t s;
#ifdef __rtems__
time = round_sbt(time);
s = (uint32_t)(time >> 32);
#else
s = (uint32_t)(time / 1000000000);
#endif
(void)T_snprintf(string, sizeof(T_time_string), "%" PRIu32, s);
return string;
}
const char *
T_ticks_to_string_ns(T_ticks ticks, T_time_string string)
{
return T_time_to_string_ns(T_ticks_to_time(ticks), string);
}
const char *
T_ticks_to_string_us(T_ticks ticks, T_time_string string)
{
return T_time_to_string_us(T_ticks_to_time(ticks), string);
}
const char *
T_ticks_to_string_ms(T_ticks ticks, T_time_string string)
{
return T_time_to_string_ms(T_ticks_to_time(ticks), string);
}
const char *
T_ticks_to_string_s(T_ticks ticks, T_time_string string)
{
return T_time_to_string_s(T_ticks_to_time(ticks), string);
}
uint64_t
T_ticks_to_time(T_ticks ticks)
{
#ifdef __rtems__
return (uint64_t)rtems_counter_ticks_to_sbintime(ticks);
#else
return ticks;
#endif
}
T_ticks
T_time_to_ticks(T_time time)
{
#ifdef __rtems__
return rtems_counter_sbintime_to_ticks((sbintime_t)time);
#else
return time;
#endif
}
T_time
T_seconds_and_nanoseconds_to_time(uint32_t s, uint32_t ns)
{
#ifdef __rtems__
struct timespec ts;
ts.tv_sec = s;
ts.tv_nsec = (long)ns;
return (T_time)tstosbt(ts);
#else
return (T_time)s * (T_time)1000000000 + (T_time)ns;
#endif
}
void
T_time_to_seconds_and_nanoseconds(T_time time, uint32_t *s, uint32_t *ns)
{
#ifdef __rtems__
time = round_sbt(time);
*s = (uint32_t)(time >> 32);
*ns = (uint32_t)(((uint64_t)1000000000 * (uint32_t)time) >> 32);
#else
*s = (uint32_t)(time / 1000000000);
*ns = (uint32_t)(time % 1000000000);
#endif
}
#ifndef __rtems__
T_time
T_now(void)
{
struct timespec tp;
(void)clock_gettime(CLOCK_MONOTONIC, &tp);
return (T_time)tp.tv_sec * (T_time)1000000000 + (T_time)tp.tv_nsec;
}
T_ticks
T_tick(void)
{
return T_now();
}
#endif
static atomic_uint dummy_time;
T_time
T_now_dummy(void)
{
return atomic_fetch_add_explicit(&dummy_time, 1, memory_order_relaxed);
}
T_time
T_now_via_tick(void)
{
return T_ticks_to_time(T_tick());
}
File diff suppressed because it is too large Load Diff