quickfix_ruby 1.14.3.1 → 1.15.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (105) hide show
  1. checksums.yaml +4 -4
  2. data/ext/quickfix/Acceptor.h +2 -0
  3. data/ext/quickfix/AtomicCount.h +82 -12
  4. data/ext/quickfix/DOMDocument.h +9 -7
  5. data/ext/quickfix/DataDictionary.cpp +77 -14
  6. data/ext/quickfix/DataDictionary.h +90 -16
  7. data/ext/quickfix/Dictionary.cpp +1 -2
  8. data/ext/quickfix/Exceptions.h +3 -5
  9. data/ext/quickfix/Field.h +83 -32
  10. data/ext/quickfix/FieldConvertors.cpp +93 -0
  11. data/ext/quickfix/FieldConvertors.h +129 -275
  12. data/ext/quickfix/FieldMap.cpp +53 -13
  13. data/ext/quickfix/FieldMap.h +200 -62
  14. data/ext/quickfix/FieldTypes.cpp +10 -10
  15. data/ext/quickfix/FieldTypes.h +293 -44
  16. data/ext/quickfix/FileLog.cpp +6 -10
  17. data/ext/quickfix/FileLog.h +4 -10
  18. data/ext/quickfix/FileStore.cpp +19 -6
  19. data/ext/quickfix/FileStore.h +4 -0
  20. data/ext/quickfix/FixFieldNumbers.h +1462 -1461
  21. data/ext/quickfix/FixFields.h +1462 -1461
  22. data/ext/quickfix/FixValues.h +3230 -3227
  23. data/ext/quickfix/HttpConnection.cpp +1 -1
  24. data/ext/quickfix/Initiator.cpp +7 -1
  25. data/ext/quickfix/Initiator.h +2 -0
  26. data/ext/quickfix/Log.h +6 -12
  27. data/ext/quickfix/Message.cpp +186 -57
  28. data/ext/quickfix/Message.h +109 -47
  29. data/ext/quickfix/MySQLConnection.h +1 -1
  30. data/ext/quickfix/PostgreSQLConnection.h +1 -1
  31. data/ext/quickfix/QuickfixRuby.cpp +79141 -77959
  32. data/ext/quickfix/QuickfixRuby.h +1 -1
  33. data/ext/quickfix/SSLSocketAcceptor.cpp +410 -0
  34. data/ext/quickfix/SSLSocketAcceptor.h +185 -0
  35. data/ext/quickfix/SSLSocketConnection.cpp +427 -0
  36. data/ext/quickfix/SSLSocketConnection.h +206 -0
  37. data/ext/quickfix/SSLSocketInitiator.cpp +485 -0
  38. data/ext/quickfix/SSLSocketInitiator.h +196 -0
  39. data/ext/quickfix/Session.cpp +113 -20
  40. data/ext/quickfix/Session.h +18 -4
  41. data/ext/quickfix/SessionFactory.cpp +10 -3
  42. data/ext/quickfix/SessionSettings.cpp +5 -3
  43. data/ext/quickfix/SessionSettings.h +97 -5
  44. data/ext/quickfix/Settings.cpp +72 -2
  45. data/ext/quickfix/Settings.h +3 -0
  46. data/ext/quickfix/SharedArray.h +140 -6
  47. data/ext/quickfix/SocketConnection.cpp +2 -2
  48. data/ext/quickfix/SocketConnector.cpp +5 -2
  49. data/ext/quickfix/SocketConnector.h +3 -2
  50. data/ext/quickfix/SocketInitiator.cpp +28 -4
  51. data/ext/quickfix/SocketInitiator.h +1 -1
  52. data/ext/quickfix/SocketMonitor.cpp +5 -5
  53. data/ext/quickfix/ThreadedSSLSocketAcceptor.cpp +455 -0
  54. data/ext/quickfix/ThreadedSSLSocketAcceptor.h +217 -0
  55. data/ext/quickfix/ThreadedSSLSocketConnection.cpp +404 -0
  56. data/ext/quickfix/ThreadedSSLSocketConnection.h +189 -0
  57. data/ext/quickfix/ThreadedSSLSocketInitiator.cpp +469 -0
  58. data/ext/quickfix/ThreadedSSLSocketInitiator.h +201 -0
  59. data/ext/quickfix/ThreadedSocketAcceptor.cpp +5 -1
  60. data/ext/quickfix/ThreadedSocketConnection.cpp +8 -2
  61. data/ext/quickfix/ThreadedSocketConnection.h +4 -1
  62. data/ext/quickfix/ThreadedSocketInitiator.cpp +24 -4
  63. data/ext/quickfix/ThreadedSocketInitiator.h +1 -1
  64. data/ext/quickfix/Utility.cpp +23 -1
  65. data/ext/quickfix/Utility.h +28 -2
  66. data/ext/quickfix/UtilitySSL.cpp +1733 -0
  67. data/ext/quickfix/UtilitySSL.h +277 -0
  68. data/ext/quickfix/config-all.h +10 -0
  69. data/ext/quickfix/dirent_windows.h +838 -0
  70. data/ext/quickfix/double-conversion/bignum-dtoa.cc +641 -0
  71. data/ext/quickfix/double-conversion/bignum-dtoa.h +84 -0
  72. data/ext/quickfix/double-conversion/bignum.cc +766 -0
  73. data/ext/quickfix/double-conversion/bignum.h +144 -0
  74. data/ext/quickfix/double-conversion/cached-powers.cc +176 -0
  75. data/ext/quickfix/double-conversion/cached-powers.h +64 -0
  76. data/ext/quickfix/double-conversion/diy-fp.cc +57 -0
  77. data/ext/quickfix/double-conversion/diy-fp.h +118 -0
  78. data/ext/quickfix/double-conversion/double-conversion.cc +994 -0
  79. data/ext/quickfix/double-conversion/double-conversion.h +543 -0
  80. data/ext/quickfix/double-conversion/fast-dtoa.cc +665 -0
  81. data/ext/quickfix/double-conversion/fast-dtoa.h +88 -0
  82. data/ext/quickfix/double-conversion/fixed-dtoa.cc +404 -0
  83. data/ext/quickfix/double-conversion/fixed-dtoa.h +56 -0
  84. data/ext/quickfix/double-conversion/ieee.h +402 -0
  85. data/ext/quickfix/double-conversion/strtod.cc +557 -0
  86. data/ext/quickfix/double-conversion/strtod.h +45 -0
  87. data/ext/quickfix/double-conversion/utils.h +372 -0
  88. data/ext/quickfix/stdint_msvc.h +254 -0
  89. data/lib/quickfix44.rb +3329 -10
  90. data/lib/quickfix50.rb +6649 -81
  91. data/lib/quickfix50sp1.rb +8054 -142
  92. data/lib/quickfix50sp2.rb +10900 -234
  93. data/lib/quickfix_fields.rb +7662 -7649
  94. data/spec/FIX40.xml +28 -28
  95. data/spec/FIX41.xml +29 -29
  96. data/spec/FIX42.xml +47 -47
  97. data/spec/FIX43.xml +148 -148
  98. data/spec/FIX44.xml +1078 -1081
  99. data/spec/FIX50.xml +1292 -1289
  100. data/spec/FIX50SP1.xml +1811 -1802
  101. data/spec/FIX50SP2.xml +1948 -1939
  102. data/spec/FIXT11.xml +5 -8
  103. data/test/test_FieldBaseTestCase.rb +1 -1
  104. data/test/test_MessageTestCase.rb +2 -2
  105. metadata +42 -6
