| 1486 | /* |
| 1487 | ** Month, week, day. |
| 1488 | */ |
| 1489 | rulep->r_type = MONTH_NTH_DAY_OF_WEEK; |
| 1490 | ++strp; |
| 1491 | strp = getnum(strp, &rulep->r_mon, 1, MONSPERYEAR); |
| 1492 | if (strp == NULL) |
| 1493 | return NULL; |
| 1494 | if (*strp++ != '.') |
| 1495 | return NULL; |
| 1496 | strp = getnum(strp, &rulep->r_week, 1, 5); |
| 1497 | if (strp == NULL) |
| 1498 | return NULL; |
| 1499 | if (*strp++ != '.') |
| 1500 | return NULL; |
| 1501 | strp = getnum(strp, &rulep->r_day, 0, DAYSPERWEEK - 1); |
| 1502 | } else if (is_digit(*strp)) { |
| 1503 | /* |
| 1504 | ** Day of year. |
| 1505 | */ |
| 1506 | rulep->r_type = DAY_OF_YEAR; |
| 1507 | strp = getnum(strp, &rulep->r_day, 0, DAYSPERLYEAR - 1); |
| 1508 | } else return NULL; /* invalid format */ |
| 1509 | if (strp == NULL) |
| 1510 | return NULL; |
| 1511 | if (*strp == '/') { |
| 1512 | /* |
| 1513 | ** Time specified. |
| 1514 | */ |
| 1515 | ++strp; |
| 1516 | strp = getoffset(strp, &rulep->r_time); |
| 1517 | } else rulep->r_time = 2 * SECSPERHOUR; /* default = 2:00:00 */ |
| 1518 | return strp; |
| 1519 | } |
| 1520 | |
| 1521 | /* |
| 1522 | ** Given a year, a rule, and the offset from UT at the time that rule takes |
| 1523 | ** effect, calculate the year-relative time that rule takes effect. |
| 1524 | */ |
| 1525 | |
| 1526 | static int_fast32_t |
| 1527 | transtime(time_t year, register const struct rule *const rulep, |
| 1528 | const int_fast32_t offset) |
| 1529 | { |
| 1530 | int d; /* Day of year (zero-origin). */ |
| 1531 | register bool leapyear; |
| 1532 | |
| 1533 | leapyear = isleap(year); |
| 1534 | |
| 1535 | if (rulep->r_type <= DAY_OF_YEAR) { |