diff options
Diffstat (limited to 'arch/arm/mach-omap2/powerdomain.c')
| -rw-r--r-- | arch/arm/mach-omap2/powerdomain.c | 87 | 
1 files changed, 62 insertions, 25 deletions
diff --git a/arch/arm/mach-omap2/powerdomain.c b/arch/arm/mach-omap2/powerdomain.c index ef71fdd40fc..896cb4c5eb1 100644 --- a/arch/arm/mach-omap2/powerdomain.c +++ b/arch/arm/mach-omap2/powerdomain.c @@ -1,7 +1,7 @@  /*   * OMAP powerdomain control   * - * Copyright (C) 2007-2008 Texas Instruments, Inc. + * Copyright (C) 2007-2008, 2011 Texas Instruments, Inc.   * Copyright (C) 2007-2011 Nokia Corporation   *   * Written by Paul Walmsley @@ -81,9 +81,6 @@ static int _pwrdm_register(struct powerdomain *pwrdm)  	if (!pwrdm || !pwrdm->name)  		return -EINVAL; -	if (!omap_chip_is(pwrdm->omap_chip)) -		return -EINVAL; -  	if (cpu_is_omap44xx() &&  	    pwrdm->prcm_partition == OMAP4430_INVALID_PRCM_PARTITION) {  		pr_err("powerdomain: %s: missing OMAP4 PRCM partition ID\n", @@ -194,36 +191,76 @@ static int _pwrdm_post_transition_cb(struct powerdomain *pwrdm, void *unused)  /* Public functions */  /** - * pwrdm_init - set up the powerdomain layer - * @pwrdms: array of struct powerdomain pointers to register - * @custom_funcs: func pointers for arch specific implementations + * pwrdm_register_platform_funcs - register powerdomain implementation fns + * @po: func pointers for arch specific implementations + * + * Register the list of function pointers used to implement the + * powerdomain functions on different OMAP SoCs.  Should be called + * before any other pwrdm_register*() function.  Returns -EINVAL if + * @po is null, -EEXIST if platform functions have already been + * registered, or 0 upon success. + */ +int pwrdm_register_platform_funcs(struct pwrdm_ops *po) +{ +	if (!po) +		return -EINVAL; + +	if (arch_pwrdm) +		return -EEXIST; + +	arch_pwrdm = po; + +	return 0; +} + +/** + * pwrdm_register_pwrdms - register SoC powerdomains + * @ps: pointer to an array of struct powerdomain to register   * - * Loop through the array of powerdomains @pwrdms, registering all - * that are available on the current CPU.  Also, program all - * powerdomain target state as ON; this is to prevent domains from - * hitting low power states (if bootloader has target states set to - * something other than ON) and potentially even losing context while - * PM is not fully initialized.  The PM late init code can then program - * the desired target state for all the power domains.  No return - * value. + * Register the powerdomains available on a particular OMAP SoC.  Must + * be called after pwrdm_register_platform_funcs().  May be called + * multiple times.  Returns -EACCES if called before + * pwrdm_register_platform_funcs(); -EINVAL if the argument @ps is + * null; or 0 upon success.   */ -void pwrdm_init(struct powerdomain **pwrdms, struct pwrdm_ops *custom_funcs) +int pwrdm_register_pwrdms(struct powerdomain **ps)  {  	struct powerdomain **p = NULL; -	struct powerdomain *temp_p; -	if (!custom_funcs) -		WARN(1, "powerdomain: No custom pwrdm functions registered\n"); -	else -		arch_pwrdm = custom_funcs; +	if (!arch_pwrdm) +		return -EEXIST; -	if (pwrdms) { -		for (p = pwrdms; *p; p++) -			_pwrdm_register(*p); -	} +	if (!ps) +		return -EINVAL; + +	for (p = ps; *p; p++) +		_pwrdm_register(*p); + +	return 0; +} + +/** + * pwrdm_complete_init - set up the powerdomain layer + * + * Do whatever is necessary to initialize registered powerdomains and + * powerdomain code.  Currently, this programs the next power state + * for each powerdomain to ON.  This prevents powerdomains from + * unexpectedly losing context or entering high wakeup latency modes + * with non-power-management-enabled kernels.  Must be called after + * pwrdm_register_pwrdms().  Returns -EACCES if called before + * pwrdm_register_pwrdms(), or 0 upon success. + */ +int pwrdm_complete_init(void) +{ +	struct powerdomain *temp_p; + +	if (list_empty(&pwrdm_list)) +		return -EACCES;  	list_for_each_entry(temp_p, &pwrdm_list, node)  		pwrdm_set_next_pwrst(temp_p, PWRDM_POWER_ON); + +	return 0;  }  /**  |