电源管理-配置唤醒源

由上一次的分析可知,在suspend_ops->enter(state);中会进行唤醒源的配置。下面分析平台代码:

//位于linux-3.18\arch\arm\plat-samsung\pm.c
static int s3c_pm_enter(suspend_state_t state)
{
	int ret;
	/* ensure the debug is initialised (if enabled) */

	s3c_pm_debug_init();

	S3C_PMDBG("%s(%d)\n", __func__, state);

	if (pm_cpu_prep == NULL || pm_cpu_sleep == NULL) {
		printk(KERN_ERR "%s: error: no cpu sleep function\n", __func__);
		return -EINVAL;
	}

	/*
	这里会检查是否配置了唤醒源s3c_irqwake_intmask=0xffffffffL s3c_irqwake_eintmask= 0xffffffff表示无内外唤醒源,如果设置成0xfffffffe表示bit0为内部唤醒源,可以通过调用s3c_irq_wake或s3c_irqext_wake配置哪个引脚是内部或者外部唤醒源
	*/
	if (!of_have_populated_dt() &&
	    !any_allowed(s3c_irqwake_intmask, s3c_irqwake_intallow) &&
	    !any_allowed(s3c_irqwake_eintmask, s3c_irqwake_eintallow)) {
		printk(KERN_ERR "%s: No wake-up sources!\n", __func__);
		printk(KERN_ERR "%s: Aborting sleep\n", __func__);
		return -EINVAL;
	}

	/* save all necessary core registers not covered by the drivers */

	if (!of_have_populated_dt()) {
		samsung_pm_save_gpios();
		samsung_pm_saved_gpios();
	}

	s3c_pm_save_uarts();
	s3c_pm_save_core();

	/*配置外部中断引脚
	*/
	s3c_pm_configure_extint();

	S3C_PMDBG("sleep: irq wakeup masks: %08lx,%08lx\n",
	    s3c_irqwake_intmask, s3c_irqwake_eintmask);

	s3c_pm_arch_prepare_irqs();

	/* call cpu specific preparation */

	pm_cpu_prep();

	/* flush cache back to ram */

	flush_cache_all();

	s3c_pm_check_store();

	/* send the cpu to sleep... */

	s3c_pm_arch_stop_clocks();

	/* this will also act as our return point from when
	 * we resume as it saves its own register state and restores it
	 * during the resume.  */

	ret = cpu_suspend(0, pm_cpu_sleep);
	if (ret)
		return ret;

	/* restore the system state */

	s3c_pm_restore_core();
	s3c_pm_restore_uarts();

	if (!of_have_populated_dt()) {
		samsung_pm_restore_gpios();
		s3c_pm_restored_gpios();
	}

	s3c_pm_debug_init();

	/* check what irq (if any) restored the system */

	s3c_pm_arch_show_resume_irqs();

	S3C_PMDBG("%s: post sleep, preparing to return\n", __func__);

	/* LEDs should now be 1110 */
	s3c_pm_debug_smdkled(1 << 1, 0);

	s3c_pm_check_restore();

	/* ok, let's return from sleep */

	S3C_PMDBG("S3C PM Resume (post-restore)\n");
	return 0;
}

怎样修改内核:
a. 通过调用s3c_irq_wake来修改s3c_irqwake_intmask、s3c_irqwake_eintmask用来表示唤醒源是哪个
b. 需要自己设置GPIO用于中断功能,并设置它的触发方式

s3c2440中可以配置内部唤醒源有:int0,1,2,3
外部中断可以配置唤醒源有eint4,5,…15

在我们的按键驱动中: request_irq之后调用s3c_irq_wake或s3c_irqext_wake

示例代码:

for (i = 0; i < 4; i++)
	{
		request_irq(pins_desc[i].irq, buttons_irq, (IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING), pins_desc[i].name, &pins_desc[i]);
	}

	/* 指定这些中断可以用于唤醒系统 ,这里指定了IRQ_EINT0,IRQ_EINT2,IRQ_EINT11
	irq_set_irq_wake表示
	*/
	irq_set_irq_wake(IRQ_EINT0, 1); 
	irq_set_irq_wake(IRQ_EINT2, 1);
	irq_set_irq_wake(IRQ_EINT11, 1);
  • 0
    点赞
  • 3
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值