@@ -33,14 +33,14 @@ namespace FIX {
33
33
 
34
34
  DateTime DateTime::nowUtc()
35
35
  {
36
- #if defined( HAVE_FTIME )
36
+ #if defined( _POSIX_SOURCE ) || defined(HAVE_GETTIMEOFDAY)
37
+ struct timeval tv;
38
+ gettimeofday (&tv, 0);
39
+ return fromUtcTimeT( tv.tv_sec, tv.tv_usec, 6 );
40
+ #elif defined( HAVE_FTIME )
37
41
  timeb tb;
38
42
  ftime (&tb);
39
43
  return fromUtcTimeT (tb.time, tb.millitm);
40
- #elif defined( _POSIX_SOURCE )
41
- struct timeval tv;
42
- gettimeofday (&tv, 0);
43
- return fromUtcTimeT( tv.tv_sec, tv.tv_usec / 1000 );
44
44
  #else
45
45
  return fromUtcTimeT( ::time (0), 0 );
46
46
  #endif
@@ -48,14 +48,14 @@ DateTime DateTime::nowUtc()
48
48
 
49
49
  DateTime DateTime::nowLocal()
50
50
  {
51
- #if defined( HAVE_FTIME )
51
+ #if defined( _POSIX_SOURCE ) || defined(HAVE_GETTIMEOFDAY)
52
+ struct timeval tv;
53
+ gettimeofday (&tv, 0);
54
+ return fromLocalTimeT( tv.tv_sec, tv.tv_usec, 6 );
55
+ #elif defined( HAVE_FTIME )
52
56
  timeb tb;
53
57
  ftime (&tb);
54
58
  return fromLocalTimeT( tb.time, tb.millitm );
55
- #elif defined( _POSIX_SOURCE )
56
- struct timeval tv;
57
- gettimeofday (&tv, 0);
58
- return fromLocalTimeT( tv.tv_sec, tv.tv_usec / 1000 );
59
59
  #else
60
60
  return fromLocalTimeT( ::time (0), 0 );
61
61
  #endif
@@ -26,6 +26,12 @@
26
26
  #pragma warning( disable : 4503 4355 4786 4290 )
27
27
  #endif
28
28
 
29
+ #if defined(_MSC_VER) && (_MSC_VER < 1600)
30
+ #include "stdint_msvc.h"
31
+ #else
32
+ #include <stdint.h> /* integer types int8_t .. uint64_t, intptr_t */
33
+ #endif
34
+
29
35
  #include "Utility.h"
30
36
  #include <string>
31
37
  #include <time.h>
@@ -37,7 +43,7 @@ namespace FIX
37
43
  */
38
44
 
39
45
  /// Date and Time stored as a Julian day number and number of
40
- /// milliseconds since midnight. Does not perform any timezone
46
+ /// nanoseconds since midnight. Does not perform any timezone
41
47
  /// calculations. All magic numbers and related calculations
42
48
  /// have been taken from:
43
49
  ///
@@ -47,40 +53,50 @@ namespace FIX
47
53
  /// \sa http://scienceworld.wolfram.com/astronomy/Weekday.html
48
54
  ///
49
55
  /// \author Caleb Epstein <caleb.epstein at gmail dot com>
56
+
57
+ // Precision factor of timestamp. [0] - second, [9] - nanosecond
58
+ static const int PRECISION_FACTOR[10] = {1000000000, 100000000, 10000000, 1000000, 100000, 10000, 1000, 100, 10, 1};
59
+
50
60
  struct DateTime
51
61
  {
52
62
  int m_date;
53
- int m_time;
63
+ int64_t m_time;
54
64
 
55
65
  /// Magic numbers
56
- enum
57
- {
58
- SECONDS_PER_DAY = 86400,
59
- SECONDS_PER_HOUR = 3600,
60
- SECONDS_PER_MIN = 60,
61
- MINUTES_PER_HOUR = 60,
66
+ static const int64_t SECONDS_PER_DAY = 86400;
67
+ static const int64_t SECONDS_PER_HOUR = 3600;
68
+ static const int64_t SECONDS_PER_MIN = 60;
69
+ static const int64_t MINUTES_PER_HOUR = 60;
62
70
 
63
- MILLIS_PER_DAY = 86400000,
64
- MILLIS_PER_HOUR = 3600000,
65
- MILLIS_PER_MIN = 60000,
66
- MILLIS_PER_SEC = 1000,
71
+ static const int64_t NANOS_PER_DAY = 86400000000000;
72
+ static const int64_t NANOS_PER_HOUR = 3600000000000;
73
+ static const int64_t NANOS_PER_MIN = 60000000000;
74
+ static const int64_t NANOS_PER_SEC = 1000000000;
67
75
 
68
- // time_t epoch (1970-01-01) as a Julian date
69
- JULIAN_19700101 = 2440588
70
- };
76
+ // time_t epoch (1970-01-01) as a Julian date
77
+ static const int64_t JULIAN_19700101 = 2440588;
71
78
 
72
79
  /// Default constructor - initializes to zero
73
80
  DateTime () : m_date (0), m_time (0) {}
74
81
 
75
82
  /// Construct from a Julian day number and time in millis
76
- DateTime (int date, int time) : m_date (date), m_time (time) {}
83
+ DateTime (int date, int64_t time) : m_date (date), m_time (time) {}
77
84
 
78
85
  /// Construct from the specified components
79
86
  DateTime( int year, int month, int day,
80
87
  int hour, int minute, int second, int millis )
81
88
  {
82
89
  m_date = julianDate( year, month, day );
83
- m_time = makeHMS( hour, minute, second, millis );
90
+ m_time = makeHMS( hour, minute, second, millis * PRECISION_FACTOR[3] );
91
+ }
92
+
93
+ /// Construct from the specified components
94
+ DateTime( int year, int month, int day,
95
+ int hour, int minute, int second, int fraction, int precision )
96
+ {
97
+ m_date = julianDate( year, month, day );
98
+ int nanos = convertToNanos(fraction, precision);
99
+ m_time = makeHMS( hour, minute, second, nanos );
84
100
  }
85
101
 
86
102
  virtual ~DateTime() {}
@@ -117,27 +133,77 @@ struct DateTime
117
133
  inline int getJulianDate() const { return m_date; }
118
134
 
119
135
  /// Return the hour portion of the time (0-23)
120
- inline int getHour() const
136
+ inline int getHour() const
121
137
  {
122
- return m_time / MILLIS_PER_HOUR;
138
+ return (int)(m_time / NANOS_PER_HOUR);
123
139
  }
124
140
 
125
141
  /// Return the minute portion of the time (0-59)
126
- inline int getMinute() const
142
+ inline int getMinute() const
127
143
  {
128
- return (m_time / MILLIS_PER_MIN) % MINUTES_PER_HOUR;
144
+ return (m_time / NANOS_PER_MIN) % MINUTES_PER_HOUR;
129
145
  }
130
146
 
131
147
  /// Return the second portion of the time (0-59)
132
- inline int getSecond() const
148
+ inline int getSecond() const
149
+ {
150
+ return (m_time / NANOS_PER_SEC) % SECONDS_PER_MIN;
151
+ }
152
+
153
+ /// Return the millisecond portion of the time (0-999)
154
+ inline int getMillisecond() const
133
155
  {
134
- return (m_time / MILLIS_PER_SEC) % SECONDS_PER_MIN;
156
+ return (getNanosecond() / PRECISION_FACTOR[3]);
135
157
  }
136
158
 
137
- /// Return the millisecond portion of the time
138
- inline int getMillisecond() const
159
+ /// Return the microsecond portion of the time
160
+ inline int getMicroecond() const
139
161
  {
140
- return m_time % MILLIS_PER_SEC;
162
+ return (getNanosecond() / PRECISION_FACTOR[6]);
163
+ }
164
+
165
+ /// Return the nanosecond portion of the time
166
+ inline unsigned int getNanosecond() const
167
+ {
168
+ return static_cast<uint64_t>(m_time) % NANOS_PER_SEC;
169
+ }
170
+
171
+ /// Return the fraction portion of the time
172
+ inline int getFraction(int precision) const
173
+ {
174
+ switch (precision)
175
+ {
176
+ case 0:
177
+ return (getNanosecond() / PRECISION_FACTOR[0]);
178
+
179
+ case 1:
180
+ return (getNanosecond() / PRECISION_FACTOR[1]);
181
+
182
+ case 2:
183
+ return (getNanosecond() / PRECISION_FACTOR[2]);
184
+
185
+ case 3:
186
+ return (getNanosecond() / PRECISION_FACTOR[3]);
187
+
188
+ case 4:
189
+ return (getNanosecond() / PRECISION_FACTOR[4]);
190
+
191
+ case 5:
192
+ return (getNanosecond() / PRECISION_FACTOR[5]);
193
+
194
+ case 6:
195
+ return (getNanosecond() / PRECISION_FACTOR[6]);
196
+
197
+ case 7:
198
+ return (getNanosecond() / PRECISION_FACTOR[7]);
199
+
200
+ case 8:
201
+ return (getNanosecond() / PRECISION_FACTOR[8]);
202
+
203
+ case 9:
204
+ default:
205
+ return (getNanosecond() / PRECISION_FACTOR[9]);
206
+ }
141
207
  }
142
208
 
143
209
  /// Load the referenced values with the year, month and day
@@ -151,11 +217,22 @@ struct DateTime
151
217
  /// millisecond portions of the time in a single operation
152
218
  inline void getHMS( int& hour, int& minute, int& second, int& millis ) const
153
219
  {
154
- int ticks = m_time / MILLIS_PER_SEC;
220
+ int ticks = (int)(m_time / NANOS_PER_SEC);
221
+ hour = ticks / SECONDS_PER_HOUR;
222
+ minute = (ticks / SECONDS_PER_MIN) % MINUTES_PER_HOUR;
223
+ second = ticks % SECONDS_PER_MIN;
224
+ millis = getMillisecond();
225
+ }
226
+
227
+ /// Load the referenced values with the hour, minute, second and
228
+ /// fraction portions of the time in a single operation
229
+ inline void getHMS( int& hour, int& minute, int& second, int& fraction, int precision ) const
230
+ {
231
+ int ticks = (int)(m_time / NANOS_PER_SEC);
155
232
  hour = ticks / SECONDS_PER_HOUR;
156
233
  minute = (ticks / SECONDS_PER_MIN) % MINUTES_PER_HOUR;
157
234
  second = ticks % SECONDS_PER_MIN;
158
- millis = m_time % MILLIS_PER_SEC;
235
+ fraction = getFraction(precision);
159
236
  }
160
237
 
161
238
  /// Calculate the weekday of the date (Sunday is 1, Saturday is 7)
@@ -177,7 +254,7 @@ struct DateTime
177
254
  inline time_t getTimeT() const
178
255
  {
179
256
  return (SECONDS_PER_DAY * (m_date - JULIAN_19700101) +
180
- m_time / MILLIS_PER_SEC);
257
+ m_time / NANOS_PER_SEC);
181
258
  }
182
259
 
183
260
  /// Convert the DateTime to a struct tm which is in UTC
@@ -210,7 +287,15 @@ struct DateTime
210
287
  /// Set the time portion of the DateTime
211
288
  void setHMS( int hour, int minute, int second, int millis )
212
289
  {
213
- m_time = makeHMS( hour, minute, second, millis );
290
+ m_time = makeHMS( hour, minute, second, millis * PRECISION_FACTOR[3] );
291
+ }
292
+
293
+ /// Set the time portion of the DateTime
294
+ void setHMS( int hour, int minute, int second, int fraction, int precision )
295
+ {
296
+ int nanos = convertToNanos(fraction, precision);
297
+
298
+ m_time = makeHMS( hour, minute, second, nanos);
214
299
  }
215
300
 
216
301
  /// Set the hour portion of the time
@@ -245,6 +330,30 @@ struct DateTime
245
330
  setHMS( hour, min, sec, millis );
246
331
  }
247
332
 
333
+ /// Set the microsecond portion of the time
334
+ void setMicrosecond( int micros )
335
+ {
336
+ int hour, min, sec, old_nanos;
337
+ getHMS( hour, min, sec, old_nanos, 9 );
338
+ setHMS( hour, min, sec, micros, 6 );
339
+ }
340
+
341
+ /// Set the nanosecond portion of the time
342
+ void setNanosecond( int nanos )
343
+ {
344
+ int hour, min, sec, old_nanos;
345
+ getHMS( hour, min, sec, old_nanos, 9 );
346
+ setHMS( hour, min, sec, nanos, 9 );
347
+ }
348
+
349
+ /// Set the fraction portion of the time
350
+ void setFraction( int fraction, int precision )
351
+ {
352
+ int hour, min, sec, old_nanos;
353
+ getHMS( hour, min, sec, old_nanos, 9 );
354
+ setHMS( hour, min, sec, fraction, precision );
355
+ }
356
+
248
357
  /// Clear the date portion of the DateTime
249
358
  void clearDate()
250
359
  {
@@ -258,7 +367,7 @@ struct DateTime
258
367
  }
259
368
 
260
369
  /// Set the internal date and time members
261
- void set( int date, int time ) { m_date = date; m_time = time; }
370
+ void set( int date, int64_t time ) { m_date = date; m_time = time; }
262
371
 
263
372
  /// Initialize from another DateTime
264
373
  void set( const DateTime& other )
@@ -268,33 +377,85 @@ struct DateTime
268
377
  }
269
378
 
270
379
  /// Add a number of seconds to this
271
- void operator+=( int seconds )
380
+ void operator+=( int seconds )
272
381
  {
273
382
  int d = seconds / SECONDS_PER_DAY;
274
383
  int s = seconds % SECONDS_PER_DAY;
275
384
 
276
385
  m_date += d;
277
- m_time += s * MILLIS_PER_SEC;
386
+ m_time += s * NANOS_PER_SEC;
278
387
 
279
- if( m_time > MILLIS_PER_DAY )
388
+ if( m_time > NANOS_PER_DAY )
280
389
  {
281
390
  m_date++;
282
- m_time %= MILLIS_PER_DAY;
391
+ m_time %= NANOS_PER_DAY;
283
392
  }
284
393
  else if( m_time < 0 )
285
394
  {
286
395
  m_date--;
287
- m_time += MILLIS_PER_DAY;
396
+ m_time += NANOS_PER_DAY;
397
+ }
398
+ }
399
+
400
+ /// Convert to internal nanos
401
+ static int convertToNanos(int fraction, int precision)
402
+ {
403
+ int nanos;
404
+
405
+ switch (precision)
406
+ {
407
+ case 0:
408
+ nanos = fraction * PRECISION_FACTOR[0];
409
+ break;
410
+
411
+ case 1:
412
+ nanos = fraction * PRECISION_FACTOR[1];
413
+ break;
414
+
415
+ case 2:
416
+ nanos = fraction * PRECISION_FACTOR[2];
417
+ break;
418
+
419
+ case 3:
420
+ nanos = fraction * PRECISION_FACTOR[3];
421
+ break;
422
+
423
+ case 4:
424
+ nanos = fraction * PRECISION_FACTOR[4];
425
+ break;
426
+
427
+ case 5:
428
+ nanos = fraction * PRECISION_FACTOR[5];
429
+ break;
430
+
431
+ case 6:
432
+ nanos = fraction * PRECISION_FACTOR[6];
433
+ break;
434
+
435
+ case 7:
436
+ nanos = fraction * PRECISION_FACTOR[7];
437
+ break;
438
+
439
+ case 8:
440
+ nanos = fraction * PRECISION_FACTOR[8];
441
+ break;
442
+
443
+ case 9:
444
+ default:
445
+ nanos = fraction * PRECISION_FACTOR[9];
446
+ break;
288
447
  }
448
+
449
+ return nanos;
289
450
  }
290
451
 
291
452
  /// Helper method to convert a broken down time to a number of
292
- /// milliseconds since midnight
293
- static int makeHMS( int hour, int minute, int second, int millis )
453
+ /// nanoseconds since midnight
454
+ static int64_t makeHMS( int hour, int minute, int second, int nanos )
294
455
  {
295
- return MILLIS_PER_SEC * (SECONDS_PER_HOUR * hour +
296
- SECONDS_PER_MIN * minute +
297
- second) + millis;
456
+ return NANOS_PER_SEC * (SECONDS_PER_HOUR * hour +
457
+ SECONDS_PER_MIN * minute +
458
+ second) + nanos;
298
459
  }
299
460
 
300
461
  /// Return the current wall-clock time as a utc DateTime
@@ -316,13 +477,35 @@ struct DateTime
316
477
  return fromTm( tm, millis );
317
478
  }
