]> pd.if.org Git - pdclib/blob - functions/time/strftime.c
Turned sprints into a helper macro, avoiding out-of-bounds array access in the process.
[pdclib] / functions / time / strftime.c
1 /* strftime( char * restrict, size_t, const char * restrict, const struct tm * restrict )
2
3    This file is part of the Public Domain C Library (PDCLib).
4    Permission is granted to use, modify, and / or redistribute at will.
5 */
6
7 #include <time.h>
8 #include <stdlib.h>
9 #include <locale.h>
10 #include <string.h>
11 #include <assert.h>
12
13 #ifndef REGTEST
14
15 /* TODO: Alternative representations / numerals not supported. Multibyte support missing. */
16
17 /* This implementation's code is highly repetitive, but I did not really
18    care for putting it into a number of macros / helper functions.
19 */
20
21 enum wstart_t
22 {
23     E_SUNDAY = 0,
24     E_MONDAY = 1
25 };
26
27 #include <stdio.h>
28
29 static int weeknr( const struct tm * timeptr, int wstart )
30 {
31     int wday = ( timeptr->tm_wday + 7 - wstart ) % 7;
32     div_t week = div( timeptr->tm_yday, 7 );
33     if ( week.rem >= wday )
34     {
35         ++week.quot;
36     }
37     return week.quot;
38 }
39
40 static int iso_week( const struct tm * timeptr )
41 {
42     /* calculations below rely on Sunday == 7 */
43     int wday = timeptr->tm_wday;
44     if ( wday == 0 )
45     {
46         wday = 7;
47     }
48     /* https://en.wikipedia.org/wiki/ISO_week_date */
49     int week = ( timeptr->tm_yday - wday + 11 ) / 7;
50     if ( week == 53 )
51     {
52         /* date *may* belong to the *next* year, if:
53            * it is 31.12. and Monday - Wednesday
54            * it is 30.12. and Monday - Tuesday
55            * it is 29.12. and Monday
56            We can safely assume December...
57         */
58         if ( ( timeptr->tm_yday - wday - _PDCLIB_is_leap( timeptr->tm_year ) ) > 360 )
59         {
60             week = 1;
61         }
62     }
63     else if ( week == 0 )
64     {
65         /* date *does* belong to *previous* year,
66            i.e. has week 52 *unless*...
67            * current year started on a Friday, or
68            * previous year is leap and this year
69              started on a Saturday.
70         */
71         int firstday = timeptr->tm_wday - ( timeptr->tm_yday % 7 );
72         if ( firstday < 0 )
73         {
74             firstday += 7;
75         }
76         if ( ( firstday == 5 ) || ( _PDCLIB_is_leap( timeptr->tm_year - 1 ) && firstday == 6 ) )
77         {
78             week = 53;
79         }
80         else
81         {
82             week = 52;
83         }
84     }
85     return week;
86 }
87
88 /* Assuming presence of s, rc, maxsize.
89    Checks index for valid range, target buffer for sufficient remaining
90    capacity, and copies the locale-specific string (or "?" if index out
91    of range). Returns with zero if buffer capacity insufficient.
92 */
93 #define SPRINTSTR( array, index, max ) \
94     { \
95         const char * str = "?"; \
96         if ( index >= 0 && index <= max ) \
97         { \
98             str = array[ index ]; \
99         } \
100         size_t len = strlen( str ); \
101         if ( rc < ( maxsize - len ) ) \
102         { \
103             strcpy( s + rc, str ); \
104             rc += len; \
105         } \
106         else \
107         { \
108             return 0; \
109         } \
110     }
111
112 size_t strftime( char * _PDCLIB_restrict s, size_t maxsize, const char * _PDCLIB_restrict format, const struct tm * _PDCLIB_restrict timeptr )
113 {
114     size_t rc = 0;
115
116     while ( rc < maxsize )
117     {
118         if ( *format != '%' )
119         {
120             if ( ( s[rc] = *format++ ) == '\0' )
121             {
122                 return rc;
123             }
124             else
125             {
126                 ++rc;
127             }
128         }
129         else
130         {
131             /* char flag = 0; */
132             switch ( *++format )
133             {
134                 case 'E':
135                 case 'O':
136                     /* flag = *format++; */
137                     break;
138                 default:
139                     /* EMPTY */
140                     break;
141             }
142             switch( *format++ )
143             {
144                 case 'a':
145                     {
146                         /* tm_wday abbreviated */
147                         SPRINTSTR( _PDCLIB_lconv.day_name_abbr, timeptr->tm_wday, 6 );
148                         break;
149                     }
150                 case 'A':
151                     {
152                         /* tm_wday full */
153                         SPRINTSTR( _PDCLIB_lconv.day_name_full, timeptr->tm_wday, 6 );
154                         break;
155                     }
156                 case 'b':
157                 case 'h':
158                     {
159                         /* tm_mon abbreviated */
160                         SPRINTSTR( _PDCLIB_lconv.month_name_abbr, timeptr->tm_mon, 11 );
161                         break;
162                     }
163                 case 'B':
164                     {
165                         /* tm_mon full */
166                         SPRINTSTR( _PDCLIB_lconv.month_name_full, timeptr->tm_mon, 11 );
167                         break;
168                     }
169                 case 'c':
170                     {
171                         /* locale's date / time representation, %a %b %e %T %Y for C locale */
172                         /* 'E' for locale's alternative representation */
173                         size_t count = strftime( s + rc, maxsize - rc, _PDCLIB_lconv.date_time_format, timeptr );
174                         if ( count == 0 )
175                         {
176                             return 0;
177                         }
178                         else
179                         {
180                             rc += count;
181                         }
182                         break;
183                     }
184                 case 'C':
185                     {
186                         /* tm_year divided by 100, truncated to decimal (00-99) */
187                         /* 'E' for base year (period) in locale's alternative representation */
188                         if ( rc < ( maxsize - 2 ) )
189                         {
190                             div_t period = div( ( ( timeptr->tm_year + 1900 ) / 100 ), 10 );
191                             s[rc++] = '0' + period.quot;
192                             s[rc++] = '0' + period.rem;
193                         }
194                         else
195                         {
196                             return 0;
197                         }
198                         break;
199                     }
200                 case 'd':
201                     {
202                         /* tm_mday as decimal (01-31) */
203                         /* 'O' for locale's alternative numeric symbols */
204                         if ( rc < ( maxsize - 2 ) )
205                         {
206                             div_t day = div( timeptr->tm_mday, 10 );
207                             s[rc++] = '0' + day.quot;
208                             s[rc++] = '0' + day.rem;
209                         }
210                         else
211                         {
212                             return 0;
213                         }
214                         break;
215                     }
216                 case 'D':
217                     {
218                         /* %m/%d/%y */
219                         size_t count = strftime( s + rc, maxsize - rc, "%m/%d/%y", timeptr );
220                         if ( count == 0 )
221                         {
222                             return 0;
223                         }
224                         else
225                         {
226                             rc += count;
227                         }
228                         break;
229                     }
230                 case 'e':
231                     {
232                         /* tm_mday as decimal ( 1-31) */
233                         /* 'O' for locale's alternative numeric symbols */
234                         if ( rc < ( maxsize - 2 ) )
235                         {
236                             div_t day = div( timeptr->tm_mday, 10 );
237                             s[rc++] = ( day.quot > 0 ) ? '0' + day.quot : ' ';
238                             s[rc++] = '0' + day.rem;
239                         }
240                         else
241                         {
242                             return 0;
243                         }
244                         break;
245                     }
246                 case 'F':
247                     {
248                         /* %Y-%m-%d */
249                         size_t count = strftime( s + rc, maxsize - rc, "%Y-%m-%d", timeptr );
250                         if ( count == 0 )
251                         {
252                             return 0;
253                         }
254                         else
255                         {
256                             rc += count;
257                         }
258                         break;
259                     }
260                 case 'g':
261                     {
262                         /* last 2 digits of the week-based year as decimal (00-99) */
263                         if ( rc < ( maxsize - 2 ) )
264                         {
265                             int week = iso_week( timeptr );
266                             int bias = 0;
267                             if ( week >= 52 && timeptr->tm_mon == 0 )
268                             {
269                                 --bias;
270                             }
271                             else if ( week == 1 && timeptr->tm_mon == 11 )
272                             {
273                                 ++bias;
274                             }
275                             div_t year = div( timeptr->tm_year % 100 + bias, 10 );
276                             s[rc++] = '0' + year.quot;
277                             s[rc++] = '0' + year.rem;
278                         }
279                         else
280                         {
281                             return 0;
282                         }
283                         break;
284                     }
285                 case 'G':
286                     {
287                         /* week-based year as decimal (e.g. 1997) */
288                         if ( rc < ( maxsize - 4 ) )
289                         {
290                             int week = iso_week( timeptr );
291                             int year = timeptr->tm_year + 1900;
292                             if ( week >= 52 && timeptr->tm_mon == 0 )
293                             {
294                                 --year;
295                             }
296                             else if ( week == 1 && timeptr->tm_mon == 11 )
297                             {
298                                 ++year;
299                             }
300                             for ( int i = 3; i >= 0; --i )
301                             {
302                                 div_t digit = div( year, 10 );
303                                 s[ rc + i ] = '0' + digit.rem;
304                                 year = digit.quot;
305                             }
306
307                             rc += 4;
308                         }
309                         else
310                         {
311                             return 0;
312                         }
313                         break;
314                     }
315                 case 'H':
316                     {
317                         /* tm_hour as 24h decimal (00-23) */
318                         /* 'O' for locale's alternative numeric symbols */
319                         if ( rc < ( maxsize - 2 ) )
320                         {
321                             div_t hour = div( timeptr->tm_hour, 10 );
322                             s[rc++] = '0' + hour.quot;
323                             s[rc++] = '0' + hour.rem;
324                         }
325                         else
326                         {
327                             return 0;
328                         }
329                         break;
330                     }
331                 case 'I':
332                     {
333                         /* tm_hour as 12h decimal (01-12) */
334                         /* 'O' for locale's alternative numeric symbols */
335                         if ( rc < ( maxsize - 2 ) )
336                         {
337                             div_t hour = div( ( timeptr->tm_hour + 11 ) % 12 + 1, 10 );
338                             s[rc++] = '0' + hour.quot;
339                             s[rc++] = '0' + hour.rem;
340                         }
341                         else
342                         {
343                             return 0;
344                         }
345                         break;
346                     }
347                 case 'j':
348                     {
349                         /* tm_yday as decimal (001-366) */
350                         if ( rc < ( maxsize - 3 ) )
351                         {
352                             div_t yday = div( timeptr->tm_yday + 1, 100 );
353                             s[rc++] = '0' + yday.quot;
354                             s[rc++] = '0' + yday.rem / 10;
355                             s[rc++] = '0' + yday.rem % 10;
356                         }
357                         else
358                         {
359                             return 0;
360                         }
361                         break;
362                     }
363                 case 'm':
364                     {
365                         /* tm_mon as decimal (01-12) */
366                         /* 'O' for locale's alternative numeric symbols */
367                         if ( rc < ( maxsize - 2 ) )
368                         {
369                             div_t mon = div( timeptr->tm_mon + 1, 10 );
370                             s[rc++] = '0' + mon.quot;
371                             s[rc++] = '0' + mon.rem;
372                         }
373                         else
374                         {
375                             return 0;
376                         }
377                         break;
378                     }
379                 case 'M':
380                     {
381                         /* tm_min as decimal (00-59) */
382                         /* 'O' for locale's alternative numeric symbols */
383                         if ( rc < ( maxsize - 2 ) )
384                         {
385                             div_t min = div( timeptr->tm_min, 10 );
386                             s[rc++] = '0' + min.quot;
387                             s[rc++] = '0' + min.rem;
388                         }
389                         else
390                         {
391                             return 0;
392                         }
393                         break;
394                     }
395                 case 'n':
396                     {
397                         /* newline */
398                         s[rc++] = '\n';
399                         break;
400                     }
401                 case 'p':
402                     {
403                         /* tm_hour locale's AM/PM designations */
404                         const char * designation = _PDCLIB_lconv.am_pm[ timeptr->tm_hour > 11 ];
405                         size_t len = strlen( designation );
406                         if ( rc < ( maxsize - len ) )
407                         {
408                             strcpy( s + rc, designation );
409                             rc += len;
410                         }
411                         else
412                         {
413                             return 0;
414                         }
415                         break;
416                     }
417                 case 'r':
418                     {
419                         /* tm_hour / tm_min / tm_sec as locale's 12-hour clock time, %I:%M:%S %p for C locale */
420                         size_t count = strftime( s + rc, maxsize - rc, _PDCLIB_lconv.time_format_12h, timeptr );
421                         if ( count == 0 )
422                         {
423                             return 0;
424                         }
425                         else
426                         {
427                             rc += count;
428                         }
429                         break;
430                     }
431                 case 'R':
432                     {
433                         /* %H:%M */
434                         size_t count = strftime( s + rc, maxsize - rc, "%H:%M", timeptr );
435                         if ( count == 0 )
436                         {
437                             return 0;
438                         }
439                         else
440                         {
441                             rc += count;
442                         }
443                         break;
444                     }
445                 case 'S':
446                     {
447                         /* tm_sec as decimal (00-60) */
448                         /* 'O' for locale's alternative numeric symbols */
449                         if ( rc < ( maxsize - 2 ) )
450                         {
451                             div_t sec = div( timeptr->tm_sec, 10 );
452                             s[rc++] = '0' + sec.quot;
453                             s[rc++] = '0' + sec.rem;
454                         }
455                         else
456                         {
457                             return 0;
458                         }
459                         break;
460                     }
461                 case 't':
462                     {
463                         /* tabulator */
464                         s[rc++] = '\t';
465                         break;
466                     }
467                 case 'T':
468                     {
469                         /* %H:%M:%S */
470                         size_t count = strftime( s + rc, maxsize - rc, "%H:%M:%S", timeptr );
471                         if ( count == 0 )
472                         {
473                             return 0;
474                         }
475                         else
476                         {
477                             rc += count;
478                         }
479                         break;
480                     }
481                 case 'u':
482                     {
483                         /* tm_wday as decimal (1-7) with Monday == 1 */
484                         /* 'O' for locale's alternative numeric symbols */
485                         s[rc++] = ( timeptr->tm_wday == 0 ) ? '7' : '0' + timeptr->tm_wday;
486                         break;
487                     }
488                 case 'U':
489                     {
490                         /* week number of the year (first Sunday as the first day of week 1) as decimal (00-53) */
491                         /* 'O' for locale's alternative numeric symbols */
492                         if ( rc < ( maxsize - 2 ) )
493                         {
494                             div_t week = div( weeknr( timeptr, E_SUNDAY ), 10 );
495                             s[rc++] = '0' + week.quot;
496                             s[rc++] = '0' + week.rem;
497                         }
498                         else
499                         {
500                             return 0;
501                         }
502                         break;
503                     }
504                 case 'V':
505                     {
506                         /* ISO week number as decimal (01-53) */
507                         /* 'O' for locale's alternative numeric symbols */
508                         if ( rc < ( maxsize - 2 ) )
509                         {
510                             div_t week = div( iso_week( timeptr ), 10 );
511                             s[rc++] = '0' + week.quot;
512                             s[rc++] = '0' + week.rem;
513                         }
514                         else
515                         {
516                             return 0;
517                         }
518                         break;
519                     }
520                 case 'w':
521                     {
522                         /* tm_wday as decimal number (0-6) with Sunday == 0 */
523                         /* 'O' for locale's alternative numeric symbols */
524                         s[rc++] = '0' + timeptr->tm_wday;
525                         break;
526                     }
527                 case 'W':
528                     {
529                         /* week number of the year (first Monday as the first day of week 1) as decimal (00-53) */
530                         /* 'O' for locale's alternative numeric symbols */
531                         if ( rc < ( maxsize - 2 ) )
532                         {
533                             div_t week = div( weeknr( timeptr, E_MONDAY ), 10 );
534                             s[rc++] = '0' + week.quot;
535                             s[rc++] = '0' + week.rem;
536                         }
537                         else
538                         {
539                             return 0;
540                         }
541                         break;
542                     }
543                 case 'x':
544                     {
545                         /* locale's date representation, %m/%d/%y for C locale */
546                         /* 'E' for locale's alternative representation */
547                         size_t count = strftime( s + rc, maxsize - rc, _PDCLIB_lconv.date_format, timeptr );
548                         if ( count == 0 )
549                         {
550                             return 0;
551                         }
552                         else
553                         {
554                             rc += count;
555                         }
556                         break;
557                     }
558                 case 'X':
559                     {
560                         /* locale's time representation, %T for C locale */
561                         /* 'E' for locale's alternative representation */
562                         size_t count = strftime( s + rc, maxsize - rc, _PDCLIB_lconv.time_format, timeptr );
563                         if ( count == 0 )
564                         {
565                             return 0;
566                         }
567                         else
568                         {
569                             rc += count;
570                         }
571                         break;
572                     }
573                 case 'y':
574                     {
575                         /* last 2 digits of tm_year as decimal (00-99) */
576                         /* 'E' for offset from %EC (year only) in locale's alternative representation */
577                         /* 'O' for locale's alternative numeric symbols */
578                         if ( rc < ( maxsize - 2 ) )
579                         {
580                             div_t year = div( ( timeptr->tm_year % 100 ), 10 );
581                             s[rc++] = '0' + year.quot;
582                             s[rc++] = '0' + year.rem;
583                         }
584                         else
585                         {
586                             return 0;
587                         }
588                         break;
589                     }
590                 case 'Y':
591                     {
592                         /* tm_year as decimal (e.g. 1997) */
593                         /* 'E' for locale's alternative representation */
594                         if ( rc < ( maxsize - 4 ) )
595                         {
596                             int year = timeptr->tm_year + 1900;
597
598                             for ( int i = 3; i >= 0; --i )
599                             {
600                                 div_t digit = div( year, 10 );
601                                 s[ rc + i ] = '0' + digit.rem;
602                                 year = digit.quot;
603                             }
604
605                             rc += 4;
606                         }
607                         else
608                         {
609                             return 0;
610                         }
611                         break;
612                     }
613                 case 'z':
614                     {
615                         /* tm_isdst / UTC offset in ISO8601 format (e.g. -0430 meaning 4 hours 30 minutes behind Greenwich), or no characters */
616                         /* TODO: 'z' */
617                         break;
618                     }
619                 case 'Z':
620                     {
621                         /* tm_isdst / locale's time zone name or abbreviation, or no characters */
622                         /* TODO: 'Z' */
623                         break;
624                     }
625                 case '%':
626                     {
627                         /* '%' character */
628                         s[rc++] = '%';
629                         break;
630                     }
631             }
632         }
633     }
634
635     return 0;
636 }
637
638 #endif
639
640 #ifdef TEST
641
642 #include "_PDCLIB_test.h"
643
644 #define MKTIME( tm, sec, min, hour, day, month, year, wday, yday ) tm.tm_sec = sec; tm.tm_min = min; tm.tm_hour = hour; tm.tm_mday = day; tm.tm_mon = month; tm.tm_year = year; tm.tm_wday = wday; tm.tm_yday = yday; tm.tm_isdst = -1;
645
646 /* Test data generated by reference mktime() / strftime(), listing:
647    * tm_year
648    * tm_wday
649    * tm_yday
650    * '%U' result
651    * '%V' result
652    * '%W' result
653 */
654 int data[1020][6] =
655 {
656 { 70, 4, 0, 0, 1, 0 },
657 { 70, 5, 1, 0, 1, 0 },
658 { 70, 6, 2, 0, 1, 0 },
659 { 70, 0, 3, 1, 1, 0 },
660 { 70, 1, 4, 1, 2, 1 },
661 { 70, 2, 5, 1, 2, 1 },
662 { 70, 3, 6, 1, 2, 1 },
663 { 70, 4, 357, 51, 52, 51 },
664 { 70, 5, 358, 51, 52, 51 },
665 { 70, 6, 359, 51, 52, 51 },
666 { 70, 0, 360, 52, 52, 51 },
667 { 70, 1, 361, 52, 53, 52 },
668 { 70, 2, 362, 52, 53, 52 },
669 { 70, 3, 363, 52, 53, 52 },
670 { 70, 4, 364, 52, 53, 52 },
671 { 71, 5, 0, 0, 53, 0 },
672 { 71, 6, 1, 0, 53, 0 },
673 { 71, 0, 2, 1, 53, 0 },
674 { 71, 1, 3, 1, 1, 1 },
675 { 71, 2, 4, 1, 1, 1 },
676 { 71, 3, 5, 1, 1, 1 },
677 { 71, 4, 6, 1, 1, 1 },
678 { 71, 5, 357, 51, 51, 51 },
679 { 71, 6, 358, 51, 51, 51 },
680 { 71, 0, 359, 52, 51, 51 },
681 { 71, 1, 360, 52, 52, 52 },
682 { 71, 2, 361, 52, 52, 52 },
683 { 71, 3, 362, 52, 52, 52 },
684 { 71, 4, 363, 52, 52, 52 },
685 { 71, 5, 364, 52, 52, 52 },
686 { 72, 6, 0, 0, 52, 0 },
687 { 72, 0, 1, 1, 52, 0 },
688 { 72, 1, 2, 1, 1, 1 },
689 { 72, 2, 3, 1, 1, 1 },
690 { 72, 3, 4, 1, 1, 1 },
691 { 72, 4, 5, 1, 1, 1 },
692 { 72, 5, 6, 1, 1, 1 },
693 { 72, 0, 358, 52, 51, 51 },
694 { 72, 1, 359, 52, 52, 52 },
695 { 72, 2, 360, 52, 52, 52 },
696 { 72, 3, 361, 52, 52, 52 },
697 { 72, 4, 362, 52, 52, 52 },
698 { 72, 5, 363, 52, 52, 52 },
699 { 72, 6, 364, 52, 52, 52 },
700 { 72, 0, 365, 53, 52, 52 },
701 { 73, 1, 0, 0, 1, 1 },
702 { 73, 2, 1, 0, 1, 1 },
703 { 73, 3, 2, 0, 1, 1 },
704 { 73, 4, 3, 0, 1, 1 },
705 { 73, 5, 4, 0, 1, 1 },
706 { 73, 6, 5, 0, 1, 1 },
707 { 73, 0, 6, 1, 1, 1 },
708 { 73, 1, 357, 51, 52, 52 },
709 { 73, 2, 358, 51, 52, 52 },
710 { 73, 3, 359, 51, 52, 52 },
711 { 73, 4, 360, 51, 52, 52 },
712 { 73, 5, 361, 51, 52, 52 },
713 { 73, 6, 362, 51, 52, 52 },
714 { 73, 0, 363, 52, 52, 52 },
715 { 73, 1, 364, 52, 1, 53 },
716 { 74, 2, 0, 0, 1, 0 },
717 { 74, 3, 1, 0, 1, 0 },
718 { 74, 4, 2, 0, 1, 0 },
719 { 74, 5, 3, 0, 1, 0 },
720 { 74, 6, 4, 0, 1, 0 },
721 { 74, 0, 5, 1, 1, 0 },
722 { 74, 1, 6, 1, 2, 1 },
723 { 74, 2, 357, 51, 52, 51 },
724 { 74, 3, 358, 51, 52, 51 },
725 { 74, 4, 359, 51, 52, 51 },
726 { 74, 5, 360, 51, 52, 51 },
727 { 74, 6, 361, 51, 52, 51 },
728 { 74, 0, 362, 52, 52, 51 },
729 { 74, 1, 363, 52, 1, 52 },
730 { 74, 2, 364, 52, 1, 52 },
731 { 75, 3, 0, 0, 1, 0 },
732 { 75, 4, 1, 0, 1, 0 },
733 { 75, 5, 2, 0, 1, 0 },
734 { 75, 6, 3, 0, 1, 0 },
735 { 75, 0, 4, 1, 1, 0 },
736 { 75, 1, 5, 1, 2, 1 },
737 { 75, 2, 6, 1, 2, 1 },
738 { 75, 3, 357, 51, 52, 51 },
739 { 75, 4, 358, 51, 52, 51 },
740 { 75, 5, 359, 51, 52, 51 },
741 { 75, 6, 360, 51, 52, 51 },
742 { 75, 0, 361, 52, 52, 51 },
743 { 75, 1, 362, 52, 1, 52 },
744 { 75, 2, 363, 52, 1, 52 },
745 { 75, 3, 364, 52, 1, 52 },
746 { 76, 4, 0, 0, 1, 0 },
747 { 76, 5, 1, 0, 1, 0 },
748 { 76, 6, 2, 0, 1, 0 },
749 { 76, 0, 3, 1, 1, 0 },
750 { 76, 1, 4, 1, 2, 1 },
751 { 76, 2, 5, 1, 2, 1 },
752 { 76, 3, 6, 1, 2, 1 },
753 { 76, 5, 358, 51, 52, 51 },
754 { 76, 6, 359, 51, 52, 51 },
755 { 76, 0, 360, 52, 52, 51 },
756 { 76, 1, 361, 52, 53, 52 },
757 { 76, 2, 362, 52, 53, 52 },
758 { 76, 3, 363, 52, 53, 52 },
759 { 76, 4, 364, 52, 53, 52 },
760 { 76, 5, 365, 52, 53, 52 },
761 { 77, 6, 0, 0, 53, 0 },
762 { 77, 0, 1, 1, 53, 0 },
763 { 77, 1, 2, 1, 1, 1 },
764 { 77, 2, 3, 1, 1, 1 },
765 { 77, 3, 4, 1, 1, 1 },
766 { 77, 4, 5, 1, 1, 1 },
767 { 77, 5, 6, 1, 1, 1 },
768 { 77, 6, 357, 51, 51, 51 },
769 { 77, 0, 358, 52, 51, 51 },
770 { 77, 1, 359, 52, 52, 52 },
771 { 77, 2, 360, 52, 52, 52 },
772 { 77, 3, 361, 52, 52, 52 },
773 { 77, 4, 362, 52, 52, 52 },
774 { 77, 5, 363, 52, 52, 52 },
775 { 77, 6, 364, 52, 52, 52 },
776 { 78, 0, 0, 1, 52, 0 },
777 { 78, 1, 1, 1, 1, 1 },
778 { 78, 2, 2, 1, 1, 1 },
779 { 78, 3, 3, 1, 1, 1 },
780 { 78, 4, 4, 1, 1, 1 },
781 { 78, 5, 5, 1, 1, 1 },
782 { 78, 6, 6, 1, 1, 1 },
783 { 78, 0, 357, 52, 51, 51 },
784 { 78, 1, 358, 52, 52, 52 },
785 { 78, 2, 359, 52, 52, 52 },
786 { 78, 3, 360, 52, 52, 52 },
787 { 78, 4, 361, 52, 52, 52 },
788 { 78, 5, 362, 52, 52, 52 },
789 { 78, 6, 363, 52, 52, 52 },
790 { 78, 0, 364, 53, 52, 52 },
791 { 79, 1, 0, 0, 1, 1 },
792 { 79, 2, 1, 0, 1, 1 },
793 { 79, 3, 2, 0, 1, 1 },
794 { 79, 4, 3, 0, 1, 1 },
795 { 79, 5, 4, 0, 1, 1 },
796 { 79, 6, 5, 0, 1, 1 },
797 { 79, 0, 6, 1, 1, 1 },
798 { 79, 1, 357, 51, 52, 52 },
799 { 79, 2, 358, 51, 52, 52 },
800 { 79, 3, 359, 51, 52, 52 },
801 { 79, 4, 360, 51, 52, 52 },
802 { 79, 5, 361, 51, 52, 52 },
803 { 79, 6, 362, 51, 52, 52 },
804 { 79, 0, 363, 52, 52, 52 },
805 { 79, 1, 364, 52, 1, 53 },
806 { 80, 2, 0, 0, 1, 0 },
807 { 80, 3, 1, 0, 1, 0 },
808 { 80, 4, 2, 0, 1, 0 },
809 { 80, 5, 3, 0, 1, 0 },
810 { 80, 6, 4, 0, 1, 0 },
811 { 80, 0, 5, 1, 1, 0 },
812 { 80, 1, 6, 1, 2, 1 },
813 { 80, 3, 358, 51, 52, 51 },
814 { 80, 4, 359, 51, 52, 51 },
815 { 80, 5, 360, 51, 52, 51 },
816 { 80, 6, 361, 51, 52, 51 },
817 { 80, 0, 362, 52, 52, 51 },
818 { 80, 1, 363, 52, 1, 52 },
819 { 80, 2, 364, 52, 1, 52 },
820 { 80, 3, 365, 52, 1, 52 },
821 { 81, 4, 0, 0, 1, 0 },
822 { 81, 5, 1, 0, 1, 0 },
823 { 81, 6, 2, 0, 1, 0 },
824 { 81, 0, 3, 1, 1, 0 },
825 { 81, 1, 4, 1, 2, 1 },
826 { 81, 2, 5, 1, 2, 1 },
827 { 81, 3, 6, 1, 2, 1 },
828 { 81, 4, 357, 51, 52, 51 },
829 { 81, 5, 358, 51, 52, 51 },
830 { 81, 6, 359, 51, 52, 51 },
831 { 81, 0, 360, 52, 52, 51 },
832 { 81, 1, 361, 52, 53, 52 },
833 { 81, 2, 362, 52, 53, 52 },
834 { 81, 3, 363, 52, 53, 52 },
835 { 81, 4, 364, 52, 53, 52 },
836 { 82, 5, 0, 0, 53, 0 },
837 { 82, 6, 1, 0, 53, 0 },
838 { 82, 0, 2, 1, 53, 0 },
839 { 82, 1, 3, 1, 1, 1 },
840 { 82, 2, 4, 1, 1, 1 },
841 { 82, 3, 5, 1, 1, 1 },
842 { 82, 4, 6, 1, 1, 1 },
843 { 82, 5, 357, 51, 51, 51 },
844 { 82, 6, 358, 51, 51, 51 },
845 { 82, 0, 359, 52, 51, 51 },
846 { 82, 1, 360, 52, 52, 52 },
847 { 82, 2, 361, 52, 52, 52 },
848 { 82, 3, 362, 52, 52, 52 },
849 { 82, 4, 363, 52, 52, 52 },
850 { 82, 5, 364, 52, 52, 52 },
851 { 83, 6, 0, 0, 52, 0 },
852 { 83, 0, 1, 1, 52, 0 },
853 { 83, 1, 2, 1, 1, 1 },
854 { 83, 2, 3, 1, 1, 1 },
855 { 83, 3, 4, 1, 1, 1 },
856 { 83, 4, 5, 1, 1, 1 },
857 { 83, 5, 6, 1, 1, 1 },
858 { 83, 6, 357, 51, 51, 51 },
859 { 83, 0, 358, 52, 51, 51 },
860 { 83, 1, 359, 52, 52, 52 },
861 { 83, 2, 360, 52, 52, 52 },
862 { 83, 3, 361, 52, 52, 52 },
863 { 83, 4, 362, 52, 52, 52 },
864 { 83, 5, 363, 52, 52, 52 },
865 { 83, 6, 364, 52, 52, 52 },
866 { 84, 0, 0, 1, 52, 0 },
867 { 84, 1, 1, 1, 1, 1 },
868 { 84, 2, 2, 1, 1, 1 },
869 { 84, 3, 3, 1, 1, 1 },
870 { 84, 4, 4, 1, 1, 1 },
871 { 84, 5, 5, 1, 1, 1 },
872 { 84, 6, 6, 1, 1, 1 },
873 { 84, 1, 358, 52, 52, 52 },
874 { 84, 2, 359, 52, 52, 52 },
875 { 84, 3, 360, 52, 52, 52 },
876 { 84, 4, 361, 52, 52, 52 },
877 { 84, 5, 362, 52, 52, 52 },
878 { 84, 6, 363, 52, 52, 52 },
879 { 84, 0, 364, 53, 52, 52 },
880 { 84, 1, 365, 53, 1, 53 },
881 { 85, 2, 0, 0, 1, 0 },
882 { 85, 3, 1, 0, 1, 0 },
883 { 85, 4, 2, 0, 1, 0 },
884 { 85, 5, 3, 0, 1, 0 },
885 { 85, 6, 4, 0, 1, 0 },
886 { 85, 0, 5, 1, 1, 0 },
887 { 85, 1, 6, 1, 2, 1 },
888 { 85, 2, 357, 51, 52, 51 },
889 { 85, 3, 358, 51, 52, 51 },
890 { 85, 4, 359, 51, 52, 51 },
891 { 85, 5, 360, 51, 52, 51 },
892 { 85, 6, 361, 51, 52, 51 },
893 { 85, 0, 362, 52, 52, 51 },
894 { 85, 1, 363, 52, 1, 52 },
895 { 85, 2, 364, 52, 1, 52 },
896 { 86, 3, 0, 0, 1, 0 },
897 { 86, 4, 1, 0, 1, 0 },
898 { 86, 5, 2, 0, 1, 0 },
899 { 86, 6, 3, 0, 1, 0 },
900 { 86, 0, 4, 1, 1, 0 },
901 { 86, 1, 5, 1, 2, 1 },
902 { 86, 2, 6, 1, 2, 1 },
903 { 86, 3, 357, 51, 52, 51 },
904 { 86, 4, 358, 51, 52, 51 },
905 { 86, 5, 359, 51, 52, 51 },
906 { 86, 6, 360, 51, 52, 51 },
907 { 86, 0, 361, 52, 52, 51 },
908 { 86, 1, 362, 52, 1, 52 },
909 { 86, 2, 363, 52, 1, 52 },
910 { 86, 3, 364, 52, 1, 52 },
911 { 87, 4, 0, 0, 1, 0 },
912 { 87, 5, 1, 0, 1, 0 },
913 { 87, 6, 2, 0, 1, 0 },
914 { 87, 0, 3, 1, 1, 0 },
915 { 87, 1, 4, 1, 2, 1 },
916 { 87, 2, 5, 1, 2, 1 },
917 { 87, 3, 6, 1, 2, 1 },
918 { 87, 4, 357, 51, 52, 51 },
919 { 87, 5, 358, 51, 52, 51 },
920 { 87, 6, 359, 51, 52, 51 },
921 { 87, 0, 360, 52, 52, 51 },
922 { 87, 1, 361, 52, 53, 52 },
923 { 87, 2, 362, 52, 53, 52 },
924 { 87, 3, 363, 52, 53, 52 },
925 { 87, 4, 364, 52, 53, 52 },
926 { 88, 5, 0, 0, 53, 0 },
927 { 88, 6, 1, 0, 53, 0 },
928 { 88, 0, 2, 1, 53, 0 },
929 { 88, 1, 3, 1, 1, 1 },
930 { 88, 2, 4, 1, 1, 1 },
931 { 88, 3, 5, 1, 1, 1 },
932 { 88, 4, 6, 1, 1, 1 },
933 { 88, 6, 358, 51, 51, 51 },
934 { 88, 0, 359, 52, 51, 51 },
935 { 88, 1, 360, 52, 52, 52 },
936 { 88, 2, 361, 52, 52, 52 },
937 { 88, 3, 362, 52, 52, 52 },
938 { 88, 4, 363, 52, 52, 52 },
939 { 88, 5, 364, 52, 52, 52 },
940 { 88, 6, 365, 52, 52, 52 },
941 { 89, 0, 0, 1, 52, 0 },
942 { 89, 1, 1, 1, 1, 1 },
943 { 89, 2, 2, 1, 1, 1 },
944 { 89, 3, 3, 1, 1, 1 },
945 { 89, 4, 4, 1, 1, 1 },
946 { 89, 5, 5, 1, 1, 1 },
947 { 89, 6, 6, 1, 1, 1 },
948 { 89, 0, 357, 52, 51, 51 },
949 { 89, 1, 358, 52, 52, 52 },
950 { 89, 2, 359, 52, 52, 52 },
951 { 89, 3, 360, 52, 52, 52 },
952 { 89, 4, 361, 52, 52, 52 },
953 { 89, 5, 362, 52, 52, 52 },
954 { 89, 6, 363, 52, 52, 52 },
955 { 89, 0, 364, 53, 52, 52 },
956 { 90, 1, 0, 0, 1, 1 },
957 { 90, 2, 1, 0, 1, 1 },
958 { 90, 3, 2, 0, 1, 1 },
959 { 90, 4, 3, 0, 1, 1 },
960 { 90, 5, 4, 0, 1, 1 },
961 { 90, 6, 5, 0, 1, 1 },
962 { 90, 0, 6, 1, 1, 1 },
963 { 90, 1, 357, 51, 52, 52 },
964 { 90, 2, 358, 51, 52, 52 },
965 { 90, 3, 359, 51, 52, 52 },
966 { 90, 4, 360, 51, 52, 52 },
967 { 90, 5, 361, 51, 52, 52 },
968 { 90, 6, 362, 51, 52, 52 },
969 { 90, 0, 363, 52, 52, 52 },
970 { 90, 1, 364, 52, 1, 53 },
971 { 91, 2, 0, 0, 1, 0 },
972 { 91, 3, 1, 0, 1, 0 },
973 { 91, 4, 2, 0, 1, 0 },
974 { 91, 5, 3, 0, 1, 0 },
975 { 91, 6, 4, 0, 1, 0 },
976 { 91, 0, 5, 1, 1, 0 },
977 { 91, 1, 6, 1, 2, 1 },
978 { 91, 2, 357, 51, 52, 51 },
979 { 91, 3, 358, 51, 52, 51 },
980 { 91, 4, 359, 51, 52, 51 },
981 { 91, 5, 360, 51, 52, 51 },
982 { 91, 6, 361, 51, 52, 51 },
983 { 91, 0, 362, 52, 52, 51 },
984 { 91, 1, 363, 52, 1, 52 },
985 { 91, 2, 364, 52, 1, 52 },
986 { 92, 3, 0, 0, 1, 0 },
987 { 92, 4, 1, 0, 1, 0 },
988 { 92, 5, 2, 0, 1, 0 },
989 { 92, 6, 3, 0, 1, 0 },
990 { 92, 0, 4, 1, 1, 0 },
991 { 92, 1, 5, 1, 2, 1 },
992 { 92, 2, 6, 1, 2, 1 },
993 { 92, 4, 358, 51, 52, 51 },
994 { 92, 5, 359, 51, 52, 51 },
995 { 92, 6, 360, 51, 52, 51 },
996 { 92, 0, 361, 52, 52, 51 },
997 { 92, 1, 362, 52, 53, 52 },
998 { 92, 2, 363, 52, 53, 52 },
999 { 92, 3, 364, 52, 53, 52 },
1000 { 92, 4, 365, 52, 53, 52 },
1001 { 93, 5, 0, 0, 53, 0 },
1002 { 93, 6, 1, 0, 53, 0 },
1003 { 93, 0, 2, 1, 53, 0 },
1004 { 93, 1, 3, 1, 1, 1 },
1005 { 93, 2, 4, 1, 1, 1 },
1006 { 93, 3, 5, 1, 1, 1 },
1007 { 93, 4, 6, 1, 1, 1 },
1008 { 93, 5, 357, 51, 51, 51 },
1009 { 93, 6, 358, 51, 51, 51 },
1010 { 93, 0, 359, 52, 51, 51 },
1011 { 93, 1, 360, 52, 52, 52 },
1012 { 93, 2, 361, 52, 52, 52 },
1013 { 93, 3, 362, 52, 52, 52 },
1014 { 93, 4, 363, 52, 52, 52 },
1015 { 93, 5, 364, 52, 52, 52 },
1016 { 94, 6, 0, 0, 52, 0 },
1017 { 94, 0, 1, 1, 52, 0 },
1018 { 94, 1, 2, 1, 1, 1 },
1019 { 94, 2, 3, 1, 1, 1 },
1020 { 94, 3, 4, 1, 1, 1 },
1021 { 94, 4, 5, 1, 1, 1 },
1022 { 94, 5, 6, 1, 1, 1 },
1023 { 94, 6, 357, 51, 51, 51 },
1024 { 94, 0, 358, 52, 51, 51 },
1025 { 94, 1, 359, 52, 52, 52 },
1026 { 94, 2, 360, 52, 52, 52 },
1027 { 94, 3, 361, 52, 52, 52 },
1028 { 94, 4, 362, 52, 52, 52 },
1029 { 94, 5, 363, 52, 52, 52 },
1030 { 94, 6, 364, 52, 52, 52 },
1031 { 95, 0, 0, 1, 52, 0 },
1032 { 95, 1, 1, 1, 1, 1 },
1033 { 95, 2, 2, 1, 1, 1 },
1034 { 95, 3, 3, 1, 1, 1 },
1035 { 95, 4, 4, 1, 1, 1 },
1036 { 95, 5, 5, 1, 1, 1 },
1037 { 95, 6, 6, 1, 1, 1 },
1038 { 95, 0, 357, 52, 51, 51 },
1039 { 95, 1, 358, 52, 52, 52 },
1040 { 95, 2, 359, 52, 52, 52 },
1041 { 95, 3, 360, 52, 52, 52 },
1042 { 95, 4, 361, 52, 52, 52 },
1043 { 95, 5, 362, 52, 52, 52 },
1044 { 95, 6, 363, 52, 52, 52 },
1045 { 95, 0, 364, 53, 52, 52 },
1046 { 96, 1, 0, 0, 1, 1 },
1047 { 96, 2, 1, 0, 1, 1 },
1048 { 96, 3, 2, 0, 1, 1 },
1049 { 96, 4, 3, 0, 1, 1 },
1050 { 96, 5, 4, 0, 1, 1 },
1051 { 96, 6, 5, 0, 1, 1 },
1052 { 96, 0, 6, 1, 1, 1 },
1053 { 96, 2, 358, 51, 52, 52 },
1054 { 96, 3, 359, 51, 52, 52 },
1055 { 96, 4, 360, 51, 52, 52 },
1056 { 96, 5, 361, 51, 52, 52 },
1057 { 96, 6, 362, 51, 52, 52 },
1058 { 96, 0, 363, 52, 52, 52 },
1059 { 96, 1, 364, 52, 1, 53 },
1060 { 96, 2, 365, 52, 1, 53 },
1061 { 97, 3, 0, 0, 1, 0 },
1062 { 97, 4, 1, 0, 1, 0 },
1063 { 97, 5, 2, 0, 1, 0 },
1064 { 97, 6, 3, 0, 1, 0 },
1065 { 97, 0, 4, 1, 1, 0 },
1066 { 97, 1, 5, 1, 2, 1 },
1067 { 97, 2, 6, 1, 2, 1 },
1068 { 97, 3, 357, 51, 52, 51 },
1069 { 97, 4, 358, 51, 52, 51 },
1070 { 97, 5, 359, 51, 52, 51 },
1071 { 97, 6, 360, 51, 52, 51 },
1072 { 97, 0, 361, 52, 52, 51 },
1073 { 97, 1, 362, 52, 1, 52 },
1074 { 97, 2, 363, 52, 1, 52 },
1075 { 97, 3, 364, 52, 1, 52 },
1076 { 98, 4, 0, 0, 1, 0 },
1077 { 98, 5, 1, 0, 1, 0 },
1078 { 98, 6, 2, 0, 1, 0 },
1079 { 98, 0, 3, 1, 1, 0 },
1080 { 98, 1, 4, 1, 2, 1 },
1081 { 98, 2, 5, 1, 2, 1 },
1082 { 98, 3, 6, 1, 2, 1 },
1083 { 98, 4, 357, 51, 52, 51 },
1084 { 98, 5, 358, 51, 52, 51 },
1085 { 98, 6, 359, 51, 52, 51 },
1086 { 98, 0, 360, 52, 52, 51 },
1087 { 98, 1, 361, 52, 53, 52 },
1088 { 98, 2, 362, 52, 53, 52 },
1089 { 98, 3, 363, 52, 53, 52 },
1090 { 98, 4, 364, 52, 53, 52 },
1091 { 99, 5, 0, 0, 53, 0 },
1092 { 99, 6, 1, 0, 53, 0 },
1093 { 99, 0, 2, 1, 53, 0 },
1094 { 99, 1, 3, 1, 1, 1 },
1095 { 99, 2, 4, 1, 1, 1 },
1096 { 99, 3, 5, 1, 1, 1 },
1097 { 99, 4, 6, 1, 1, 1 },
1098 { 99, 5, 357, 51, 51, 51 },
1099 { 99, 6, 358, 51, 51, 51 },
1100 { 99, 0, 359, 52, 51, 51 },
1101 { 99, 1, 360, 52, 52, 52 },
1102 { 99, 2, 361, 52, 52, 52 },
1103 { 99, 3, 362, 52, 52, 52 },
1104 { 99, 4, 363, 52, 52, 52 },
1105 { 99, 5, 364, 52, 52, 52 },
1106 { 100, 6, 0, 0, 52, 0 },
1107 { 100, 0, 1, 1, 52, 0 },
1108 { 100, 1, 2, 1, 1, 1 },
1109 { 100, 2, 3, 1, 1, 1 },
1110 { 100, 3, 4, 1, 1, 1 },
1111 { 100, 4, 5, 1, 1, 1 },
1112 { 100, 5, 6, 1, 1, 1 },
1113 { 100, 0, 358, 52, 51, 51 },
1114 { 100, 1, 359, 52, 52, 52 },
1115 { 100, 2, 360, 52, 52, 52 },
1116 { 100, 3, 361, 52, 52, 52 },
1117 { 100, 4, 362, 52, 52, 52 },
1118 { 100, 5, 363, 52, 52, 52 },
1119 { 100, 6, 364, 52, 52, 52 },
1120 { 100, 0, 365, 53, 52, 52 },
1121 { 101, 1, 0, 0, 1, 1 },
1122 { 101, 2, 1, 0, 1, 1 },
1123 { 101, 3, 2, 0, 1, 1 },
1124 { 101, 4, 3, 0, 1, 1 },
1125 { 101, 5, 4, 0, 1, 1 },
1126 { 101, 6, 5, 0, 1, 1 },
1127 { 101, 0, 6, 1, 1, 1 },
1128 { 101, 1, 357, 51, 52, 52 },
1129 { 101, 2, 358, 51, 52, 52 },
1130 { 101, 3, 359, 51, 52, 52 },
1131 { 101, 4, 360, 51, 52, 52 },
1132 { 101, 5, 361, 51, 52, 52 },
1133 { 101, 6, 362, 51, 52, 52 },
1134 { 101, 0, 363, 52, 52, 52 },
1135 { 101, 1, 364, 52, 1, 53 },
1136 { 102, 2, 0, 0, 1, 0 },
1137 { 102, 3, 1, 0, 1, 0 },
1138 { 102, 4, 2, 0, 1, 0 },
1139 { 102, 5, 3, 0, 1, 0 },
1140 { 102, 6, 4, 0, 1, 0 },
1141 { 102, 0, 5, 1, 1, 0 },
1142 { 102, 1, 6, 1, 2, 1 },
1143 { 102, 2, 357, 51, 52, 51 },
1144 { 102, 3, 358, 51, 52, 51 },
1145 { 102, 4, 359, 51, 52, 51 },
1146 { 102, 5, 360, 51, 52, 51 },
1147 { 102, 6, 361, 51, 52, 51 },
1148 { 102, 0, 362, 52, 52, 51 },
1149 { 102, 1, 363, 52, 1, 52 },
1150 { 102, 2, 364, 52, 1, 52 },
1151 { 103, 3, 0, 0, 1, 0 },
1152 { 103, 4, 1, 0, 1, 0 },
1153 { 103, 5, 2, 0, 1, 0 },
1154 { 103, 6, 3, 0, 1, 0 },
1155 { 103, 0, 4, 1, 1, 0 },
1156 { 103, 1, 5, 1, 2, 1 },
1157 { 103, 2, 6, 1, 2, 1 },
1158 { 103, 3, 357, 51, 52, 51 },
1159 { 103, 4, 358, 51, 52, 51 },
1160 { 103, 5, 359, 51, 52, 51 },
1161 { 103, 6, 360, 51, 52, 51 },
1162 { 103, 0, 361, 52, 52, 51 },
1163 { 103, 1, 362, 52, 1, 52 },
1164 { 103, 2, 363, 52, 1, 52 },
1165 { 103, 3, 364, 52, 1, 52 },
1166 { 104, 4, 0, 0, 1, 0 },
1167 { 104, 5, 1, 0, 1, 0 },
1168 { 104, 6, 2, 0, 1, 0 },
1169 { 104, 0, 3, 1, 1, 0 },
1170 { 104, 1, 4, 1, 2, 1 },
1171 { 104, 2, 5, 1, 2, 1 },
1172 { 104, 3, 6, 1, 2, 1 },
1173 { 104, 5, 358, 51, 52, 51 },
1174 { 104, 6, 359, 51, 52, 51 },
1175 { 104, 0, 360, 52, 52, 51 },
1176 { 104, 1, 361, 52, 53, 52 },
1177 { 104, 2, 362, 52, 53, 52 },
1178 { 104, 3, 363, 52, 53, 52 },
1179 { 104, 4, 364, 52, 53, 52 },
1180 { 104, 5, 365, 52, 53, 52 },
1181 { 105, 6, 0, 0, 53, 0 },
1182 { 105, 0, 1, 1, 53, 0 },
1183 { 105, 1, 2, 1, 1, 1 },
1184 { 105, 2, 3, 1, 1, 1 },
1185 { 105, 3, 4, 1, 1, 1 },
1186 { 105, 4, 5, 1, 1, 1 },
1187 { 105, 5, 6, 1, 1, 1 },
1188 { 105, 6, 357, 51, 51, 51 },
1189 { 105, 0, 358, 52, 51, 51 },
1190 { 105, 1, 359, 52, 52, 52 },
1191 { 105, 2, 360, 52, 52, 52 },
1192 { 105, 3, 361, 52, 52, 52 },
1193 { 105, 4, 362, 52, 52, 52 },
1194 { 105, 5, 363, 52, 52, 52 },
1195 { 105, 6, 364, 52, 52, 52 },
1196 { 106, 0, 0, 1, 52, 0 },
1197 { 106, 1, 1, 1, 1, 1 },
1198 { 106, 2, 2, 1, 1, 1 },
1199 { 106, 3, 3, 1, 1, 1 },
1200 { 106, 4, 4, 1, 1, 1 },
1201 { 106, 5, 5, 1, 1, 1 },
1202 { 106, 6, 6, 1, 1, 1 },
1203 { 106, 0, 357, 52, 51, 51 },
1204 { 106, 1, 358, 52, 52, 52 },
1205 { 106, 2, 359, 52, 52, 52 },
1206 { 106, 3, 360, 52, 52, 52 },
1207 { 106, 4, 361, 52, 52, 52 },
1208 { 106, 5, 362, 52, 52, 52 },
1209 { 106, 6, 363, 52, 52, 52 },
1210 { 106, 0, 364, 53, 52, 52 },
1211 { 107, 1, 0, 0, 1, 1 },
1212 { 107, 2, 1, 0, 1, 1 },
1213 { 107, 3, 2, 0, 1, 1 },
1214 { 107, 4, 3, 0, 1, 1 },
1215 { 107, 5, 4, 0, 1, 1 },
1216 { 107, 6, 5, 0, 1, 1 },
1217 { 107, 0, 6, 1, 1, 1 },
1218 { 107, 1, 357, 51, 52, 52 },
1219 { 107, 2, 358, 51, 52, 52 },
1220 { 107, 3, 359, 51, 52, 52 },
1221 { 107, 4, 360, 51, 52, 52 },
1222 { 107, 5, 361, 51, 52, 52 },
1223 { 107, 6, 362, 51, 52, 52 },
1224 { 107, 0, 363, 52, 52, 52 },
1225 { 107, 1, 364, 52, 1, 53 },
1226 { 108, 2, 0, 0, 1, 0 },
1227 { 108, 3, 1, 0, 1, 0 },
1228 { 108, 4, 2, 0, 1, 0 },
1229 { 108, 5, 3, 0, 1, 0 },
1230 { 108, 6, 4, 0, 1, 0 },
1231 { 108, 0, 5, 1, 1, 0 },
1232 { 108, 1, 6, 1, 2, 1 },
1233 { 108, 3, 358, 51, 52, 51 },
1234 { 108, 4, 359, 51, 52, 51 },
1235 { 108, 5, 360, 51, 52, 51 },
1236 { 108, 6, 361, 51, 52, 51 },
1237 { 108, 0, 362, 52, 52, 51 },
1238 { 108, 1, 363, 52, 1, 52 },
1239 { 108, 2, 364, 52, 1, 52 },
1240 { 108, 3, 365, 52, 1, 52 },
1241 { 109, 4, 0, 0, 1, 0 },
1242 { 109, 5, 1, 0, 1, 0 },
1243 { 109, 6, 2, 0, 1, 0 },
1244 { 109, 0, 3, 1, 1, 0 },
1245 { 109, 1, 4, 1, 2, 1 },
1246 { 109, 2, 5, 1, 2, 1 },
1247 { 109, 3, 6, 1, 2, 1 },
1248 { 109, 4, 357, 51, 52, 51 },
1249 { 109, 5, 358, 51, 52, 51 },
1250 { 109, 6, 359, 51, 52, 51 },
1251 { 109, 0, 360, 52, 52, 51 },
1252 { 109, 1, 361, 52, 53, 52 },
1253 { 109, 2, 362, 52, 53, 52 },
1254 { 109, 3, 363, 52, 53, 52 },
1255 { 109, 4, 364, 52, 53, 52 },
1256 { 110, 5, 0, 0, 53, 0 },
1257 { 110, 6, 1, 0, 53, 0 },
1258 { 110, 0, 2, 1, 53, 0 },
1259 { 110, 1, 3, 1, 1, 1 },
1260 { 110, 2, 4, 1, 1, 1 },
1261 { 110, 3, 5, 1, 1, 1 },
1262 { 110, 4, 6, 1, 1, 1 },
1263 { 110, 5, 357, 51, 51, 51 },
1264 { 110, 6, 358, 51, 51, 51 },
1265 { 110, 0, 359, 52, 51, 51 },
1266 { 110, 1, 360, 52, 52, 52 },
1267 { 110, 2, 361, 52, 52, 52 },
1268 { 110, 3, 362, 52, 52, 52 },
1269 { 110, 4, 363, 52, 52, 52 },
1270 { 110, 5, 364, 52, 52, 52 },
1271 { 111, 6, 0, 0, 52, 0 },
1272 { 111, 0, 1, 1, 52, 0 },
1273 { 111, 1, 2, 1, 1, 1 },
1274 { 111, 2, 3, 1, 1, 1 },
1275 { 111, 3, 4, 1, 1, 1 },
1276 { 111, 4, 5, 1, 1, 1 },
1277 { 111, 5, 6, 1, 1, 1 },
1278 { 111, 6, 357, 51, 51, 51 },
1279 { 111, 0, 358, 52, 51, 51 },
1280 { 111, 1, 359, 52, 52, 52 },
1281 { 111, 2, 360, 52, 52, 52 },
1282 { 111, 3, 361, 52, 52, 52 },
1283 { 111, 4, 362, 52, 52, 52 },
1284 { 111, 5, 363, 52, 52, 52 },
1285 { 111, 6, 364, 52, 52, 52 },
1286 { 112, 0, 0, 1, 52, 0 },
1287 { 112, 1, 1, 1, 1, 1 },
1288 { 112, 2, 2, 1, 1, 1 },
1289 { 112, 3, 3, 1, 1, 1 },
1290 { 112, 4, 4, 1, 1, 1 },
1291 { 112, 5, 5, 1, 1, 1 },
1292 { 112, 6, 6, 1, 1, 1 },
1293 { 112, 1, 358, 52, 52, 52 },
1294 { 112, 2, 359, 52, 52, 52 },
1295 { 112, 3, 360, 52, 52, 52 },
1296 { 112, 4, 361, 52, 52, 52 },
1297 { 112, 5, 362, 52, 52, 52 },
1298 { 112, 6, 363, 52, 52, 52 },
1299 { 112, 0, 364, 53, 52, 52 },
1300 { 112, 1, 365, 53, 1, 53 },
1301 { 113, 2, 0, 0, 1, 0 },
1302 { 113, 3, 1, 0, 1, 0 },
1303 { 113, 4, 2, 0, 1, 0 },
1304 { 113, 5, 3, 0, 1, 0 },
1305 { 113, 6, 4, 0, 1, 0 },
1306 { 113, 0, 5, 1, 1, 0 },
1307 { 113, 1, 6, 1, 2, 1 },
1308 { 113, 2, 357, 51, 52, 51 },
1309 { 113, 3, 358, 51, 52, 51 },
1310 { 113, 4, 359, 51, 52, 51 },
1311 { 113, 5, 360, 51, 52, 51 },
1312 { 113, 6, 361, 51, 52, 51 },
1313 { 113, 0, 362, 52, 52, 51 },
1314 { 113, 1, 363, 52, 1, 52 },
1315 { 113, 2, 364, 52, 1, 52 },
1316 { 114, 3, 0, 0, 1, 0 },
1317 { 114, 4, 1, 0, 1, 0 },
1318 { 114, 5, 2, 0, 1, 0 },
1319 { 114, 6, 3, 0, 1, 0 },
1320 { 114, 0, 4, 1, 1, 0 },
1321 { 114, 1, 5, 1, 2, 1 },
1322 { 114, 2, 6, 1, 2, 1 },
1323 { 114, 3, 357, 51, 52, 51 },
1324 { 114, 4, 358, 51, 52, 51 },
1325 { 114, 5, 359, 51, 52, 51 },
1326 { 114, 6, 360, 51, 52, 51 },
1327 { 114, 0, 361, 52, 52, 51 },
1328 { 114, 1, 362, 52, 1, 52 },
1329 { 114, 2, 363, 52, 1, 52 },
1330 { 114, 3, 364, 52, 1, 52 },
1331 { 115, 4, 0, 0, 1, 0 },
1332 { 115, 5, 1, 0, 1, 0 },
1333 { 115, 6, 2, 0, 1, 0 },
1334 { 115, 0, 3, 1, 1, 0 },
1335 { 115, 1, 4, 1, 2, 1 },
1336 { 115, 2, 5, 1, 2, 1 },
1337 { 115, 3, 6, 1, 2, 1 },
1338 { 115, 4, 357, 51, 52, 51 },
1339 { 115, 5, 358, 51, 52, 51 },
1340 { 115, 6, 359, 51, 52, 51 },
1341 { 115, 0, 360, 52, 52, 51 },
1342 { 115, 1, 361, 52, 53, 52 },
1343 { 115, 2, 362, 52, 53, 52 },
1344 { 115, 3, 363, 52, 53, 52 },
1345 { 115, 4, 364, 52, 53, 52 },
1346 { 116, 5, 0, 0, 53, 0 },
1347 { 116, 6, 1, 0, 53, 0 },
1348 { 116, 0, 2, 1, 53, 0 },
1349 { 116, 1, 3, 1, 1, 1 },
1350 { 116, 2, 4, 1, 1, 1 },
1351 { 116, 3, 5, 1, 1, 1 },
1352 { 116, 4, 6, 1, 1, 1 },
1353 { 116, 6, 358, 51, 51, 51 },
1354 { 116, 0, 359, 52, 51, 51 },
1355 { 116, 1, 360, 52, 52, 52 },
1356 { 116, 2, 361, 52, 52, 52 },
1357 { 116, 3, 362, 52, 52, 52 },
1358 { 116, 4, 363, 52, 52, 52 },
1359 { 116, 5, 364, 52, 52, 52 },
1360 { 116, 6, 365, 52, 52, 52 },
1361 { 117, 0, 0, 1, 52, 0 },
1362 { 117, 1, 1, 1, 1, 1 },
1363 { 117, 2, 2, 1, 1, 1 },
1364 { 117, 3, 3, 1, 1, 1 },
1365 { 117, 4, 4, 1, 1, 1 },
1366 { 117, 5, 5, 1, 1, 1 },
1367 { 117, 6, 6, 1, 1, 1 },
1368 { 117, 0, 357, 52, 51, 51 },
1369 { 117, 1, 358, 52, 52, 52 },
1370 { 117, 2, 359, 52, 52, 52 },
1371 { 117, 3, 360, 52, 52, 52 },
1372 { 117, 4, 361, 52, 52, 52 },
1373 { 117, 5, 362, 52, 52, 52 },
1374 { 117, 6, 363, 52, 52, 52 },
1375 { 117, 0, 364, 53, 52, 52 },
1376 { 118, 1, 0, 0, 1, 1 },
1377 { 118, 2, 1, 0, 1, 1 },
1378 { 118, 3, 2, 0, 1, 1 },
1379 { 118, 4, 3, 0, 1, 1 },
1380 { 118, 5, 4, 0, 1, 1 },
1381 { 118, 6, 5, 0, 1, 1 },
1382 { 118, 0, 6, 1, 1, 1 },
1383 { 118, 1, 357, 51, 52, 52 },
1384 { 118, 2, 358, 51, 52, 52 },
1385 { 118, 3, 359, 51, 52, 52 },
1386 { 118, 4, 360, 51, 52, 52 },
1387 { 118, 5, 361, 51, 52, 52 },
1388 { 118, 6, 362, 51, 52, 52 },
1389 { 118, 0, 363, 52, 52, 52 },
1390 { 118, 1, 364, 52, 1, 53 },
1391 { 119, 2, 0, 0, 1, 0 },
1392 { 119, 3, 1, 0, 1, 0 },
1393 { 119, 4, 2, 0, 1, 0 },
1394 { 119, 5, 3, 0, 1, 0 },
1395 { 119, 6, 4, 0, 1, 0 },
1396 { 119, 0, 5, 1, 1, 0 },
1397 { 119, 1, 6, 1, 2, 1 },
1398 { 119, 2, 357, 51, 52, 51 },
1399 { 119, 3, 358, 51, 52, 51 },
1400 { 119, 4, 359, 51, 52, 51 },
1401 { 119, 5, 360, 51, 52, 51 },
1402 { 119, 6, 361, 51, 52, 51 },
1403 { 119, 0, 362, 52, 52, 51 },
1404 { 119, 1, 363, 52, 1, 52 },
1405 { 119, 2, 364, 52, 1, 52 },
1406 { 120, 3, 0, 0, 1, 0 },
1407 { 120, 4, 1, 0, 1, 0 },
1408 { 120, 5, 2, 0, 1, 0 },
1409 { 120, 6, 3, 0, 1, 0 },
1410 { 120, 0, 4, 1, 1, 0 },
1411 { 120, 1, 5, 1, 2, 1 },
1412 { 120, 2, 6, 1, 2, 1 },
1413 { 120, 4, 358, 51, 52, 51 },
1414 { 120, 5, 359, 51, 52, 51 },
1415 { 120, 6, 360, 51, 52, 51 },
1416 { 120, 0, 361, 52, 52, 51 },
1417 { 120, 1, 362, 52, 53, 52 },
1418 { 120, 2, 363, 52, 53, 52 },
1419 { 120, 3, 364, 52, 53, 52 },
1420 { 120, 4, 365, 52, 53, 52 },
1421 { 121, 5, 0, 0, 53, 0 },
1422 { 121, 6, 1, 0, 53, 0 },
1423 { 121, 0, 2, 1, 53, 0 },
1424 { 121, 1, 3, 1, 1, 1 },
1425 { 121, 2, 4, 1, 1, 1 },
1426 { 121, 3, 5, 1, 1, 1 },
1427 { 121, 4, 6, 1, 1, 1 },
1428 { 121, 5, 357, 51, 51, 51 },
1429 { 121, 6, 358, 51, 51, 51 },
1430 { 121, 0, 359, 52, 51, 51 },
1431 { 121, 1, 360, 52, 52, 52 },
1432 { 121, 2, 361, 52, 52, 52 },
1433 { 121, 3, 362, 52, 52, 52 },
1434 { 121, 4, 363, 52, 52, 52 },
1435 { 121, 5, 364, 52, 52, 52 },
1436 { 122, 6, 0, 0, 52, 0 },
1437 { 122, 0, 1, 1, 52, 0 },
1438 { 122, 1, 2, 1, 1, 1 },
1439 { 122, 2, 3, 1, 1, 1 },
1440 { 122, 3, 4, 1, 1, 1 },
1441 { 122, 4, 5, 1, 1, 1 },
1442 { 122, 5, 6, 1, 1, 1 },
1443 { 122, 6, 357, 51, 51, 51 },
1444 { 122, 0, 358, 52, 51, 51 },
1445 { 122, 1, 359, 52, 52, 52 },
1446 { 122, 2, 360, 52, 52, 52 },
1447 { 122, 3, 361, 52, 52, 52 },
1448 { 122, 4, 362, 52, 52, 52 },
1449 { 122, 5, 363, 52, 52, 52 },
1450 { 122, 6, 364, 52, 52, 52 },
1451 { 123, 0, 0, 1, 52, 0 },
1452 { 123, 1, 1, 1, 1, 1 },
1453 { 123, 2, 2, 1, 1, 1 },
1454 { 123, 3, 3, 1, 1, 1 },
1455 { 123, 4, 4, 1, 1, 1 },
1456 { 123, 5, 5, 1, 1, 1 },
1457 { 123, 6, 6, 1, 1, 1 },
1458 { 123, 0, 357, 52, 51, 51 },
1459 { 123, 1, 358, 52, 52, 52 },
1460 { 123, 2, 359, 52, 52, 52 },
1461 { 123, 3, 360, 52, 52, 52 },
1462 { 123, 4, 361, 52, 52, 52 },
1463 { 123, 5, 362, 52, 52, 52 },
1464 { 123, 6, 363, 52, 52, 52 },
1465 { 123, 0, 364, 53, 52, 52 },
1466 { 124, 1, 0, 0, 1, 1 },
1467 { 124, 2, 1, 0, 1, 1 },
1468 { 124, 3, 2, 0, 1, 1 },
1469 { 124, 4, 3, 0, 1, 1 },
1470 { 124, 5, 4, 0, 1, 1 },
1471 { 124, 6, 5, 0, 1, 1 },
1472 { 124, 0, 6, 1, 1, 1 },
1473 { 124, 2, 358, 51, 52, 52 },
1474 { 124, 3, 359, 51, 52, 52 },
1475 { 124, 4, 360, 51, 52, 52 },
1476 { 124, 5, 361, 51, 52, 52 },
1477 { 124, 6, 362, 51, 52, 52 },
1478 { 124, 0, 363, 52, 52, 52 },
1479 { 124, 1, 364, 52, 1, 53 },
1480 { 124, 2, 365, 52, 1, 53 },
1481 { 125, 3, 0, 0, 1, 0 },
1482 { 125, 4, 1, 0, 1, 0 },
1483 { 125, 5, 2, 0, 1, 0 },
1484 { 125, 6, 3, 0, 1, 0 },
1485 { 125, 0, 4, 1, 1, 0 },
1486 { 125, 1, 5, 1, 2, 1 },
1487 { 125, 2, 6, 1, 2, 1 },
1488 { 125, 3, 357, 51, 52, 51 },
1489 { 125, 4, 358, 51, 52, 51 },
1490 { 125, 5, 359, 51, 52, 51 },
1491 { 125, 6, 360, 51, 52, 51 },
1492 { 125, 0, 361, 52, 52, 51 },
1493 { 125, 1, 362, 52, 1, 52 },
1494 { 125, 2, 363, 52, 1, 52 },
1495 { 125, 3, 364, 52, 1, 52 },
1496 { 126, 4, 0, 0, 1, 0 },
1497 { 126, 5, 1, 0, 1, 0 },
1498 { 126, 6, 2, 0, 1, 0 },
1499 { 126, 0, 3, 1, 1, 0 },
1500 { 126, 1, 4, 1, 2, 1 },
1501 { 126, 2, 5, 1, 2, 1 },
1502 { 126, 3, 6, 1, 2, 1 },
1503 { 126, 4, 357, 51, 52, 51 },
1504 { 126, 5, 358, 51, 52, 51 },
1505 { 126, 6, 359, 51, 52, 51 },
1506 { 126, 0, 360, 52, 52, 51 },
1507 { 126, 1, 361, 52, 53, 52 },
1508 { 126, 2, 362, 52, 53, 52 },
1509 { 126, 3, 363, 52, 53, 52 },
1510 { 126, 4, 364, 52, 53, 52 },
1511 { 127, 5, 0, 0, 53, 0 },
1512 { 127, 6, 1, 0, 53, 0 },
1513 { 127, 0, 2, 1, 53, 0 },
1514 { 127, 1, 3, 1, 1, 1 },
1515 { 127, 2, 4, 1, 1, 1 },
1516 { 127, 3, 5, 1, 1, 1 },
1517 { 127, 4, 6, 1, 1, 1 },
1518 { 127, 5, 357, 51, 51, 51 },
1519 { 127, 6, 358, 51, 51, 51 },
1520 { 127, 0, 359, 52, 51, 51 },
1521 { 127, 1, 360, 52, 52, 52 },
1522 { 127, 2, 361, 52, 52, 52 },
1523 { 127, 3, 362, 52, 52, 52 },
1524 { 127, 4, 363, 52, 52, 52 },
1525 { 127, 5, 364, 52, 52, 52 },
1526 { 128, 6, 0, 0, 52, 0 },
1527 { 128, 0, 1, 1, 52, 0 },
1528 { 128, 1, 2, 1, 1, 1 },
1529 { 128, 2, 3, 1, 1, 1 },
1530 { 128, 3, 4, 1, 1, 1 },
1531 { 128, 4, 5, 1, 1, 1 },
1532 { 128, 5, 6, 1, 1, 1 },
1533 { 128, 0, 358, 52, 51, 51 },
1534 { 128, 1, 359, 52, 52, 52 },
1535 { 128, 2, 360, 52, 52, 52 },
1536 { 128, 3, 361, 52, 52, 52 },
1537 { 128, 4, 362, 52, 52, 52 },
1538 { 128, 5, 363, 52, 52, 52 },
1539 { 128, 6, 364, 52, 52, 52 },
1540 { 128, 0, 365, 53, 52, 52 },
1541 { 129, 1, 0, 0, 1, 1 },
1542 { 129, 2, 1, 0, 1, 1 },
1543 { 129, 3, 2, 0, 1, 1 },
1544 { 129, 4, 3, 0, 1, 1 },
1545 { 129, 5, 4, 0, 1, 1 },
1546 { 129, 6, 5, 0, 1, 1 },
1547 { 129, 0, 6, 1, 1, 1 },
1548 { 129, 1, 357, 51, 52, 52 },
1549 { 129, 2, 358, 51, 52, 52 },
1550 { 129, 3, 359, 51, 52, 52 },
1551 { 129, 4, 360, 51, 52, 52 },
1552 { 129, 5, 361, 51, 52, 52 },
1553 { 129, 6, 362, 51, 52, 52 },
1554 { 129, 0, 363, 52, 52, 52 },
1555 { 129, 1, 364, 52, 1, 53 },
1556 { 130, 2, 0, 0, 1, 0 },
1557 { 130, 3, 1, 0, 1, 0 },
1558 { 130, 4, 2, 0, 1, 0 },
1559 { 130, 5, 3, 0, 1, 0 },
1560 { 130, 6, 4, 0, 1, 0 },
1561 { 130, 0, 5, 1, 1, 0 },
1562 { 130, 1, 6, 1, 2, 1 },
1563 { 130, 2, 357, 51, 52, 51 },
1564 { 130, 3, 358, 51, 52, 51 },
1565 { 130, 4, 359, 51, 52, 51 },
1566 { 130, 5, 360, 51, 52, 51 },
1567 { 130, 6, 361, 51, 52, 51 },
1568 { 130, 0, 362, 52, 52, 51 },
1569 { 130, 1, 363, 52, 1, 52 },
1570 { 130, 2, 364, 52, 1, 52 },
1571 { 131, 3, 0, 0, 1, 0 },
1572 { 131, 4, 1, 0, 1, 0 },
1573 { 131, 5, 2, 0, 1, 0 },
1574 { 131, 6, 3, 0, 1, 0 },
1575 { 131, 0, 4, 1, 1, 0 },
1576 { 131, 1, 5, 1, 2, 1 },
1577 { 131, 2, 6, 1, 2, 1 },
1578 { 131, 3, 357, 51, 52, 51 },
1579 { 131, 4, 358, 51, 52, 51 },
1580 { 131, 5, 359, 51, 52, 51 },
1581 { 131, 6, 360, 51, 52, 51 },
1582 { 131, 0, 361, 52, 52, 51 },
1583 { 131, 1, 362, 52, 1, 52 },
1584 { 131, 2, 363, 52, 1, 52 },
1585 { 131, 3, 364, 52, 1, 52 },
1586 { 132, 4, 0, 0, 1, 0 },
1587 { 132, 5, 1, 0, 1, 0 },
1588 { 132, 6, 2, 0, 1, 0 },
1589 { 132, 0, 3, 1, 1, 0 },
1590 { 132, 1, 4, 1, 2, 1 },
1591 { 132, 2, 5, 1, 2, 1 },
1592 { 132, 3, 6, 1, 2, 1 },
1593 { 132, 5, 358, 51, 52, 51 },
1594 { 132, 6, 359, 51, 52, 51 },
1595 { 132, 0, 360, 52, 52, 51 },
1596 { 132, 1, 361, 52, 53, 52 },
1597 { 132, 2, 362, 52, 53, 52 },
1598 { 132, 3, 363, 52, 53, 52 },
1599 { 132, 4, 364, 52, 53, 52 },
1600 { 132, 5, 365, 52, 53, 52 },
1601 { 133, 6, 0, 0, 53, 0 },
1602 { 133, 0, 1, 1, 53, 0 },
1603 { 133, 1, 2, 1, 1, 1 },
1604 { 133, 2, 3, 1, 1, 1 },
1605 { 133, 3, 4, 1, 1, 1 },
1606 { 133, 4, 5, 1, 1, 1 },
1607 { 133, 5, 6, 1, 1, 1 },
1608 { 133, 6, 357, 51, 51, 51 },
1609 { 133, 0, 358, 52, 51, 51 },
1610 { 133, 1, 359, 52, 52, 52 },
1611 { 133, 2, 360, 52, 52, 52 },
1612 { 133, 3, 361, 52, 52, 52 },
1613 { 133, 4, 362, 52, 52, 52 },
1614 { 133, 5, 363, 52, 52, 52 },
1615 { 133, 6, 364, 52, 52, 52 },
1616 { 134, 0, 0, 1, 52, 0 },
1617 { 134, 1, 1, 1, 1, 1 },
1618 { 134, 2, 2, 1, 1, 1 },
1619 { 134, 3, 3, 1, 1, 1 },
1620 { 134, 4, 4, 1, 1, 1 },
1621 { 134, 5, 5, 1, 1, 1 },
1622 { 134, 6, 6, 1, 1, 1 },
1623 { 134, 0, 357, 52, 51, 51 },
1624 { 134, 1, 358, 52, 52, 52 },
1625 { 134, 2, 359, 52, 52, 52 },
1626 { 134, 3, 360, 52, 52, 52 },
1627 { 134, 4, 361, 52, 52, 52 },
1628 { 134, 5, 362, 52, 52, 52 },
1629 { 134, 6, 363, 52, 52, 52 },
1630 { 134, 0, 364, 53, 52, 52 },
1631 { 135, 1, 0, 0, 1, 1 },
1632 { 135, 2, 1, 0, 1, 1 },
1633 { 135, 3, 2, 0, 1, 1 },
1634 { 135, 4, 3, 0, 1, 1 },
1635 { 135, 5, 4, 0, 1, 1 },
1636 { 135, 6, 5, 0, 1, 1 },
1637 { 135, 0, 6, 1, 1, 1 },
1638 { 135, 1, 357, 51, 52, 52 },
1639 { 135, 2, 358, 51, 52, 52 },
1640 { 135, 3, 359, 51, 52, 52 },
1641 { 135, 4, 360, 51, 52, 52 },
1642 { 135, 5, 361, 51, 52, 52 },
1643 { 135, 6, 362, 51, 52, 52 },
1644 { 135, 0, 363, 52, 52, 52 },
1645 { 135, 1, 364, 52, 1, 53 },
1646 { 136, 2, 0, 0, 1, 0 },
1647 { 136, 3, 1, 0, 1, 0 },
1648 { 136, 4, 2, 0, 1, 0 },
1649 { 136, 5, 3, 0, 1, 0 },
1650 { 136, 6, 4, 0, 1, 0 },
1651 { 136, 0, 5, 1, 1, 0 },
1652 { 136, 1, 6, 1, 2, 1 },
1653 { 136, 3, 358, 51, 52, 51 },
1654 { 136, 4, 359, 51, 52, 51 },
1655 { 136, 5, 360, 51, 52, 51 },
1656 { 136, 6, 361, 51, 52, 51 },
1657 { 136, 0, 362, 52, 52, 51 },
1658 { 136, 1, 363, 52, 1, 52 },
1659 { 136, 2, 364, 52, 1, 52 },
1660 { 136, 3, 365, 52, 1, 52 },
1661 { 137, 4, 0, 0, 1, 0 },
1662 { 137, 5, 1, 0, 1, 0 },
1663 { 137, 6, 2, 0, 1, 0 },
1664 { 137, 0, 3, 1, 1, 0 },
1665 { 137, 1, 4, 1, 2, 1 },
1666 { 137, 2, 5, 1, 2, 1 },
1667 { 137, 3, 6, 1, 2, 1 },
1668 { 137, 4, 357, 51, 52, 51 },
1669 { 137, 5, 358, 51, 52, 51 },
1670 { 137, 6, 359, 51, 52, 51 },
1671 { 137, 0, 360, 52, 52, 51 },
1672 { 137, 1, 361, 52, 53, 52 },
1673 { 137, 2, 362, 52, 53, 52 },
1674 { 137, 3, 363, 52, 53, 52 },
1675 { 137, 4, 364, 52, 53, 52 },
1676 };
1677
1678 static int test_week_calc( void )
1679 {
1680     char buffer[100];
1681     int rc = 1;
1682     for ( int i = 0; i < 1020; ++i )
1683     {
1684         struct tm t = { 0 };
1685         t.tm_year = data[i][0];
1686         t.tm_wday = data[i][1];
1687         t.tm_yday = data[i][2];
1688         assert( strftime( buffer, 100, "%U %V %W", &t ) == 8 );
1689         int U, V, W;
1690         assert( sscanf( buffer, "%d %d %d", &U, &V, &W ) == 3 );
1691         if ( data[i][3] != U || data[i][4] != V || data[i][5] != W )
1692         {
1693             printf( "Fehler in { %d, %d, %d, %d, %d, %d } (encountered { %d, %d, %d })\n", data[i][0], data[i][1], data[i][2], data[i][3], data[i][4], data[i][5], U, V, W );
1694             rc = 0;
1695         }
1696     }
1697     return rc;
1698 }
1699
1700 int main( void )
1701 {
1702     char buffer[100];
1703     /* Basic functionality */
1704     struct tm timeptr;
1705     MKTIME( timeptr, 59, 30, 12, 1, 9, 72, 0, 274 );
1706     TESTCASE( strftime( buffer, 100, "%a ", &timeptr ) == 4 );
1707     TESTCASE( strcmp( buffer, "Sun " ) == 0 );
1708     TESTCASE( strftime( buffer, 100, "%A ", &timeptr ) == 7 );
1709     TESTCASE( strcmp( buffer, "Sunday " ) == 0 );
1710     TESTCASE( strftime( buffer, 100, "%b ", &timeptr ) == 4 );
1711     TESTCASE( strcmp( buffer, "Oct " ) == 0 );
1712     TESTCASE( strftime( buffer, 100, "%h ", &timeptr ) == 4 );
1713     TESTCASE( strcmp( buffer, "Oct " ) == 0 );
1714     TESTCASE( strftime( buffer, 100, "%B ", &timeptr ) == 8 );
1715     TESTCASE( strcmp( buffer, "October " ) == 0 );
1716     TESTCASE( strftime( buffer, 100, "%c ", &timeptr ) == 25 );
1717     TESTCASE( strcmp( buffer, "Sun Oct  1 12:30:59 1972 " ) == 0 );
1718     TESTCASE( strftime( buffer, 100, "%C ", &timeptr ) == 3 );
1719     TESTCASE( strcmp( buffer, "19 " ) == 0 );
1720     TESTCASE( strftime( buffer, 100, "%d ", &timeptr ) == 3 );
1721     TESTCASE( strcmp( buffer, "01 " ) == 0 );
1722     TESTCASE( strftime( buffer, 100, "%D ", &timeptr ) == 9 );
1723     TESTCASE( strcmp( buffer, "10/01/72 " ) == 0 );
1724     TESTCASE( strftime( buffer, 100, "%e ", &timeptr ) == 3 );
1725     TESTCASE( strcmp( buffer, " 1 " ) == 0 );
1726     TESTCASE( strftime( buffer, 100, "%F ", &timeptr ) == 11 );
1727     TESTCASE( strcmp( buffer, "1972-10-01 " ) == 0 );
1728     TESTCASE( strftime( buffer, 100, "%H ", &timeptr ) == 3 );
1729     TESTCASE( strcmp( buffer, "12 " ) == 0 );
1730     TESTCASE( strftime( buffer, 100, "%I ", &timeptr ) == 3 );
1731     TESTCASE( strcmp( buffer, "12 " ) == 0 );
1732     TESTCASE( strftime( buffer, 100, "%j ", &timeptr ) == 4 );
1733     TESTCASE( strcmp( buffer, "275 " ) == 0 );
1734     TESTCASE( strftime( buffer, 100, "%m ", &timeptr ) == 3 );
1735     TESTCASE( strcmp( buffer, "10 " ) == 0 );
1736     TESTCASE( strftime( buffer, 100, "%M ", &timeptr ) == 3 );
1737     TESTCASE( strcmp( buffer, "30 " ) == 0 );
1738     TESTCASE( strftime( buffer, 100, "%p ", &timeptr ) == 3 );
1739     TESTCASE( strcmp( buffer, "PM " ) == 0 );
1740     TESTCASE( strftime( buffer, 100, "%r ", &timeptr ) == 12 );
1741     TESTCASE( strcmp( buffer, "12:30:59 PM " ) == 0 );
1742     TESTCASE( strftime( buffer, 100, "%R ", &timeptr ) == 6 );
1743     TESTCASE( strcmp( buffer, "12:30 " ) == 0 );
1744     TESTCASE( strftime( buffer, 100, "%S ", &timeptr ) == 3 );
1745     TESTCASE( strcmp( buffer, "59 " ) == 0 );
1746     TESTCASE( strftime( buffer, 100, "%T ", &timeptr ) == 9 );
1747     TESTCASE( strcmp( buffer, "12:30:59 " ) == 0 );
1748     TESTCASE( strftime( buffer, 100, "%u ", &timeptr ) == 2 );
1749     TESTCASE( strcmp( buffer, "7 " ) == 0 );
1750     TESTCASE( strftime( buffer, 100, "%w ", &timeptr ) == 2 );
1751     TESTCASE( strcmp( buffer, "0 " ) == 0 );
1752     TESTCASE( strftime( buffer, 100, "%x ", &timeptr ) == 9 );
1753     TESTCASE( strcmp( buffer, "10/01/72 " ) == 0 );
1754     TESTCASE( strftime( buffer, 100, "%X ", &timeptr ) == 9 );
1755     TESTCASE( strcmp( buffer, "12:30:59 " ) == 0 );
1756     TESTCASE( strftime( buffer, 100, "%y ", &timeptr ) == 3 );
1757     TESTCASE( strcmp( buffer, "72 " ) == 0 );
1758     TESTCASE( strftime( buffer, 100, "%Y ", &timeptr ) == 5 );
1759     TESTCASE( strcmp( buffer, "1972 " ) == 0 );
1760     TESTCASE( strftime( buffer, 100, "%% ", &timeptr ) == 2 );
1761     TESTCASE( strcmp( buffer, "% " ) == 0 );
1762     TESTCASE( strftime( buffer, 100, "%n ", &timeptr ) == 2 );
1763     TESTCASE( strcmp( buffer, "\n " ) == 0 );
1764     TESTCASE( strftime( buffer, 100, "%t ", &timeptr ) == 2 );
1765     TESTCASE( strcmp( buffer, "\t " ) == 0 );
1766     TESTCASE( test_week_calc() );
1767     return TEST_RESULTS;
1768 }
1769
1770 #endif