Ejemplo n.º 1
0
static OSStatus
DER_CFDateToUTCTime(CFAbsoluteTime date, CSSM_DATA_PTR utcTime)
{
    CFGregorianDate gdate =  CFAbsoluteTimeGetGregorianDate(date, NULL /* GMT */);
    unsigned char *d;
    SInt8 second;

    utcTime->Length = 13;
    utcTime->Data = d = PORT_Alloc(13);
    if (!utcTime->Data)
	return SECFailure;

    /* UTC time does not handle the years before 1950 */
    if (gdate.year < 1950)
            return SECFailure;

    /* remove the century since it's added to the year by the
       CFAbsoluteTimeGetGregorianDate routine, but is not needed for UTC time */
    gdate.year %= 100;
    second = gdate.second + 0.5;

    d[0] = HIDIGIT(gdate.year);
    d[1] = LODIGIT(gdate.year);
    d[2] = HIDIGIT(gdate.month);   
    d[3] = LODIGIT(gdate.month);
    d[4] = HIDIGIT(gdate.day);
    d[5] = LODIGIT(gdate.day);
    d[6] = HIDIGIT(gdate.hour);
    d[7] = LODIGIT(gdate.hour);  
    d[8] = HIDIGIT(gdate.minute);
    d[9] = LODIGIT(gdate.minute);
    d[10] = HIDIGIT(second);
    d[11] = LODIGIT(second);
    d[12] = 'Z';
    return SECSuccess;
}
Ejemplo n.º 2
0
 Gregorian(CFAbsoluteTime ref)
 { static_cast<CFGregorianDate &>(*this) = CFAbsoluteTimeGetGregorianDate(ref, NULL); }
Ejemplo n.º 3
0
/* Note that the units of years and months are not equal length, but are treated as such. */
CFAbsoluteTime CFAbsoluteTimeAddGregorianUnits(CFAbsoluteTime at, 
                                               CFTimeZoneRef tz, 
                                               CFGregorianUnits units)
{
    CFGregorianDate gdate;
    CFGregorianUnits working;
    CFAbsoluteTime candidate_at0, candidate_at1;
    uint8_t monthdays;

    /* Most people seem to expect years, then months, then days, etc.
     * to be added in that order.  Thus, 27 April + (4 days, 1 month)
     * = 31 May, and not 1 June. This is also relatively predictable.
     *
     * On another issue, months not being equal length, people also
     * seem to expect late day-of-month clamping (don't clamp as you
     * go through months), but clamp before adding in the days. Late
     * clamping is also more predictable given random starting points
     * and random numbers of months added (ie Jan 31 + 2 months could
     * be March 28 or March 29 in different years with aggressive
     * clamping). Proportionality (28 Feb + 1 month = 31 March) is
     * also not expected.
     *
     * Also, people don't expect time zone transitions to have any
     * effect when adding years and/or months and/or days, only.
     * Hours, minutes, and seconds, though, are added in as humans
     * would experience the passing of that time. What this means
     * is that if the date, after adding years, months, and days
     * lands on some date, and then adding hours, minutes, and
     * seconds crosses a time zone transition, the time zone
     * transition is accounted for. If adding years, months, and
     * days gets the date into a different time zone offset period,
     * that transition is not taken into account.
     */
    gdate = CFAbsoluteTimeGetGregorianDate(at, tz);
    // We must work in a CFGregorianUnits, because the fields 
    //  in the CFGregorianDate can easily overflow.
    working.years = gdate.year;
    working.months = gdate.month;
    working.days = gdate.day;
    working.years += units.years;
    working.months += units.months;
    while (12 < working.months) {
        working.months -= 12;
        working.years += 1;
    }
    while (working.months < 1) {
        working.months += 12;
        working.years -= 1;
    }
    monthdays = __CFDaysInMonth(working.months, working.years - 2001);
    if (monthdays < working.days) { // Clamp day to new month
        working.days = monthdays;
    }
    working.days += units.days;
    while (monthdays < working.days) {
        working.months += 1;
        if (12 < working.months) {
            working.months -= 12;
            working.years += 1;
        }
        working.days -= monthdays;
        monthdays = __CFDaysInMonth(working.months, working.years - 2001);
    }
    while (working.days < 1) {
        working.months -= 1;
        if (working.months < 1) {
            working.months += 12;
            working.years -= 1;
        }
        monthdays = __CFDaysInMonth(working.months, working.years - 2001);
        working.days += monthdays;
    }
    gdate.year = working.years;
    gdate.month = working.months;
    gdate.day = working.days;
    /* Roll in hours, minutes, and seconds */
    candidate_at0 = CFGregorianDateGetAbsoluteTime(gdate, tz);
    candidate_at1 = candidate_at0 + 3600.0 * units.hours + 60.0 * units.minutes + units.seconds;
    /* If summing in the hours, minutes, and seconds delta pushes us
     * into a new time zone offset, that will automatically be taken
     * care of by the fact that we just add the raw time above. To
     * undo that effect, we'd have to get the time zone offsets for
     * candidate_at0 and candidate_at1 here, and subtract the
     * difference (offset1 - offset0) from candidate_at1. */
    return candidate_at1;
}
Ejemplo n.º 4
0
/*
 * Returns a copy of repeat event after changing the repeat date
 * into next event date.
 *
 * Caller is responsible for releasing the copy after use.
 */