318
479
 
480
+ static DateTime fromUtcTimeT( time_t t, int fraction, int precision )
481
+ {
482
+ struct tm tm = time_gmtime( &t );
483
+ return fromTm( tm, fraction, precision );
484
+ }
485
+
486
+ static DateTime fromLocalTimeT( time_t t, int fraction, int precision )
487
+ {
488
+ struct tm tm = time_localtime( &t );
489
+ return fromTm( tm, fraction, precision );
490
+ }
491
+
319
492
  /// Convert a tm and optional milliseconds to a DateTime. \note
320
493
  /// the tm structure is assumed to contain a date specified in UTC
321
494
  static DateTime fromTm( const tm& tm, int millis = 0 )
322
495
  {
323
496
  return DateTime ( julianDate(tm.tm_year + 1900, tm.tm_mon + 1,
324
497
  tm.tm_mday),
325
- makeHMS(tm.tm_hour, tm.tm_min, tm.tm_sec, millis) );
498
+ makeHMS(tm.tm_hour, tm.tm_min, tm.tm_sec, millis * PRECISION_FACTOR[3]) );
499
+ }
500
+
501
+ /// Convert a tm and optional milliseconds to a DateTime. \note
502
+ /// the tm structure is assumed to contain a date specified in UTC
503
+ static DateTime fromTm( const tm& tm, int fraction, int precision )
504
+ {
505
+ int nanos = convertToNanos(fraction, precision);
506
+ return DateTime ( julianDate(tm.tm_year + 1900, tm.tm_mon + 1,
507
+ tm.tm_mday),
508
+ makeHMS(tm.tm_hour, tm.tm_min, tm.tm_sec, nanos) );
326
509
  }
