All of lore.kernel.org
 help / color / mirror / Atom feed
* [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs
       [not found] <[PATCH 02/10 V4] omap3: pm: introduce opp accessor functions>
@ 2009-12-12  5:00 ` Nishanth Menon
  2009-12-12  5:00   ` [PATCH 02/10 V5] omap3: pm: introduce opp accessor functions Nishanth Menon
  2009-12-16 19:59   ` [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs Kevin Hilman
  0 siblings, 2 replies; 10+ messages in thread
From: Nishanth Menon @ 2009-12-12  5:00 UTC (permalink / raw)
  To: Kevin Hilman; +Cc: linux-omap, Nishanth Menon

Hi,
Thanks for all the comments. Here are the *changed* patches since V5

What changed in V5:
* review comment incorporated
* vsel is deprecated now
* I seem to have hit a checkpatch.pl bug as in 
  http://lkml.org/lkml/2009/12/11/573, made me check the usage
  of __deprecated for struct params, and used it in a
  consistent manner to functions..
* More warnings added to build :( (deprecated ones ofcourse)
* removed OMAP_OPP_DEF_TERMINATOR
* 3430 and 3630 patches changed as a result

History:
V4: http://marc.info/?t=126033962600001&r=1&w=2
V3: http://marc.info/?t=125912234200001&r=1&w=2
V2: http://marc.info/?l=linux-omap&m=125809232732700&w=2
V1: http://marc.info/?l=linux-omap&m=125800488923479&w=2

Ref: http://elinux.org/OMAP_Power_Management#Future_directions

TODO: The list is still the same as in:
http://marc.info/?l=linux-omap&m=126033945313269&w=2

Regards,
Nishanth Menon

^ permalink raw reply	[flat|nested] 10+ messages in thread

* [PATCH 02/10 V5] omap3: pm: introduce opp accessor functions
  2009-12-12  5:00 ` [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs Nishanth Menon
@ 2009-12-12  5:00   ` Nishanth Menon
  2009-12-12  5:00     ` [PATCH 03/10 V5] omap3: pm: use opp accessor functions for omap34xx Nishanth Menon
  2009-12-16 19:59   ` [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs Kevin Hilman
  1 sibling, 1 reply; 10+ messages in thread
From: Nishanth Menon @ 2009-12-12  5:00 UTC (permalink / raw)
  Cc: linux-omap, Nishanth Menon, Benoit Cousson, Eduardo Valentin,
	Madhusudhan Chikkature Rajashekar, Paul Walmsley, Romit Dasgupta,
	Santosh Shilimkar, Sergio Alberto Aguirre Rodriguez, Tero Kristo,
	Thara Gopinath, Vishwanath Sripathy, Sanjeev Premi, Kevin Hilman

Modifies the initial patch From Sanjeev:
http://patchwork.kernel.org/patch/50998/
Discussions and comments from:
http://marc.info/?l=linux-omap&m=126033945313269&w=2
http://marc.info/?l=linux-omap&m=125482970102327&w=2
http://marc.info/?t=125809247500002&r=1&w=2
http://marc.info/?l=linux-omap&m=126025973426007&w=2
incorporated.

OMAP SOCs have a standard set of tuples consisting of frequency and
voltage pairs that the device will support per voltage domain. This
is called Operating Points or OPP. The actual definitions of OMAP
Operating Points varies over silicon within the same family of
devices. For a specific domain, you can have a set of
{frequency, voltage} pairs. As the kernel boots and more information
is available, a set of these are activated based on the precise
nature of device the kernel boots up on. It is interesting to
remember that each IP which belongs to a voltage domain may define
their own set of OPPs on top of this.

This introduces a common handling OPP mechanism accross all OMAPs.
As a start this is introduced for OMAP3 and intends to replace
current OMAP3 opp handling mechanism.

Note:
fields of struct omap_opp is currently exposed due to the necessity
that SRF and SR logic directly indexes the structure array fields.
The goal however, is to make the direct usage of omap_opp deprecated
and move to using these accessor functions. The usage in SRF and SR
indexes based on opp_id and hence opp_id is marked deprecated to
generate build warnings at least. Further, this usage necessitates
need of terminator entries at the start and end of opp_* tables which
are dynamically allocated.

The accessor function definitions were collaborated with Kevin, and
doing justice here, this implementation could not go with some of
the better suggestions from kevin due to constraint imposed by SRF
and SR. A better and more optimal implementation is definitely
possible once SRF and SR are cleanedup/replaced.

NOTE: OPP is a concept that can be used in all OMAPs, it is hence
introduced under plat-omap

Introduces warning:
arch/arm/plat-omap/opp.c: In function 'opp_get_voltage':
arch/arm/plat-omap/opp.c:53: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c: In function 'opp_get_opp_count':
arch/arm/plat-omap/opp.c:76: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c: In function 'opp_find_freq_exact':
arch/arm/plat-omap/opp.c:94: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:96: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:102: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c: In function 'opp_find_freq_approx':
arch/arm/plat-omap/opp.c:115: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:119: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:122: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:130: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c: In function 'omap_opp_populate':
arch/arm/plat-omap/opp.c:143: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:145: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:146: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c: In function 'opp_add':
arch/arm/plat-omap/opp.c:160: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:167: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:191: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/plat-omap/opp.c:194: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:199: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/plat-omap/opp.c: In function 'opp_init_list':
arch/arm/plat-omap/opp.c:236: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/plat-omap/opp.c:240: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/plat-omap/opp.c:249: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)

Cc: Benoit Cousson <b-cousson@ti.com>
Cc: Eduardo Valentin <eduardo.valentin@nokia.com>
Cc: Madhusudhan Chikkature Rajashekar <madhu.cr@ti.com>
Cc: Paul Walmsley <paul@pwsan.com>
Cc: Romit Dasgupta <romit@ti.com>
Cc: Santosh Shilimkar <santosh.shilimkar@ti.com>
Cc: Sergio Alberto Aguirre Rodriguez <saaguirre@ti.com>
Cc: Tero Kristo <Tero.Kristo@nokia.com>
Cc: Thara Gopinath <thara@ti.com>
Cc: Vishwanath Sripathy <vishwanath.bs@ti.com>

Signed-off-by: Sanjeev Premi <premi@ti.com>
Signed-off-by: Kevin Hilman <khilman@deeprootsystems.com>
Signed-off-by: Nishanth Menon <nm@ti.com>
---
Kevin,
I have put your Signed-off-by to ack your contribs. pending
formal confirmation ofcourse.

 arch/arm/plat-omap/Makefile           |    3 +
 arch/arm/plat-omap/include/plat/opp.h |  231 ++++++++++++++++++++++++++++
 arch/arm/plat-omap/opp.c              |  271 +++++++++++++++++++++++++++++++++
 3 files changed, 505 insertions(+), 0 deletions(-)
 create mode 100644 arch/arm/plat-omap/include/plat/opp.h
 create mode 100644 arch/arm/plat-omap/opp.c

diff --git a/arch/arm/plat-omap/Makefile b/arch/arm/plat-omap/Makefile
index 95f8413..e9cf601 100644
--- a/arch/arm/plat-omap/Makefile
+++ b/arch/arm/plat-omap/Makefile
@@ -12,6 +12,9 @@ obj-  :=
 # OCPI interconnect support for 1710, 1610 and 5912
 obj-$(CONFIG_ARCH_OMAP16XX) += ocpi.o
 
+# OPP support in (OMAP3+ only at the moment)
+obj-$(CONFIG_ARCH_OMAP3) += opp.o
+
 # omap_device support (OMAP2+ only at the moment)
 obj-$(CONFIG_ARCH_OMAP2) += omap_device.o
 obj-$(CONFIG_ARCH_OMAP3) += omap_device.o
diff --git a/arch/arm/plat-omap/include/plat/opp.h b/arch/arm/plat-omap/include/plat/opp.h
new file mode 100644
index 0000000..5d5d21b
--- /dev/null
+++ b/arch/arm/plat-omap/include/plat/opp.h
@@ -0,0 +1,231 @@
+/*
+ * OMAP OPP Interface
+ *
+ * Copyright (C) 2009 Texas Instruments Incorporated.
+ *	Nishanth Menon
+ * Copyright (C) 2009 Deep Root Systems, LLC.
+ *	Kevin Hilman
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+#ifndef __ASM_ARM_OMAP_OPP_H
+#define __ASM_ARM_OMAP_OPP_H
+
+/**
+ * struct omap_opp - OMAP OPP description structure
+ * @enabled:	true/false - marking this OPP as enabled/disabled
+ * @rate:	Frequency in hertz
+ * @opp_id:	(DEPRECATED) opp identifier
+ * @vsel:	Voltage in volt processor level(this usage is
+ *		DEPRECATED to use Voltage in microvolts in future)
+ *		uV = ((vsel * 12.5) + 600) * 1000
+ *
+ * This structure stores the OPP information for a given domain.
+ * Due to legacy reasons, this structure is currently exposed and
+ * will soon be removed elsewhere and will only be used as a handle
+ * from the OPP internal referencing mechanism
+ */
+struct omap_opp {
+	bool enabled;
+	unsigned long rate;
+	u8 __deprecated opp_id;
+	u16 __deprecated vsel;
+};
+
+/**
+ * opp_get_voltage() - Gets the voltage corresponding to an opp
+ * @opp:	opp for which voltage has to be returned for
+ *
+ * Return voltage in micro volt corresponding to the opp, else
+ * return 0
+ */
+unsigned long opp_get_voltage(const struct omap_opp *opp);
+
+/**
+ * opp_get_freq() - Gets the frequency corresponding to an opp
+ * @opp:	opp for which frequency has to be returned for
+ *
+ * Return frequency in hertz corresponding to the opp, else
+ * return 0
+ */
+unsigned long opp_get_freq(const struct omap_opp *opp);
+
+/**
+ * opp_get_opp_count() - Get number of opps enabled in the opp list
+ * @num:	returns the number of opps
+ * @oppl:	opp list
+ *
+ * This functions returns the number of opps if there are any OPPs enabled,
+ * else returns corresponding error value.
+ */
+int opp_get_opp_count(const struct omap_opp *oppl);
+
+/**
+ * opp_find_freq_exact() - search for an exact frequency
+ * @oppl:	OPP list
+ * @freq:	frequency to search for
+ * @enabled:	enabled/disabled OPP to search for
+ *
+ * searches for the match in the opp list and returns handle to the matching
+ * opp if found, else returns ERR_PTR in case of error and should be handled
+ * using IS_ERR.
+ *
+ * Note enabled is a modifier for the search. if enabled=true, then the match is
+ * for exact matching frequency and is enabled. if true, the match is for exact
+ * frequency which is disabled.
+ */
+struct omap_opp *opp_find_freq_exact(struct omap_opp *oppl,
+				     unsigned long freq, bool enabled);
+
+#define OPP_SEARCH_HIGH		(0 << 1)
+#define OPP_SEARCH_LOW		(1 << 1)
+/**
+ * opp_find_freq_approx() - Search for an rounded freq
+ * @oppl:	Starting list
+ * @freq:	Start frequency
+ * @dir_flag:	Search direction
+ *		OPP_SEARCH_HIGH - search for next highest freq
+ *		OPP_SEARCH_LOW - search for next lowest freq
+ *
+ * Search for the higher/lower *enabled* OPP from a starting freq
+ * from a start opp list.
+ *
+ * Returns *opp and *freq is populated with the next match,
+ * else returns NULL
+ * opp if found, else returns ERR_PTR in case of error.
+ *
+ * Example usages:
+ *	* find match/next highest available frequency
+ *	freq = 350000;
+ *	opp = opp_find_freq_approx(oppl, &freq, OPP_SEARCH_HIGH)))
+ *	if (IS_ERR(opp))
+ *		pr_err ("unable to find a higher frequency\n");
+ *	else
+ *		pr_info("match freq = %ld\n", freq);
+ *
+ *	* find match/next lowest available frequency
+ *	freq = 350000;
+ *	opp = opp_find_freq_approx(oppl, &freq, OPP_SEARCH_LOW)))
+ *	if (IS_ERR(opp))
+ *		pr_err ("unable to find a lower frequency\n");
+ *	else
+ *		pr_info("match freq = %ld\n", freq);
+ *
+ *	* print all supported frequencies in descending order *
+ *	opp = oppl;
+ *	freq = ULONG_MAX;
+ *	while (!IS_ERR(opp = opp_find_freq_approx(opp, &freq,
+ *		OPP_SEARCH_LOW))) {
+ *		pr_info("freq = %ld\n", freq);
+ *		freq--; * for next lower match *
+ *	}
+ *
+ *	* print all supported frequencies in ascending order *
+ *	opp = oppl;
+ *	freq = 0;
+ *	while (!IS_ERR(opp = opp_find_freq_approx(opp, &freq,
+ *			OPP_SEARCH_HIGH))) {
+ *		pr_info("freq = %ld\n", freq);
+ *		freq++; * for next higher match *
+ *	}
+ *
+ * NOTE: if we set freq as ULONG_MAX and search low, we get the highest enabled
+ * frequency
+ */
+struct omap_opp *opp_find_freq_approx(struct omap_opp *oppl,
+				      unsigned long *freq, u8 dir_flag);
+
+/**
+ * struct omap_opp_def - OMAP OPP Definition
+ * @enabled:	True/false - is this OPP enabled/disabled by default
+ * @freq:	Frequency in hertz corresponding to this OPP
+ * @u_volt:	Nominal voltage in microvolts corresponding to this OPP
+ *
+ * OMAP SOCs have a standard set of tuples consisting of frequency and voltage
+ * pairs that the device will support per voltage domain. This is called
+ * Operating Points or OPP. The actual definitions of OMAP Operating Points
+ * varies over silicon within the same family of devices. For a specific
+ * domain, you can have a set of {frequency, voltage} pairs and this is denoted
+ * by an array of omap_opp_def. As the kernel boots and more information is
+ * available, a set of these are activated based on the precise nature of
+ * device the kernel boots up on. It is interesting to remember that each IP
+ * which belongs to a voltage domain may define their own set of OPPs on top
+ * of this - but this is handled by the appropriate driver.
+ */
+struct omap_opp_def {
+	bool enabled;
+	unsigned long freq;
+	unsigned long u_volt;
+};
+
+/*
+ * Initialization wrapper used to define an OPP
+ * to point at the end of a terminator of a list of OPPs,
+ * use OMAP_OPP_DEF(0, 0, 0)
+ */
+#define OMAP_OPP_DEF(_enabled, _freq, _uv)	\
+{						\
+	.enabled	= _enabled,		\
+	.freq		= _freq,		\
+	.u_volt		= _uv,			\
+}
+
+/**
+ * opp_init_list() - Initialize an opp list from the opp definitions
+ * @opp_defs:	Initial opp definitions to create the list.
+ *
+ * This function creates a list of opp definitions and returns a handle.
+ * This list can be used to further validation/search/modifications. New
+ * opp entries can be added to this list by using opp_add().
+ *
+ * In the case of error, ERR_PTR is returned to the caller and should be
+ * appropriately handled with IS_ERR.
+ */
+struct omap_opp __init *opp_init_list(const struct omap_opp_def *opp_defs);
+
+/**
+ * opp_add()  - Add an OPP table from a table definitions
+ * @oppl:	List to add the OPP to
+ * @opp_def:	omap_opp_def to describe the OPP which we want to add to list.
+ *
+ * This function adds an opp definition to the opp list and returns
+ * a handle representing the new OPP list. This handle is then used for further
+ * validation, search, modification operations on the OPP list.
+ *
+ * This function returns the pointer to the allocated list through oppl if
+ * success, else corresponding ERR_PTR value. Caller should NOT free the oppl.
+ * opps_defs can be freed after use.
+ *
+ * NOTE: caller should assume that on success, oppl is probably populated with
+ * a new handle and the new handle should be used for further referencing
+ */
+struct omap_opp *opp_add(struct omap_opp *oppl,
+			 const struct omap_opp_def *opp_def);
+
+/**
+ * opp_enable() - Enable a specific OPP
+ * @opp:	Pointer to opp
+ *
+ * Enables a provided opp. If the operation is valid, this returns 0, else the
+ * corresponding error value.
+ *
+ * OPP used here is from the the opp_is_valid/opp_has_freq or other search
+ * functions
+ */
+int opp_enable(struct omap_opp *opp);
+
+/**
+ * opp_disable() - Disable a specific OPP
+ * @opp:	Pointer to opp
+ *
+ * Disables a provided opp. If the operation is valid, this returns 0, else the
+ * corresponding error value.
+ *
+ * OPP used here is from the the opp_is_valid/opp_has_freq or other search
+ * functions
+ */
+int opp_disable(struct omap_opp *opp);
+
+#endif		/* __ASM_ARM_OMAP_OPP_H */
diff --git a/arch/arm/plat-omap/opp.c b/arch/arm/plat-omap/opp.c
new file mode 100644
index 0000000..c4dc07b
--- /dev/null
+++ b/arch/arm/plat-omap/opp.c
@@ -0,0 +1,271 @@
+/*
+ * OMAP OPP Interface
+ *
+ * Copyright (C) 2009 Texas Instruments Incorporated.
+ *	Nishanth Menon
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 as
+ * published by the Free Software Foundation.
+ */
+
+#include <linux/kernel.h>
+#include <linux/errno.h>
+#include <linux/err.h>
+#include <linux/init.h>
+#include <linux/slab.h>
+
+#include <plat/opp.h>
+
+/*
+ * DEPRECATED: Meant to detect end of opp array
+ * This is meant to help co-exist with current SRF etc
+ * TODO: REMOVE!
+ */
+#define OPP_TERM(opp) (!(opp)->rate && !(opp)->vsel && !(opp)->enabled)
+
+/*
+ * DEPRECATED: Meant to convert vsel value to uVolt
+ * This is meant to help co-exist with current SRF etc
+ * TODO: REMOVE!
+ */
+static inline unsigned long vsel_to_uv(const u8 vsel)
+{
+	return (((vsel * 125) + 6000)) * 100;
+}
+
+/*
+ * DEPRECATED: Meant to convert uVolt to vsel value
+ * This is meant to help co-exist with current SRF etc
+ * TODO: REMOVE!
+ */
+static inline unsigned char uv_to_vsel(unsigned long uV)
+{
+	return ((uV / 100) - 6000) / 125;
+}
+
+unsigned long opp_get_voltage(const struct omap_opp *opp)
+{
+	if (unlikely(!opp || IS_ERR(opp)) || !opp->enabled) {
+		pr_err("%s: Invalid parameters being passed\n", __func__);
+		return 0;
+	}
+	return vsel_to_uv(opp->vsel);
+}
+
+unsigned long opp_get_freq(const struct omap_opp *opp)
+{
+	if (unlikely(!opp || IS_ERR(opp)) || !opp->enabled) {
+		pr_err("%s: Invalid parameters being passed\n", __func__);
+		return 0;
+	}
+	return opp->rate;
+}
+
+int opp_get_opp_count(const struct omap_opp *oppl)
+{
+	struct omap_opp *opp;
+	u8 n = 0;
+
+	if (unlikely(!oppl || IS_ERR(oppl))) {
+		pr_err("%s: Invalid parameters being passed\n", __func__);
+		return -EINVAL;
+	}
+	opp = (struct omap_opp *)oppl;
+	opp++;			/* skip initial terminator */
+	while (!OPP_TERM(opp)) {
+		if (opp->enabled)
+			n++;
+		opp++;
+	}
+	return n;
+}
+
+struct omap_opp *opp_find_freq_exact(struct omap_opp *oppl,
+				     unsigned long freq, bool enabled)
+{
+	struct omap_opp *opp = (struct omap_opp *)oppl;
+
+	if (unlikely(!oppl || IS_ERR(oppl))) {
+		pr_err("%s: Invalid parameters being passed\n", __func__);
+		return ERR_PTR(-EINVAL);
+	}
+	/* skip initial terminator */
+	if (OPP_TERM(opp))
+		opp++;
+	while (!OPP_TERM(opp)) {
+		if ((opp->rate == freq) && (opp->enabled == enabled))
+			break;
+		opp++;
+	}
+
+	return OPP_TERM(opp) ? ERR_PTR(-ENOENT) : opp;
+}
+
+struct omap_opp *opp_find_freq_approx(struct omap_opp *oppl,
+				      unsigned long *freq, u8 dir_flag)
+{
+	struct omap_opp *opp = (struct omap_opp *)oppl;
+
+	if (unlikely(!oppl || IS_ERR(oppl) || !freq || IS_ERR(freq))) {
+		pr_err("%s: Invalid parameters being passed\n", __func__);
+		return ERR_PTR(-EINVAL);
+	}
+	/* skip initial terminator */
+	if (OPP_TERM(opp)) {
+		opp++;
+		/* If searching init list for a high val, skip to very top */
+		if (dir_flag == OPP_SEARCH_LOW)
+			while (!OPP_TERM(opp + 1))
+				opp++;
+	}
+	while (!OPP_TERM(opp)) {
+		if (opp->enabled &&
+		    (((dir_flag == OPP_SEARCH_HIGH) && (opp->rate >= *freq)) ||
+		     ((dir_flag == OPP_SEARCH_LOW) && (opp->rate <= *freq))))
+			break;
+		opp += (dir_flag == OPP_SEARCH_LOW) ? -1 : 1;
+	}
+
+	if (OPP_TERM(opp))
+		return ERR_PTR(-ENOENT);
+
+	*freq = opp->rate;
+	return opp;
+}
+
+/* wrapper to reuse converting opp_def to opp struct */
+static void omap_opp_populate(struct omap_opp *opp,
+			      const struct omap_opp_def *opp_def)
+{
+	opp->rate = opp_def->freq;
+	opp->enabled = opp_def->enabled;
+	opp->vsel = uv_to_vsel(opp_def->u_volt);
+	/* round off to higher voltage */
+	if (opp_def->u_volt > vsel_to_uv(opp->vsel))
+		opp->vsel++;
+}
+
+struct omap_opp *opp_add(struct omap_opp *oppl,
+			 const struct omap_opp_def *opp_def)
+{
+	struct omap_opp *opp, *oppt, *oppr;
+	u8 n, i, ins;
+
+	if (unlikely(!oppl || IS_ERR(oppl) || !opp_def || IS_ERR(opp_def))) {
+		pr_err("%s: Invalid params being passed\n", __func__);
+		return ERR_PTR(-EINVAL);
+	}
+	/* need a start terminator.. */
+	if (unlikely(!OPP_TERM(oppl))) {
+		pr_err("%s: Expected a start terminator!!\n", __func__);
+		return ERR_PTR(-EINVAL);
+	}
+	n = 0;
+	opp = oppl;
+	opp++;
+	while (!OPP_TERM(opp)) {
+		n++;
+		opp++;
+	}
+	/* lets now reallocate memory */
+	oppr = kmalloc(sizeof(struct omap_opp) * (n + 3), GFP_KERNEL);
+	if (!oppr) {
+		pr_err("%s: No memory for new opp array\n", __func__);
+		return ERR_PTR(-ENOMEM);
+	}
+
+	/* Simple insertion sort */
+	opp = oppl;
+	oppt = oppr;
+	ins = 0;
+	i = 0;
+	do {
+		if (ins || opp->rate < opp_def->freq) {
+			memcpy(oppt, opp, sizeof(struct omap_opp));
+			opp++;
+		} else {
+			omap_opp_populate(oppt, opp_def);
+			ins++;
+		}
+		oppt->opp_id = i;
+		oppt++;
+		i++;
+	} while (!OPP_TERM(opp));
+
+	/* If nothing got inserted, this belongs to the end */
+	if (!ins) {
+		omap_opp_populate(oppt, opp_def);
+		oppt->opp_id = i;
+		oppt++;
+	}
+	/* Put the terminator back on */
+	memcpy(oppt, opp, sizeof(struct omap_opp));
+
+	/* Free the old list */
+	kfree(oppl);
+
+	return oppr;
+}
+
+struct omap_opp __init *opp_init_list(const struct omap_opp_def *opp_defs)
+{
+	struct omap_opp_def *t = (struct omap_opp_def *)opp_defs;
+	struct omap_opp *opp, *oppl;
+	u8 n = 0, i = 1;
+
+	if (unlikely(!opp_defs || IS_ERR(opp_defs))) {
+		pr_err("%s: Invalid params being passed\n", __func__);
+		return ERR_PTR(-EINVAL);
+	}
+	/* Grab a count */
+	while (t->enabled || t->freq || t->u_volt) {
+		n++;
+		t++;
+	}
+
+	oppl = kmalloc(sizeof(struct omap_opp) * (n + 2), GFP_KERNEL);
+	if (!oppl) {
+		pr_err("%s: No memory for opp array\n", __func__);
+		return ERR_PTR(-ENOMEM);
+	}
+	opp = oppl;
+	/* Setup start terminator - SRF depends on this for indexing :( */
+	opp->rate = 0;
+	opp->enabled = 0;
+	opp->vsel = 0;
+	opp++;
+	while (n) {
+		omap_opp_populate(opp, opp_defs);
+		opp->opp_id = i;
+		n--;
+		opp++;
+		opp_defs++;
+		i++;
+	}
+	/* Setup terminator - this is for our search algos */
+	opp->rate = 0;
+	opp->enabled = 0;
+	opp->vsel = 0;
+	return oppl;
+}
+
+int opp_enable(struct omap_opp *opp)
+{
+	if (unlikely(!opp || IS_ERR(opp))) {
+		pr_err("%s: Invalid parameters being passed\n", __func__);
+		return -EINVAL;
+	}
+	opp->enabled = true;
+	return 0;
+}
+
+int opp_disable(struct omap_opp *opp)
+{
+	if (unlikely(!opp || IS_ERR(opp))) {
+		pr_err("%s: Invalid parameters being passed\n", __func__);
+		return -EINVAL;
+	}
+	opp->enabled = false;
+	return 0;
+}
-- 
1.6.3.3


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [PATCH 03/10 V5] omap3: pm: use opp accessor functions for omap34xx
  2009-12-12  5:00   ` [PATCH 02/10 V5] omap3: pm: introduce opp accessor functions Nishanth Menon
@ 2009-12-12  5:00     ` Nishanth Menon
  2009-12-12  5:00       ` [PATCH 09/10 V5] omap3: pm: introduce 3630 opps Nishanth Menon
  0 siblings, 1 reply; 10+ messages in thread
From: Nishanth Menon @ 2009-12-12  5:00 UTC (permalink / raw)
  Cc: linux-omap, Nishanth Menon, Benoit Cousson, Eduardo Valentin,
	Kevin Hilman, Madhusudhan Chikkature Rajashekar, Paul Walmsley,
	Romit Dasgupta, Sanjeev Premi, Santosh Shilimkar,
	Sergio Alberto Aguirre Rodriguez, Tero Kristo, Thara Gopinath,
	Vishwanath Sripathy

Move the definitions from omap3-opp.h to pm34xx.c. The definitions
are now based on omap_opp_def instead of omap_opp itself.
Since the opp.h has the omap_opp definition, omap-pm.h conflicts and
has been removed in favor of opp.h.

omap3_pm_init_opp_table is used to initialize the OPP table and
relevant board files which have omap2_init_common_hw called with opp
arrays have been updated with omap3_pm_init_opp_table.

This change now allows us to dynamically register OPPs to the system
based on silicon type we detect.

NOTE: This introduces the following warnings highlighting areas we
need to cleanup:
arch/arm/mach-omap2/smartreflex.c: In function 'get_opp':
arch/arm/mach-omap2/smartreflex.c:161: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/smartreflex.c:164: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/smartreflex.c:166: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/smartreflex.c:168: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/smartreflex.c: In function 'sr_configure_vp':
arch/arm/mach-omap2/smartreflex.c:307: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/smartreflex.c:309: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/smartreflex.c:353: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/smartreflex.c:355: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/smartreflex.c: In function 'sr_reset_voltage':
arch/arm/mach-omap2/smartreflex.c:461: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/smartreflex.c:472: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/smartreflex.c: In function 'sr_enable':
arch/arm/mach-omap2/smartreflex.c:582: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/smartreflex.c:600: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/resource34xx.c: In function 'get_opp':
arch/arm/mach-omap2/resource34xx.c:165: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/resource34xx.c:168: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/resource34xx.c:170: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/resource34xx.c:172: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/resource34xx.c: In function 'program_opp':
arch/arm/mach-omap2/resource34xx.c:284: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/resource34xx.c:285: warning: 'opp_id' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:33)
arch/arm/mach-omap2/resource34xx.c:293: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/resource34xx.c:308: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)
arch/arm/mach-omap2/resource34xx.c:309: warning: 'vsel' is deprecated (declared at arch/arm/plat-omap/include/plat/opp.h:34)

