]> git.saurik.com Git - apple/libdispatch.git/blob - src/swift/Time.swift
libdispatch-913.20.5.tar.gz
[apple/libdispatch.git] / src / swift / Time.swift
1 //===----------------------------------------------------------------------===//
2 //
3 // This source file is part of the Swift.org open source project
4 //
5 // Copyright (c) 2014 - 2016 Apple Inc. and the Swift project authors
6 // Licensed under Apache License v2.0 with Runtime Library Exception
7 //
8 // See http://swift.org/LICENSE.txt for license information
9 // See http://swift.org/CONTRIBUTORS.txt for the list of Swift project authors
10 //
11 //===----------------------------------------------------------------------===//
12
13 // dispatch/time.h
14 // DISPATCH_TIME_NOW: ok
15 // DISPATCH_TIME_FOREVER: ok
16
17 import CDispatch
18
19 public struct DispatchTime : Comparable {
20 #if HAVE_MACH
21 private static let timebaseInfo: mach_timebase_info_data_t = {
22 var info = mach_timebase_info_data_t(numer: 1, denom: 1)
23 mach_timebase_info(&info)
24 return info
25 }()
26 #endif
27
28 public let rawValue: dispatch_time_t
29
30 public static func now() -> DispatchTime {
31 let t = CDispatch.dispatch_time(0, 0)
32 return DispatchTime(rawValue: t)
33 }
34
35 public static let distantFuture = DispatchTime(rawValue: ~0)
36
37 fileprivate init(rawValue: dispatch_time_t) {
38 self.rawValue = rawValue
39 }
40
41 /// Creates a `DispatchTime` relative to the system clock that
42 /// ticks since boot.
43 ///
44 /// - Parameters:
45 /// - uptimeNanoseconds: The number of nanoseconds since boot, excluding
46 /// time the system spent asleep
47 /// - Returns: A new `DispatchTime`
48 /// - Discussion: This clock is the same as the value returned by
49 /// `mach_absolute_time` when converted into nanoseconds.
50 /// On some platforms, the nanosecond value is rounded up to a
51 /// multiple of the Mach timebase, using the conversion factors
52 /// returned by `mach_timebase_info()`. The nanosecond equivalent
53 /// of the rounded result can be obtained by reading the
54 /// `uptimeNanoseconds` property.
55 /// Note that `DispatchTime(uptimeNanoseconds: 0)` is
56 /// equivalent to `DispatchTime.now()`, that is, its value
57 /// represents the number of nanoseconds since boot (excluding
58 /// system sleep time), not zero nanoseconds since boot.
59 public init(uptimeNanoseconds: UInt64) {
60 var rawValue = uptimeNanoseconds
61 #if HAVE_MACH
62 if (DispatchTime.timebaseInfo.numer != DispatchTime.timebaseInfo.denom) {
63 rawValue = (rawValue * UInt64(DispatchTime.timebaseInfo.denom)
64 + UInt64(DispatchTime.timebaseInfo.numer - 1)) / UInt64(DispatchTime.timebaseInfo.numer)
65 }
66 #endif
67 self.rawValue = dispatch_time_t(rawValue)
68 }
69
70 public var uptimeNanoseconds: UInt64 {
71 var result = self.rawValue
72 #if HAVE_MACH
73 if (DispatchTime.timebaseInfo.numer != DispatchTime.timebaseInfo.denom) {
74 result = result * UInt64(DispatchTime.timebaseInfo.numer) / UInt64(DispatchTime.timebaseInfo.denom)
75 }
76 #endif
77 return result
78 }
79 }
80
81 public func <(a: DispatchTime, b: DispatchTime) -> Bool {
82 if a.rawValue == ~0 || b.rawValue == ~0 { return false }
83 return a.rawValue < b.rawValue
84 }
85
86 public func ==(a: DispatchTime, b: DispatchTime) -> Bool {
87 return a.rawValue == b.rawValue
88 }
89
90 public struct DispatchWallTime : Comparable {
91 public let rawValue: dispatch_time_t
92
93 public static func now() -> DispatchWallTime {
94 return DispatchWallTime(rawValue: CDispatch.dispatch_walltime(nil, 0))
95 }
96
97 public static let distantFuture = DispatchWallTime(rawValue: ~0)
98
99 fileprivate init(rawValue: dispatch_time_t) {
100 self.rawValue = rawValue
101 }
102
103 public init(timespec: timespec) {
104 var t = timespec
105 self.rawValue = CDispatch.dispatch_walltime(&t, 0)
106 }
107 }
108
109 public func <(a: DispatchWallTime, b: DispatchWallTime) -> Bool {
110 if b.rawValue == ~0 {
111 return a.rawValue != ~0
112 } else if a.rawValue == ~0 {
113 return false
114 }
115 return -Int64(bitPattern: a.rawValue) < -Int64(bitPattern: b.rawValue)
116 }
117
118 public func ==(a: DispatchWallTime, b: DispatchWallTime) -> Bool {
119 return a.rawValue == b.rawValue
120 }
121
122 public enum DispatchTimeInterval {
123 case seconds(Int)
124 case milliseconds(Int)
125 case microseconds(Int)
126 case nanoseconds(Int)
127 @_downgrade_exhaustivity_check
128 case never
129
130 internal var rawValue: Int64 {
131 switch self {
132 case .seconds(let s): return Int64(s) * Int64(NSEC_PER_SEC)
133 case .milliseconds(let ms): return Int64(ms) * Int64(NSEC_PER_MSEC)
134 case .microseconds(let us): return Int64(us) * Int64(NSEC_PER_USEC)
135 case .nanoseconds(let ns): return Int64(ns)
136 case .never: return Int64.max
137 }
138 }
139
140 public static func ==(lhs: DispatchTimeInterval, rhs: DispatchTimeInterval) -> Bool {
141 switch (lhs, rhs) {
142 case (.never, .never): return true
143 case (.never, _): return false
144 case (_, .never): return false
145 default: return lhs.rawValue == rhs.rawValue
146 }
147 }
148 }
149
150 public func +(time: DispatchTime, interval: DispatchTimeInterval) -> DispatchTime {
151 let t = CDispatch.dispatch_time(time.rawValue, interval.rawValue)
152 return DispatchTime(rawValue: t)
153 }
154
155 public func -(time: DispatchTime, interval: DispatchTimeInterval) -> DispatchTime {
156 let t = CDispatch.dispatch_time(time.rawValue, -interval.rawValue)
157 return DispatchTime(rawValue: t)
158 }
159
160 public func +(time: DispatchTime, seconds: Double) -> DispatchTime {
161 let interval = seconds * Double(NSEC_PER_SEC)
162 let t = CDispatch.dispatch_time(time.rawValue,
163 interval.isInfinite || interval.isNaN ? Int64.max : Int64(interval))
164 return DispatchTime(rawValue: t)
165 }
166
167 public func -(time: DispatchTime, seconds: Double) -> DispatchTime {
168 let interval = -seconds * Double(NSEC_PER_SEC)
169 let t = CDispatch.dispatch_time(time.rawValue,
170 interval.isInfinite || interval.isNaN ? Int64.min : Int64(interval))
171 return DispatchTime(rawValue: t)
172 }
173
174 public func +(time: DispatchWallTime, interval: DispatchTimeInterval) -> DispatchWallTime {
175 let t = CDispatch.dispatch_time(time.rawValue, interval.rawValue)
176 return DispatchWallTime(rawValue: t)
177 }
178
179 public func -(time: DispatchWallTime, interval: DispatchTimeInterval) -> DispatchWallTime {
180 let t = CDispatch.dispatch_time(time.rawValue, -interval.rawValue)
181 return DispatchWallTime(rawValue: t)
182 }
183
184 public func +(time: DispatchWallTime, seconds: Double) -> DispatchWallTime {
185 let interval = seconds * Double(NSEC_PER_SEC)
186 let t = CDispatch.dispatch_time(time.rawValue,
187 interval.isInfinite || interval.isNaN ? Int64.max : Int64(interval))
188 return DispatchWallTime(rawValue: t)
189 }
190
191 public func -(time: DispatchWallTime, seconds: Double) -> DispatchWallTime {
192 let interval = -seconds * Double(NSEC_PER_SEC)
193 let t = CDispatch.dispatch_time(time.rawValue,
194 interval.isInfinite || interval.isNaN ? Int64.min : Int64(interval))
195 return DispatchWallTime(rawValue: t)
196 }