예제 #1
1
void nrf_pwr_mgmt_run(void)
{
#if NRF_PWR_MGMT_CONFIG_FPU_SUPPORT_ENABLED
    /*
     * Clear FPU exceptions.
     * Without this step, the FPU interrupt is marked as pending,
     * preventing system from sleeping.
     */
    uint32_t fpscr = __get_FPSCR();
    __set_FPSCR(fpscr & ~0x9Fu);
    __DMB();
    NVIC_ClearPendingIRQ(FPU_IRQn);

    // Assert if a critical FPU exception is signaled.
    ASSERT((fpscr & 0x03) == 0);
#endif // NRF_PWR_MGMT_CONFIG_FPU_SUPPORT_ENABLED

    SLEEP_LOCK();

#if NRF_PWR_MGMT_CONFIG_CPU_USAGE_MONITOR_ENABLED
    uint32_t sleep_start;
    uint32_t sleep_end;
    uint32_t sleep_duration;

    sleep_start = app_timer_cnt_get();
#endif // NRF_PWR_MGMT_CONFIG_CPU_USAGE_MONITOR_ENABLED

    DEBUG_PIN_SET();

    // Wait for an event.
#ifdef SOFTDEVICE_PRESENT
    ret_code_t ret_code = sd_app_evt_wait();
    if (ret_code == NRF_ERROR_SOFTDEVICE_NOT_ENABLED)
    {
        __WFE();
        __SEV();
        __WFE();
    }
    else
    {
        APP_ERROR_CHECK(ret_code);
    }
#else
    __WFE();
    __SEV();
    __WFE();
#endif // SOFTDEVICE_PRESENT

    DEBUG_PIN_CLEAR();

#if NRF_PWR_MGMT_CONFIG_CPU_USAGE_MONITOR_ENABLED
    sleep_end = app_timer_cnt_get();
    UNUSED_VARIABLE(app_timer_cnt_diff_compute(sleep_end,
                                               sleep_start,
                                               &sleep_duration));
    m_ticks_sleeping += sleep_duration;
#endif // NRF_PWR_MGMT_CONFIG_CPU_USAGE_MONITOR_ENABLED

    SLEEP_RELEASE();
}
예제 #2
0
/***
 * try_to_wake_up - wake up a thread
 * @p: the to-be-woken-up thread
 * @state: the mask of task states that can be woken
 * @sync: do a synchronous wakeup?
 */
int try_to_wake_up(struct task_struct *p, unsigned int state, int sync)
{
	Assert(p);
	dde26_thread_data *t = lxtask_to_ddethread(p);

	Assert(t);
	Assert(SLEEP_LOCK(t));

	p->state = TASK_RUNNING;
	ddekit_sem_up(SLEEP_LOCK(t));

	return 0;
}
예제 #3
0
void L1Audio_SetFlag( uint16 audio_id )
{
   uint32 savedMask;
   if (!kal_if_hisr() && !kal_if_lisr())
      kal_trace( TRACE_GROUP_AUD_MD2GCTRL, L1AUDIO_SETFLAG_A,audio_id,l1audio.runningState);
   else
      kal_dev_trace( TRACE_GROUP_AUD_MD2GCTRL, L1AUDIO_SETFLAG_A,audio_id,l1audio.runningState);

   kal_take_sem( l1audio.sema, KAL_INFINITE_WAIT );
   ASSERT( l1audio.id_flag & (1 << audio_id) );
   ASSERT( (l1audio.runningState & (1 << audio_id)) == 0 );

   if( (l1audio.runningState == 0) && (l1audio.disallowSleepState == 0) ) {
#if defined( __CENTRALIZED_SLEEP_MANAGER__ )
      Audio_Wake_DSP(audio_id, KAL_TRUE);
#endif
   }

   if (l1audio.runningState == 0)
      SLEEP_LOCK();

   savedMask = SaveAndSetIRQMask();
   l1audio.runningState |= (1 << audio_id);
   RestoreIRQMask( savedMask );
   kal_give_sem( l1audio.sema ); 
}
예제 #4
0
/* Initialize a dde26 thread. 
 *
 * - Allocate thread data, as well as a Linux task struct, 
 * - Fill in default values for thread_info, and task,
 * - Adapt task struct's thread_info backreference
 * - Initialize the DDE sleep lock
 */
