/* depend: */
/* cflags: */
-/* linker: -lpthread */
+/* linker: mtime.o -lpthread */
#include <assert.h>
//#include <math.h>
#include <sched.h>
#include <stdio.h>
#include <stdlib.h>
+#include <sys/time.h>
#include <unistd.h>
+#include "rdtsc.h"
+
/* constants */
//#define N 32
int nb_threads = 1;
int sched_rt_prio = 50;
+int mode = 0;
/* types */
int usage (int ret)
{
FILE *fd = ret ? stderr : stdout;
- fprintf (fd, "usage: %s [-h] [-n int] [-v]\n", progname);
+ fprintf (fd, "usage: %s [-c] [-h] [-n int] [-r int] [-v]\n", progname);
+ fprintf (fd, " -c: estimate clock\n");
fprintf (fd, " -h: help message\n");
fprintf (fd, " -n: number of thread (%d)\n", nb_threads);
- fprintf (fd, " -n: print version\n");
fprintf (fd, " -r: real-time priority, -1 to desactivate (%d)\n", sched_rt_prio);
+ fprintf (fd, " -v: print version\n");
fprintf (fd, "%s version %s\n", progname, version);
return ret;
generate_matrix (matrix);
double det = determinant (matrix);
printf ("det: %g\n", det);
+ free_matrix (matrix);
}
pthread_exit (NULL);
}
+double estimate_clock (void)
+{
+ int n = 4;
+ int64_t diff_nc = 0;
+ double clock = 0;
+ while ((diff_nc < 1000) && (n < 13)) {
+
+ struct timeval tv1;
+ gettimeofday (&tv1, NULL);
+ //sys_timestamp (&ts1);
+ int64_t nc1 = rdtsc ();
+
+ matrix_t *matrix = alloc_matrix (n++);
+ generate_matrix (matrix);
+ determinant (matrix);
+ free_matrix (matrix);
+
+ struct timeval tv2;
+ gettimeofday (&tv2, NULL);
+ int64_t nc2 = rdtsc ();
+
+ diff_nc = nc2 - nc1;
+ double delta = ((double)tv2.tv_sec + tv2.tv_usec * 1e-6) -
+ ((double)tv1.tv_sec + tv1.tv_usec * 1e-6);
+ clock = diff_nc / delta;
+ }
+
+ return clock;
+}
+
/* main function */
int main (int argc, char *argv[])
}
char c = arg[1];
switch (c) {
+ case 'c':
+ arg = (arg[2]) ? arg + 2 : (--argc > 0) ? *(++argv) : NULL;
+ mode = (arg == NULL) ? 1 : atoi (arg);
+ break;
case 'n':
arg = (arg[2]) ? arg + 2 : (--argc > 0) ? *(++argv) : NULL;
if (arg == NULL) {
/* main process */
- if (nb_threads == 0) {
+ if (mode) {
+ while (mode--) {
+ printf ("Clock: %.0fMHz\n", estimate_clock () / 1e6);
+ }
+ } else if (nb_threads == 0) {
while (1) {
sleep (60);
}
--- /dev/null
+/*
+ File name : rdtsc.h
+ Date of creation : 26/1/2012
+ Version : 1.0
+ Copyright : Soft'n'design
+ Author : Laurent Mazet <mazet@softndesign.org>
+
+ Description : This file contains rdtsc inline function
+
+ History :
+ - initial version
+*/
+
+#ifndef __RDTSC_H__
+#define __RDTSC_H__
+
+#include <stdint.h>
+#include <sys/cdefs.h>
+
+__BEGIN_DECLS
+
+/**
+ Get RDTSC counter
+
+ @return counter
+*/
+#if defined(__i386__)
+static __inline__ int64_t rdtsc (void) {
+ int64_t x;
+ __asm__ volatile ("rdtsc" : "=A" (x));
+ return x;
+}
+#elif defined(__amd64__)
+static __inline__ int64_t rdtsc (void) {
+ int64_t a, d;
+ __asm__ volatile ("rdtsc" : "=a" (a), "=d" (d));
+ return (d << 32) | a;
+}
+#elif defined(__PPC64__)
+static __inline__ int64_t rdtsc (void) {
+ int64_t x;
+ __asm__ volatile ("mfspr %0, 268\n" : "=r" (x));
+ return x;
+}
+#elif defined(__x86_64__)
+static __inline__ int64_t rdtsc (void) {
+ int64_t a, d;
+ __asm__ volatile ("lfence");
+ __asm__ volatile ("rdtsc" : "=a" (a), "=d" (d));
+ return (d << 32) | a;
+}
+#elif defined(__aarch64__)
+static __inline__ int64_t rdtsc (void) {
+ int64_t x;
+ //__asm__ volatile ("isb" : : : "memory");
+ //__asm__ volatile ("mrs %0, cntvct_el0" : "=r" (x) :: "memory");
+ //__asm__ volatile ("isb" : : : "memory");
+ __asm__ volatile ("mrs %0, cntvct_el0" : "=r" (x));
+ return x;
+}
+#elif defined(__arm__)
+static __inline__ int64_t rdtsc (void) {
+ int32_t a, d = 0;
+ __asm__ volatile ("mrrc p15, 1, %0, %1, c14" : "=r"(a), "=r"(d));
+ //__asm__ volatile ("mrc p15, 0, %0, c9, c13, 0" : "=r"(a));
+ return ((int64_t)d << 32) | (int64_t)a;
+}
+#else
+static __inline__ int64_t rdtsc (void) {
+ static int64_t a = 0;
+ return a++;
+}
+#endif
+
+__END_DECLS
+
+#endif /* __RDTSC_H__ */
+
+/* vi:set tabstop=4 expandtab shiftwidth=4: this line set vi mode */