Cc: Benoit Cousson <b-cousson@ti.com>
Cc: Eduardo Valentin <eduardo.valentin@nokia.com>
Cc: Kevin Hilman <khilman@deeprootsystems.com>
Cc: Madhusudhan Chikkature Rajashekar <madhu.cr@ti.com>
Cc: Paul Walmsley <paul@pwsan.com>
Cc: Romit Dasgupta <romit@ti.com>
Cc: Sanjeev Premi <premi@ti.com>
Cc: Santosh Shilimkar <santosh.shilimkar@ti.com>
Cc: Sergio Alberto Aguirre Rodriguez <saaguirre@ti.com>
Cc: Tero Kristo <Tero.Kristo@nokia.com>
Cc: Thara Gopinath <thara@ti.com>
Cc: Vishwanath Sripathy <vishwanath.bs@ti.com>

Signed-off-by: Nishanth Menon <nm@ti.com>
---
 arch/arm/mach-omap2/board-3430sdp.c       |    1 +
 arch/arm/mach-omap2/board-omap3beagle.c   |    1 +
 arch/arm/mach-omap2/board-omap3evm.c      |    1 +
 arch/arm/mach-omap2/board-rx51.c          |    1 +
 arch/arm/mach-omap2/board-zoom2.c         |    2 +
 arch/arm/mach-omap2/omap3-opp.h           |   58 +-----------------------
 arch/arm/mach-omap2/pm.h                  |    6 +++
 arch/arm/mach-omap2/pm34xx.c              |   68 +++++++++++++++++++++++++++++
 arch/arm/plat-omap/include/plat/omap-pm.h |   17 +-------
 9 files changed, 84 insertions(+), 71 deletions(-)

