[project @ 1999-08-30 18:19:39 by simonpj]
[ghc-hetmet.git] / ghc / lib / std / CPUTime.lhs
1 %
2 % (c) The GRASP/AQUA Project, Glasgow University, 1995-1997
3 %
4 \section[CPUTime]{Haskell 1.4 CPU Time Library}
5
6 \begin{code}
7 {-# OPTIONS -fno-implicit-prelude -#include "cbits/stgio.h" #-}
8
9 module CPUTime 
10         (
11          getCPUTime,       -- :: IO Integer
12          cpuTimePrecision  -- :: Integer
13         ) where
14
15 #ifdef __HUGS__
16 import PreludeBuiltin
17 #else
18 import PrelBase
19 import PrelArr          ( ByteArray(..), newIntArray, unsafeFreezeByteArray )
20 import PrelMaybe
21 import PrelNum
22 import PrelNumExtra
23 import PrelAddr
24 import PrelIOBase
25 import PrelST
26 #endif
27 import IO               ( ioError )
28 import PrelNum ( Num(..), Integral(..) )        -- To get fromInt/toInt
29 import Ratio
30
31 #ifdef __HUGS__
32 #define cat2(x,y)  x/**/y
33 #define CCALL(fun) cat2(prim_,fun)
34 #define stToIO id
35 #define sizeof_int64 8
36 #else
37 #define CCALL(fun) _ccall_ fun
38 #define const_BUFSIZ ``BUFSIZ''
39 #define primPackString
40 #endif
41
42 \end{code}
43
44 Computation @getCPUTime@ returns the number of picoseconds CPU time
45 used by the current program.  The precision of this result is
46 implementation-dependent.
47
48 The @cpuTimePrecision@ constant is the smallest measurable difference
49 in CPU time that the implementation can record, and is given as an
50 integral number of picoseconds.
51
52 \begin{code}
53 #ifdef __HUGS__
54
55 getCPUTime :: IO Integer
56 getCPUTime = do
57     marr <- primNewByteArray (sizeof_int * 4)
58     ptr  <- CCALL(getCPUTime) marr
59     if (ptr /= nullAddr) then do
60         x0 <- primReadIntArray marr 0
61         x1 <- primReadIntArray marr 1
62         x2 <- primReadIntArray marr 2
63         x3 <- primReadIntArray marr 3
64         return ((fromIntegral x0 * 1000000000 + fromIntegral  x1 + 
65                  fromIntegral x2 * 1000000000 + fromIntegral  x3)
66                * 1000)
67       else
68         ioError (IOError Nothing UnsupportedOperation 
69                          "getCPUTime"
70                          "can't get CPU time")
71
72 #else
73
74 getCPUTime :: IO Integer
75 getCPUTime = 
76     stToIO (newIntArray ((0::Int),3))   >>= \ marr ->
77     stToIO (unsafeFreezeByteArray marr) >>= \ barr@(ByteArray _ frozen#) ->
78     _ccall_ getCPUTime barr             >>= \ ptr ->
79     if (ptr::Addr) /= ``NULL'' then
80         return ((fromIntegral (I# (indexIntArray# frozen# 0#)) * 1000000000 + 
81                  fromIntegral (I# (indexIntArray# frozen# 1#)) + 
82                  fromIntegral (I# (indexIntArray# frozen# 2#)) * 1000000000 + 
83                  fromIntegral (I# (indexIntArray# frozen# 3#))) * 1000)
84     else
85         ioError (IOError Nothing UnsupportedOperation 
86                          "getCPUTime"
87                          "can't get CPU time")
88
89 #endif
90
91 cpuTimePrecision :: Integer
92 cpuTimePrecision = round ((1000000000000::Integer) % 
93                           fromInt (unsafePerformIO (CCALL(clockTicks) )))
94 \end{code}
95
96 \begin{code}
97 #ifdef __HUGS__
98
99 sizeof_int = 4
100
101 foreign import stdcall "libHS_cbits.so" "getCPUTime" prim_getCPUTime :: Bytes -> IO Addr
102 foreign import stdcall "libHS_cbits.so" "clockTicks" prim_clockTicks :: IO Int
103 #endif
104 \end{code}
105
106
107