__private_extern__ CFDictionaryRef
copyNextRepeatingEvent(CFStringRef type)
{
    CFDictionaryRef         repeatDict = NULL;
    CFStringRef             repeatDictType = NULL;
    CFMutableDictionaryRef  repeatDictCopy = NULL;
    CFGregorianDate         greg;
    CFTimeZoneRef           tizzy;
    CFAbsoluteTime          ev_time;
    CFDateRef               ev_date;
    int                     days;
    int                     minutes_scheduled;
    int                     cf_day_of_week;

    /*
     * 'WakeOrPowerOn' repeat events are returned when caller asks
     * for 'Wake' events or 'PowerOn' events.
     * Don't bother to return anything if caller is looking specifically for
     * WakeOrPowerOn type repeat events.
     */
    if( CFEqual(type, CFSTR(kIOPMAutoSleep))
        || CFEqual(type, CFSTR(kIOPMAutoShutdown)) ||
        CFEqual(type, CFSTR(kIOPMAutoRestart)) )
    {
        repeatDict = repeatingPowerOff;
    }
    else if (
        CFEqual(type, CFSTR(kIOPMAutoPowerOn)) ||
        CFEqual(type, CFSTR(kIOPMAutoWake)) )
    {
        repeatDict = repeatingPowerOn;
    }
    else
        return NULL;

    repeatDictType = getRepeatingDictionaryType(repeatDict);
    if (CFEqual(type, repeatDictType) ||
            ( (CFEqual(repeatDictType, CFSTR(kIOPMAutoWakeOrPowerOn))) &&
              (CFEqual(type, CFSTR(kIOPMAutoPowerOn)) || CFEqual(type, CFSTR(kIOPMAutoWake)))
            )
       )
    {
        repeatDictCopy = CFDictionaryCreateMutableCopy(0,0,repeatDict);

        tizzy = CFTimeZoneCopySystem();

        // Massage the scheduled time into today's date
        cf_day_of_week = CFAbsoluteTimeGetDayOfWeek(
                CFAbsoluteTimeGetCurrent(), tizzy);
        days = daysUntil(repeatDict, cf_day_of_week);

        greg = CFAbsoluteTimeGetGregorianDate(
                        CFAbsoluteTimeGetCurrent() + days*(60*60*24), 
                        tizzy);
                                
        minutes_scheduled = getRepeatingDictionaryMinutes(repeatDict);

        greg.hour = minutes_scheduled/60;
        greg.minute = minutes_scheduled%60;
        greg.second = 0.0;
        
        ev_time = CFGregorianDateGetAbsoluteTime(greg, tizzy);
        ev_date = CFDateCreate(kCFAllocatorDefault, ev_time);
 
        CFDictionarySetValue(repeatDictCopy, CFSTR(kIOPMPowerEventTimeKey),
                ev_date);

        /* Set 'AppNameKey' to 'Repeating' */
        CFDictionarySetValue(repeatDictCopy, CFSTR(kIOPMPowerEventAppNameKey),
                CFSTR(kIOPMRepeatingAppName));
        CFRelease(ev_date);
        CFRelease(tizzy);
    }

    return repeatDictCopy;
}