コード例 #1
0
void xntbase_start(xntbase_t *base)
{
	xnticks_t start_date;
	spl_t s;

	if (base == &nktbase || xntbase_enabled_p(base))
		return;

	trace_mark(xn_nucleus, tbase_start, "base %s", base->name);

	xnlock_get_irqsave(&nklock, s);

	start_date = xnarch_get_cpu_time();

	/* Only synchronise non-isolated time bases on the master base. */
	if (!xntbase_isolated_p(base)) {
		base->wallclock_offset = xntbase_ns2ticks(base,
			start_date + nktbase.wallclock_offset);
		__setbits(base->status, XNTBSET);
	}

	start_date += base->tickvalue;
	__setbits(base->status, XNTBRUN);

	xnlock_put_irqrestore(&nklock, s);

	xntslave_start(base2slave(base), start_date, base->tickvalue);
}
コード例 #2
0
static inline void xntimer_dequeue_periodic(xntimer_t *timer)
{
	unsigned slot = (xntlholder_date(&timer->plink) & XNTIMER_WHEELMASK);
	unsigned cpu = xnsched_cpu(timer->sched);
	struct percpu_cascade *pc = &base2slave(timer->base)->cascade[cpu];
	xntlist_remove(&pc->wheel[slot], &timer->plink);
	__setbits(timer->status, XNTIMER_DEQUEUED);
}
コード例 #3
0
static inline void xntimer_enqueue_periodic(xntimer_t *timer)
{
	unsigned slot = (xntlholder_date(&timer->plink) & XNTIMER_WHEELMASK);
	unsigned cpu = xnsched_cpu(timer->sched);
	struct percpu_cascade *pc = &base2slave(timer->base)->cascade[cpu];
	/* Just prepend the new timer to the proper slot. */
	xntlist_insert(&pc->wheel[slot], &timer->plink);
	__clrbits(timer->status, XNTIMER_DEQUEUED);
	xnstat_counter_inc(&timer->scheduled);
}
コード例 #4
0
void xntbase_stop(xntbase_t *base)
{
	if (base == &nktbase || !xntbase_enabled_p(base))
		return;

	xntslave_stop(base2slave(base));
	__clrbits(base->status, XNTBRUN | XNTBSET);

	trace_mark(xn_nucleus, tbase_stop, "base %s", base->name);
}
コード例 #5
0
void xntbase_adjust_time(xntbase_t *base, xnsticks_t delta)
{
	xnticks_t now;

#ifdef CONFIG_XENO_OPT_TIMING_PERIODIC
	if (xntbase_isolated_p(base)) {
		/* Only update the specified isolated base. */
		base->wallclock_offset += delta;
		__setbits(base->status, XNTBSET);
		xntslave_adjust(base2slave(base), delta);

	} else {
		xnholder_t *holder;
#endif /* CONFIG_XENO_OPT_TIMING_PERIODIC */
		/* Update all non-isolated bases in the system. */
		nktbase.wallclock_offset += xntbase_ticks2ns(base, delta);
		now = xnarch_get_cpu_time() + nktbase.wallclock_offset;
		xntimer_adjust_all_aperiodic(xntbase_ticks2ns(base, delta));

#ifdef CONFIG_XENO_OPT_TIMING_PERIODIC
		for (holder = getheadq(&nktimebaseq);
		     holder != NULL; holder = nextq(&nktimebaseq, holder)) {
			xntbase_t *tbase = link2tbase(holder);
			if (tbase == &nktbase || xntbase_isolated_p(tbase))
				continue;

			tbase->wallclock_offset =
				xntbase_ns2ticks(tbase, now) -
				xntbase_get_jiffies(tbase);
			xntslave_adjust(base2slave(tbase), delta);
		}
	}
#endif /* CONFIG_XENO_OPT_TIMING_PERIODIC */

	trace_mark(xn_nucleus, tbase_adjust, "base %s delta %Lu",
		   base->name, delta);
}
コード例 #6
0
void xntbase_free(xntbase_t *base)
{
	spl_t s;

	if (base == &nktbase)
		return;

	xntslave_destroy(base2slave(base));
	xntbase_remove_proc(base);

	xnlock_get_irqsave(&nklock, s);
	removeq(&nktimebaseq, &base->link);
	xnlock_put_irqrestore(&nklock, s);

	xnarch_free_host_mem(base, sizeof(*base));
}
コード例 #7
0
void xntbase_tick(xntbase_t *base)
{
	spl_t s;

	xnlock_get_irqsave(&nklock, s);

	trace_mark(xn_nucleus, tbase_tick, "base %s", base->name);

	if (base == &nktbase)
		xntimer_tick_aperiodic();
	else {
		xntslave_t *slave = base2slave(base);
		xntimer_tick_periodic_inner(slave);
	}

	xnlock_put_irqrestore(&nklock, s);
}
コード例 #8
0
int xntbase_update(xntbase_t *base, u_long period)
{
	spl_t s;

	if (base == &nktbase || base->tickvalue == period)
		return 0;

	if (period == XN_APERIODIC_TICK)
		return -EINVAL;

	xnlock_get_irqsave(&nklock, s);
	base->tickvalue = period;
	base->ticks2sec = 1000000000UL / period;
	xntslave_update(base2slave(base), period);
	xnlock_put_irqrestore(&nklock, s);

	return 0;
}