diff --git a/arch/arm/mach-omap2/board-3430sdp.c b/arch/arm/mach-omap2/board-3430sdp.c
index eac529f..0ec8327 100644
--- a/arch/arm/mach-omap2/board-3430sdp.c
+++ b/arch/arm/mach-omap2/board-3430sdp.c
@@ -220,6 +220,7 @@ static void __init omap_3430sdp_init_irq(void)
 {
 	omap_board_config = sdp3430_config;
 	omap_board_config_size = ARRAY_SIZE(sdp3430_config);
+	omap3_pm_init_opp_table();
 	omap3_pm_init_vc(&omap3_setuptime_table);
 	omap3_pm_init_cpuidle(omap3_cpuidle_params_table);
 	omap2_init_common_hw(hyb18m512160af6_sdrc_params, NULL, omap3_mpu_rate_table,
diff --git a/arch/arm/mach-omap2/board-omap3beagle.c b/arch/arm/mach-omap2/board-omap3beagle.c
index 2ec3520..a937238 100644
--- a/arch/arm/mach-omap2/board-omap3beagle.c
+++ b/arch/arm/mach-omap2/board-omap3beagle.c
@@ -361,6 +361,7 @@ static void __init omap3_beagle_init_irq(void)
 {
 	omap_board_config = omap3_beagle_config;
 	omap_board_config_size = ARRAY_SIZE(omap3_beagle_config);
+	omap3_pm_init_opp_table();
 	omap2_init_common_hw(mt46h32m32lf6_sdrc_params,
 			     mt46h32m32lf6_sdrc_params, omap3_mpu_rate_table,
 			     omap3_dsp_rate_table, omap3_l3_rate_table);
diff --git a/arch/arm/mach-omap2/board-omap3evm.c b/arch/arm/mach-omap2/board-omap3evm.c
index 8130eca..44a5861 100644
--- a/arch/arm/mach-omap2/board-omap3evm.c
+++ b/arch/arm/mach-omap2/board-omap3evm.c
@@ -404,6 +404,7 @@ static void __init omap3_evm_init_irq(void)
 {
 	omap_board_config = omap3_evm_config;
 	omap_board_config_size = ARRAY_SIZE(omap3_evm_config);
+	omap3_pm_init_opp_table();
 	omap2_init_common_hw(mt46h32m32lf6_sdrc_params, NULL, omap3_mpu_rate_table,
 	                     omap3_dsp_rate_table, omap3_l3_rate_table);
 	omap_init_irq();
diff --git a/arch/arm/mach-omap2/board-rx51.c b/arch/arm/mach-omap2/board-rx51.c
index 2f1c2be..997fd1c 100644
--- a/arch/arm/mach-omap2/board-rx51.c
+++ b/arch/arm/mach-omap2/board-rx51.c
@@ -103,6 +103,7 @@ static void __init rx51_init_irq(void)
 
 	omap_board_config = rx51_config;
 	omap_board_config_size = ARRAY_SIZE(rx51_config);
+	omap3_pm_init_opp_table();
 	omap3_pm_init_cpuidle(rx51_cpuidle_params);
 	sdrc_params = rx51_get_sdram_timings();
 	omap2_init_common_hw(sdrc_params, sdrc_params,
diff --git a/arch/arm/mach-omap2/board-zoom2.c b/arch/arm/mach-omap2/board-zoom2.c
index dcc5fb8..9d5b078 100644
--- a/arch/arm/mach-omap2/board-zoom2.c
+++ b/arch/arm/mach-omap2/board-zoom2.c
@@ -24,10 +24,12 @@
 #include <mach/board-zoom.h>
 
 #include "sdram-micron-mt46h32m32lf-6.h"
+#include "pm.h"
 #include "omap3-opp.h"
 
 static void __init omap_zoom2_init_irq(void)
 {
+	omap3_pm_init_opp_table();
 	omap2_init_common_hw(mt46h32m32lf6_sdrc_params,
 				 mt46h32m32lf6_sdrc_params, omap3_mpu_rate_table,
 				 omap3_dsp_rate_table, omap3_l3_rate_table);
diff --git a/arch/arm/mach-omap2/omap3-opp.h b/arch/arm/mach-omap2/omap3-opp.h
index 42557e1..994d8d4 100644
--- a/arch/arm/mach-omap2/omap3-opp.h
+++ b/arch/arm/mach-omap2/omap3-opp.h
@@ -3,60 +3,8 @@
 
 #include <plat/omap-pm.h>
 
-/* MPU speeds */
-#define S600M   600000000
-#define S550M   550000000
-#define S500M   500000000
-#define S250M   250000000
-#define S125M   125000000
-
-/* DSP speeds */
-#define S430M   430000000
-#define S400M   400000000
-#define S360M   360000000
-#define S180M   180000000
-#define S90M    90000000
-
-/* L3 speeds */
-#define S83M    83000000
-#define S166M   166000000
-
-static struct omap_opp omap3_mpu_rate_table[] = {
-	{0, 0, 0, 0},
-	/*OPP1*/
-	{true, S125M, VDD1_OPP1, 0x1E},
-	/*OPP2*/
-	{true, S250M, VDD1_OPP2, 0x26},
-	/*OPP3*/
-	{true, S500M, VDD1_OPP3, 0x30},
-	/*OPP4*/
-	{true, S550M, VDD1_OPP4, 0x36},
-	/*OPP5*/
-	{true, S600M, VDD1_OPP5, 0x3C},
-};
-
-static struct omap_opp omap3_l3_rate_table[] = {
-	{0, 0, 0, 0},
-	/*OPP1*/
-	{false, 0, VDD2_OPP1, 0x1E},
-	/*OPP2*/
-	{true, S83M, VDD2_OPP2, 0x24},
-	/*OPP3*/
-	{true, S166M, VDD2_OPP3, 0x2C},
-};
-
-static struct omap_opp omap3_dsp_rate_table[] = {
-	{0, 0, 0, 0},
-	/*OPP1*/
-	{true, S90M, VDD1_OPP1, 0x1E},
-	/*OPP2*/
-	{true, S180M, VDD1_OPP2, 0x26},
-	/*OPP3*/
-	{true, S360M, VDD1_OPP3, 0x30},
-	/*OPP4*/
-	{true, S400M, VDD1_OPP4, 0x36},
-	/*OPP5*/
-	{true, S430M, VDD1_OPP5, 0x3C},
-};
+extern struct omap_opp *omap3_mpu_rate_table;
+extern struct omap_opp *omap3_dsp_rate_table;
+extern struct omap_opp *omap3_l3_rate_table;
 
 #endif
diff --git a/arch/arm/mach-omap2/pm.h b/arch/arm/mach-omap2/pm.h
index 7bc86b6..80a1c1d 100644
--- a/arch/arm/mach-omap2/pm.h
+++ b/arch/arm/mach-omap2/pm.h
@@ -58,6 +58,12 @@ static inline void omap3_pm_init_cpuidle(
 {
 }
 #endif
+/**
+ * omap3_pm_init_opp_table - OMAP opp table lookup called after cpu is detected.
+ * Initialize the basic opp table here, board files could choose to modify opp
+ * table after the basic initialization
+ */
+extern void omap3_pm_init_opp_table(void);
 
 extern int resource_set_opp_level(int res, u32 target_level, int flags);
 extern int resource_access_opp_lock(int res, int delta);
diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c
index 627a509..f9d061d 100644
--- a/arch/arm/mach-omap2/pm34xx.c
+++ b/arch/arm/mach-omap2/pm34xx.c
@@ -40,6 +40,7 @@
 #include <plat/dmtimer.h>
 #include <plat/usb.h>
 
+#include <plat/opp.h>
 #include <plat/resource.h>
 
 #include <asm/tlbflush.h>
@@ -52,6 +53,7 @@
 #include "prm.h"
 #include "pm.h"
 #include "sdrc.h"
+#include "omap3-opp.h"
 
 static int regset_save_on_suspend;
 
@@ -100,6 +102,52 @@ static struct prm_setup_vc prm_setup = {
 	.vdd1_off = 0x00,	/* 0.6v */
 };
 
+static struct omap_opp_def __initdata omap34xx_mpu_rate_table[] = {
+	/* OPP1 */
+	OMAP_OPP_DEF(true, 125000000, 975000),
+	/* OPP2 */
+	OMAP_OPP_DEF(true, 250000000, 1075000),
+	/* OPP3 */
+	OMAP_OPP_DEF(true, 500000000, 1200000),
+	/* OPP4 */
+	OMAP_OPP_DEF(true, 550000000, 1270000),
+	/* OPP5 */
+	OMAP_OPP_DEF(true, 600000000, 1350000),
+	/* Terminator */
+	OMAP_OPP_DEF(0, 0, 0)
+};
+
+static struct omap_opp_def __initdata omap34xx_l3_rate_table[] = {
+	/* OPP1 */
+	OMAP_OPP_DEF(false, 0, 975000),
+	/* OPP2 */
+	OMAP_OPP_DEF(true, 83000000, 1050000),
+	/* OPP3 */
+	OMAP_OPP_DEF(true, 166000000, 1150000),
+	/* Terminator */
+	OMAP_OPP_DEF(0, 0, 0)
+};
+
+static struct omap_opp_def __initdata omap34xx_dsp_rate_table[] = {
+	/* OPP1 */
+	OMAP_OPP_DEF(true, 90000000, 975000),
+	/* OPP2 */
+	OMAP_OPP_DEF(true, 180000000, 1075000),
+	/* OPP3 */
+	OMAP_OPP_DEF(true, 360000000, 1200000),
+	/* OPP4 */
+	OMAP_OPP_DEF(true, 400000000, 1270000),
+	/* OPP5 */
+	OMAP_OPP_DEF(true, 430000000, 1350000),
+	/* Terminator */
+	OMAP_OPP_DEF(0, 0, 0)
+};
+
+/* OMAP3 Rate Table */
+struct omap_opp *omap3_mpu_rate_table;
+struct omap_opp *omap3_dsp_rate_table;
+struct omap_opp *omap3_l3_rate_table;
+
 static inline void omap3_per_save_context(void)
 {
 	omap_gpio_save_context();
@@ -1248,6 +1296,26 @@ static void __init configure_vc(void)
 	pm_dbg_regset_init(2);
 }
 
+void __init omap3_pm_init_opp_table(void)
+{
+	int i;
+	struct omap_opp_def *omap34xx_opp_def_list[] = {
+		omap34xx_mpu_rate_table,
+		omap34xx_l3_rate_table,
+		omap34xx_dsp_rate_table
+	};
+	struct omap_opp **omap3_rate_tables[] = {
+		&omap3_mpu_rate_table,
+		&omap3_l3_rate_table,
+		&omap3_dsp_rate_table
+	};
+	for (i = 0; i < ARRAY_SIZE(omap3_rate_tables); i++) {
+		*omap3_rate_tables[i] = opp_init_list(omap34xx_opp_def_list[i]);
+		/* We dont want half configured system at the moment */
+		BUG_ON(IS_ERR(omap3_rate_tables[i]));
+	}
+}
+
 static int __init omap3_pm_early_init(void)
 {
 	prm_clear_mod_reg_bits(OMAP3430_OFFMODE_POL, OMAP3430_GR_MOD,
diff --git a/arch/arm/plat-omap/include/plat/omap-pm.h b/arch/arm/plat-omap/include/plat/omap-pm.h
index 5dc2048..aa36339 100644
--- a/arch/arm/plat-omap/include/plat/omap-pm.h
+++ b/arch/arm/plat-omap/include/plat/omap-pm.h
@@ -18,22 +18,7 @@
 #include <linux/cpufreq.h>
 
 #include "powerdomain.h"
-
-/**
- * struct omap_opp - clock frequency-to-OPP ID table for DSP, MPU
- * @enabled: enabled if true, disabled if false
- * @rate: target clock rate
- * @opp_id: OPP ID
- * @min_vdd: minimum VDD1 voltage (in millivolts) for this OPP
- *
- * Operating performance point data.  Can vary by OMAP chip and board.
- */
-struct omap_opp {
-	bool enabled;
-	unsigned long rate;
-	u8 opp_id;
-	u16 vsel;
-};
+#include <plat/opp.h>
 
 extern struct omap_opp *mpu_opps;
 extern struct omap_opp *dsp_opps;
-- 
1.6.3.3


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* [PATCH 09/10 V5] omap3: pm: introduce 3630 opps
  2009-12-12  5:00     ` [PATCH 03/10 V5] omap3: pm: use opp accessor functions for omap34xx Nishanth Menon
@ 2009-12-12  5:00       ` Nishanth Menon
  0 siblings, 0 replies; 10+ messages in thread
From: Nishanth Menon @ 2009-12-12  5:00 UTC (permalink / raw)
  Cc: linux-omap, Nishanth Menon, Benoit Cousson, Eduardo Valentin,
	Kevin Hilman, Madhusudhan Chikkature Rajashekar, Paul Walmsley,
	Romit Dasgupta, Sanjeev Premi, Santosh Shilimkar,
	Sergio Alberto Aguirre Rodriguez, Tero Kristo, Thara Gopinath,
	Vishwanath Sripathy

Introduce the OMAP3630 OPPs including the defined OPP tuples.

Further information on OMAP3630 can be found here:
http://focus.ti.com/general/docs/wtbu/wtbuproductcontent.tsp?templateId=6123&navigationId=12836&contentId=52606

OMAP36xx family introduces:
VDD1 with 4 OPPs, of which OPP3 & 4 are available only on devices yet
to be introduced in 36xx family. Meanwhile, VDD2 has 2 opps.

Device Support of OPPs->
           |<-3630-600->| (default)
           |<-      3630-800    ->| (device: TBD)
           |<-      3630-1000            ->| (device: TBD)
H/w OPP-> OPP50 OPP100       OPP-Turbo   OPP1G-SB
VDD1      OPP1  OPP2         OPP3        OPP4
VDD2      OPP1  OPP2         OPP2        OPP2

Note:
a) TI h/w naming for OPPs are now standardized in terms of OPP50, 100,
   Turbo and SB. This maps as shown above to the opp IDs (s/w term).
b) For boards which need custom VDD1/2 OPPs, the opp table can be
   updated by the board file on a need basis after the
   omap3_pm_init_opp_table call. The OPPs introduced here are the
   official OPP table at this point in time.

Cc: Benoit Cousson <b-cousson@ti.com>
Cc: Eduardo Valentin <eduardo.valentin@nokia.com>
Cc: Kevin Hilman <khilman@deeprootsystems.com>
Cc: Madhusudhan Chikkature Rajashekar <madhu.cr@ti.com>
Cc: Paul Walmsley <paul@pwsan.com>
Cc: Romit Dasgupta <romit@ti.com>
Cc: Sanjeev Premi <premi@ti.com>
Cc: Santosh Shilimkar <santosh.shilimkar@ti.com>
Cc: Sergio Alberto Aguirre Rodriguez <saaguirre@ti.com>
Cc: Tero Kristo <Tero.Kristo@nokia.com>
Cc: Thara Gopinath <thara@ti.com>
Cc: Vishwanath Sripathy <vishwanath.bs@ti.com>

Signed-off-by: Nishanth Menon <nm@ti.com>
---
 arch/arm/mach-omap2/pm34xx.c |   46 +++++++++++++++++++++++++++++++++++++++++-
 1 files changed, 45 insertions(+), 1 deletions(-)

diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c
index f9d061d..73bfc18 100644
--- a/arch/arm/mach-omap2/pm34xx.c
+++ b/arch/arm/mach-omap2/pm34xx.c
@@ -143,6 +143,41 @@ static struct omap_opp_def __initdata omap34xx_dsp_rate_table[] = {
 	OMAP_OPP_DEF(0, 0, 0)
 };
 
+static struct omap_opp_def __initdata omap36xx_mpu_rate_table[] = {
+	/* OPP1 - OPP50 */
+	OMAP_OPP_DEF(true,  300000000, 930000),
+	/* OPP2 - OPP100 */
+	OMAP_OPP_DEF(true,  600000000, 1100000),
+	/* OPP3 - OPP-Turbo */
+	OMAP_OPP_DEF(false, 800000000, 1260000),
+	/* OPP4 - OPP-SB */
+	OMAP_OPP_DEF(false, 1000000000, 1310000),
+	/* Terminator */
+	OMAP_OPP_DEF(0, 0, 0)
+};
+
+static struct omap_opp_def __initdata omap36xx_l3_rate_table[] = {
+	/* OPP1 - OPP50 */
+	OMAP_OPP_DEF(true, 100000000, 930000),
+	/* OPP2 - OPP100, OPP-Turbo, OPP-SB */
+	OMAP_OPP_DEF(true, 200000000, 1137500),
+	/* Terminator */
+	OMAP_OPP_DEF(0, 0, 0)
+};
+
+static struct omap_opp_def __initdata omap36xx_dsp_rate_table[] = {
+	/* OPP1 - OPP50 */
+	OMAP_OPP_DEF(true,  260000000, 930000),
+	/* OPP2 - OPP100 */
+	OMAP_OPP_DEF(true,  520000000, 1100000),
+	/* OPP3 - OPP-Turbo */
+	OMAP_OPP_DEF(false, 660000000, 1260000),
+	/* OPP4 - OPP-SB */
+	OMAP_OPP_DEF(false, 875000000, 1310000),
+	/* Terminator */
+	OMAP_OPP_DEF(0, 0, 0)
+};
+
 /* OMAP3 Rate Table */
 struct omap_opp *omap3_mpu_rate_table;
 struct omap_opp *omap3_dsp_rate_table;
@@ -1299,18 +1334,27 @@ static void __init configure_vc(void)
 void __init omap3_pm_init_opp_table(void)
 {
 	int i;
+	struct omap_opp_def **omap3_opp_def_list;
 	struct omap_opp_def *omap34xx_opp_def_list[] = {
 		omap34xx_mpu_rate_table,
 		omap34xx_l3_rate_table,
 		omap34xx_dsp_rate_table
 	};
+	struct omap_opp_def *omap36xx_opp_def_list[] = {
+		omap36xx_mpu_rate_table,
+		omap36xx_l3_rate_table,
+		omap36xx_dsp_rate_table
+	};
 	struct omap_opp **omap3_rate_tables[] = {
 		&omap3_mpu_rate_table,
 		&omap3_l3_rate_table,
 		&omap3_dsp_rate_table
 	};
+
+	omap3_opp_def_list = cpu_is_omap3630() ? omap36xx_opp_def_list :
+				omap34xx_opp_def_list;
 	for (i = 0; i < ARRAY_SIZE(omap3_rate_tables); i++) {
-		*omap3_rate_tables[i] = opp_init_list(omap34xx_opp_def_list[i]);
+		*omap3_rate_tables[i] = opp_init_list(omap3_opp_def_list[i]);
 		/* We dont want half configured system at the moment */
 		BUG_ON(IS_ERR(omap3_rate_tables[i]));
 	}
-- 
1.6.3.3


^ permalink raw reply related	[flat|nested] 10+ messages in thread

* Re: [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs
  2009-12-12  5:00 ` [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs Nishanth Menon
  2009-12-12  5:00   ` [PATCH 02/10 V5] omap3: pm: introduce opp accessor functions Nishanth Menon
@ 2009-12-16 19:59   ` Kevin Hilman
  2009-12-16 22:37     ` Kevin Hilman
  1 sibling, 1 reply; 10+ messages in thread
From: Kevin Hilman @ 2009-12-16 19:59 UTC (permalink / raw)
  To: Nishanth Menon; +Cc: linux-omap

Nishanth Menon <nm@ti.com> writes:

> Hi,
> Thanks for all the comments. Here are the *changed* patches since V5
>
> What changed in V5:
> * review comment incorporated
> * vsel is deprecated now
> * I seem to have hit a checkpatch.pl bug as in 
>   http://lkml.org/lkml/2009/12/11/573, made me check the usage
>   of __deprecated for struct params, and used it in a
>   consistent manner to functions..
> * More warnings added to build :( (deprecated ones ofcourse)
> * removed OMAP_OPP_DEF_TERMINATOR
> * 3430 and 3630 patches changed as a result
>
> History:
> V4: http://marc.info/?t=126033962600001&r=1&w=2
> V3: http://marc.info/?t=125912234200001&r=1&w=2
> V2: http://marc.info/?l=linux-omap&m=125809232732700&w=2
> V1: http://marc.info/?l=linux-omap&m=125800488923479&w=2
>
> Ref: http://elinux.org/OMAP_Power_Management#Future_directions
>
> TODO: The list is still the same as in:
> http://marc.info/?l=linux-omap&m=126033945313269&w=2

FYI...

To facilitate the ongoing discussions on OPP rework, and to have a
common base, this series is available as a branch in my linux-omap-pm
repo[1].

The branch is called 'pm-wip-opp' and I have rebased onto the PM
branch I pushed today.

Kevin

[1] http://git.kernel.org/?p=linux/kernel/git/khilman/linux-omap-pm.git

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs
  2009-12-16 19:59   ` [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs Kevin Hilman
@ 2009-12-16 22:37     ` Kevin Hilman
  2009-12-17  3:22       ` Menon, Nishanth
  0 siblings, 1 reply; 10+ messages in thread
From: Kevin Hilman @ 2009-12-16 22:37 UTC (permalink / raw)
  To: Nishanth Menon; +Cc: linux-omap

Kevin Hilman <khilman@deeprootsystems.com> writes:

> Nishanth Menon <nm@ti.com> writes:
>
>> Hi,
>> Thanks for all the comments. Here are the *changed* patches since V5
>>
>> What changed in V5:
>> * review comment incorporated
>> * vsel is deprecated now
>> * I seem to have hit a checkpatch.pl bug as in 
>>   http://lkml.org/lkml/2009/12/11/573, made me check the usage
>>   of __deprecated for struct params, and used it in a
>>   consistent manner to functions..
>> * More warnings added to build :( (deprecated ones ofcourse)
>> * removed OMAP_OPP_DEF_TERMINATOR
>> * 3430 and 3630 patches changed as a result
[...]

> To facilitate the ongoing discussions on OPP rework, and to have a
> common base, this series is available as a branch in my linux-omap-pm
> repo[1].
>
> The branch is called 'pm-wip-opp' and I have rebased onto the PM
> branch I pushed today.

I forgot to mention that I've also pushed the patch for removing OPP
interface from the OMAP PM layer[1] to the work-in-progress OPP
branch.

Kevin

[1] http://marc.info/?l=linux-omap&m=125917007423545&w=2

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs
  2009-12-16 22:37     ` Kevin Hilman
@ 2009-12-17  3:22       ` Menon, Nishanth
  2009-12-17 16:10         ` Kevin Hilman
  0 siblings, 1 reply; 10+ messages in thread
From: Menon, Nishanth @ 2009-12-17  3:22 UTC (permalink / raw)
  To: Kevin Hilman; +Cc: linux-omap

Kevin Hilman said the following on 12/17/2009 04:07 AM:
> Kevin Hilman <khilman@deeprootsystems.com> writes:
>
>   
>> Nishanth Menon <nm@ti.com> writes:
>>
>>     
>>> Hi,
>>> Thanks for all the comments. Here are the *changed* patches since V5
>>>
>>> What changed in V5:
>>> * review comment incorporated
>>> * vsel is deprecated now
>>> * I seem to have hit a checkpatch.pl bug as in 
>>>   http://lkml.org/lkml/2009/12/11/573, made me check the usage
>>>   of __deprecated for struct params, and used it in a
>>>   consistent manner to functions..
>>> * More warnings added to build :( (deprecated ones ofcourse)
>>> * removed OMAP_OPP_DEF_TERMINATOR
>>> * 3430 and 3630 patches changed as a result
>>>       
> [...]
>
>   
>> To facilitate the ongoing discussions on OPP rework, and to have a
>> common base, this series is available as a branch in my linux-omap-pm
>> repo[1].
>>
>> The branch is called 'pm-wip-opp' and I have rebased onto the PM
>> branch I pushed today.
>>     
>
>   
Thanks Kevin.

> I forgot to mention that I've also pushed the patch for removing OPP
> interface from the OMAP PM layer[1] to the work-in-progress OPP
> branch.
>
> Kevin
>
> [1] http://marc.info/?l=linux-omap&m=125917007423545&w=2
>   
Reg [1]
What is the point of having
void __init omap2_init_common_hw(struct omap_sdrc_params *sdrc_cs0,
<http://git.kernel.org/?p=linux/kernel/git/khilman/linux-omap-pm.git;a=blob;f=arch/arm/mach-omap2/io.c;h=a45ff981b8d65ed3004cec7b4e3431862d4447de;hb=925b2120f036c3374df3f58aeb2a0f39d1ba8d84#l305> 
struct omap_sdrc_params *sdrc_cs1,
<http://git.kernel.org/?p=linux/kernel/git/khilman/linux-omap-pm.git;a=blob;f=arch/arm/mach-omap2/io.c;h=a45ff981b8d65ed3004cec7b4e3431862d4447de;hb=925b2120f036c3374df3f58aeb2a0f39d1ba8d84#l306> 
struct omap_opp *mpu_opps,
<http://git.kernel.org/?p=linux/kernel/git/khilman/linux-omap-pm.git;a=blob;f=arch/arm/mach-omap2/io.c;h=a45ff981b8d65ed3004cec7b4e3431862d4447de;hb=925b2120f036c3374df3f58aeb2a0f39d1ba8d84#l307> 
struct omap_opp *dsp_opps,
<http://git.kernel.org/?p=linux/kernel/git/khilman/linux-omap-pm.git;a=blob;f=arch/arm/mach-omap2/io.c;h=a45ff981b8d65ed3004cec7b4e3431862d4447de;hb=925b2120f036c3374df3f58aeb2a0f39d1ba8d84#l308> 
struct omap_opp *l3_opps)


Why have mpu_opps, dsp_opps and l3_opps anymore? those parameters are 
unused anymore. the patch should have changed omap2_init_common_hw and 
related board calls - am I right?

regards,
Nishanth Menon
Ref:
[1]: 
http://git.kernel.org/?p=linux/kernel/git/khilman/linux-omap-pm.git;a=commitdiff;h=925b2120f036c3374df3f58aeb2a0f39d1ba8d84

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs
  2009-12-17  3:22       ` Menon, Nishanth
@ 2009-12-17 16:10         ` Kevin Hilman
  2009-12-18 10:26           ` Romit Dasgupta
  0 siblings, 1 reply; 10+ messages in thread
From: Kevin Hilman @ 2009-12-17 16:10 UTC (permalink / raw)
  To: Menon, Nishanth; +Cc: linux-omap

"Menon, Nishanth" <nm@ti.com> writes:

> Kevin Hilman said the following on 12/17/2009 04:07 AM:
>> Kevin Hilman <khilman@deeprootsystems.com> writes:
>>
>>   
>>> Nishanth Menon <nm@ti.com> writes:
>>>
>>>     
>>>> Hi,
>>>> Thanks for all the comments. Here are the *changed* patches since V5
>>>>
>>>> What changed in V5:
>>>> * review comment incorporated
>>>> * vsel is deprecated now
>>>> * I seem to have hit a checkpatch.pl bug as in
>>>> http://lkml.org/lkml/2009/12/11/573, made me check the usage
>>>>   of __deprecated for struct params, and used it in a
>>>>   consistent manner to functions..
>>>> * More warnings added to build :( (deprecated ones ofcourse)
>>>> * removed OMAP_OPP_DEF_TERMINATOR
>>>> * 3430 and 3630 patches changed as a result
>>>>       
>> [...]
>>
>>   
>>> To facilitate the ongoing discussions on OPP rework, and to have a
>>> common base, this series is available as a branch in my linux-omap-pm
>>> repo[1].
>>>
>>> The branch is called 'pm-wip-opp' and I have rebased onto the PM
>>> branch I pushed today.
>>>     
>>
>>   
> Thanks Kevin.
>
>> I forgot to mention that I've also pushed the patch for removing OPP
>> interface from the OMAP PM layer[1] to the work-in-progress OPP
>> branch.
>>
>> Kevin
>>
>> [1] http://marc.info/?l=linux-omap&m=125917007423545&w=2
>>   
> Reg [1]
> What is the point of having
> void __init omap2_init_common_hw(struct omap_sdrc_params *sdrc_cs0,
> struct omap_sdrc_params *sdrc_cs1,
> struct omap_opp *mpu_opps,
> struct omap_opp *dsp_opps,
> struct omap_opp *l3_opps)
>
> Why have mpu_opps, dsp_opps and l3_opps anymore? those parameters are
> unused anymore. the patch should have changed omap2_init_common_hw and
> related board calls - am I right?

Yes, I'm in the process cleaning that up.

Once I get some of that cleanup done, I plan to rebase your OPP V5 and
include it in the PM branch.

Kevin

^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs
  2009-12-17 16:10         ` Kevin Hilman
@ 2009-12-18 10:26           ` Romit Dasgupta
  2009-12-18 16:04             ` Kevin Hilman
  0 siblings, 1 reply; 10+ messages in thread
From: Romit Dasgupta @ 2009-12-18 10:26 UTC (permalink / raw)
  To: Kevin Hilman; +Cc: Menon, Nishanth, linux-omap

>>> [...]
>>>
>>>   
>>>> To facilitate the ongoing discussions on OPP rework, and to have a
>>>> common base, this series is available as a branch in my linux-omap-pm
>>>> repo[1].
>>>>
<snip>
> 
> Yes, I'm in the process cleaning that up.
> 
> Once I get some of that cleanup done, I plan to rebase your OPP V5 and
> include it in the PM branch.
> I tried the latest HEAD on pm-wip-opp. Looks like the cpufreq tables are not
initialized because are not initializing {mpu|dsp|l3}_opps. Looks like the
comment on the latest commit is to use OPP APIs directly. Is there any patch
currently on that direction? Otherwise in the pm-wip-opp branch cpufreq is broken.

Thanks,
-Romit


^ permalink raw reply	[flat|nested] 10+ messages in thread

* Re: [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs
  2009-12-18 10:26           ` Romit Dasgupta
@ 2009-12-18 16:04             ` Kevin Hilman
  0 siblings, 0 replies; 10+ messages in thread
From: Kevin Hilman @ 2009-12-18 16:04 UTC (permalink / raw)
  To: Romit Dasgupta; +Cc: Menon, Nishanth, linux-omap

Romit Dasgupta <romit@ti.com> writes:

>>>> [...]
>>>>
>>>>   
>>>>> To facilitate the ongoing discussions on OPP rework, and to have a
>>>>> common base, this series is available as a branch in my linux-omap-pm
>>>>> repo[1].
>>>>>
> <snip>
>> 
>> Yes, I'm in the process cleaning that up.
>> 
>> Once I get some of that cleanup done, I plan to rebase your OPP V5 and
>> include it in the PM branch.
>
> I tried the latest HEAD on pm-wip-opp. Looks like the cpufreq tables are not
> initialized because are not initializing {mpu|dsp|l3}_opps. 

Good catch.  The patch below should fix that.  I've folded it into
my "OMAP3: PM: remove OPP interfaces from OMAP PM layer" patch at the
tip of pm-wip-opp and pushed a new version of that branch.

> Looks like the comment on the latest commit is to use OPP APIs
> directly. Is there any patch currently on that direction?
> Otherwise in the pm-wip-opp branch cpufreq is broken.

Please try this patch on top of your current code, or pull a new
version of pm-wip-opp which should have this included.

Kevin

diff --git a/arch/arm/mach-omap2/pm34xx.c b/arch/arm/mach-omap2/pm34xx.c
index 37f0f0d..86d0304 100644
--- a/arch/arm/mach-omap2/pm34xx.c
+++ b/arch/arm/mach-omap2/pm34xx.c
@@ -1377,6 +1377,10 @@ void __init omap3_pm_init_opp_table(void)
                /* We dont want half configured system at the moment */
                BUG_ON(IS_ERR(omap3_rate_tables[i]));
        }
+
+       mpu_opps = omap3_mpu_rate_table;
+       dsp_opps = omap3_dsp_reate_table;
+       l3_opps = omap3_l3_rate_table;
 }
 

^ permalink raw reply related	[flat|nested] 10+ messages in thread

end of thread, other threads:[~2009-12-18 16:05 UTC | newest]

Thread overview: 10+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
     [not found] <[PATCH 02/10 V4] omap3: pm: introduce opp accessor functions>
2009-12-12  5:00 ` [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs Nishanth Menon
2009-12-12  5:00   ` [PATCH 02/10 V5] omap3: pm: introduce opp accessor functions Nishanth Menon
2009-12-12  5:00     ` [PATCH 03/10 V5] omap3: pm: use opp accessor functions for omap34xx Nishanth Menon
2009-12-12  5:00       ` [PATCH 09/10 V5] omap3: pm: introduce 3630 opps Nishanth Menon
2009-12-16 19:59   ` [PATCH 00/10 V5] omap3: pm: introduce support for 3630 OPPs Kevin Hilman
2009-12-16 22:37     ` Kevin Hilman
2009-12-17  3:22       ` Menon, Nishanth
2009-12-17 16:10         ` Kevin Hilman
2009-12-18 10:26           ` Romit Dasgupta
2009-12-18 16:04             ` Kevin Hilman

This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.