1 | /* Copyright (c) 2002,2003 CrystalClear Software, Inc. |
2 | * Use, modification and distribution is subject to the |
3 | * Boost Software License, Version 1.0. (See accompanying |
4 | * file LICENSE_1_0.txt or http://www.boost.org/LICENSE_1_0.txt) |
5 | * Author: Jeff Garland |
6 | */ |
7 | |
8 | #include <stdexcept> |
9 | #include "boost/date_time/posix_time/posix_time.hpp" |
10 | #include "boost/date_time/c_local_time_adjustor.hpp" |
11 | #include "../testfrmwk.hpp" |
12 | |
13 | int |
14 | main() |
15 | { |
16 | using namespace boost::posix_time; |
17 | using namespace boost::gregorian; |
18 | |
19 | //These are a compile check / test. They have to be hand inspected |
20 | //b/c they depend on the TZ settings of the machine and hence it is |
21 | //unclear what the results will be |
22 | typedef boost::date_time::c_local_adjustor<ptime> local_adj; |
23 | |
24 | bool btd1e = false; |
25 | bool btd2e = false; |
26 | bool btd3e = false; |
27 | time_duration td1; |
28 | time_duration td2; |
29 | time_duration td3; |
30 | |
31 | try |
32 | { |
33 | ptime t1(date(2002,Jan,1), hours(7)+millisec(5)); |
34 | std::cout << "UTC <--> TZ Setting of Machine -- No DST" << std::endl; |
35 | ptime t2 = local_adj::utc_to_local(t: t1); |
36 | std::cout << t2 << " LOCAL is " |
37 | << t1 << " UTC time " |
38 | << std::endl; |
39 | td1 = t2 - t1; |
40 | std::cout << "A difference of: " << td1 |
41 | << std::endl; |
42 | } |
43 | catch (std::runtime_error & re) |
44 | { |
45 | btd1e = true; |
46 | check(testname: re.what(), testcond: false); |
47 | } |
48 | |
49 | try |
50 | { |
51 | ptime t3(date(2002,May,1), hours(5)+millisec(5)); |
52 | std::cout << "UTC <--> TZ Setting of Machine -- In DST" << std::endl; |
53 | ptime t4 = local_adj::utc_to_local(t: t3); |
54 | std::cout << t4 << " LOCAL is " |
55 | << t3 << " UTC time " |
56 | << std::endl; |
57 | td2 = t4 - t3; |
58 | std::cout << "A difference of: " << td2 |
59 | << std::endl; |
60 | } |
61 | catch (std::runtime_error & re) |
62 | { |
63 | btd2e = true; |
64 | check(testname: re.what(), testcond: false); |
65 | } |
66 | |
67 | try |
68 | { |
69 | ptime t5(date(2040,May,1), hours(5)+millisec(5)); |
70 | std::cout << "UTC <--> TZ Setting of Machine -- In DST" << std::endl; |
71 | ptime t6 = local_adj::utc_to_local(t: t5); |
72 | std::cout << t6 << " LOCAL is " |
73 | << t5 << " UTC time " |
74 | << std::endl; |
75 | td3 = t6 - t5; |
76 | std::cout << "a difference of: " << td3 |
77 | << std::endl; |
78 | } |
79 | catch (std::runtime_error & re) |
80 | { |
81 | btd3e = true; |
82 | check(testname: re.what(), testcond: false); |
83 | } |
84 | catch (std::bad_cast&) |
85 | { |
86 | btd3e = true; |
87 | check(testname: "32-bit time_t overflow detected" , testcond: sizeof(std::time_t) < 8); |
88 | } |
89 | |
90 | // The following tests are unaware of the local time zone, but they |
91 | // should help spot some errors. Manual inspection could still be |
92 | // required. |
93 | |
94 | // Based on http://stackoverflow.com/questions/8131023 |
95 | // All time zones are between -12 and +14 |
96 | if (!btd1e) |
97 | { |
98 | check(testname: "td1 isn't too low" , testcond: td1 >= hours(-12)); |
99 | check(testname: "td1 isn't too high" , testcond: td1 <= hours(14)); |
100 | } |
101 | if (!btd2e) |
102 | { |
103 | check(testname: "td2 isn't too low" , testcond: td2 >= hours(-12)); |
104 | check(testname: "td2 isn't too high" , testcond: td2 <= hours(14)); |
105 | } |
106 | if (!btd3e) |
107 | { |
108 | check(testname: "td3 isn't too low" , testcond: td3 >= hours(-12)); |
109 | check(testname: "td3 isn't too high" , testcond: td3 <= hours(14)); |
110 | } |
111 | |
112 | // Assuming that no one uses DST of more than an hour. |
113 | if (!btd1e && !btd2e) |
114 | { |
115 | check(testname: "td1 and td2 are close" , |
116 | testcond: td1 - td2 <= hours(1) && td2 - td1 <= hours(1)); |
117 | } |
118 | if (!btd2e && !btd3e) |
119 | { |
120 | check(testname: "td2 and td3 are close" , |
121 | testcond: td2 - td3 <= hours(2) && td3 - td2 <= hours(2)); |
122 | } |
123 | if (!btd1e && !btd3e) |
124 | { |
125 | check(testname: "td1 and td3 are close" , |
126 | testcond: td1 - td3 <= hours(1) && td3 - td1 <= hours(1)); |
127 | } |
128 | |
129 | return printTestStats(); |
130 | } |
131 | |
132 | |