static dde26_thread_data *init_dde26_thread(void)
{
	/*
	 * Virtual PID counter
	 */
	static atomic_t pid_counter = ATOMIC_INIT(0);
	dde26_thread_data *t = vmalloc(sizeof(dde26_thread_data));
	Assert(t);
	
	memcpy(&t->_vpid, &init_struct_pid, sizeof(struct pid));
	t->_vpid.numbers[0].nr = atomic_inc_return(&pid_counter);
	
	memcpy(&LX_THREAD(t), &init_thread, sizeof(struct thread_info));

	LX_TASK(t) = vmalloc(sizeof(struct task_struct));
	Assert(LX_TASK(t));

	memcpy(LX_TASK(t), &init_task, sizeof(struct task_struct));

	/* nice: Linux backreferences a task`s thread_info from the
	*        task struct (which in turn can be found using the
	*        thread_info...) */
	LX_TASK(t)->stack = &LX_THREAD(t);

	/* initialize this thread's sleep lock */
	SLEEP_LOCK(t) = ddekit_sem_init(0);

	return t;
}
예제 #5
0
void L1Audio_DisallowSleep( kal_uint16 audio_id )
{
   uint32 savedMask;
   
   ASSERT( l1audio.id_flag & (1 << audio_id) );
   ASSERT( l1audio.runningState & (1 << audio_id) );

   savedMask = SaveAndSetIRQMask();
   l1audio.disallowSleepState |= (1 << audio_id);
   RestoreIRQMask( savedMask );
   
   if( (l1audio.runningState & l1audio.disallowSleepState) )
      SLEEP_LOCK();
}
예제 #6
0
/* Our version of scheduler invocation.
 *
 * Scheduling is performed by Fiasco, so we don't care about it as long as
 * a thread is running. If a task becomes TASK_INTERRUPTIBLE or
 * TASK_UNINTERRUPTIBLE, we make sure that the task does not become
 * scheduled by locking the task's sleep lock.
 */
asmlinkage void schedule(void)
{
	dde26_thread_data *t = lxtask_to_ddethread(current);

	switch (current->state) {
		case TASK_RUNNING:
			ddekit_thread_schedule();
			break;
		case TASK_INTERRUPTIBLE:
		case TASK_UNINTERRUPTIBLE:
			ddekit_sem_down(SLEEP_LOCK(t));
			break;
		default:
			panic("current->state = %d --- unknown state\n", current->state);
	}
}
예제 #7
0
/**
 * Initialize a DDE Linux 2.6 thread
 *
 * - Allocate thread data, as well as a Linux task struct, 
 * - Fill in default values for thread_info, and task,
 * - Adapt task struct's thread_info backreference
 * - Initialize the DDE sleep lock
 */
static inline dde_linux26_thread_data *init_dde_linux26_thread(void)
{
	dde_linux26_thread_data *t = vmalloc(sizeof(dde_linux26_thread_data));
	dde_kit_assert(t);
	
	memcpy(&LX_THREAD(t), &init_thread, sizeof(struct thread_info));

	LX_TASK(t) = vmalloc(sizeof(struct task_struct));
	dde_kit_assert(LX_TASK(t));

	memcpy(LX_TASK(t), &init_task, sizeof(struct task_struct));

	/* nice: Linux backreferences a task`s thread_info from the
	*        task struct (which in turn can be found using the
	*        thread_info...) */
	LX_TASK(t)->thread_info = &LX_THREAD(t);

	/* initialize this thread's sleep lock */
	SLEEP_LOCK(t) = dde_kit_sem_init(0);

	return t;
}