327
510
 
328
511
  /// Helper method to calculate a Julian day number.
@@ -391,8 +574,8 @@ inline bool operator>=( const DateTime& lhs, const DateTime& rhs )
391
574
  inline int operator-( const DateTime& lhs, const DateTime& rhs )
392
575
  {
393
576
  return (DateTime::SECONDS_PER_DAY * (lhs.m_date - rhs.m_date) +
394
- // Truncate the millis before subtracting
395
- lhs.m_time / 1000 - rhs.m_time / 1000);
577
+ // Truncate the nanos before subtracting
578
+ (int)(lhs.m_time / DateTime::NANOS_PER_SEC) - (int)(rhs.m_time / DateTime::NANOS_PER_SEC));
396
579
  }
397
580
 
398
581
  /// Date and Time represented in UTC.
@@ -410,6 +593,12 @@ public:
410
593
  setHMS( hour, minute, second, millisecond );
411
594
  }
412
595
 
596
+ UtcTimeStamp( int hour, int minute, int second, int fraction, int precision )
597
+ : DateTime( DateTime::nowUtc() )
598
+ {
599
+ setHMS( hour, minute, second, fraction, precision );
600
+ }
601
+
413
602
  UtcTimeStamp( int hour, int minute, int second,
414
603
  int date, int month, int year )
