1ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/*
2ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru ****************************************************************************
3ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Copyright (c) 1997-2007, International Business Machines Corporation and *
4ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * others. All Rights Reserved.                                             *
5ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru ****************************************************************************
6ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */
7ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
8ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include "unicode/utypes.h"
9ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
10ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#if !UCONFIG_NO_FORMATTING
11ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
12ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include "unicode/utmscale.h"
13ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include "unicode/ucal.h"
14ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
15ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include "cintltst.h"
16ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
17ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include <stdlib.h>
18ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#include <time.h>
19ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
20ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#define LENGTHOF(array) (int32_t)(sizeof(array)/sizeof((array)[0]))
21ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
22ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#define LOOP_COUNT 10000
23ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
24ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestAPI(void);
25ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestData(void);
26ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestMonkey(void);
27ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestDotNet(void);
28ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
29ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruvoid addUtmsTest(TestNode** root);
30ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
31ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queruvoid addUtmsTest(TestNode** root)
32ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
33ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    addTest(root, &TestAPI, "tsformat/utmstest/TestAPI");
34ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    addTest(root, &TestData, "tsformat/utmstest/TestData");
35ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    addTest(root, &TestMonkey, "tsformat/utmstest/TestMonkey");
36ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    addTest(root, &TestDotNet, "tsformat/utmstest/TestDotNet");
37ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
38ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
39ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/**
40ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Return a random int64_t where U_INT64_MIN <= ran <= U_INT64_MAX.
41ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */
42ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic uint64_t randomInt64(void)
43ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
44ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t ran = 0;
45ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t i;
46ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    static UBool initialized = FALSE;
47ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
48ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (!initialized) {
49ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        srand((unsigned)time(NULL));
50ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        initialized = TRUE;
51ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
52ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
53ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    /* Assume rand has at least 12 bits of precision */
54ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for (i = 0; i < sizeof(ran); i += 1) {
55ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        ((char*)&ran)[i] = (char)((rand() & 0x0FF0) >> 4);
56ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
57ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
58ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    return ran;
59ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
60ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
61ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic int64_t ranInt;
62ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic int64_t ranMin;
63ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic int64_t ranMax;
64ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
65ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void initRandom(int64_t min, int64_t max)
66ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
67ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    uint64_t interval = max - min;
68ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
69ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    ranMin = min;
70ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    ranMax = max;
71ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    ranInt = 0;
72ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
73ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    /* Verify that we don't have a huge interval. */
74ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (interval < (uint64_t)U_INT64_MAX) {
75ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        ranInt = interval;
76ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
77ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
78ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
79ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic int64_t randomInRange(void)
80ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
81ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t value;
82ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
83ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (ranInt != 0) {
84ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        value = randomInt64() % ranInt;
85ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
86ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (value < 0) {
87ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            value = -value;
88ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
89ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
90ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        value += ranMin;
91ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    } else {
92ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        do {
93ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            value = randomInt64();
94ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        } while (value < ranMin || value > ranMax);
95ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
96ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
97ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    return value;
98ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
99ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
100ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void roundTripTest(int64_t value, UDateTimeScale scale)
101ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
102ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
103ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t rt = utmscale_toInt64(utmscale_fromInt64(value, scale, &status), scale, &status);
104ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
105ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (rt != value) {
106ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("Round-trip error: time scale = %d, value = %lld, round-trip = %lld.\n", scale, value, rt);
107ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
108ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
109ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
110ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void toLimitTest(int64_t toLimit, int64_t fromLimit, UDateTimeScale scale)
111ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
112ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
113ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t result = utmscale_toInt64(toLimit, scale, &status);
114ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
115ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (result != fromLimit) {
116ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("toLimit failure: scale = %d, toLimit = %lld , utmscale_toInt64(toLimit, scale, &status) = %lld, fromLimit = %lld.\n",
117ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            scale, toLimit, result, fromLimit);
118ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
119ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
120ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
121ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void epochOffsetTest(int64_t epochOffset, int64_t units, UDateTimeScale scale)
122ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
123ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
124ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t universal = 0;
125ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t universalEpoch = epochOffset * units;
126ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t local = utmscale_toInt64(universalEpoch, scale, &status);
127ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
128ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (local != 0) {
129ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("utmscale_toInt64(epochOffset, scale, &status): scale = %d epochOffset = %lld, result = %lld.\n", scale, epochOffset, local);
130ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
131ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
132ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    local = utmscale_toInt64(0, scale, &status);
133ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
134ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (local != -epochOffset) {
135ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("utmscale_toInt64(0, scale): scale = %d, result = %lld.\n", scale, local);
136ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
137ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
138ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    universal = utmscale_fromInt64(-epochOffset, scale, &status);
139ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
140ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (universal != 0) {
141ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("from(-epochOffest, scale): scale = %d, epochOffset = %lld, result = %lld.\n", scale, epochOffset, universal);
142ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
143ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
144ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    universal = utmscale_fromInt64(0, scale, &status);
145ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
146ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (universal != universalEpoch) {
147ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("utmscale_fromInt64(0, scale): scale = %d, result = %lld.\n", scale, universal);
148ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
149ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
150ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
151ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestEpochOffsets(void)
152ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
153ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
154ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t scale;
155ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
156ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for (scale = 0; scale < UDTS_MAX_SCALE; scale += 1) {
157ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t units       = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_UNITS_VALUE, &status);
158ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t epochOffset = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_EPOCH_OFFSET_VALUE, &status);
159ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
160ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        epochOffsetTest(epochOffset, units, (UDateTimeScale)scale);
161ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
162ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
163ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
164ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestFromLimits(void)
165ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
166ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
167ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t scale;
168ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
169ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for (scale = 0; scale < UDTS_MAX_SCALE; scale += 1) {
170ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t fromMin = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MIN_VALUE, &status);
171ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t fromMax = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MAX_VALUE, &status);
172ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
173ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        roundTripTest(fromMin, (UDateTimeScale)scale);
174ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        roundTripTest(fromMax, (UDateTimeScale)scale);
175ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
176ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
177ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
178ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestToLimits(void)
179ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
180ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
181ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t scale;
182ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
183ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for (scale = 0; scale < UDTS_MAX_SCALE; scale += 1) {
184ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t fromMin = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MIN_VALUE, &status);
185ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t fromMax = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MAX_VALUE, &status);
186ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t toMin   = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_TO_MIN_VALUE, &status);
187ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t toMax   = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_TO_MAX_VALUE, &status);
188ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
189ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        toLimitTest(toMin, fromMin, (UDateTimeScale)scale);
190ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        toLimitTest(toMax, fromMax, (UDateTimeScale)scale);
191ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
192ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
193ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
194ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestFromInt64(void)
195ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
196ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t scale;
197ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t result;
198ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
199ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
200ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    result = utmscale_fromInt64(0, -1, &status);
201ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (status != U_ILLEGAL_ARGUMENT_ERROR) {
202ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("utmscale_fromInt64(0, -1, status) did not set status to U_ILLEGAL_ARGUMENT_ERROR.\n");
203ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
204ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
205ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for (scale = 0; scale < UDTS_MAX_SCALE; scale += 1) {
206ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t fromMin, fromMax;
207ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
208ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
209ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        fromMin = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MIN_VALUE, &status);
210ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        fromMax = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MAX_VALUE, &status);
211ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
212ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
213ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        result = utmscale_fromInt64(0, (UDateTimeScale)scale, &status);
214ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (status == U_ILLEGAL_ARGUMENT_ERROR) {
215ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_fromInt64(0, %d, &status) generated U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
216ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
217ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
218ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
219ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        result = utmscale_fromInt64(fromMin, (UDateTimeScale)scale, &status);
220ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (status == U_ILLEGAL_ARGUMENT_ERROR) {
221ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_fromInt64(fromMin, %d, &status) generated U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
222ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
223ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
224ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (fromMin > U_INT64_MIN) {
225ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            status = U_ZERO_ERROR;
226ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            result = utmscale_fromInt64(fromMin - 1, (UDateTimeScale)scale, &status);
227ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            if (status != U_ILLEGAL_ARGUMENT_ERROR) {
228ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru                log_err("utmscale_fromInt64(fromMin - 1, %d, &status) did not generate U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
229ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            }
230ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
231ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
232ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
233ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        result = utmscale_fromInt64(fromMax, (UDateTimeScale)scale, &status);
234ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (status == U_ILLEGAL_ARGUMENT_ERROR) {
235ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_fromInt64(fromMax, %d, &status) generated U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
236ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
237ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
238ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (fromMax < U_INT64_MAX) {
239ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            status = U_ZERO_ERROR;
240ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            result = utmscale_fromInt64(fromMax + 1, (UDateTimeScale)scale, &status);
241ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            if (status != U_ILLEGAL_ARGUMENT_ERROR) {
242ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru                log_err("utmscale_fromInt64(fromMax + 1, %d, &status) didn't generate U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
243ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            }
244ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
245ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
246ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
247ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    status = U_ZERO_ERROR;
248ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    result = utmscale_fromInt64(0, UDTS_MAX_SCALE, &status);
249ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (status != U_ILLEGAL_ARGUMENT_ERROR) {
250ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("utmscale_fromInt64(0, UDTS_MAX_SCALE, &status) did not generate U_ILLEGAL_ARGUMENT_ERROR.\n");
251ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
252ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
253ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
254ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestToInt64(void)
255ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
256ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t scale;
257ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t result;
258ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
259ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
260ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    result = utmscale_toInt64(0, -1, &status);
261ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (status != U_ILLEGAL_ARGUMENT_ERROR) {
262ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("utmscale_toInt64(0, -1, &status) did not generate U_ILLEGAL_ARGUMENT_ERROR.\n");
263ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
264ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
265ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for (scale = 0; scale < UDTS_MAX_SCALE; scale += 1) {
266ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t toMin, toMax;
267ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
268ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
269ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        toMin = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_TO_MIN_VALUE, &status);
270ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        toMax = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_TO_MAX_VALUE, &status);
271ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
272ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
273ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        result = utmscale_toInt64(0, (UDateTimeScale)scale, &status);
274ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (status == U_ILLEGAL_ARGUMENT_ERROR) {
275ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_toInt64(0, %d, &status) generated U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
276ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
277ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
278ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
279ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        result = utmscale_toInt64(toMin, (UDateTimeScale)scale, &status);
280ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (status == U_ILLEGAL_ARGUMENT_ERROR) {
281ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_toInt64(toMin, %d, &status) generated U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
282ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
283ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
284ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (toMin > U_INT64_MIN) {
285ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            status = U_ZERO_ERROR;
286ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            result = utmscale_toInt64(toMin - 1, (UDateTimeScale)scale, &status);
287ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            if (status != U_ILLEGAL_ARGUMENT_ERROR) {
288ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru                log_err("utmscale_toInt64(toMin - 1, %d, &status) did not generate U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
289ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            }
290ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
291ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
292ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
293ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        status = U_ZERO_ERROR;
294ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        result = utmscale_toInt64(toMax, (UDateTimeScale)scale, &status);
295ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (status == U_ILLEGAL_ARGUMENT_ERROR) {
296ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_toInt64(toMax, %d, &status) generated U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
297ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
298ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
299ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if (toMax < U_INT64_MAX) {
300ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            status = U_ZERO_ERROR;
301ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            result = utmscale_toInt64(toMax + 1, (UDateTimeScale)scale, &status);
302ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            if (status != U_ILLEGAL_ARGUMENT_ERROR) {
303ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru                log_err("utmscale_toInt64(toMax + 1, %d, &status) did not generate U_ILLEGAL_ARGUMENT_ERROR.\n", scale);
304ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            }
305ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
306ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
307ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
308ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    status = U_ZERO_ERROR;
309ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    result = utmscale_toInt64(0, UDTS_MAX_SCALE, &status);
310ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if (status != U_ILLEGAL_ARGUMENT_ERROR) {
311ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("utmscale_toInt64(0, UDTS_MAX_SCALE, &status) did not generate U_ILLEGAL_ARGUMENT_ERROR.\n");
312ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
313ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
314ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
315ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestAPI(void)
316ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
317ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    TestFromInt64();
318ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    TestToInt64();
319ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
320ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
321ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestData(void)
322ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
323ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    TestEpochOffsets();
324ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    TestFromLimits();
325ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    TestToLimits();
326ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
327ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
328ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void TestMonkey(void)
329ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru{
330ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t scale;
331ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode status = U_ZERO_ERROR;
332ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
333ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for (scale = 0; scale < UDTS_MAX_SCALE; scale += 1) {
334ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t fromMin = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MIN_VALUE, &status);
335ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int64_t fromMax = utmscale_getTimeScaleValue((UDateTimeScale)scale, UTSV_FROM_MAX_VALUE, &status);
336ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        int32_t i;
337ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
338ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        initRandom(fromMin, fromMax);
339ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
340ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        for (i = 0; i < LOOP_COUNT; i += 1) {
341ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            int64_t value = randomInRange();
342ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
343ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            roundTripTest(value, (UDateTimeScale)scale);
344ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
345ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
346ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
347ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
348ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustruct DotNetDateTimeTicks {
349ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t year;
350ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t month;
351ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t day;
352ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t ticks;
353ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru};
354ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querutypedef struct DotNetDateTimeTicks DotNetDateTimeTicks;
355ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
356ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/*
357ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * This data was generated by C++.Net code like
358ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Console::WriteLine(L"    {{ {0}, 1, 1, INT64_C({1}) }},", year, DateTime(year, 1, 1).Ticks);
359ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * with the DateTime constructor taking int values for year, month, and date.
360ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */
361ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic const DotNetDateTimeTicks dotNetDateTimeTicks[]={
362ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    /* year, month, day, ticks */
363ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 100, 1, 1, INT64_C(31241376000000000) },
364ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 100, 3, 1, INT64_C(31292352000000000) },
365ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 200, 1, 1, INT64_C(62798112000000000) },
366ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 200, 3, 1, INT64_C(62849088000000000) },
367ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 300, 1, 1, INT64_C(94354848000000000) },
368ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 300, 3, 1, INT64_C(94405824000000000) },
369ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 400, 1, 1, INT64_C(125911584000000000) },
370ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 400, 3, 1, INT64_C(125963424000000000) },
371ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 500, 1, 1, INT64_C(157469184000000000) },
372ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 500, 3, 1, INT64_C(157520160000000000) },
373ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 600, 1, 1, INT64_C(189025920000000000) },
374ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 600, 3, 1, INT64_C(189076896000000000) },
375ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 700, 1, 1, INT64_C(220582656000000000) },
376ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 700, 3, 1, INT64_C(220633632000000000) },
377ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 800, 1, 1, INT64_C(252139392000000000) },
378ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 800, 3, 1, INT64_C(252191232000000000) },
379ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 900, 1, 1, INT64_C(283696992000000000) },
380ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 900, 3, 1, INT64_C(283747968000000000) },
381ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1000, 1, 1, INT64_C(315253728000000000) },
382ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1000, 3, 1, INT64_C(315304704000000000) },
383ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1100, 1, 1, INT64_C(346810464000000000) },
384ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1100, 3, 1, INT64_C(346861440000000000) },
385ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1200, 1, 1, INT64_C(378367200000000000) },
386ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1200, 3, 1, INT64_C(378419040000000000) },
387ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1300, 1, 1, INT64_C(409924800000000000) },
388ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1300, 3, 1, INT64_C(409975776000000000) },
389ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1400, 1, 1, INT64_C(441481536000000000) },
390ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1400, 3, 1, INT64_C(441532512000000000) },
391ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1500, 1, 1, INT64_C(473038272000000000) },
392ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1500, 3, 1, INT64_C(473089248000000000) },
393ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1600, 1, 1, INT64_C(504595008000000000) },
394ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1600, 3, 1, INT64_C(504646848000000000) },
395ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1700, 1, 1, INT64_C(536152608000000000) },
396ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1700, 3, 1, INT64_C(536203584000000000) },
397ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1800, 1, 1, INT64_C(567709344000000000) },
398ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1800, 3, 1, INT64_C(567760320000000000) },
399ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1900, 1, 1, INT64_C(599266080000000000) },
400ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1900, 3, 1, INT64_C(599317056000000000) },
401ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2000, 1, 1, INT64_C(630822816000000000) },
402ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2000, 3, 1, INT64_C(630874656000000000) },
403ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2100, 1, 1, INT64_C(662380416000000000) },
404ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2100, 3, 1, INT64_C(662431392000000000) },
405ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2200, 1, 1, INT64_C(693937152000000000) },
406ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2200, 3, 1, INT64_C(693988128000000000) },
407ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2300, 1, 1, INT64_C(725493888000000000) },
408ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2300, 3, 1, INT64_C(725544864000000000) },
409ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2400, 1, 1, INT64_C(757050624000000000) },
410ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2400, 3, 1, INT64_C(757102464000000000) },
411ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2500, 1, 1, INT64_C(788608224000000000) },
412ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2500, 3, 1, INT64_C(788659200000000000) },
413ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2600, 1, 1, INT64_C(820164960000000000) },
414ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2600, 3, 1, INT64_C(820215936000000000) },
415ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2700, 1, 1, INT64_C(851721696000000000) },
416ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2700, 3, 1, INT64_C(851772672000000000) },
417ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2800, 1, 1, INT64_C(883278432000000000) },
418ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2800, 3, 1, INT64_C(883330272000000000) },
419ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2900, 1, 1, INT64_C(914836032000000000) },
420ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2900, 3, 1, INT64_C(914887008000000000) },
421ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 3000, 1, 1, INT64_C(946392768000000000) },
422ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 3000, 3, 1, INT64_C(946443744000000000) },
423ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1, 1, 1, INT64_C(0) },
424ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1601, 1, 1, INT64_C(504911232000000000) },
425ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1899, 12, 31, INT64_C(599265216000000000) },
426ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1904, 1, 1, INT64_C(600527520000000000) },
427ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 1970, 1, 1, INT64_C(621355968000000000) },
428ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 2001, 1, 1, INT64_C(631139040000000000) },
429ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 9900, 3, 1, INT64_C(3123873216000000000) },
430ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    { 9999, 12, 31, INT64_C(3155378112000000000) }
431ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru};
432ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
433ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru/*
434ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * ICU's Universal Time Scale is designed to be tick-for-tick compatible with
435ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * .Net System.DateTime. Verify that this is so for the
436ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * .Net-supported date range (years 1-9999 AD).
437ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * This requires a proleptic Gregorian calendar because that's what .Net uses.
438ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * Proleptic: No Julian/Gregorian switchover, or a switchover before
439ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru * any date that we test, that is, before 0001 AD.
440ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru */
441ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Querustatic void
442ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste QueruTestDotNet() {
443ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    static const UChar utc[] = { 0x45, 0x74, 0x63, 0x2f, 0x47, 0x4d, 0x54, 0 }; /* "Etc/GMT" */
444ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    const int32_t dayMillis = 86400 * INT64_C(1000);    /* 1 day = 86400 seconds */
445ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    const int64_t dayTicks = 86400 * INT64_C(10000000);
446ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    const DotNetDateTimeTicks *dt;
447ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UCalendar *cal;
448ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UErrorCode errorCode;
449ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    UDate icuDate;
450ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int64_t ticks, millis;
451ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    int32_t i;
452ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
453ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    /* Open a proleptic Gregorian calendar. */
454ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    errorCode = U_ZERO_ERROR;
455ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    cal = ucal_open(utc, -1, "", UCAL_GREGORIAN, &errorCode);
456ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    ucal_setGregorianChange(cal, -1000000 * (dayMillis * (UDate)1), &errorCode);
457ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    if(U_FAILURE(errorCode)) {
458ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        log_err("ucal_open(UTC/proleptic Gregorian) failed: %s\n", u_errorName(errorCode));
459ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        ucal_close(cal);
460ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        return;
461ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
462ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    for(i = 0; i < LENGTHOF(dotNetDateTimeTicks); ++i) {
463ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        /* Test conversion from .Net/Universal time to ICU time. */
464ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        dt = dotNetDateTimeTicks + i;
465ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        millis = utmscale_toInt64(dt->ticks, UDTS_ICU4C_TIME, &errorCode);
466ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        ucal_clear(cal);
467ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        ucal_setDate(cal, dt->year, dt->month - 1, dt->day, &errorCode); /* Java & ICU use January = month 0. */
468ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        icuDate = ucal_getMillis(cal, &errorCode);
469ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if(millis != icuDate) {
470ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            /* Print days not millis to stay within printf() range. */
471ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_toInt64(ticks[%d], ICU4C)=%dd != %dd=ucal_getMillis(%04d-%02d-%02d)\n",
472ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru                    (int)i, (int)(millis/dayMillis), (int)(icuDate/dayMillis), (int)dt->year, (int)dt->month, (int)dt->day);
473ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
474ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
475ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        /* Test conversion from ICU time to .Net/Universal time. */
476ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        ticks = utmscale_fromInt64((int64_t)icuDate, UDTS_ICU4C_TIME, &errorCode);
477ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        if(ticks != dt->ticks) {
478ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            /* Print days not ticks to stay within printf() range. */
479ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru            log_err("utmscale_fromInt64(date[%d], ICU4C)=%dd != %dd=.Net System.DateTime(%04d-%02d-%02d).Ticks\n",
480ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru                    (int)i, (int)(ticks/dayTicks), (int)(dt->ticks/dayTicks), (int)dt->year, (int)dt->month, (int)dt->day);
481ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru        }
482ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    }
483ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
484ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru    ucal_close(cal);
485ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru}
486ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru
487ac04d0bbe12b3ef54518635711412f178cb4d16Jean-Baptiste Queru#endif /* #if !UCONFIG_NO_FORMATTING */
488