Esempio n. 1
0
/**
 * Remove specified timer handler from queue and free allocated memory
 *
 * @param timer instance of timer that should be remove
 */
void delete_timer(TimerHandle* timer) {
    TimerHandle **ptr = get_timer_ptr(timer);
    REPORT_INFO1(LC_PUSH, "[delete_timer] timer=%p", timer);

    if (ptr != NULL) {
        *ptr = timer->next;
        midpFree(timer);
    }
}
Esempio n. 2
0
/**
 * Remove specified timer handler from queue but don't free allocated memory
 *
 * @param timer instance that should be remove
 *
 * @return poitner to timer instance that should be remove from queue
 */
TimerHandle* remove_timer(TimerHandle* timer) {
    TimerHandle **ptr = get_timer_ptr(timer);
    REPORT_INFO1(LC_PUSH, "[remove_timer] timer=%p", timer);

    if (ptr != NULL) {
        *ptr = timer->next;
    }

    return timer;
}
/*
 * Setup the local clock events for a CPU.
 */
int __cpuinit local_timer_setup(struct clock_event_device *evt)
{
	unsigned int cpu = smp_processor_id();
	struct kona_td kona_td;
	struct timer_ch_cfg config;

	pr_info("local_timer_setup called for %d\n", cpu);
	/* allocate an AON timer channel as local tick timer
	 */
	kona_td = (struct kona_td)__get_cpu_var(percpu_kona_td);

	if (!kona_td.allocated) {
		kona_td.kona_timer =
		    kona_timer_request(TICK_TIMER_NAME,
				       TICK_TIMER_OFFSET + cpu);
		if (kona_td.kona_timer) {
			kona_td.allocated = true;
		} else { /* kona_td.kona_timer is already allocated, hence
			    we get the pointer and reuse the same. This is
			    done to ensure we don't use an extra channel for
			    timer event before local timer comes up
			    */
			kona_td.kona_timer = get_timer_ptr(TICK_TIMER_NAME,
					TICK_TIMER_OFFSET + cpu);
			if (!kona_td.kona_timer) {
				pr_err("%s: Failed to allocate %s channel %d"
					"as CPU %d local tick device\n",
					__func__,
				       TICK_TIMER_NAME,
				       TICK_TIMER_OFFSET + cpu, cpu);
				return -ENXIO;
			} else {
				kona_td.allocated = true;
			}
		}
	}

	/*
	 * In the future: The following codes should be one time configuration
	 */
	config.mode = MODE_ONESHOT;
	config.arg = evt;
	config.cb = kona_tick_interrupt_cb;
	kona_timer_config(kona_td.kona_timer, &config);

	irq_set_affinity(kona_td.kona_timer->irq, cpumask_of(cpu));

	evt->name = "local_timer";
	evt->cpumask = cpumask_of(cpu);
	evt->irq = kona_td.kona_timer->irq;
	evt->set_next_event = kona_tick_set_next_event;
	evt->set_mode = kona_tick_set_mode;
	evt->features = CLOCK_EVT_FEAT_ONESHOT;
	evt->rating = 250;
	evt->shift = 32;
	evt->mult = div_sc(CLOCK_TICK_RATE, NSEC_PER_SEC, evt->shift);
	evt->max_delta_ns = clockevent_delta2ns(MAX_KONA_COUNT_CLOCK, evt);
	/* There is MIN_KONA_DELTA_CLOCK clock cycles delay in HUB Timer by
	 * ASIC limitation. When min_delta_ns set N, real requested load value
	 * in hrtimer becomes N - 1. So add 1 to be MIN_DELTA_CLOCK
	 */
	evt->min_delta_ns = clockevent_delta2ns(MIN_KONA_DELTA_CLOCK + 1, evt);

	per_cpu(percpu_kona_td, cpu) = kona_td;

	clockevents_register_device(evt);
	return 0;
}