415
604
  : DateTime( year, month, date, hour, minute, second, 0 ) {}
@@ -418,12 +607,22 @@ public:
418
607
  int date, int month, int year )
419
608
  : DateTime( year, month, date, hour, minute, second, millisecond ) {}
420
609
 
610
+ UtcTimeStamp( int hour, int minute, int second, int fraction,
611
+ int date, int month, int year, int precision )
612
+ : DateTime( year, month, date, hour, minute, second, fraction, precision ) {}
613
+
421
614
  explicit UtcTimeStamp( time_t time, int millisecond = 0 )
422
615
  : DateTime( fromUtcTimeT (time, millisecond) ) {}
423
616
 
617
+ UtcTimeStamp( time_t time, int fraction, int precision )
618
+ : DateTime( fromUtcTimeT (time, fraction, precision) ) {}
619
+
424
620
  UtcTimeStamp( const tm* time, int millisecond = 0 )
425
621
  : DateTime( fromTm (*time, millisecond) ) {}
426
622
 
623
+ UtcTimeStamp( const tm* time, int fraction, int precision )
624
+ : DateTime( fromTm (*time, fraction, precision) ) {}
625
+
427
626
  void setCurrent()
428
627
  {
429
628
  set( DateTime::nowUtc() );
@@ -445,6 +644,12 @@ public:
445
644
  setHMS( hour, minute, second, millisecond );
446
645
  }
