PostgreSQL Source Code: src/interfaces/ecpg/pgtypeslib/timestamp.c Source File (original) (raw)
1
2
3
5
7#include <limits.h>
8#include <math.h>
9
10#ifdef __FAST_MATH__
11#error -ffast-math is known to break this code
12#endif
13
15#include "dt.h"
19
21time2t(const int hour, const int min, const int sec, const fsec_t fsec)
22{
24}
25
28{
30 return dt;
31}
32
33
34
35
36
37
38
39
40int
42{
43 int dDate;
45
46
48 return -1;
49
54 return -1;
55 if (tzp != NULL)
56 *result = dt2local(*result, -(*tzp));
57
58
60 return -1;
61
62 return 0;
63}
64
67{
68 int64 noresult = 0;
70 struct tm tt,
71 *tm = &tt;
72
74 return noresult;
75
77 return dt;
78}
79
80
81
82
83
84
85
86
87
88
89
90
91static int
93{
95 date0;
97#if defined(HAVE_STRUCT_TM_TM_ZONE) || defined(HAVE_INT_TIMEZONE)
98 time_t utime;
99 struct tm *tx;
100#endif
101
102 date0 = date2j(2000, 1, 1);
103
104 time = dt;
106
108 {
110 dDate -= 1;
111 }
112
113
114 dDate += date0;
115
116
117 if (dDate < 0 || dDate > (timestamp) INT_MAX)
118 return -1;
119
122
123 if (tzp != NULL)
124 {
125
126
127
128
130 {
131#if defined(HAVE_STRUCT_TM_TM_ZONE) || defined(HAVE_INT_TIMEZONE)
132 struct tm tmbuf;
133
136
137 tx = localtime_r(&utime, &tmbuf);
138 tm->tm_year = tx->tm_year + 1900;
144
145#if defined(HAVE_STRUCT_TM_TM_ZONE)
148
150 if (tzn != NULL)
152#elif defined(HAVE_INT_TIMEZONE)
154 if (tzn != NULL)
156#endif
157#else
158
159 *tzp = 0;
160
162 if (tzn != NULL)
163 *tzn = NULL;
164#endif
165 }
166 else
167 {
168 *tzp = 0;
169
171 if (tzn != NULL)
172 *tzn = NULL;
173 }
174 }
175 else
176 {
178 if (tzn != NULL)
179 *tzn = NULL;
180 }
181
183
184 return 0;
185}
186
187
188
189
190static void
192{
197 else
198 abort();
199}
200
203{
205 int64 noresult = 0;
207 struct tm tt,
208 *tm = &tt;
209 int dtype;
210 int nf;
214 char *realptr;
215 char **ptr = (endptr != NULL) ? endptr : &realptr;
216
218 {
220 return noresult;
221 }
222
223 if (ParseDateTime(str, lowstr, field, ftype, &nf, ptr) != 0 ||
225 {
227 return noresult;
228 }
229
230 switch (dtype)
231 {
234 {
236 return noresult;
237 }
238 break;
239
242 break;
243
246 break;
247
250 break;
251
252 default:
254 return noresult;
255 }
256
257
258
259
260
261
262
263 errno = 0;
264 return result;
265}
266
267char *
269{
270 struct tm tt,
271 *tm = &tt;
274 int DateStyle = 1;
275
276
279 else if (timestamp2tm(tstamp, NULL, tm, &fsec, NULL) == 0)
281 else
282 {
284 return NULL;
285 }
287}
288
289void
291{
293
295 if (errno == 0)
297}
298
299static int
301 char *output, int *pstr_len, const char *fmtstr)
302{
304 int replace_type;
305 int i;
306 const char *p = fmtstr;
308
309 while (*p)
310 {
311 if (*p == '%')
312 {
313 p++;
314
316 switch (*p)
317 {
318
319
320 case 'a':
323 break;
324
325
326 case 'A':
329 break;
330
331
332 case 'b':
333 case 'h':
336 break;
337
338
339 case 'B':
342 break;
343
344
345
346
347
348 case 'c':
349
350 break;
351
352 case 'C':
355 break;
356
357 case 'd':
360 break;
361
362 case 'D':
363
364
365
366
367
368
369
370
371
373 q, pstr_len,
374 "%m/%d/%y");
375 if (i)
376 return i;
377 break;
378
379 case 'e':
382 break;
383
384
385
386
387 case 'E':
388 {
389 char tmp[4] = "%Ex";
390
391 p++;
392 if (*p == '\0')
393 return -1;
394 tmp[2] = *p;
395
396
397
398
400 i = strftime(q, *pstr_len, tmp, tm);
401 if (i == 0)
402 return -1;
403 while (*q)
404 {
405 q++;
406 (*pstr_len)--;
407 }
410 break;
411 }
412
413
414
415
416
417 case 'G':
418 {
419
420 const char *fmt = "%G";
421
423 i = strftime(q, *pstr_len, fmt, tm);
424 if (i == 0)
425 return -1;
426 while (*q)
427 {
428 q++;
429 (*pstr_len)--;
430 }
433 }
434 break;
435
436
437
438
439
440 case 'g':
441 {
442 const char *fmt = "%g";
443
444
446 i = strftime(q, *pstr_len, fmt, tm);
447 if (i == 0)
448 return -1;
449 while (*q)
450 {
451 q++;
452 (*pstr_len)--;
453 }
456 }
457 break;
458
459 case 'H':
462 break;
463
464 case 'I':
467 break;
468
469
470
471
472
473 case 'j':
476 break;
477
478
479
480
481
482 case 'k':
485 break;
486
487
488
489
490
491 case 'l':
494 break;
495
496 case 'm':
499 break;
500
501 case 'M':
504 break;
505
506 case 'n':
509 break;
510
511
512 case 'p':
514 replace_val.str_val = "AM";
515 else
516 replace_val.str_val = "PM";
518 break;
519
520
521 case 'P':
523 replace_val.str_val = "am";
524 else
525 replace_val.str_val = "pm";
527 break;
528
529
530 case 'r':
532 q, pstr_len,
533 "%I:%M:%S %p");
534 if (i)
535 return i;
536 break;
537
538 case 'R':
540 q, pstr_len,
541 "%H:%M");
542 if (i)
543 return i;
544 break;
545
546 case 's':
549 break;
550
551 case 'S':
554 break;
555
556 case 't':
559 break;
560
561 case 'T':
563 q, pstr_len,
564 "%H:%M:%S");
565 if (i)
566 return i;
567 break;
568
569
570
571
572
573 case 'u':
575 if (replace_val.uint_val == 0)
578 break;
579
580 case 'U':
582 i = strftime(q, *pstr_len, "%U", tm);
583 if (i == 0)
584 return -1;
585 while (*q)
586 {
587 q++;
588 (*pstr_len)--;
589 }
592 break;
593
594
595
596
597
598 case 'V':
599 {
600
601 const char *fmt = "%V";
602
603 i = strftime(q, *pstr_len, fmt, tm);
604 if (i == 0)
605 return -1;
606 while (*q)
607 {
608 q++;
609 (*pstr_len)--;
610 }
612 }
613 break;
614
615
616
617
618
619 case 'w':
622 break;
623
624 case 'W':
626 i = strftime(q, *pstr_len, "%U", tm);
627 if (i == 0)
628 return -1;
629 while (*q)
630 {
631 q++;
632 (*pstr_len)--;
633 }
636 break;
637
638
639
640
641
642 case 'x':
643 {
644 const char *fmt = "%x";
645
646
648 i = strftime(q, *pstr_len, fmt, tm);
649 if (i == 0)
650 return -1;
651 while (*q)
652 {
653 q++;
654 (*pstr_len)--;
655 }
658 }
659 break;
660
661
662
663
664
665 case 'X':
667 i = strftime(q, *pstr_len, "%X", tm);
668 if (i == 0)
669 return -1;
670 while (*q)
671 {
672 q++;
673 (*pstr_len)--;
674 }
677 break;
678
679 case 'y':
682 break;
683
684 case 'Y':
687 break;
688
689 case 'z':
691 i = strftime(q, *pstr_len, "%z", tm);
692 if (i == 0)
693 return -1;
694 while (*q)
695 {
696 q++;
697 (*pstr_len)--;
698 }
701 break;
702
703 case 'Z':
705 i = strftime(q, *pstr_len, "%Z", tm);
706 if (i == 0)
707 return -1;
708 while (*q)
709 {
710 q++;
711 (*pstr_len)--;
712 }
715 break;
716
717 case '%':
720 break;
721 case '\0':
722
723
724
725
726
727 return -1;
728 default:
729
730
731
732
733 if (*pstr_len > 1)
734 {
735 *q = '%';
736 q++;
737 (*pstr_len)--;
738 if (*pstr_len > 1)
739 {
740 *q = *p;
741 q++;
742 (*pstr_len)--;
743 }
744 else
745 {
746 *q = '\0';
747 return -1;
748 }
749 *q = '\0';
750 }
751 else
752 return -1;
753 break;
754 }
756 if (i)
757 return i;
758 }
759 else
760 {
761 if (*pstr_len > 1)
762 {
763 *q = *p;
764 (*pstr_len)--;
765 q++;
766 *q = '\0';
767 }
768 else
769 return -1;
770 }
771 p++;
772 }
773 return 0;
774}
775
776
777int
779{
783 int dow;
784
788
790}
791
792int
794{
797 else
798 iv->time = (*ts1 - *ts2);
799
801
802 return 0;
803}
804
805int
807{
808 int year,
809 month,
810 day;
811 int hour,
812 minute,
813 second;
814 int tz;
815
816 int i;
817 char *mstr;
818 char *mfmt;
819
820 if (!fmt)
821 fmt = "%Y-%m-%d %H:%M:%S";
822 if (!fmt[0])
823 return 1;
824
827
828
829
830
831
832
833 year = -1;
834 month = -1;
835 day = -1;
836 hour = 0;
837 minute = -1;
838 second = -1;
839 tz = 0;
840
844 return i;
845}
846
847
848
849
850
851
852
853
854
855
856
857int
859{
861 *tout = *tin;
862 else
863 {
864 if (span->month != 0)
865 {
866 struct tm tt,
867 *tm = &tt;
869
871 return -1;
874 {
877 }
879 {
882 }
883
884
885
888
889
891 return -1;
892 }
893
894 *tin += span->time;
895 *tout = *tin;
896 }
897
898 return 0;
899}
900
901
902
903
904
905
906
907
908
909
910
911
912int
914{
916
919
921}
int ParseDateTime(const char *timestr, char *workbuf, size_t buflen, char **field, int *ftype, int maxfields, int *numfields)
void j2date(int jd, int *year, int *month, int *day)
void GetCurrentDateTime(struct pg_tm *tm)
void EncodeDateTime(struct pg_tm *tm, fsec_t fsec, bool print_tz, int tz, const char *tzn, int style, char *str)
const char *const months[]
int DecodeDateTime(char **field, int *ftype, int nf, int *dtype, struct pg_tm *tm, fsec_t *fsec, int *tzp, DateTimeErrorExtra *extra)
int date2j(int year, int month, int day)
void dt2time(Timestamp jd, int *hour, int *min, int *sec, fsec_t *fsec)
void GetEpochTime(struct pg_tm *tm)
Timestamp SetEpochTimestamp(void)
int tm2timestamp(struct pg_tm *tm, fsec_t fsec, int *tzp, Timestamp *result)
void EncodeSpecialTimestamp(Timestamp dt, char *str)
int timestamp2tm(Timestamp dt, int *tzp, struct pg_tm *tm, fsec_t *fsec, const char **tzn, pg_tz *attimezone)
#define TIMESTAMP_NOBEGIN(j)
#define IS_VALID_JULIAN(y, m, d)
#define IS_VALID_TIMESTAMP(t)
#define TIMESTAMP_IS_NOEND(j)
#define TIMESTAMP_IS_NOBEGIN(j)
#define TIMESTAMP_NOT_FINITE(j)
#define TIMESTAMP_NOEND(j)
int PGTYPEStimestamp_defmt_scan(char **str, char *fmt, timestamp *d, int *year, int *month, int *day, int *hour, int *minute, int *second, int *tz)
#define IS_VALID_UTIME(y, m, d)
char * pgtypes_date_months[]
char * pgtypes_date_weekdays_short[]
static bool pg_mul_s64_overflow(int64 a, int64 b, int64 *result)
static bool pg_add_s64_overflow(int64 a, int64 b, int64 *result)
char * pgtypes_strdup(const char *str)
int pgtypes_fmt_replace(union un_fmt_comb replace_val, int replace_type, char **output, int *pstr_len)
int PGTYPEStimestamp_sub_interval(timestamp *tin, interval *span, timestamp *tout)
timestamp PGTYPEStimestamp_from_asc(char *str, char **endptr)
static timestamp dt2local(timestamp dt, int tz)
int PGTYPEStimestamp_sub(timestamp *ts1, timestamp *ts2, interval *iv)
static int64 time2t(const int hour, const int min, const int sec, const fsec_t fsec)
int PGTYPEStimestamp_add_interval(timestamp *tin, interval *span, timestamp *tout)
char * PGTYPEStimestamp_to_asc(timestamp tstamp)
void PGTYPEStimestamp_current(timestamp *ts)
int PGTYPEStimestamp_fmt_asc(timestamp *ts, char *output, int str_len, const char *fmtstr)
int PGTYPEStimestamp_defmt_asc(const char *str, const char *fmt, timestamp *d)
static int dttofmtasc_replace(timestamp *ts, date dDate, int dow, struct tm *tm, char *output, int *pstr_len, const char *fmtstr)
date PGTYPESdate_from_timestamp(timestamp dt)
int PGTYPESdate_dayofweek(date dDate)
#define PGTYPES_TS_BAD_TIMESTAMP
#define PGTYPES_TS_ERR_EINFTIME
#define PGTYPES_TYPE_STRING_CONSTANT
#define PGTYPES_TYPE_NOTHING
#define PGTYPES_TYPE_UINT
#define PGTYPES_TYPE_CHAR
#define PGTYPES_TYPE_UINT_2_LS
#define PGTYPES_TYPE_UINT_2_LZ
#define PGTYPES_TYPE_INT64
#define PGTYPES_TYPE_UINT_3_LZ
static void fmtstr(const char *value, int leftjust, int minlen, int maxwidth, int pointflag, PrintfTarget *target)