summaryrefslogtreecommitdiff
path: root/examples/timing.c
diff options
context:
space:
mode:
authorMartin Storsjö <martin@martin.st>2013-03-25 12:25:14 +0200
committerNiels Möller <nisse@lysator.liu.se>2013-03-25 15:10:14 +0100
commit8051068be7058e6347fa84c48188e14dd82d1faa (patch)
treed4160e752911644a80b0ba49f8ba5aa26e5708c4 /examples/timing.c
parenta3376b3ad15c8a0972671fb2ea570b9016659e7b (diff)
downloadnettle-8051068be7058e6347fa84c48188e14dd82d1faa.tar.gz
Factorize timing functions to a separate file
This avoids unconditionally using clock_gettime in {ecc,hogweed}-benchmark, falling back to clock() in these as well. This makes building succeed on e.g. OS X.
Diffstat (limited to 'examples/timing.c')
-rw-r--r--examples/timing.c110
1 files changed, 110 insertions, 0 deletions
diff --git a/examples/timing.c b/examples/timing.c
new file mode 100644
index 00000000..108399ad
--- /dev/null
+++ b/examples/timing.c
@@ -0,0 +1,110 @@
+/* timing.c */
+
+/* nettle, low-level cryptographics library
+ *
+ * Copyright (C) 2013 Niels Möller
+ *
+ * The nettle library is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU Lesser General Public License as published by
+ * the Free Software Foundation; either version 2.1 of the License, or (at your
+ * option) any later version.
+ *
+ * The nettle library is distributed in the hope that it will be useful, but
+ * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY
+ * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public
+ * License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with the nettle library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
+ * MA 02111-1301, USA.
+ */
+
+#if HAVE_CONFIG_H
+# include "config.h"
+#endif
+
+#include "timing.h"
+
+#include <errno.h>
+#include <stdarg.h>
+#include <stdio.h>
+#include <stdlib.h>
+#include <string.h>
+#include <time.h>
+
+#if HAVE_CLOCK_GETTIME && defined CLOCK_PROCESS_CPUTIME_ID
+#define TRY_CLOCK_GETTIME 1
+struct timespec cgt_start;
+
+static void NORETURN PRINTF_STYLE(1,2)
+die(const char *format, ...)
+{
+ va_list args;
+ va_start(args, format);
+ vfprintf(stderr, format, args);
+ va_end(args);
+
+ exit(EXIT_FAILURE);
+}
+
+static int
+cgt_works_p(void)
+{
+ struct timespec now;
+ return clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &now) == 0;
+}
+
+static void
+cgt_time_start(void)
+{
+ if (clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &cgt_start) < 0)
+ die("clock_gettime failed: %s\n", strerror(errno));
+}
+
+static double
+cgt_time_end(void)
+{
+ struct timespec end;
+ if (clock_gettime(CLOCK_PROCESS_CPUTIME_ID, &end) < 0)
+ die("clock_gettime failed: %s\n", strerror(errno));
+
+ return end.tv_sec - cgt_start.tv_sec
+ + 1e-9 * (end.tv_nsec - cgt_start.tv_nsec);
+}
+#endif /* !HAVE_CLOCK_GETTIME */
+
+static clock_t clock_start;
+
+static void
+clock_time_start(void)
+{
+ clock_start = clock();
+}
+
+static double
+clock_time_end(void)
+{
+ return (double) (clock() - (clock_start)) / CLOCKS_PER_SEC;
+}
+
+void (*time_start)(void) = clock_time_start;
+double (*time_end)(void) = clock_time_end;
+
+void time_init(void)
+{
+ /* Choose timing function */
+#if TRY_CLOCK_GETTIME
+ if (cgt_works_p())
+ {
+ time_start = cgt_time_start;
+ time_end = cgt_time_end;
+ }
+ else
+ {
+ fprintf(stderr, "clock_gettime not working, falling back to clock\n");
+ time_start = clock_time_start;
+ time_end = clock_time_end;
+ }
+#endif
+}