447
646
 
647
+ LocalTimeStamp( int hour, int minute, int second, int fraction, int precision )
648
+ : DateTime( DateTime::nowLocal() )
649
+ {
650
+ setHMS( hour, minute, second, fraction, precision );
651
+ }
652
+
448
653
  LocalTimeStamp( int hour, int minute, int second,
449
654
  int date, int month, int year )
450
655
  : DateTime( year, month, date, hour, minute, second, 0 ) {}
@@ -453,12 +658,22 @@ public:
453
658
  int date, int month, int year )
454
659
  : DateTime( year, month, date, hour, minute, second, millisecond ) {}
455
660
 
661
+ LocalTimeStamp( int hour, int minute, int second, int fraction,
662
+ int date, int month, int year, int precision )
663
+ : DateTime( year, month, date, hour, minute, second, fraction, precision ) {}
664
+
456
665
  explicit LocalTimeStamp( time_t time, int millisecond = 0 )
457
666
  : DateTime( fromLocalTimeT (time, millisecond) ) {}
458
667
 
668
+ LocalTimeStamp( time_t time, int fraction, int precision )
669
+ : DateTime( fromLocalTimeT (time, fraction, precision) ) {}
670
+
459
671
  LocalTimeStamp( const tm* time, int millisecond = 0 )
