7 #include <minix/config.h>
8 #include <minix/const.h>
12 #define CALIBRATE_TICKS(h) ((h)/5)
13 #define MICROHZ 1000000 /* number of micros per second */
14 #define MICROSPERTICK(h) (MICROHZ/(h)) /* number of micros per HZ tick */
19 if((r=tsc_calibrate()) != OK) \
20 panic("calibrate failed: %d", r); \
23 static u32_t calib_tsc
, Hz
= 0;
24 static int calibrated
= 0;
29 u64_t start
, end
, diff
;
36 /* Wait for clock to tick. */
37 while(!t
|| (t
== times(&tms
)))
42 /* Wait for clock to tick CALIBRATE_TICKS times, and time
46 while(times(&tms
) < t
+CALIBRATE_TICKS(Hz
)) ;
49 diff
= sub64(end
, start
);
51 panic("tsc_calibrate: CALIBRATE_TICKS too high for TSC frequency");
52 calib_tsc
= ex64lo(diff
);
54 printf("tsc_calibrate: "
55 "%lu cycles/%d ticks of %d Hz; %lu cycles/s\n",
56 calib_tsc
, CALIBRATE_TICKS(Hz
), Hz
,
57 div64u(mul64u(calib_tsc
, Hz
), CALIBRATE_TICKS(Hz
)));
65 micro_delay(u32_t micros
)
74 /* We have to know when to end the delay. */
75 end
= add64u(now
, div64u(mul64u(calib_tsc
,
76 micros
* Hz
/ CALIBRATE_TICKS(Hz
)), MICROHZ
));
78 /* If we have to wait for at least one HZ tick, use the regular
79 * tickdelay first. Round downwards on purpose, so the average
80 * half-tick we wait short (depending on where in the current tick
81 * we call tickdelay). We can correct for both overhead of tickdelay
82 * itself and the short wait in the busywait later.
84 if(micros
>= MICROSPERTICK(Hz
))
85 tickdelay(micros
*Hz
/MICROHZ
);
87 /* Wait (the rest) of the delay time using busywait. */
88 while(cmp64(now
, end
) < 0)
94 u32_t
tsc_64_to_micros(u64_t tsc
)
96 return tsc_to_micros(ex64lo(tsc
), ex64hi(tsc
));
99 u32_t
tsc_to_micros(u32_t low
, u32_t high
)
108 micros
= (div64u(mul64u(low
, MICROHZ
* CALIBRATE_TICKS(Hz
)),