/*!
 * Delete alarm
 * \param param Alarm
 * \returns status (0 for success)
 */
int k_alarm_remove ( void *id )
{
	kalarm_t *kalarm;
	int reschedule = 0;

	kalarm = id;

	ASSERT ( kalarm && kalarm->magic == ALARM_MAGIC );

	/* remove from active alarms (if it was there) */
	if ( kalarm->active )
		list_remove ( &kalarms, FIRST, &kalarm->list );

#ifdef DEBUG
	kalarm->magic = 0;
#endif

	SET_ERRNO ( SUCCESS );

	/* release all waiting threads, if any */
	reschedule = k_release_all_threads ( &kalarm->queue );

	kfree ( kalarm );

	reschedule += k_schedule_alarms ();

	if ( reschedule )
		k_schedule_threads ();

	RETURN ( SUCCESS );
}
/* Add alarm to alarm pool if its expiration time is defined
   If expiration time is in the past, alarm will be immediately activated!
 */
static void k_alarm_add ( kalarm_t *kalarm )
{
	int reschedule = 0;

	/* if exp_time is given (>0) add it into active alarms */
	if ( kalarm->alarm.exp_time.sec + kalarm->alarm.exp_time.nsec > 0 )
	{
		kalarm->active = 1;
		list_sort_add ( &kalarms, kalarm, &kalarm->list, alarm_cmp );
	}
	else {
		kalarm->active = 0;
	}

	reschedule = k_schedule_alarms (); /* this or other alarm may expire */

	SET_ERRNO ( SUCCESS );

	/* block thread? */
	if ( kalarm->active && ( kalarm->alarm.flags & IPC_WAIT ) )
	{
		k_enqueue_thread ( NULL, &kalarm->queue );
		reschedule = 1;
	}

	if ( reschedule )
		k_schedule_threads ();
}
/*!
 * Add alarm to alarm pool if its expiration time is defined
 * If expiration time is in the past, alarm will be immediately activated!
 */
static void k_alarm_add ( kalarm_t *kalarm )
{
	/* if exp_time is given (>0) add it into active alarms */
	if ( kalarm->alarm.exp_time.sec + kalarm->alarm.exp_time.nsec > 0 )
	{
		kalarm->active = 1;
		list_sort_add ( &kalarms, kalarm, &kalarm->list, alarm_cmp );
	}
	else {
		kalarm->active = 0;
	}

	k_schedule_alarms (); /* this or other alarm may expire */
}
/*!
 * Delete alarm
 * \param param Alarm
 * \return status (0 for success)
 */
int k_alarm_remove ( void *id )
{
	kalarm_t *kalarm;

	kalarm = id;

	ASSERT ( kalarm && kalarm->magic == ALARM_MAGIC );

	/* remove from active alarms (if it was there) */
	if ( kalarm->active )
		list_remove ( &kalarms, FIRST, &kalarm->list );

#ifdef DEBUG
	kalarm->magic = 0;
#endif

	kfree ( kalarm );

	k_schedule_alarms ();

	return SUCCESS;
}
/*! Called from interrupt handler when an alarm has expired */
static void k_timer_interrupt ()
{
	k_schedule_alarms ();
}
/*!
 * Called from interrupt handler when an alarm has expired
 */
static void k_timer_interrupt ()
{
	if ( k_schedule_alarms () )
		k_schedule_threads ();
}