460
672
  : DateTime( fromTm (*time, millisecond) ) {}
461
673
 
674
+ LocalTimeStamp( const tm* time, int fraction, int precision )
675
+ : DateTime( fromTm (*time, fraction, precision) ) {}
676
+
462
677
  void setCurrent()
463
678
  {
464
679
  set( DateTime::nowLocal() );
@@ -486,18 +701,35 @@ public:
486
701
  setHMS( hour, minute, second, millisecond );
487
702
  }
488
703
 
704
+ UtcTimeOnly( int hour, int minute, int second, int fraction, int precision )
705
+ {
706
+ setHMS( hour, minute, second, fraction, precision );
707
+ }
708
+
489
709
  explicit UtcTimeOnly( time_t time, int millisecond = 0 )
490
710
  : DateTime( fromUtcTimeT (time, millisecond) )
491
711
  {
492
712
  clearDate();
493
713
  }
494
714
 
715
+ UtcTimeOnly( time_t time, int fraction, int precision )
716
+ : DateTime( fromUtcTimeT (time, fraction, precision) )
717
+ {
718
+ clearDate();
719
+ }
720
+
495
721
  UtcTimeOnly( const tm* time, int millisecond = 0 )
496
722
  : DateTime( fromTm (*time, millisecond) )
497
723
  {
498
724
  clearDate();
499
725
  }
