timers.nim 3.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103
  1. #
  2. #
  3. # Nim's Runtime Library
  4. # (c) Copyright 2012 Andreas Rumpf
  5. #
  6. # See the file "copying.txt", included in this
  7. # distribution, for details about the copyright.
  8. #
  9. ## Timer support for the realtime GC. Based on
  10. ## `<https://github.com/jckarter/clay/blob/master/compiler/src/hirestimer.cpp>`_
  11. type
  12. Ticks = distinct int64
  13. Nanos = int64
  14. {.deprecated: [TTicks: Ticks, TNanos: Nanos].}
  15. when defined(windows):
  16. proc QueryPerformanceCounter(res: var Ticks) {.
  17. importc: "QueryPerformanceCounter", stdcall, dynlib: "kernel32".}
  18. proc QueryPerformanceFrequency(res: var int64) {.
  19. importc: "QueryPerformanceFrequency", stdcall, dynlib: "kernel32".}
  20. proc getTicks(): Ticks {.inline.} =
  21. QueryPerformanceCounter(result)
  22. proc `-`(a, b: Ticks): Nanos =
  23. var frequency: int64
  24. QueryPerformanceFrequency(frequency)
  25. var performanceCounterRate = 1e+9'f64 / float64(frequency)
  26. result = Nanos(float64(a.int64 - b.int64) * performanceCounterRate)
  27. elif defined(macosx):
  28. type
  29. MachTimebaseInfoData {.pure, final,
  30. importc: "mach_timebase_info_data_t",
  31. header: "<mach/mach_time.h>".} = object
  32. numer, denom: int32
  33. {.deprecated: [TMachTimebaseInfoData: MachTimebaseInfoData].}
  34. proc mach_absolute_time(): int64 {.importc, header: "<mach/mach.h>".}
  35. proc mach_timebase_info(info: var MachTimebaseInfoData) {.importc,
  36. header: "<mach/mach_time.h>".}
  37. proc getTicks(): Ticks {.inline.} =
  38. result = Ticks(mach_absolute_time())
  39. var timeBaseInfo: MachTimebaseInfoData
  40. mach_timebase_info(timeBaseInfo)
  41. proc `-`(a, b: Ticks): Nanos =
  42. result = (a.int64 - b.int64) * timeBaseInfo.numer div timeBaseInfo.denom
  43. elif defined(posixRealtime):
  44. type
  45. Clockid {.importc: "clockid_t", header: "<time.h>", final.} = object
  46. TimeSpec {.importc: "struct timespec", header: "<time.h>",
  47. final, pure.} = object ## struct timespec
  48. tv_sec: int ## Seconds.
  49. tv_nsec: int ## Nanoseconds.
  50. {.deprecated: [TClockid: Clockid, TTimeSpec: TimeSpec].}
  51. var
  52. CLOCK_REALTIME {.importc: "CLOCK_REALTIME", header: "<time.h>".}: Clockid
  53. proc clock_gettime(clkId: Clockid, tp: var Timespec) {.
  54. importc: "clock_gettime", header: "<time.h>".}
  55. proc getTicks(): Ticks =
  56. var t: Timespec
  57. clock_gettime(CLOCK_REALTIME, t)
  58. result = Ticks(int64(t.tv_sec) * 1000000000'i64 + int64(t.tv_nsec))
  59. proc `-`(a, b: Ticks): Nanos {.borrow.}
  60. else:
  61. # fallback Posix implementation:
  62. when not declared(Time):
  63. when defined(linux):
  64. type Time = clong
  65. else:
  66. type Time = int
  67. type
  68. Timeval {.importc: "struct timeval", header: "<sys/select.h>",
  69. final, pure.} = object ## struct timeval
  70. tv_sec: Time ## Seconds.
  71. tv_usec: clong ## Microseconds.
  72. {.deprecated: [Ttimeval: Timeval].}
  73. proc posix_gettimeofday(tp: var Timeval, unused: pointer = nil) {.
  74. importc: "gettimeofday", header: "<sys/time.h>".}
  75. proc getTicks(): Ticks =
  76. var t: Timeval
  77. posix_gettimeofday(t)
  78. result = Ticks(int64(t.tv_sec) * 1000_000_000'i64 +
  79. int64(t.tv_usec) * 1000'i64)
  80. proc `-`(a, b: Ticks): Nanos {.borrow.}