500
726
 
727
+ UtcTimeOnly( const tm* time, int fraction, int precision )
728
+ : DateTime( fromTm (*time, fraction, precision) )
729
+ {
730
+ clearDate();
731
+ }
732
+
501
733
  /// Set to the current time.
502
734
  void setCurrent()
503
735
  {
@@ -527,18 +759,35 @@ public:
527
759
  setHMS( hour, minute, second, millisecond );
528
760
  }
529
761
 
762
+ LocalTimeOnly( int hour, int minute, int second, int fraction, int precision )
763
+ {
764
+ setHMS( hour, minute, second, fraction, precision );
765
+ }
766
+
530
767
  explicit LocalTimeOnly( time_t time, int millisecond = 0 )
531
768
  : DateTime( fromLocalTimeT (time, millisecond) )
532
769
  {
533
770
  clearDate();
534
771
  }
535
772
 
773
+ LocalTimeOnly( time_t time, int fraction, int precision )
774
+ : DateTime( fromLocalTimeT (time, fraction, precision) )
775
+ {
776
+ clearDate();
777
+ }
778
+
536
779
  LocalTimeOnly( const tm* time, int millisecond = 0 )
537
780
  : DateTime( fromTm (*time, millisecond) )
538
781
  {
539
782
  clearDate();
540
783
  }
541
784
 
785
+ LocalTimeOnly( const tm* time, int fraction, int precision )
786
+ : DateTime( fromTm (*time, fraction, precision) )
787
+ {
788
+ clearDate();
789
+ }
790
+
542
791
  /// Set to the current time.
543
792
  void setCurrent()
544
793
  {