[PATCH] ARM: apq8064: Add pinmux and i2c pinctrl nodes

2014-08-14 Thread Kiran Padwal
This patch adds pinmux and i2c pinctrl DT node for IFC6410 board.
It also adds necessary DT support for i2c eeprom which is present on
IFC6410.

Tested on IFC6410 board.

Signed-off-by: Kiran Padwal kiran.pad...@smartplayin.com
---
 arch/arm/boot/dts/qcom-apq8064-ifc6410.dts |   29 ++
 arch/arm/boot/dts/qcom-apq8064.dtsi|   59 
 2 files changed, 88 insertions(+)

diff --git a/arch/arm/boot/dts/qcom-apq8064-ifc6410.dts 
b/arch/arm/boot/dts/qcom-apq8064-ifc6410.dts
index 7c2441d..d52ac3c 100644
--- a/arch/arm/boot/dts/qcom-apq8064-ifc6410.dts
+++ b/arch/arm/boot/dts/qcom-apq8064-ifc6410.dts
@@ -5,6 +5,15 @@
compatible = qcom,apq8064-ifc6410, qcom,apq8064;
 
soc {
+   pinmux@80 {
+   i2c1_pins: i2c1_pinmux {
+   mux {
+   pins = gpio20, gpio21;
+   function = gsbi1;
+   };
+   };
+   };
+
gsbi@1660 {
status = ok;
qcom,mode = GSBI_PROT_I2C_UART;
@@ -12,5 +21,25 @@
status = ok;
};
};
+
+   gsbi1: gsbi@1244 {
+   qcom,mode = GSBI_PROT_I2C;
+   status = ok;
+
+   i2c1: i2c@1246 {
+   status = ok;
+
+   clock-frequency = 20;
+
+   pinctrl-0 = i2c1_pins;
+   pinctrl-names = default;
+
+   eeprom: eeprom@52 {
+   compatible = atmel,24c128;
+   reg = 0x52;
+   pagesize = 32;
+   };
+   };
+   };
};
 };
diff --git a/arch/arm/boot/dts/qcom-apq8064.dtsi 
b/arch/arm/boot/dts/qcom-apq8064.dtsi
index 92bf793..fbebf5c 100644
--- a/arch/arm/boot/dts/qcom-apq8064.dtsi
+++ b/arch/arm/boot/dts/qcom-apq8064.dtsi
@@ -70,6 +70,17 @@
ranges;
compatible = simple-bus;
 
+   qcom_pinmux: pinmux@80 {
+   compatible = qcom,apq8064-pinctrl;
+   reg = 0x80 0x4000;
+
+   gpio-controller;
+   #gpio-cells = 2;
+   interrupt-controller;
+   #interrupt-cells = 2;
+   interrupts = 0 32 0x4;
+   };
+
intc: interrupt-controller@200 {
compatible = qcom,msm-qgic2;
interrupt-controller;
@@ -133,6 +144,54 @@
regulator;
};
 
+   gsbi1: gsbi@1244 {
+   compatible = qcom,gsbi-v1.0.0;
+   reg = 0x1244 0x100;
+   clocks = gcc GSBI1_H_CLK;
+   clock-names = iface;
+   #address-cells = 1;
+   #size-cells = 1;
+   ranges;
+   status = disabled;
+
+   i2c@1246 {
+   compatible = qcom,i2c-qup-v1.1.1;
+   reg = 0x1246 0x1000;
+   interrupts = 0 194 0;
+
+   clocks = gcc GSBI1_QUP_CLK, gcc 
GSBI1_H_CLK;
+   clock-names = core, iface;
+   status = disabled;
+
+   #address-cells = 1;
+   #size-cells = 0;
+   };
+   };
+
+   gsbi2: gsbi@1248 {
+   compatible = qcom,gsbi-v1.0.0;
+   reg = 0x1248 0x100;
+   clocks = gcc GSBI2_H_CLK;
+   clock-names = iface;
+   #address-cells = 1;
+   #size-cells = 1;
+   ranges;
+   status = disabled;
+
+   i2c@124a {
+   compatible = qcom,i2c-qup-v1.1.1;
+   reg = 0x124a 0x1000;
+   interrupts = 0 196 0;
+
+   clocks = gcc GSBI2_QUP_CLK, gcc 
GSBI2_H_CLK;
+   clock-names = core, iface;
+   status = disabled;
+
+   #address-cells = 1;
+   #size-cells = 0;
+   };
+   };
+
gsbi7: gsbi@1660 {
status = disabled;
compatible = qcom,gsbi-v1.0.0;
-- 
1.7.9.5

--
To 

Re: [PATCH v2 05/10] arm: qcom-msm8974: Add CPU phandles to CPU definitions

2014-08-14 Thread Pramod Gurav


On Wednesday 13 August 2014 01:13 AM, Lina Iyer wrote:
 Add CPU phandle labels for all Krait CPUS.
 
 Signed-off-by: Lina Iyer lina.i...@linaro.org
 ---
  arch/arm/boot/dts/qcom-msm8974.dtsi | 8 
  1 file changed, 4 insertions(+), 4 deletions(-)
 
Hi Lina,
These changes are already done  by Stephen's below cpufreq patch whicth
adds OPP table for 8974. You might want to sync them up.

Author: Stephen Boyd sb...@codeaurora.org
Date:   Wed Jun 25 05:36:23 2014 +0530

ARM: dts: qcom: Add necessary DT data for Krait cpufreq

Add the necessary DT nodes and data so we can probe the cpufreq
driver on MSM devices with Krait CPUs.

Signed-off-by: Stephen Boyd sb...@codeaurora.org

 diff --git a/arch/arm/boot/dts/qcom-msm8974.dtsi 
 b/arch/arm/boot/dts/qcom-msm8974.dtsi



Thanks
Pramod
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 02/10] msm: scm: Add SCM warmboot flags for quad core targets.

2014-08-14 Thread Pramod Gurav
On Wednesday 13 August 2014 01:13 AM, Lina Iyer wrote:
 Quad core targets like APQ8074, APQ8064, APQ8084 need SCM support set up
 warm boot addresses in the Secure Monitor. Extend the SCM flags to
 support warmboot addresses for seconday cores.
 
 Signed-off-by: Lina Iyer lina.i...@linaro.org
 ---
  include/soc/qcom/scm-boot.h | 3 +++
  1 file changed, 3 insertions(+)
 
 diff --git a/include/soc/qcom/scm-boot.h b/include/soc/qcom/scm-boot.h
 index 6aabb24..7ae2152 100644
 --- a/include/soc/qcom/scm-boot.h
 +++ b/include/soc/qcom/scm-boot.h
 @@ -18,6 +18,9 @@
  #define SCM_FLAG_COLDBOOT_CPU3   0x20
  #define SCM_FLAG_WARMBOOT_CPU0   0x04
  #define SCM_FLAG_WARMBOOT_CPU1   0x02
 +#define SCM_FLAG_WARMBOOT_CPU2   0x10
 +#define SCM_FLAG_WARMBOOT_CPU3   0x40
 +
An extra line introduced here.

  
  int scm_set_boot_addr(phys_addr_t addr, int flags);
  
 
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


MSM Camera: 3.10 kernel support for APQ8074?

2014-08-14 Thread Alaganraj
Hi,

I wants to validate OV5640 camera on 3.10 kernel.

I don't find any 3.10 tag for APQ8074 in CAF.I've taken 8084
tag(LNX.LA.3.6.1.c2-01500-8084.0),
Kernel is booting but Android home screen(GUI) is not up.
Ported ov5640 sensor driver, probe is success with reading proper sensor ID.
As GUI is not up, I'm trying to capture YUV frames using
mm-qcamera-app commandline application.

Please clarify me as I don't have any documents
Is APQ8084 ISP compatible with APQ8074?
Is it possible to validate camera on APQ8074 with 8084 source?

Repo: git://codeaurora.org/quic/la/kernel/msm-3.10

Any input is appreciated.

ThanksRegards,
Alaganraj


--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH] ath6kl: Add SDIO device ID for QCA6234X Support

2014-08-14 Thread Kalle Valo
Srinivas Kandagatla srinivas.kandaga...@linaro.org writes:

 From: Srinivas Kandagatla srinivas.kandaga...@linaro.org

 This patch adds device ID 402 to support QCA6234X found in APQ8064 SOC
 in IFC6410 board.

 Tested with mainline mmci sdio driver.

 Signed-off-by: Srinivas Kandagatla srinivas.kandaga...@linaro.org

Thanks, applied.

-- 
Kalle Valo
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Pramod Gurav
On Wednesday 13 August 2014 01:13 AM, Lina Iyer wrote:
 Qualcomm chipsets use an separate h/w block to control the logic around
 the processor cores (cpu and L2). The SPM h/w block regulates power to
 the cores and controls the power when the core enter low power modes.
 
 Each core has its own instance of SPM. The SPM has the following key
 functions
   - Configure the h/w dependencies when entering low power modes
   - Wait for interrupt and wake up on interrupt
   - Ensure the dependencies are ready before bringing the core out
 of sleep
   - Regulating voltage to the core, interfacing with the PMIC.
   - Optimize power based on runtime recommendations.
 
 The driver identifies and configures the SPMs, by reading the nodes and
 the register values from the devicetree. The SPMs need to be configured
 to allow the processor to be idled in a low power state.
 
 Signed-off-by: Praveen Chidamabram pchid...@codeaurora.org
 Signed-off-by: Murali Nalajala mnala...@codeaurora.org
 Signed-off-by: Lina Iyer lina.i...@linaro.org
 ---
 +

snip

  CFLAGS_scm.o :=$(call as-instr,.arch_extension sec,-DREQUIRES_SEC=1)
  obj-$(CONFIG_QCOM_SCM) += scm.o scm-boot.o
 diff --git a/drivers/soc/qcom/spm-devices.c b/drivers/soc/qcom/spm-devices.c
 new file mode 100644
 index 000..567e9f9
 --- /dev/null
 +++ b/drivers/soc/qcom/spm-devices.c

snip

 + if (ret)
 + return ret;
 +
 + return dev-cpu_vdd;
 +}
 +EXPORT_SYMBOL(msm_spm_get_vdd);
 +
 +static void msm_spm_config_q2s(struct msm_spm_device *dev, unsigned int mode)
 +{
 + uint32_t spm_legacy_mode = 0;
 + uint32_t qchannel_ignore = 0;
 + uint32_t val = 0;
Initialization not needed for val.
 +
 + if (!dev-q2s_reg)
 + return;
 +
 + switch (mode) {
 + case MSM_SPM_MODE_DISABLED:
 + case MSM_SPM_MODE_CLOCK_GATING:
 + qchannel_ignore = 1;
 + spm_legacy_mode = 0;
 + break;
 + case MSM_SPM_MODE_RETENTION:
 + qchannel_ignore = 0;
 + spm_legacy_mode = 0;
 + break;
 + case MSM_SPM_MODE_GDHS:
 + case MSM_SPM_MODE_POWER_COLLAPSE:
 + qchannel_ignore = 0;
 + spm_legacy_mode = 1;
 + break;
 + default:
 + break;
 + }
 +
 + val = spm_legacy_mode  2 | qchannel_ignore  1;
 + __raw_writel(val, dev-q2s_reg);
 + mb();
This may need a comment around it.
 +}
 +
 +static int msm_spm_dev_set_low_power_mode(struct msm_spm_device *dev,
 + unsigned int mode, bool notify_rpm)
 +{
 + uint32_t i;
 + uint32_t start_addr = 0;
 + int ret = -EINVAL;
 + bool pc_mode = false;
 +
 + if (!dev-initialized)
 + return -ENXIO;
 +
 + if ((mode == MSM_SPM_MODE_POWER_COLLAPSE)
 + || (mode == MSM_SPM_MODE_GDHS))
 + pc_mode = true;
 +
 + if (mode == MSM_SPM_MODE_DISABLED) {
 + ret = msm_spm_drv_set_spm_enable(dev-reg_data, false);
 + } else if (!msm_spm_drv_set_spm_enable(dev-reg_data, true)) {
 + for (i = 0; i  dev-num_modes; i++) {
 + if ((dev-modes[i].mode == mode) 
 + (dev-modes[i].notify_rpm == notify_rpm)) {
 + start_addr = dev-modes[i].start_addr;
 + break;
 + }
 + }
 + ret = msm_spm_drv_set_low_power_mode(dev-reg_data,
 + start_addr, pc_mode);
 + }
 +
 + msm_spm_config_q2s(dev, mode);
 +
 + return ret;
 +}
 +
 +static int msm_spm_dev_init(struct msm_spm_device *dev,
 + struct msm_spm_platform_data *data)
 +{
 + int i, ret = -ENOMEM;
 + uint32_t offset = 0;
 +
 + dev-cpu_vdd = VDD_DEFAULT;
 + dev-num_modes = data-num_modes;
 + dev-modes = kmalloc(
 + sizeof(struct msm_spm_power_modes) * dev-num_modes,
 + GFP_KERNEL);
 +
 + if (!dev-modes)
 + goto spm_failed_malloc;
 +
 + dev-reg_data.major = data-major;
 + dev-reg_data.minor = data-minor;
 + ret = msm_spm_drv_init(dev-reg_data, data);
 +
Please remove extra line.
 + if (ret)
 + goto spm_failed_init;
 +
 + for (i = 0; i  dev-num_modes; i++) {
 +
 + /* Default offset is 0 and gets updated as we write more
 +  * sequences into SPM
 +  */
 + dev-modes[i].start_addr = offset;
 + ret = msm_spm_drv_write_seq_data(dev-reg_data,
 + data-modes[i].cmd, offset);
 + if (ret  0)
 + goto spm_failed_init;
 +
 + dev-modes[i].mode = data-modes[i].mode;
 + dev-modes[i].notify_rpm = data-modes[i].notify_rpm;
 + }
 + msm_spm_drv_reinit(dev-reg_data);
 + dev-initialized = true;
 + return 0;
 +
 +spm_failed_init:
 + kfree(dev-modes);
Should not we 

[PATCH/RFC V2 01/16] scsi: ufs: Allow vendor specific initialization

2014-08-14 Thread Dolev Raviv
From: Sujit Reddy Thumma sthu...@codeaurora.org

Some vendor specific controller versions might need to configure
vendor specific - registers, clocks, voltage regulators etc. to
initialize the host controller UTP layer and Uni-Pro stack.
Provide some common initialization operations that can be used
to configure vendor specifics. The methods can be extended in
future, for example, for power mode transitions.

The operations are vendor/board specific and hence determined with
the help of compatible property in device tree.

Signed-off-by: Sujit Reddy Thumma sthu...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufshcd-pci.c b/drivers/scsi/ufs/ufshcd-pci.c
index c007a7a..11a3237 100644
--- a/drivers/scsi/ufs/ufshcd-pci.c
+++ b/drivers/scsi/ufs/ufshcd-pci.c
@@ -164,7 +164,13 @@ ufshcd_pci_probe(struct pci_dev *pdev, const struct 
pci_device_id *id)
 
mmio_base = pcim_iomap_table(pdev)[0];
 
-   err = ufshcd_init(pdev-dev, hba, mmio_base, pdev-irq);
+   err = ufshcd_alloc_host(pdev-dev, hba);
+   if (err) {
+   dev_err(pdev-dev, Allocation failed\n);
+   return err;
+   }
+
+   err = ufshcd_init(hba, mmio_base, pdev-irq);
if (err) {
dev_err(pdev-dev, Initialization failed\n);
return err;
diff --git a/drivers/scsi/ufs/ufshcd-pltfrm.c b/drivers/scsi/ufs/ufshcd-pltfrm.c
index 5e46232..d727b1a 100644
--- a/drivers/scsi/ufs/ufshcd-pltfrm.c
+++ b/drivers/scsi/ufs/ufshcd-pltfrm.c
@@ -35,9 +35,24 @@
 
 #include linux/platform_device.h
 #include linux/pm_runtime.h
+#include linux/of.h
 
 #include ufshcd.h
 
+static const struct of_device_id ufs_of_match[];
+static struct ufs_hba_variant_ops *get_variant_ops(struct device *dev)
+{
+   if (dev-of_node) {
+   const struct of_device_id *match;
+
+   match = of_match_node(ufs_of_match, dev-of_node);
+   if (match)
+   return (struct ufs_hba_variant_ops *)match-data;
+   }
+
+   return NULL;
+}
+
 #ifdef CONFIG_PM
 /**
  * ufshcd_pltfrm_suspend - suspend power management function
@@ -138,8 +153,8 @@ static int ufshcd_pltfrm_probe(struct platform_device *pdev)
 
mem_res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
mmio_base = devm_ioremap_resource(dev, mem_res);
-   if (IS_ERR(mmio_base)) {
-   err = PTR_ERR(mmio_base);
+   if (IS_ERR(*(void **)mmio_base)) {
+   err = PTR_ERR(*(void **)mmio_base);
goto out;
}
 
@@ -150,10 +165,18 @@ static int ufshcd_pltfrm_probe(struct platform_device 
*pdev)
goto out;
}
 
+   err = ufshcd_alloc_host(dev, hba);
+   if (err) {
+   dev_err(pdev-dev, Allocation failed\n);
+   goto out;
+   }
+
+   hba-vops = get_variant_ops(pdev-dev);
+
pm_runtime_set_active(pdev-dev);
pm_runtime_enable(pdev-dev);
 
-   err = ufshcd_init(dev, hba, mmio_base, irq);
+   err = ufshcd_init(hba, mmio_base, irq);
if (err) {
dev_err(dev, Intialization failed\n);
goto out_disable_rpm;
diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index ba27215..d0565b0 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -3,6 +3,7 @@
  *
  * This code is based on drivers/scsi/ufs/ufshcd.c
  * Copyright (C) 2011-2013 Samsung India Software Operations
+ * Copyright (c) 2013-2014, The Linux Foundation. All rights reserved.
  *
  * Authors:
  * Santosh Yaraganavi santosh...@samsung.com
@@ -31,6 +32,9 @@
  * circumstances will the contributor of this Program be liable for
  * any damages of any kind arising from your use or distribution of
  * this program.
+ *
+ * The Linux Foundation chooses to take subject only to the GPLv2
+ * license terms, and distributes only under these terms.
  */
 
 #include linux/async.h
@@ -175,13 +179,14 @@ static inline u32 ufshcd_get_ufs_version(struct ufs_hba 
*hba)
 /**
  * ufshcd_is_device_present - Check if any device connected to
  *   the host controller
- * @reg_hcs - host controller status register value
+ * @hba: pointer to adapter instance
  *
  * Returns 1 if device present, 0 if no device detected
  */
-static inline int ufshcd_is_device_present(u32 reg_hcs)
+static inline int ufshcd_is_device_present(struct ufs_hba *hba)
 {
-   return (DEVICE_PRESENT  reg_hcs) ? 1 : 0;
+   return (ufshcd_readl(hba, REG_CONTROLLER_STATUS) 
+   DEVICE_PRESENT) ? 1 : 0;
 }
 
 /**
@@ -1798,11 +1803,10 @@ out:
  * @hba: per adapter instance
  *
  * To bring UFS host controller to operational state,
- * 1. Check if device is present
- * 2. Enable required interrupts
- * 3. Configure interrupt aggregation
- * 4. Program UTRL and UTMRL base addres
- * 5. Configure run-stop-registers
+ * 1. Enable required interrupts
+ * 2. Configure interrupt 

[PATCH/RFC V2 00/16] UFS: Power managment support

2014-08-14 Thread Dolev Raviv
This patch seies introduces support for power managment in the driver as well 
as vendor specific initialization - registers, clocks, voltage regulators etc.

It includes also a rework for the init sequnce and other PM pre-requisit such 
as write protection support, handling well-known LUN, error handling (retries), 
bkops, START_STOP unit command, and ICC levels settings.

--
Changes from V1:
 - 6 new patches apended at the end
 - Allow overriding power configuration with controller support and
   preferences/capabilities Dolev Raviv
 - Allow overriding power choice with controller capabilities Dolev Raviv
 - Add support for clock gating and clock scaling Sahitya Tummala
 - Add capability to control the auto bkops during suspend Subhash Jadavani
 - Add misc changes for phy/unipro driver usage Dolev Raviv

Dolev Raviv (2):
  scsi: ufs: refactor configuring power mode
  scsi: ufs: definitions for phy interface

Sahitya Tummala (3):
  scsi: ufs: Add support for clock gating
  scsi: ufs: Add freq-table-hz property for UFS device
  scsi: ufs: Add support for clock scaling using devfreq framework

Subhash Jadavani (5):
  scsi: ufs: refactor query descriptor API support
  scsi: support well known logical units
  scsi: ufs: introduce well known logical unit in ufs
  scsi: ufs: add UFS power management support
  scsi: ufs: add capability to control the auto bkops during suspend

Sujit Reddy Thumma (5):
  scsi: ufs: Allow vendor specific initialization
  scsi: ufs: Add regulator enable support
  scsi: ufs: Add clock initialization support
  scsi: ufs: improve init sequence
  scsi: sd: Avoid sending medium write commands if device is write
protected

Yaniv Gardi (1):
  scsi: ufs: Active Power Mode - configuring bActiveICCLevel

 .../devicetree/bindings/ufs/ufshcd-pltfrm.txt  |   37 +
 drivers/scsi/scsi_scan.c   |   16 +
 drivers/scsi/scsi_sysfs.c  |7 +
 drivers/scsi/sd.c  |6 +-
 drivers/scsi/ufs/Kconfig   |2 +
 drivers/scsi/ufs/ufs.h |  131 +-
 drivers/scsi/ufs/ufshcd-pci.c  |   55 +-
 drivers/scsi/ufs/ufshcd-pltfrm.c   |  282 ++-
 drivers/scsi/ufs/ufshcd.c  | 2400 ++--
 drivers/scsi/ufs/ufshcd.h  |  277 ++-
 drivers/scsi/ufs/ufshci.h  |9 +-
 drivers/scsi/ufs/unipro.h  |   56 +
 include/scsi/scsi.h|1 +
 include/scsi/scsi_host.h   |5 +
 14 files changed, 2959 insertions(+), 325 deletions(-)

-- 
1.8.5.2

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH/RFC V2 02/16] scsi: ufs: Add regulator enable support

2014-08-14 Thread Dolev Raviv
From: Sujit Reddy Thumma sthu...@codeaurora.org

UFS devices are powered by at most three external power supplies -
- VCC - The flash memory core power supply, 2.7V to 3.6V or 1.70V to 1.95V
- VCCQ - The controller and I/O power supply, 1.1V to 1.3V
- VCCQ2 - Secondary controller and/or I/O power supply, 1.65V to 1.95V

For some devices VCCQ or VCCQ2 are optional as they can be
generated using internal LDO inside the UFS device.

Add DT bindings for voltage regulators that can be controlled
from host driver.

Signed-off-by: Sujit Reddy Thumma sthu...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt 
b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
index 20468b2..65e3117 100644
--- a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
+++ b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
@@ -8,9 +8,33 @@ Required properties:
 - interrupts: interrupt mapping for UFS host controller IRQ
 - reg   : registers mapping
 
+Optional properties:
+- vcc-supply: phandle to VCC supply regulator node
+- vccq-supply   : phandle to VCCQ supply regulator node
+- vccq2-supply  : phandle to VCCQ2 supply regulator node
+- vcc-supply-1p8: For embedded UFS devices, valid VCC range is 
1.7-1.95V
+  or 2.7-3.6V. This boolean property when set, 
specifies
+ to use low voltage range of 1.7-1.95V. Note for 
external
+ UFS cards this property is invalid and valid VCC 
range is
+ always 2.7-3.6V.
+- vcc-max-microamp  : specifies max. load that can be drawn from vcc supply
+- vccq-max-microamp : specifies max. load that can be drawn from vccq 
supply
+- vccq2-max-microamp: specifies max. load that can be drawn from vccq2 
supply
+
+Note: If above properties are not defined it can be assumed that the supply
+regulators are always on.
+
 Example:
ufshc@0xfc598000 {
compatible = jedec,ufs-1.1;
reg = 0xfc598000 0x800;
interrupts = 0 28 0;
+
+   vcc-supply = xxx_reg1;
+   vcc-supply-1p8;
+   vccq-supply = xxx_reg2;
+   vccq2-supply = xxx_reg3;
+   vcc-max-microamp = 50;
+   vccq-max-microamp = 20;
+   vccq2-max-microamp = 20;
};
diff --git a/drivers/scsi/ufs/ufs.h b/drivers/scsi/ufs/ufs.h
index fafcf5e..729ce7d 100644
--- a/drivers/scsi/ufs/ufs.h
+++ b/drivers/scsi/ufs/ufs.h
@@ -362,4 +362,29 @@ struct ufs_query_res {
struct utp_upiu_query upiu_res;
 };
 
+#define UFS_VREG_VCC_MIN_UV   270 /* uV */
+#define UFS_VREG_VCC_MAX_UV   360 /* uV */
+#define UFS_VREG_VCC_1P8_MIN_UV170 /* uV */
+#define UFS_VREG_VCC_1P8_MAX_UV195 /* uV */
+#define UFS_VREG_VCCQ_MIN_UV  110 /* uV */
+#define UFS_VREG_VCCQ_MAX_UV  130 /* uV */
+#define UFS_VREG_VCCQ2_MIN_UV 165 /* uV */
+#define UFS_VREG_VCCQ2_MAX_UV 195 /* uV */
+
+struct ufs_vreg {
+   struct regulator *reg;
+   const char *name;
+   bool enabled;
+   int min_uV;
+   int max_uV;
+   int min_uA;
+   int max_uA;
+};
+
+struct ufs_vreg_info {
+   struct ufs_vreg *vcc;
+   struct ufs_vreg *vccq;
+   struct ufs_vreg *vccq2;
+};
+
 #endif /* End of Header */
diff --git a/drivers/scsi/ufs/ufshcd-pltfrm.c b/drivers/scsi/ufs/ufshcd-pltfrm.c
index d727b1a..51e47c4 100644
--- a/drivers/scsi/ufs/ufshcd-pltfrm.c
+++ b/drivers/scsi/ufs/ufshcd-pltfrm.c
@@ -53,6 +53,99 @@ static struct ufs_hba_variant_ops *get_variant_ops(struct 
device *dev)
return NULL;
 }
 
+#define MAX_PROP_SIZE 32
+static int ufshcd_populate_vreg(struct device *dev, const char *name,
+   struct ufs_vreg **out_vreg)
+{
+   int ret = 0;
+   char prop_name[MAX_PROP_SIZE];
+   struct ufs_vreg *vreg = NULL;
+   struct device_node *np = dev-of_node;
+
+   if (!np) {
+   dev_err(dev, %s: non DT initialization\n, __func__);
+   goto out;
+   }
+
+   snprintf(prop_name, MAX_PROP_SIZE, %s-supply, name);
+   if (!of_parse_phandle(np, prop_name, 0)) {
+   dev_info(dev, %s: Unable to find %s regulator, assuming 
enabled\n,
+   __func__, prop_name);
+   goto out;
+   }
+
+   vreg = devm_kzalloc(dev, sizeof(*vreg), GFP_KERNEL);
+   if (!vreg) {
+   dev_err(dev, No memory for %s regulator\n, name);
+   goto out;
+   }
+
+   vreg-name = kstrdup(name, GFP_KERNEL);
+
+   snprintf(prop_name, MAX_PROP_SIZE, %s-max-microamp, name);
+   ret = of_property_read_u32(np, prop_name, vreg-max_uA);
+   if (ret) {
+   dev_err(dev, %s: unable to find %s err %d\n,
+   __func__, prop_name, ret);
+   goto 

[PATCH/RFC V2 03/16] scsi: ufs: Add clock initialization support

2014-08-14 Thread Dolev Raviv
From: Sujit Reddy Thumma sthu...@codeaurora.org

Add generic clock initialization support for UFSHCD platform
driver. The clock info is read from device tree using standard
clock bindings. A generic max-clock-frequency-hz property is
defined to save information on maximum operating clock frequency
the h/w supports.

Signed-off-by: Sujit Reddy Thumma sthu...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt 
b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
index 65e3117..b0f791a 100644
--- a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
+++ b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
@@ -21,8 +21,17 @@ Optional properties:
 - vccq-max-microamp : specifies max. load that can be drawn from vccq 
supply
 - vccq2-max-microamp: specifies max. load that can be drawn from vccq2 
supply
 
+- clocks: List of phandle and clock specifier pairs
+- clock-names   : List of clock input name strings sorted in the same
+  order as the clocks property.
+- max-clock-frequency-hz : List of maximum operating frequency stored in the 
same
+   order as the clocks property. If this property is 
not
+  defined or a value in the array is 0 then it is 
assumed
+  that the frequency is set by the parent clock or a
+  fixed rate clock source.
+
 Note: If above properties are not defined it can be assumed that the supply
-regulators are always on.
+regulators or clocks are always on.
 
 Example:
ufshc@0xfc598000 {
@@ -37,4 +46,8 @@ Example:
vcc-max-microamp = 50;
vccq-max-microamp = 20;
vccq2-max-microamp = 20;
+
+   clocks = core 0, ref 0, iface 0;
+   clock-names = core_clk, ref_clk, iface_clk;
+   max-clock-frequency-hz = 1 1920 0;
};
diff --git a/drivers/scsi/ufs/ufshcd-pci.c b/drivers/scsi/ufs/ufshcd-pci.c
index 11a3237..1aac2ef 100644
--- a/drivers/scsi/ufs/ufshcd-pci.c
+++ b/drivers/scsi/ufs/ufshcd-pci.c
@@ -170,6 +170,8 @@ ufshcd_pci_probe(struct pci_dev *pdev, const struct 
pci_device_id *id)
return err;
}
 
+   INIT_LIST_HEAD(hba-clk_list_head);
+
err = ufshcd_init(hba, mmio_base, pdev-irq);
if (err) {
dev_err(pdev-dev, Initialization failed\n);
diff --git a/drivers/scsi/ufs/ufshcd-pltfrm.c b/drivers/scsi/ufs/ufshcd-pltfrm.c
index 51e47c4..642d80f 100644
--- a/drivers/scsi/ufs/ufshcd-pltfrm.c
+++ b/drivers/scsi/ufs/ufshcd-pltfrm.c
@@ -53,6 +53,71 @@ static struct ufs_hba_variant_ops *get_variant_ops(struct 
device *dev)
return NULL;
 }
 
+static int ufshcd_parse_clock_info(struct ufs_hba *hba)
+{
+   int ret = 0;
+   int cnt;
+   int i;
+   struct device *dev = hba-dev;
+   struct device_node *np = dev-of_node;
+   char *name;
+   u32 *clkfreq = NULL;
+   struct ufs_clk_info *clki;
+
+   if (!np)
+   goto out;
+
+   INIT_LIST_HEAD(hba-clk_list_head);
+
+   cnt = of_property_count_strings(np, clock-names);
+   if (!cnt || (cnt == -EINVAL)) {
+   dev_info(dev, %s: Unable to find clocks, assuming enabled\n,
+   __func__);
+   } else if (cnt  0) {
+   dev_err(dev, %s: count clock strings failed, err %d\n,
+   __func__, cnt);
+   ret = cnt;
+   }
+
+   if (cnt = 0)
+   goto out;
+
+   clkfreq = kzalloc(cnt * sizeof(*clkfreq), GFP_KERNEL);
+   if (!clkfreq) {
+   ret = -ENOMEM;
+   dev_err(dev, %s: memory alloc failed\n, __func__);
+   goto out;
+   }
+
+   ret = of_property_read_u32_array(np,
+   max-clock-frequency-hz, clkfreq, cnt);
+   if (ret  (ret != -EINVAL)) {
+   dev_err(dev, %s: invalid max-clock-frequency-hz property, 
%d\n,
+   __func__, ret);
+   goto out;
+   }
+
+   for (i = 0; i  cnt; i++) {
+   ret = of_property_read_string_index(np,
+   clock-names, i, (const char **)name);
+   if (ret)
+   goto out;
+
+   clki = devm_kzalloc(dev, sizeof(*clki), GFP_KERNEL);
+   if (!clki) {
+   ret = -ENOMEM;
+   goto out;
+   }
+
+   clki-max_freq = clkfreq[i];
+   clki-name = kstrdup(name, GFP_KERNEL);
+   list_add_tail(clki-list, hba-clk_list_head);
+   }
+out:
+   kfree(clkfreq);
+   return ret;
+}
+
 #define MAX_PROP_SIZE 32
 static int ufshcd_populate_vreg(struct device *dev, const char *name,
struct ufs_vreg **out_vreg)
@@ -266,6 +331,12 @@ static int 

[PATCH/RFC V2 11/16] scsi: ufs: refactor configuring power mode

2014-08-14 Thread Dolev Raviv
Sometimes, the device shall report its maximum power and speed
capabilities, but we might not wish to configure it to use those
maximum capabilities.
This change adds support for the vendor specific host driver to
implement power change notify callback.

To enable configuring different power modes (number of lanes,
gear number and fast/slow modes) it is necessary to split the
configuration stage from the stage that reads the device max power mode.
In addition, it is not required to read the configuration more than
once, thus the configuration is stored after reading it once.

Signed-off-by: Dolev Raviv dra...@codeaurora.org
Signed-off-by: Yaniv Gardi yga...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index fac71c9..3a66d0d 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -178,6 +178,8 @@ static int ufshcd_clear_tm_cmd(struct ufs_hba *hba, int 
tag);
 static void ufshcd_hba_exit(struct ufs_hba *hba);
 static int ufshcd_probe_hba(struct ufs_hba *hba);
 static int ufshcd_host_reset_and_restore(struct ufs_hba *hba);
+static int ufshcd_config_pwr_mode(struct ufs_hba *hba,
+   struct ufs_pa_layer_attr *desired_pwr_mode);
 
 static inline void ufshcd_enable_irq(struct ufs_hba *hba)
 {
@@ -1933,65 +1935,129 @@ static int ufshcd_uic_hibern8_exit(struct ufs_hba *hba)
 }
 
 /**
- * ufshcd_config_max_pwr_mode - Set  Change power mode with
- * maximum capability attribute information.
- * @hba: per adapter instance
- *
- * Returns 0 on success, non-zero value on failure
+ * ufshcd_get_max_pwr_mode - reads the max power mode negotiated with device
+ * @hba: per-adapter instance
  */
-static int ufshcd_config_max_pwr_mode(struct ufs_hba *hba)
+static int ufshcd_get_max_pwr_mode(struct ufs_hba *hba)
 {
-   enum {RX = 0, TX = 1};
-   u32 lanes[] = {1, 1};
-   u32 gear[] = {1, 1};
-   u8 pwr[] = {FASTAUTO_MODE, FASTAUTO_MODE};
-   int ret;
+   struct ufs_pa_layer_attr *pwr_info = hba-max_pwr_info.info;
+
+   if (hba-max_pwr_info.is_valid)
+   return 0;
+
+   pwr_info-pwr_tx = FASTAUTO_MODE;
+   pwr_info-pwr_rx = FASTAUTO_MODE;
+   pwr_info-hs_rate = PA_HS_MODE_B;
 
/* Get the connected lane count */
-   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_CONNECTEDRXDATALANES), lanes[RX]);
-   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_CONNECTEDTXDATALANES), lanes[TX]);
+   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_CONNECTEDRXDATALANES),
+   pwr_info-lane_rx);
+   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_CONNECTEDTXDATALANES),
+   pwr_info-lane_tx);
+
+   if (!pwr_info-lane_rx || !pwr_info-lane_tx) {
+   dev_err(hba-dev, %s: invalid connected lanes value. rx=%d, 
tx=%d\n,
+   __func__,
+   pwr_info-lane_rx,
+   pwr_info-lane_tx);
+   return -EINVAL;
+   }
 
/*
 * First, get the maximum gears of HS speed.
 * If a zero value, it means there is no HSGEAR capability.
 * Then, get the maximum gears of PWM speed.
 */
-   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_MAXRXHSGEAR), gear[RX]);
-   if (!gear[RX]) {
-   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_MAXRXPWMGEAR), gear[RX]);
-   pwr[RX] = SLOWAUTO_MODE;
+   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_MAXRXHSGEAR), pwr_info-gear_rx);
+   if (!pwr_info-gear_rx) {
+   ufshcd_dme_get(hba, UIC_ARG_MIB(PA_MAXRXPWMGEAR),
+   pwr_info-gear_rx);
+   if (!pwr_info-gear_rx) {
+   dev_err(hba-dev, %s: invalid max pwm rx gear read = 
%d\n,
+   __func__, pwr_info-gear_rx);
+   return -EINVAL;
+   }
+   pwr_info-pwr_rx = SLOWAUTO_MODE;
}
 
-   ufshcd_dme_peer_get(hba, UIC_ARG_MIB(PA_MAXRXHSGEAR), gear[TX]);
-   if (!gear[TX]) {
+   ufshcd_dme_peer_get(hba, UIC_ARG_MIB(PA_MAXRXHSGEAR),
+   pwr_info-gear_tx);
+   if (!pwr_info-gear_tx) {
ufshcd_dme_peer_get(hba, UIC_ARG_MIB(PA_MAXRXPWMGEAR),
-   gear[TX]);
-   pwr[TX] = SLOWAUTO_MODE;
+   pwr_info-gear_tx);
+   if (!pwr_info-gear_tx) {
+   dev_err(hba-dev, %s: invalid max pwm tx gear read = 
%d\n,
+   __func__, pwr_info-gear_tx);
+   return -EINVAL;
+   }
+   pwr_info-pwr_tx = SLOWAUTO_MODE;
}
 
+   hba-max_pwr_info.is_valid = true;
+   return 0;
+}
+
+/**
+ * ufshcd_config_pwr_mode - configure a new power mode
+ * @hba: per-adapter instance
+ * @desired_pwr_mode: desired power configuration
+ */
+static int ufshcd_config_pwr_mode(struct ufs_hba *hba,
+   struct ufs_pa_layer_attr *desired_pwr_mode)
+{
+   struct 

[PATCH/RFC V2 07/16] scsi: support well known logical units

2014-08-14 Thread Dolev Raviv
From: Subhash Jadavani subha...@codeaurora.org

REPORT LUNS command has SELECT REPORT field which controls what type of
logical units to be reported by device server. According to UFS device
standard, if this field is set to 0, REPORT LUNS would report only report
standard logical units. If it's set to 1 then it would report only well
known logical unit and if it's set to 2 then device would report both
standard and well known logical units.
Some well-known logical units might not have scsi upper-layer drivers. In
such cases, the runtime PM reference count increased during device
enumeration will not be decreased, causing the parent device (host) to
always be on even during idle.

This change allows the SCSI LLD (Low Level Driver) to choose which type
of logical units should be detected.

Signed-off-by: Subhash Jadavani subha...@codeaurora.org
Signed-off-by: Sujit Reddy Thumma sthu...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/scsi_scan.c b/drivers/scsi/scsi_scan.c
index 4a6e4ba..5a0e164 100644
--- a/drivers/scsi/scsi_scan.c
+++ b/drivers/scsi/scsi_scan.c
@@ -802,6 +802,14 @@ static int scsi_add_lun(struct scsi_device *sdev, unsigned 
char *inq_result,
} else {
sdev-type = (inq_result[0]  0x1f);
sdev-removable = (inq_result[1]  0x80)  7;
+
+   /*
+* some devices may respond with wrong type for
+* well-known logical units. Force well-known type
+* to enumerate them correctly.
+*/
+   if (scsi_is_wlun(sdev-lun)  (sdev-type != TYPE_WLUN))
+   sdev-type = TYPE_WLUN;
}
 
switch (sdev-type) {
@@ -817,6 +825,7 @@ static int scsi_add_lun(struct scsi_device *sdev, unsigned 
char *inq_result,
case TYPE_COMM:
case TYPE_RAID:
case TYPE_OSD:
+   case TYPE_WLUN:
sdev-writeable = 1;
break;
case TYPE_ROM:
@@ -1412,6 +1421,13 @@ static int scsi_report_lun_scan(struct scsi_target 
*starget, int bflags,
 */
memset(scsi_cmd[1], 0, 5);
 
+   if (shost-report_wlus)
+   /*
+* Set SELECT REPORT field to 0x2 which will make device to
+* report well known logical units along with standard LUs.
+*/
+   scsi_cmd[2] = 0x2;
+
/*
 * bytes 6 - 9: length of the command.
 */
diff --git a/drivers/scsi/scsi_sysfs.c b/drivers/scsi/scsi_sysfs.c
index 5f36788..ba9d0f0 100644
--- a/drivers/scsi/scsi_sysfs.c
+++ b/drivers/scsi/scsi_sysfs.c
@@ -1060,6 +1060,13 @@ int scsi_sysfs_add_sdev(struct scsi_device *sdev)
}
}
 
+   /*
+* put runtime pm reference for well-known logical units,
+* drivers are expected to _get_* again during probe.
+*/
+   if (scsi_is_wlun(sdev-lun))
+   scsi_autopm_put_device(sdev);
+
return error;
 }
 
diff --git a/include/scsi/scsi.h b/include/scsi/scsi.h
index 91e2e42..6a9b102 100644
--- a/include/scsi/scsi.h
+++ b/include/scsi/scsi.h
@@ -332,6 +332,7 @@ static inline int scsi_status_is_good(int status)
 #define TYPE_ENCLOSURE  0x0d/* Enclosure Services Device */
 #define TYPE_RBC   0x0e
 #define TYPE_OSD0x11
+#define TYPE_WLUN   0x1e/* well-known logical unit */
 #define TYPE_NO_LUN 0x7f
 
 /* SCSI protocols; these are taken from SPC-3 section 7.5 */
diff --git a/include/scsi/scsi_host.h b/include/scsi/scsi_host.h
index b2bc519..05664c4 100644
--- a/include/scsi/scsi_host.h
+++ b/include/scsi/scsi_host.h
@@ -675,6 +675,11 @@ struct Scsi_Host {
unsigned no_write_same:1;
 
/*
+* Set SELECT REPORT field to allow detection of well known logical
+* units along with standard LUs.
+*/
+   unsigned report_wlus:1;
+   /*
 * Optional work queue to be utilized by the transport
 */
char work_q_name[20];
-- 
1.8.5.2
-- 
QUALCOMM ISRAEL, on behalf of Qualcomm Innovation Center, Inc. is a member
of Code Aurora Forum, hosted by The Linux Foundation

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH/RFC V2 06/16] scsi: ufs: Active Power Mode - configuring bActiveICCLevel

2014-08-14 Thread Dolev Raviv
From: Yaniv Gardi yga...@codeaurora.org

The maximum power consumption in active is determined by bActiveICCLevel.
The configuration is done by reading max current supported by the
regulators connected to VCC, VCCQ and VCCQ2 rails on the boards, and
reading the current consumption levels from the device for each rails
(vcc/vccq/vccq2) using power descriptor.
We configure the bActiveICCLevel attribute, with the max value that
correspond to the minimum-of(VCC-current-level,VCCQ-current-level,
VCCQ2-current-level).
In order to minimize resume latency, pre-fetch icc levels and reference
clock during initialization and avoid reading them each link startup
during resume.

Signed-off-by: Raviv Shvili rshv...@codeaurora.org
Signed-off-by: Yaniv Gardi yga...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufs.h b/drivers/scsi/ufs/ufs.h
index 7ea8e71..b0e1f62 100644
--- a/drivers/scsi/ufs/ufs.h
+++ b/drivers/scsi/ufs/ufs.h
@@ -115,6 +115,7 @@ enum flag_idn {
 
 /* Attribute idn for Query requests */
 enum attr_idn {
+   QUERY_ATTR_IDN_ACTIVE_ICC_LVL   = 0x03,
QUERY_ATTR_IDN_BKOPS_STATUS = 0x05,
QUERY_ATTR_IDN_EE_CONTROL   = 0x0D,
QUERY_ATTR_IDN_EE_STATUS= 0x0E,
@@ -174,6 +175,31 @@ enum unit_desc_param {
UNIT_DESC_PARAM_LARGE_UNIT_SIZE_M1  = 0x22,
 };
 
+/* bActiveICCLevel parameter current units */
+enum {
+   UFSHCD_NANO_AMP = 0,
+   UFSHCD_MICRO_AMP= 1,
+   UFSHCD_MILI_AMP = 2,
+   UFSHCD_AMP  = 3,
+};
+
+#define POWER_DESC_MAX_SIZE0x62
+#define POWER_DESC_MAX_ACTV_ICC_LVLS   16
+
+/* Attribute  bActiveICCLevel parameter bit masks definitions */
+#define ATTR_ICC_LVL_UNIT_OFFSET   14
+#define ATTR_ICC_LVL_UNIT_MASK (0x3  ATTR_ICC_LVL_UNIT_OFFSET)
+#define ATTR_ICC_LVL_VALUE_MASK0x3FF
+
+/* Power descriptor parameters offsets in bytes */
+enum power_desc_param_offset {
+   PWR_DESC_LEN= 0x0,
+   PWR_DESC_TYPE   = 0x1,
+   PWR_DESC_ACTIVE_LVLS_VCC_0  = 0x2,
+   PWR_DESC_ACTIVE_LVLS_VCCQ_0 = 0x22,
+   PWR_DESC_ACTIVE_LVLS_VCCQ2_0= 0x42,
+};
+
 /* Exception event mask values */
 enum {
MASK_EE_STATUS  = 0x,
diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index 1fabff4..a851323 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -3265,6 +3265,125 @@ static int ufshcd_eh_host_reset_handler(struct 
scsi_cmnd *cmd)
 }
 
 /**
+ * ufshcd_get_max_icc_level - calculate the ICC level
+ * @sup_curr_uA: max. current supported by the regulator
+ * @start_scan: row at the desc table to start scan from
+ * @buff: power descriptor buffer
+ *
+ * Returns calculated max ICC level for specific regulator
+ */
+static u32 ufshcd_get_max_icc_level(int sup_curr_uA, u32 start_scan, char 
*buff)
+{
+   int i;
+   int curr_uA;
+   u16 data;
+   u16 unit;
+
+   for (i = start_scan; i = 0; i--) {
+   data = be16_to_cpu(*((u16 *)(buff + 2*i)));
+   unit = (data  ATTR_ICC_LVL_UNIT_MASK) 
+   ATTR_ICC_LVL_UNIT_OFFSET;
+   curr_uA = data  ATTR_ICC_LVL_VALUE_MASK;
+   switch (unit) {
+   case UFSHCD_NANO_AMP:
+   curr_uA = curr_uA / 1000;
+   break;
+   case UFSHCD_MILI_AMP:
+   curr_uA = curr_uA * 1000;
+   break;
+   case UFSHCD_AMP:
+   curr_uA = curr_uA * 1000 * 1000;
+   break;
+   case UFSHCD_MICRO_AMP:
+   default:
+   break;
+   }
+   if (sup_curr_uA = curr_uA)
+   break;
+   }
+   if (i  0) {
+   i = 0;
+   pr_err(%s: Couldn't find valid icc_level = %d, __func__, i);
+   }
+
+   return (u32)i;
+}
+
+/**
+ * ufshcd_calc_icc_level - calculate the max ICC level
+ * In case regulators are not initialized we'll return 0
+ * @hba: per-adapter instance
+ * @desc_buf: power descriptor buffer to extract ICC levels from.
+ * @len: length of desc_buff
+ *
+ * Returns calculated ICC level
+ */
+static u32 ufshcd_find_max_sup_active_icc_level(struct ufs_hba *hba,
+   u8 *desc_buf, int len)
+{
+   u32 icc_level = 0;
+
+   if (!hba-vreg_info.vcc || !hba-vreg_info.vccq ||
+   !hba-vreg_info.vccq2) {
+   dev_err(hba-dev,
+   %s: Regulator capability was not set, actvIccLevel=%d,
+   __func__, icc_level);
+   goto out;
+   }
+
+   if (hba-vreg_info.vcc)
+   icc_level = ufshcd_get_max_icc_level(
+

[PATCH/RFC V2 12/16] scsi: ufs: Add support for clock gating

2014-08-14 Thread Dolev Raviv
From: Sahitya Tummala stumm...@codeaurora.org

The UFS controller clocks can be gated after certain period of
inactivity, which is typically less than runtime suspend timeout.
In addition to clocks the link will also be put into Hibern8 mode
to save more power.

The clock gating can be turned on by enabling the capability
UFSHCD_CAP_CLK_GATING. To enable entering into Hibern8 mode as part of
clock gating, set the capability UFSHCD_CAP_HIBERN8_WITH_CLK_GATING.

The tracing events for clock gating can be enabled through debugfs as:
echo 1  /sys/kernel/debug/tracing/events/ufs/ufshcd_clk_gating/enable
cat /sys/kernel/debug/tracing/trace_pipe

Signed-off-by: Sahitya Tummala stumm...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index 3a66d0d..1e5219c 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -177,6 +177,11 @@ static int ufshcd_reset_and_restore(struct ufs_hba *hba);
 static int ufshcd_clear_tm_cmd(struct ufs_hba *hba, int tag);
 static void ufshcd_hba_exit(struct ufs_hba *hba);
 static int ufshcd_probe_hba(struct ufs_hba *hba);
+static int __ufshcd_setup_clocks(struct ufs_hba *hba, bool on,
+bool skip_ref_clk);
+static int ufshcd_setup_clocks(struct ufs_hba *hba, bool on);
+static int ufshcd_uic_hibern8_exit(struct ufs_hba *hba);
+static int ufshcd_uic_hibern8_enter(struct ufs_hba *hba);
 static int ufshcd_host_reset_and_restore(struct ufs_hba *hba);
 static int ufshcd_config_pwr_mode(struct ufs_hba *hba,
struct ufs_pa_layer_attr *desired_pwr_mode);
@@ -498,6 +503,231 @@ static inline int ufshcd_is_hba_active(struct ufs_hba 
*hba)
return (ufshcd_readl(hba, REG_CONTROLLER_ENABLE)  0x1) ? 0 : 1;
 }
 
+static void ufshcd_ungate_work(struct work_struct *work)
+{
+   int ret;
+   unsigned long flags;
+   struct ufs_hba *hba = container_of(work, struct ufs_hba,
+   clk_gating.ungate_work);
+
+   cancel_delayed_work_sync(hba-clk_gating.gate_work);
+
+   spin_lock_irqsave(hba-host-host_lock, flags);
+   if (hba-clk_gating.state == CLKS_ON) {
+   spin_unlock_irqrestore(hba-host-host_lock, flags);
+   goto unblock_reqs;
+   }
+
+   spin_unlock_irqrestore(hba-host-host_lock, flags);
+   ufshcd_setup_clocks(hba, true);
+
+   /* Exit from hibern8 */
+   if (ufshcd_can_hibern8_during_gating(hba)) {
+   /* Prevent gating in this path */
+   hba-clk_gating.is_suspended = true;
+   if (ufshcd_is_link_hibern8(hba)) {
+   ret = ufshcd_uic_hibern8_exit(hba);
+   if (ret)
+   dev_err(hba-dev, %s: hibern8 exit failed 
%d\n,
+   __func__, ret);
+   else
+   ufshcd_set_link_active(hba);
+   }
+   hba-clk_gating.is_suspended = false;
+   }
+unblock_reqs:
+   scsi_unblock_requests(hba-host);
+}
+
+/**
+ * ufshcd_hold - Enable clocks that were gated earlier due to ufshcd_release.
+ * Also, exit from hibern8 mode and set the link as active.
+ * @hba: per adapter instance
+ * @async: This indicates whether caller should ungate clocks asynchronously.
+ */
+int ufshcd_hold(struct ufs_hba *hba, bool async)
+{
+   int rc = 0;
+   unsigned long flags;
+
+   if (!ufshcd_is_clkgating_allowed(hba))
+   goto out;
+start:
+   spin_lock_irqsave(hba-host-host_lock, flags);
+   hba-clk_gating.active_reqs++;
+
+   switch (hba-clk_gating.state) {
+   case CLKS_ON:
+   break;
+   case REQ_CLKS_OFF:
+   if (cancel_delayed_work(hba-clk_gating.gate_work)) {
+   hba-clk_gating.state = CLKS_ON;
+   break;
+   }
+   /*
+* If we here, it means gating work is either done or
+* currently running. Hence, fall through to cancel gating
+* work and to enable clocks.
+*/
+   case CLKS_OFF:
+   scsi_block_requests(hba-host);
+   hba-clk_gating.state = REQ_CLKS_ON;
+   schedule_work(hba-clk_gating.ungate_work);
+   /*
+* fall through to check if we should wait for this
+* work to be done or not.
+*/
+   case REQ_CLKS_ON:
+   if (async) {
+   rc = -EAGAIN;
+   hba-clk_gating.active_reqs--;
+   break;
+   } else {
+   spin_unlock_irqrestore(hba-host-host_lock, flags);
+   flush_work(hba-clk_gating.ungate_work);
+   /* Make sure state is CLKS_ON before returning */
+   goto start;
+   }
+   default:
+   

[PATCH/RFC V2 09/16] scsi: sd: Avoid sending medium write commands if device is write protected

2014-08-14 Thread Dolev Raviv
From: Sujit Reddy Thumma sthu...@codeaurora.org

The SYNCHRONIZE_CACHE command is a medium write command and hence can
fail when the device is write protected. Avoid sending such commands by
making sure that write-cache-enable is disabled even though the device
claim to support it.

Signed-off-by: Sujit Reddy Thumma sthu...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/sd.c b/drivers/scsi/sd.c
index 3663e38..67282bf 100644
--- a/drivers/scsi/sd.c
+++ b/drivers/scsi/sd.c
@@ -185,7 +185,7 @@ cache_type_store(struct device *dev, struct 
device_attribute *attr,
if (ct  0)
return -EINVAL;
rcd = ct  0x01 ? 1 : 0;
-   wce = ct  0x02 ? 1 : 0;
+   wce = (ct  0x02)  !sdkp-write_prot ? 1 : 0;
 
if (sdkp-cache_override) {
sdkp-WCE = wce;
@@ -2493,6 +2493,10 @@ sd_read_cache_type(struct scsi_disk *sdkp, unsigned char 
*buffer)
sdkp-DPOFUA = 0;
}
 
+   /* No cache flush allowed for write protected devices */
+   if (sdkp-WCE  sdkp-write_prot)
+   sdkp-WCE = 0;
+
if (sdkp-first_scan || old_wce != sdkp-WCE ||
old_rcd != sdkp-RCD || old_dpofua != sdkp-DPOFUA)
sd_printk(KERN_NOTICE, sdkp,
-- 
1.8.5.2
-- 
QUALCOMM ISRAEL, on behalf of Qualcomm Innovation Center, Inc. is a member
of Code Aurora Forum, hosted by The Linux Foundation

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH/RFC V2 16/16] scsi: ufs: definitions for phy interface

2014-08-14 Thread Dolev Raviv
- Adding some of the definitions missing in unipro.h, including power
  enumeration.
- Read Modify Write Line helper function
- Indication for the type of suspend

Signed-off-by: Dolev Raviv dra...@codeaurora.org
Signed-off-by: Subhash Jadavani subha...@codeaurora.org
Signed-off-by: Yaniv Gardi yga...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index d9eb2da..1b04cfa 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -4924,6 +4924,8 @@ int ufshcd_system_suspend(struct ufs_hba *hba)
 
ret = ufshcd_suspend(hba, UFS_SYSTEM_PM);
 out:
+   if (!ret)
+   hba-is_sys_suspended = true;
return ret;
 }
 EXPORT_SYMBOL(ufshcd_system_suspend);
diff --git a/drivers/scsi/ufs/ufshcd.h b/drivers/scsi/ufs/ufshcd.h
index b94b835..d502d70 100644
--- a/drivers/scsi/ufs/ufshcd.h
+++ b/drivers/scsi/ufs/ufshcd.h
@@ -471,6 +471,7 @@ struct ufs_hba {
 
struct devfreq *devfreq;
struct ufs_clk_scaling clk_scaling;
+   bool is_sys_suspended;
 };
 
 /* Returns true if clocks can be gated. Otherwise false */
@@ -496,6 +497,23 @@ static inline bool 
ufshcd_can_autobkops_during_suspend(struct ufs_hba *hba)
 #define ufshcd_readl(hba, reg) \
readl((hba)-mmio_base + (reg))
 
+/**
+ * ufshcd_rmwl - read modify write into a register
+ * @hba - per adapter instance
+ * @mask - mask to apply on read value
+ * @val - actual value to write
+ * @reg - register address
+ */
+static inline void ufshcd_rmwl(struct ufs_hba *hba, u32 mask, u32 val, u32 reg)
+{
+   u32 tmp;
+
+   tmp = ufshcd_readl(hba, reg);
+   tmp = ~mask;
+   tmp |= (val  mask);
+   ufshcd_writel(hba, tmp, reg);
+}
+
 int ufshcd_alloc_host(struct device *, struct ufs_hba **);
 int ufshcd_init(struct ufs_hba * , void __iomem * , unsigned int);
 void ufshcd_remove(struct ufs_hba *);
diff --git a/drivers/scsi/ufs/unipro.h b/drivers/scsi/ufs/unipro.h
index 0bb8041..3fc3e21 100644
--- a/drivers/scsi/ufs/unipro.h
+++ b/drivers/scsi/ufs/unipro.h
@@ -13,6 +13,44 @@
 #define _UNIPRO_H_
 
 /*
+ * M-TX Configuration Attributes
+ */
+#define TX_MODE0x0021
+#define TX_HSRATE_SERIES   0x0022
+#define TX_HSGEAR  0x0023
+#define TX_PWMGEAR 0x0024
+#define TX_AMPLITUDE   0x0025
+#define TX_HS_SLEWRATE 0x0026
+#define TX_SYNC_SOURCE 0x0027
+#define TX_HS_SYNC_LENGTH  0x0028
+#define TX_HS_PREPARE_LENGTH   0x0029
+#define TX_LS_PREPARE_LENGTH   0x002A
+#define TX_HIBERN8_CONTROL 0x002B
+#define TX_LCC_ENABLE  0x002C
+#define TX_PWM_BURST_CLOSURE_EXTENSION 0x002D
+#define TX_BYPASS_8B10B_ENABLE 0x002E
+#define TX_DRIVER_POLARITY 0x002F
+#define TX_HS_UNTERMINATED_LINE_DRIVE_ENABLE   0x0030
+#define TX_LS_TERMINATED_LINE_DRIVE_ENABLE 0x0031
+#define TX_LCC_SEQUENCER   0x0032
+#define TX_MIN_ACTIVATETIME0x0033
+#define TX_PWM_G6_G7_SYNC_LENGTH   0x0034
+
+/*
+ * M-RX Configuration Attributes
+ */
+#define RX_MODE0x00A1
+#define RX_HSRATE_SERIES   0x00A2
+#define RX_HSGEAR  0x00A3
+#define RX_PWMGEAR 0x00A4
+#define RX_LS_TERMINATED_ENABLE0x00A5
+#define RX_HS_UNTERMINATED_ENABLE  0x00A6
+#define RX_ENTER_HIBERN8   0x00A7
+#define RX_BYPASS_8B10B_ENABLE 0x00A8
+#define RX_TERMINATION_FORCE_ENABLE0x0089
+
+#define is_mphy_tx_attr(attr)  (attr  RX_MODE)
+/*
  * PHY Adpater attributes
  */
 #define PA_ACTIVETXDATALANES   0x1560
@@ -87,6 +125,24 @@ enum {
PA_HS_MODE_B= 2,
 };
 
+enum ufs_pwm_gear_tag {
+   UFS_PWM_DONT_CHANGE,/* Don't change Gear */
+   UFS_PWM_G1, /* PWM Gear 1 (default for reset) */
+   UFS_PWM_G2, /* PWM Gear 2 */
+   UFS_PWM_G3, /* PWM Gear 3 */
+   UFS_PWM_G4, /* PWM Gear 4 */
+   UFS_PWM_G5, /* PWM Gear 5 */
+   UFS_PWM_G6, /* PWM Gear 6 */
+   UFS_PWM_G7, /* PWM Gear 7 */
+};
+
+enum ufs_hs_gear_tag {
+   UFS_HS_DONT_CHANGE, /* Don't change Gear */
+   UFS_HS_G1,  /* HS Gear 1 (default for reset) */
+   UFS_HS_G2,  /* HS Gear 2 */
+   UFS_HS_G3,  /* HS Gear 3 */
+};
+
 /*
  * Data Link Layer Attributes
  */
-- 
1.8.5.2
-- 
QUALCOMM ISRAEL, on behalf of Qualcomm Innovation Center, Inc. is a member
of Code Aurora Forum, hosted by The Linux Foundation

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org

[PATCH/RFC V2 15/16] scsi: ufs: add capability to control the auto bkops during suspend

2014-08-14 Thread Dolev Raviv
From: Subhash Jadavani subha...@codeaurora.org

If host explicitly enables the auto bkops (background operation) on device
then only device would perform the bkops on its own. If auto bkops is not
enabled explicitly and if the device reaches to state where it must do
background operation, device would raise the urgent bkops exception event
to host and then host will enable the auto bkops on device. This patch
adds the option to choose whether auto bkops should be enabled during
runtime suspend or not.

Signed-off-by: Subhash Jadavani subha...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index 6b769d0..d9eb2da 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -4704,13 +4704,18 @@ static int ufshcd_suspend(struct ufs_hba *hba, enum 
ufs_pm_op pm_op)
}
 
if (ufshcd_is_runtime_pm(pm_op)) {
-   /*
-* The device is idle with no requests in the queue,
-* allow background operations if needed.
-*/
-   ret = ufshcd_bkops_ctrl(hba, BKOPS_STATUS_NON_CRITICAL);
-   if (ret)
-   goto enable_gating;
+   if (ufshcd_can_autobkops_during_suspend(hba)) {
+   /*
+* The device is idle with no requests in the queue,
+* allow background operations if needed.
+*/
+   ret = ufshcd_bkops_ctrl(hba, BKOPS_STATUS_NON_CRITICAL);
+   if (ret)
+   goto enable_gating;
+   } else {
+   /* make sure that auto bkops is disabled */
+   ufshcd_disable_auto_bkops(hba);
+   }
}
 
if ((req_dev_pwr_mode != hba-curr_dev_pwr_mode) 
diff --git a/drivers/scsi/ufs/ufshcd.h b/drivers/scsi/ufs/ufshcd.h
index d5699d0..b94b835 100644
--- a/drivers/scsi/ufs/ufshcd.h
+++ b/drivers/scsi/ufs/ufshcd.h
@@ -466,6 +466,8 @@ struct ufs_hba {
 #define UFSHCD_CAP_HIBERN8_WITH_CLK_GATING (1  1)
/* Allow dynamic clk scaling */
 #define UFSHCD_CAP_CLK_SCALING (1  2)
+   /* Allow auto bkops to enabled during runtime suspend */
+#define UFSHCD_CAP_AUTO_BKOPS_SUSPEND (1  3)
 
struct devfreq *devfreq;
struct ufs_clk_scaling clk_scaling;
@@ -484,6 +486,11 @@ static inline int ufshcd_is_clkscaling_enabled(struct 
ufs_hba *hba)
 {
return hba-caps  UFSHCD_CAP_CLK_SCALING;
 }
+static inline bool ufshcd_can_autobkops_during_suspend(struct ufs_hba *hba)
+{
+   return hba-caps  UFSHCD_CAP_AUTO_BKOPS_SUSPEND;
+}
+
 #define ufshcd_writel(hba, val, reg)   \
writel((val), (hba)-mmio_base + (reg))
 #define ufshcd_readl(hba, reg) \
-- 
1.8.5.2
-- 
QUALCOMM ISRAEL, on behalf of Qualcomm Innovation Center, Inc. is a member
of Code Aurora Forum, hosted by The Linux Foundation

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH/RFC V2 14/16] scsi: ufs: Add support for clock scaling using devfreq framework

2014-08-14 Thread Dolev Raviv
From: Sahitya Tummala stumm...@codeaurora.org

The clocks for UFS device will be managed by generic DVFS (Dynamic
Voltage and Frequency Scaling) framework within kernel. This devfreq
framework works with different governors to scale the clocks. By default,
UFS devices uses simple_ondemand governor which scales the clocks up if
the load is more than upthreshold and scales down if the load is less than
downthreshold.

Signed-off-by: Sahitya Tummala stumm...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/ufs/Kconfig b/drivers/scsi/ufs/Kconfig
index f07f901..6e07b2a 100644
--- a/drivers/scsi/ufs/Kconfig
+++ b/drivers/scsi/ufs/Kconfig
@@ -35,6 +35,8 @@
 config SCSI_UFSHCD
tristate Universal Flash Storage Controller Driver Core
depends on SCSI  SCSI_DMA
+   select PM_DEVFREQ
+   select DEVFREQ_GOV_SIMPLE_ONDEMAND
---help---
This selects the support for UFS devices in Linux, say Y and make
  sure that you know the name of your UFS host adapter (the card
diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index 1e5219c..6b769d0 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -38,6 +38,7 @@
  */
 
 #include linux/async.h
+#include linux/devfreq.h
 
 #include ufshcd.h
 #include unipro.h
@@ -536,6 +537,8 @@ static void ufshcd_ungate_work(struct work_struct *work)
hba-clk_gating.is_suspended = false;
}
 unblock_reqs:
+   if (ufshcd_is_clkscaling_enabled(hba))
+   devfreq_resume_device(hba-devfreq);
scsi_unblock_requests(hba-host);
 }
 
@@ -552,10 +555,10 @@ int ufshcd_hold(struct ufs_hba *hba, bool async)
 
if (!ufshcd_is_clkgating_allowed(hba))
goto out;
-start:
spin_lock_irqsave(hba-host-host_lock, flags);
hba-clk_gating.active_reqs++;
 
+start:
switch (hba-clk_gating.state) {
case CLKS_ON:
break;
@@ -586,6 +589,7 @@ start:
spin_unlock_irqrestore(hba-host-host_lock, flags);
flush_work(hba-clk_gating.ungate_work);
/* Make sure state is CLKS_ON before returning */
+   spin_lock_irqsave(hba-host-host_lock, flags);
goto start;
}
default:
@@ -627,6 +631,11 @@ static void ufshcd_gate_work(struct work_struct *work)
ufshcd_set_link_hibern8(hba);
}
 
+   if (ufshcd_is_clkscaling_enabled(hba)) {
+   devfreq_suspend_device(hba-devfreq);
+   hba-clk_scaling.window_start_t = 0;
+   }
+
if (!ufshcd_is_link_active(hba))
ufshcd_setup_clocks(hba, false);
else
@@ -728,6 +737,32 @@ static void ufshcd_exit_clk_gating(struct ufs_hba *hba)
device_remove_file(hba-dev, hba-clk_gating.delay_attr);
 }
 
+/* Must be called with host lock acquired */
+static void ufshcd_clk_scaling_start_busy(struct ufs_hba *hba)
+{
+   if (!ufshcd_is_clkscaling_enabled(hba))
+   return;
+
+   if (!hba-clk_scaling.is_busy_started) {
+   hba-clk_scaling.busy_start_t = ktime_get();
+   hba-clk_scaling.is_busy_started = true;
+   }
+}
+
+static void ufshcd_clk_scaling_update_busy(struct ufs_hba *hba)
+{
+   struct ufs_clk_scaling *scaling = hba-clk_scaling;
+
+   if (!ufshcd_is_clkscaling_enabled(hba))
+   return;
+
+   if (!hba-outstanding_reqs  scaling-is_busy_started) {
+   scaling-tot_busy_t += ktime_to_us(ktime_sub(ktime_get(),
+   scaling-busy_start_t));
+   scaling-busy_start_t = ktime_set(0, 0);
+   scaling-is_busy_started = false;
+   }
+}
 /**
  * ufshcd_send_command - Send SCSI or device management commands
  * @hba: per adapter instance
@@ -736,6 +771,7 @@ static void ufshcd_exit_clk_gating(struct ufs_hba *hba)
 static inline
 void ufshcd_send_command(struct ufs_hba *hba, unsigned int task_tag)
 {
+   ufshcd_clk_scaling_start_busy(hba);
__set_bit(task_tag, hba-outstanding_reqs);
ufshcd_writel(hba, 1  task_tag, REG_UTP_TRANSFER_REQ_DOOR_BELL);
 }
@@ -2990,6 +3026,8 @@ static void ufshcd_transfer_req_compl(struct ufs_hba *hba)
/* clear corresponding bits of completed commands */
hba-outstanding_reqs ^= completed_reqs;
 
+   ufshcd_clk_scaling_update_busy(hba);
+
/* we might have free'd some tags above */
wake_up(hba-dev_cmd.tag_wq);
 }
@@ -4021,6 +4059,10 @@ static int ufshcd_probe_hba(struct ufs_hba *hba)
if (!hba-is_init_prefetch)
hba-is_init_prefetch = true;
 
+   /* Resume devfreq after UFS device is detected */
+   if (ufshcd_is_clkscaling_enabled(hba))
+   devfreq_resume_device(hba-devfreq);
+
 out:
/*
 * If we failed to initialize the device or the device is not
@@ -4322,6 +4364,7 @@ static int 

[PATCH/RFC V2 08/16] scsi: ufs: introduce well known logical unit in ufs

2014-08-14 Thread Dolev Raviv
From: Subhash Jadavani subha...@codeaurora.org

UFS device may have standard LUs and LUN id could be from 0x00 to 0x7F.
UFS device specification use Peripheral Device Addressing Format
(SCSI SAM-5) for standard LUs.

UFS device may also have the Well Known LUs (also referred as W-LU) which
again could be from 0x00 to 0x7F. For W-LUs, UFS device specification only
allows the Extended Addressing Format (SCSI SAM-5) which means the W-LUNs
would start from 0xC100 onwards.

This means max. LUN number reported from UFS device could be 0xC17F hence
this patch advertise the max_lun as 0xC17F which will allow SCSI mid
layer to detect the W-LUs as well.

But once the W-LUs are detected, UFSHCD driver may get the commands with
SCSI LUN id upto 0xC17F but UPIU LUN id field is only 8-bit wide so it
requires the mapping of SCSI LUN id to UPIU LUN id. This patch also add
support for this mapping.

Signed-off-by: Subhash Jadavani subha...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org
Signed-off-by: Sujit Reddy Thumma sthu...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufs.h b/drivers/scsi/ufs/ufs.h
index b0e1f62..bcc3a7f 100644
--- a/drivers/scsi/ufs/ufs.h
+++ b/drivers/scsi/ufs/ufs.h
@@ -49,9 +49,28 @@
 #define UPIU_HEADER_DWORD(byte3, byte2, byte1, byte0)\
cpu_to_be32((byte3  24) | (byte2  16) |\
 (byte1  8) | (byte0))
-
+/*
+ * UFS device may have standard LUs and LUN id could be from 0x00 to
+ * 0x7F. Standard LUs use Peripheral Device Addressing Format.
+ * UFS device may also have the Well Known LUs (also referred as W-LU)
+ * which again could be from 0x00 to 0x7F. For W-LUs, device only use
+ * the Extended Addressing Format which means the W-LUNs would be
+ * from 0xc100 (SCSI_W_LUN_BASE) onwards.
+ * This means max. LUN number reported from UFS device could be 0xC17F.
+ */
+#define UFS_UPIU_MAX_UNIT_NUM_ID   0x7F
+#define UFS_MAX_LUNS   (SCSI_W_LUN_BASE + UFS_UPIU_MAX_UNIT_NUM_ID)
+#define UFS_UPIU_WLUN_ID   (1  7)
 #define UFS_UPIU_MAX_GENERAL_LUN   8
 
+/* Well known logical unit id in LUN field of UPIU */
+enum {
+   UFS_UPIU_REPORT_LUNS_WLUN   = 0x81,
+   UFS_UPIU_UFS_DEVICE_WLUN= 0xD0,
+   UFS_UPIU_BOOT_WLUN  = 0xB0,
+   UFS_UPIU_RPMB_WLUN  = 0xC4,
+};
+
 /*
  * UFS Protocol Information Unit related definitions
  */
diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index a851323..876d210 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -100,7 +100,6 @@ static u32 ufs_query_desc_max_size[] = {
 enum {
UFSHCD_MAX_CHANNEL  = 0,
UFSHCD_MAX_ID   = 1,
-   UFSHCD_MAX_LUNS = 8,
UFSHCD_CMD_PER_LUN  = 32,
UFSHCD_CAN_QUEUE= 32,
 };
@@ -902,6 +901,21 @@ static int ufshcd_compose_upiu(struct ufs_hba *hba, struct 
ufshcd_lrb *lrbp)
 }
 
 /**
+ * ufshcd_scsi_to_upiu_lun - maps scsi LUN to UPIU LUN
+ * @scsi_lun: scsi LUN id
+ *
+ * Returns UPIU LUN id
+ */
+static inline u8 ufshcd_scsi_to_upiu_lun(unsigned int scsi_lun)
+{
+   if (scsi_is_wlun(scsi_lun))
+   return (scsi_lun  UFS_UPIU_MAX_UNIT_NUM_ID)
+   | UFS_UPIU_WLUN_ID;
+   else
+   return scsi_lun  UFS_UPIU_MAX_UNIT_NUM_ID;
+}
+
+/**
  * ufshcd_queuecommand - main entry point for SCSI requests
  * @cmd: command from SCSI Midlayer
  * @done: call back function
@@ -959,7 +973,7 @@ static int ufshcd_queuecommand(struct Scsi_Host *host, 
struct scsi_cmnd *cmd)
lrbp-sense_bufflen = SCSI_SENSE_BUFFERSIZE;
lrbp-sense_buffer = cmd-sense_buffer;
lrbp-task_tag = tag;
-   lrbp-lun = cmd-device-lun;
+   lrbp-lun = ufshcd_scsi_to_upiu_lun(cmd-device-lun);
lrbp-intr_cmd = false;
lrbp-command_type = UTP_CMD_TYPE_SCSI;
 
@@ -1513,7 +1527,7 @@ static inline int ufshcd_read_unit_desc_param(struct 
ufs_hba *hba,
 * Unit descriptors are only available for general purpose LUs (LUN id
 * from 0 to 7) and RPMB Well known LU.
 */
-   if (lun = UFS_UPIU_MAX_GENERAL_LUN)
+   if (lun != UFS_UPIU_RPMB_WLUN  (lun = UFS_UPIU_MAX_GENERAL_LUN))
return -EOPNOTSUPP;
 
return ufshcd_read_desc_param(hba, QUERY_DESC_IDN_UNIT, lun,
@@ -2144,6 +2158,44 @@ static int ufshcd_verify_dev_init(struct ufs_hba *hba)
 }
 
 /**
+ * ufshcd_set_queue_depth - set lun queue depth
+ * @sdev: pointer to SCSI device
+ *
+ * Read bLUQueueDepth value and activate scsi tagged command
+ * queueing. For WLUN, queue depth is set to 1. For best-effort
+ * cases (bLUQueueDepth = 0) the queue depth is set to a maximum
+ * value that host can queue.
+ */
+static void ufshcd_set_queue_depth(struct scsi_device *sdev)
+{
+   int ret = 0;
+   u8 lun_qdepth;
+   struct ufs_hba *hba;
+
+   hba = shost_priv(sdev-host);
+
+   lun_qdepth = hba-nutrs;
+   ret = ufshcd_read_unit_desc_param(hba,
+   

[PATCH/RFC V2 13/16] scsi: ufs: Add freq-table-hz property for UFS device

2014-08-14 Thread Dolev Raviv
From: Sahitya Tummala stumm...@codeaurora.org

Add freq-table-hz propery for UFS device to keep track of
min max frequencies supported by UFS clocks.

Signed-off-by: Sahitya Tummala stumm...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt 
b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
index b0f791a..e73a619 100644
--- a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
+++ b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
@@ -24,11 +24,11 @@ Optional properties:
 - clocks: List of phandle and clock specifier pairs
 - clock-names   : List of clock input name strings sorted in the same
   order as the clocks property.
-- max-clock-frequency-hz : List of maximum operating frequency stored in the 
same
-   order as the clocks property. If this property is 
not
-  defined or a value in the array is 0 then it is 
assumed
-  that the frequency is set by the parent clock or a
-  fixed rate clock source.
+- freq-table-hz: Array of min max operating frequencies 
stored in the same
+  order as the clocks property. If this property is not
+ defined or a value in the array is 0 then it is 
assumed
+ that the frequency is set by the parent clock or a
+ fixed rate clock source.
 
 Note: If above properties are not defined it can be assumed that the supply
 regulators or clocks are always on.
@@ -49,5 +49,5 @@ Example:
 
clocks = core 0, ref 0, iface 0;
clock-names = core_clk, ref_clk, iface_clk;
-   max-clock-frequency-hz = 1 1920 0;
+   freq-table-hz = 1 2, 0 0, 0 0;
};
diff --git a/drivers/scsi/ufs/ufshcd-pltfrm.c b/drivers/scsi/ufs/ufshcd-pltfrm.c
index edaccd0..551be95 100644
--- a/drivers/scsi/ufs/ufshcd-pltfrm.c
+++ b/drivers/scsi/ufs/ufshcd-pltfrm.c
@@ -63,6 +63,8 @@ static int ufshcd_parse_clock_info(struct ufs_hba *hba)
char *name;
u32 *clkfreq = NULL;
struct ufs_clk_info *clki;
+   int len = 0;
+   size_t sz = 0;
 
if (!np)
goto out;
@@ -82,39 +84,59 @@ static int ufshcd_parse_clock_info(struct ufs_hba *hba)
if (cnt = 0)
goto out;
 
-   clkfreq = kzalloc(cnt * sizeof(*clkfreq), GFP_KERNEL);
+   if (!of_get_property(np, freq-table-hz, len)) {
+   dev_info(dev, freq-table-hz property not specified\n);
+   goto out;
+   }
+
+   if (len = 0)
+   goto out;
+
+   sz = len / sizeof(*clkfreq);
+   if (sz != 2 * cnt) {
+   dev_err(dev, %s len mismatch\n, freq-table-hz);
+   ret = -EINVAL;
+   goto out;
+   }
+
+   clkfreq = devm_kzalloc(dev, sz * sizeof(*clkfreq),
+   GFP_KERNEL);
if (!clkfreq) {
+   dev_err(dev, %s: no memory\n, freq-table-hz);
ret = -ENOMEM;
-   dev_err(dev, %s: memory alloc failed\n, __func__);
goto out;
}
 
-   ret = of_property_read_u32_array(np,
-   max-clock-frequency-hz, clkfreq, cnt);
+   ret = of_property_read_u32_array(np, freq-table-hz,
+   clkfreq, sz);
if (ret  (ret != -EINVAL)) {
-   dev_err(dev, %s: invalid max-clock-frequency-hz property, 
%d\n,
-   __func__, ret);
-   goto out;
+   dev_err(dev, %s: error reading array %d\n,
+   freq-table-hz, ret);
+   goto free_clkfreq;
}
 
-   for (i = 0; i  cnt; i++) {
+   for (i = 0; i  sz; i += 2) {
ret = of_property_read_string_index(np,
-   clock-names, i, (const char **)name);
+   clock-names, i/2, (const char **)name);
if (ret)
-   goto out;
+   goto free_clkfreq;
 
clki = devm_kzalloc(dev, sizeof(*clki), GFP_KERNEL);
if (!clki) {
ret = -ENOMEM;
-   goto out;
+   goto free_clkfreq;
}
 
-   clki-max_freq = clkfreq[i];
+   clki-min_freq = clkfreq[i];
+   clki-max_freq = clkfreq[i+1];
clki-name = kstrdup(name, GFP_KERNEL);
+   dev_dbg(dev, %s: min %u max %u name %s\n, freq-table-hz,
+   clki-min_freq, clki-max_freq, clki-name);
list_add_tail(clki-list, hba-clk_list_head);
}
-out:
+free_clkfreq:
kfree(clkfreq);
+out:
return ret;
 }
 
diff --git a/drivers/scsi/ufs/ufshcd.h 

[PATCH/RFC V2 04/16] scsi: ufs: refactor query descriptor API support

2014-08-14 Thread Dolev Raviv
From: Subhash Jadavani subha...@codeaurora.org

Currently reading query descriptor is more tightened to each
descriptor type. This patch generalize the approach and allows
reading any parameter from any query descriptor.

Signed-off-by: Subhash Jadavani subha...@codeaurora.org
Signed-off-by: Dolev Raviv dra...@codeaurora.org

diff --git a/drivers/scsi/ufs/ufs.h b/drivers/scsi/ufs/ufs.h
index 729ce7d..7ea8e71 100644
--- a/drivers/scsi/ufs/ufs.h
+++ b/drivers/scsi/ufs/ufs.h
@@ -50,6 +50,8 @@
cpu_to_be32((byte3  24) | (byte2  16) |\
 (byte1  8) | (byte0))
 
+#define UFS_UPIU_MAX_GENERAL_LUN   8
+
 /*
  * UFS Protocol Information Unit related definitions
  */
@@ -129,10 +131,29 @@ enum desc_idn {
QUERY_DESC_IDN_RFU_1= 0x6,
QUERY_DESC_IDN_GEOMETRY = 0x7,
QUERY_DESC_IDN_POWER= 0x8,
-   QUERY_DESC_IDN_RFU_2= 0x9,
+   QUERY_DESC_IDN_MAX,
+};
+
+enum desc_header_offset {
+   QUERY_DESC_LENGTH_OFFSET= 0x00,
+   QUERY_DESC_DESC_TYPE_OFFSET = 0x01,
+};
+
+enum ufs_desc_max_size {
+   QUERY_DESC_DEVICE_MAX_SIZE  = 0x1F,
+   QUERY_DESC_CONFIGURAION_MAX_SIZE= 0x90,
+   QUERY_DESC_UNIT_MAX_SIZE= 0x23,
+   QUERY_DESC_INTERCONNECT_MAX_SIZE= 0x06,
+   /*
+* Max. 126 UNICODE characters (2 bytes per character) plus 2 bytes
+* of descriptor header.
+*/
+   QUERY_DESC_STRING_MAX_SIZE  = 0xFE,
+   QUERY_DESC_GEOMETRY_MAZ_SIZE= 0x44,
+   QUERY_DESC_POWER_MAX_SIZE   = 0x62,
+   QUERY_DESC_RFU_MAX_SIZE = 0x00,
 };
 
-#define UNIT_DESC_MAX_SIZE   0x22
 /* Unit descriptor parameters offsets in bytes*/
 enum unit_desc_param {
UNIT_DESC_PARAM_LEN = 0x0,
diff --git a/drivers/scsi/ufs/ufshcd.c b/drivers/scsi/ufs/ufshcd.c
index b033702..57a8dbb 100644
--- a/drivers/scsi/ufs/ufshcd.c
+++ b/drivers/scsi/ufs/ufshcd.c
@@ -78,6 +78,19 @@
_ret;   \
})
 
+static u32 ufs_query_desc_max_size[] = {
+   QUERY_DESC_DEVICE_MAX_SIZE,
+   QUERY_DESC_CONFIGURAION_MAX_SIZE,
+   QUERY_DESC_UNIT_MAX_SIZE,
+   QUERY_DESC_RFU_MAX_SIZE,
+   QUERY_DESC_INTERCONNECT_MAX_SIZE,
+   QUERY_DESC_STRING_MAX_SIZE,
+   QUERY_DESC_RFU_MAX_SIZE,
+   QUERY_DESC_GEOMETRY_MAZ_SIZE,
+   QUERY_DESC_POWER_MAX_SIZE,
+   QUERY_DESC_RFU_MAX_SIZE,
+};
+
 enum {
UFSHCD_MAX_CHANNEL  = 0,
UFSHCD_MAX_ID   = 1,
@@ -124,8 +137,6 @@ static void ufshcd_tmc_handler(struct ufs_hba *hba);
 static void ufshcd_async_scan(void *data, async_cookie_t cookie);
 static int ufshcd_reset_and_restore(struct ufs_hba *hba);
 static int ufshcd_clear_tm_cmd(struct ufs_hba *hba, int tag);
-static int ufshcd_read_sdev_qdepth(struct ufs_hba *hba,
-   struct scsi_device *sdev);
 
 /*
  * ufshcd_wait_for_register - wait for register value to change
@@ -1393,6 +1404,115 @@ out:
 }
 
 /**
+ * ufshcd_read_desc_param - read the specified descriptor parameter
+ * @hba: Pointer to adapter instance
+ * @desc_id: descriptor idn value
+ * @desc_index: descriptor index
+ * @param_offset: offset of the parameter to read
+ * @param_read_buf: pointer to buffer where parameter would be read
+ * @param_size: sizeof(param_read_buf)
+ *
+ * Return 0 in case of success, non-zero otherwise
+ */
+static int ufshcd_read_desc_param(struct ufs_hba *hba,
+ enum desc_idn desc_id,
+ int desc_index,
+ u32 param_offset,
+ u8 *param_read_buf,
+ u32 param_size)
+{
+   int ret;
+   u8 *desc_buf;
+   u32 buff_len;
+   bool is_kmalloc = true;
+
+   /* safety checks */
+   if (desc_id = QUERY_DESC_IDN_MAX)
+   return -EINVAL;
+
+   buff_len = ufs_query_desc_max_size[desc_id];
+   if ((param_offset + param_size)  buff_len)
+   return -EINVAL;
+
+   if (!param_offset  (param_size == buff_len)) {
+   /* memory space already available to hold full descriptor */
+   desc_buf = param_read_buf;
+   is_kmalloc = false;
+   } else {
+   /* allocate memory to hold full descriptor */
+   desc_buf = kmalloc(buff_len, GFP_KERNEL);
+   if (!desc_buf)
+   return -ENOMEM;
+   }
+
+   ret = ufshcd_query_descriptor(hba, UPIU_QUERY_OPCODE_READ_DESC,
+ desc_id, desc_index, 0, desc_buf,
+ buff_len);
+
+   if (ret || (buff_len  ufs_query_desc_max_size[desc_id]) ||
+   (desc_buf[QUERY_DESC_LENGTH_OFFSET] !=
+ufs_query_desc_max_size[desc_id])
+   

Re: [PATCH v2 07/10] qcom: msm-pm: Add cpu low power mode functions

2014-08-14 Thread Pramod Gurav
On Wednesday 13 August 2014 01:13 AM, Lina Iyer wrote:
 Add interface layer to abstract and handle hardware specific
 functionality for executing various cpu low power modes in QCOM
 chipsets.
 
 Signed-off-by: Venkat Devarasetty vdeva...@codeaurora.org
 Signed-off-by: Mahesh Sivasubramanian msiva...@codeaurora.org
 Signed-off-by: Lina Iyer lina.i...@linaro.org
 ---
  drivers/soc/qcom/Makefile |   2 +-
  drivers/soc/qcom/msm-pm.c | 219 
 ++
  include/soc/qcom/pm.h |  39 +

snip

 +{
 + u32 cache_id = 0;
 +
 +#if defined(CONFIG_CPU_V7)
 + u32 sel = 0;
 +
 + asm volatile (mcr p15, 2, %[ccselr], c0, c0, 0\n\t
 +   isb\n\t
 +   mrc p15, 1, %[ccsidr], c0, c0, 0\n\t
 +   :[ccsidr]=r (cache_id)
 +   :[ccselr]r (sel)

Space after ':' is what checkpatch asks. :)

 +  );
 + return cache_id  BIT(30);
 +#elif defined(CONFIG_ARM64)
 + u32 sel = 0;

new line missing after declaration.

 + asm volatile(msr csselr_el1, %[ccselr]\n\t
 +  isb\n\t
 +  mrs %[ccsidr],ccsidr_el1\n\t
 +  :[ccsidr]=r (cache_id)
 +  :[ccselr]r (sel)

Space after ':' is what checkpatch asks. :)

 + );
 + return cache_id  BIT(30);
 +#else
 +#error No valid CPU arch selected
 +#endif
 +}
 +

 
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 07/10] qcom: msm-pm: Add cpu low power mode functions

2014-08-14 Thread Daniel Lezcano

On 08/13/2014 04:16 PM, Lina Iyer wrote:

On Wed, Aug 13, 2014 at 01:18:01PM +0200, Daniel Lezcano wrote:

On 08/12/2014 09:43 PM, Lina Iyer wrote:

Add interface layer to abstract and handle hardware specific
functionality for executing various cpu low power modes in QCOM
chipsets.

Signed-off-by: Venkat Devarasetty vdeva...@codeaurora.org
Signed-off-by: Mahesh Sivasubramanian msiva...@codeaurora.org
Signed-off-by: Lina Iyer lina.i...@linaro.org
---
 drivers/soc/qcom/Makefile |   2 +-
 drivers/soc/qcom/msm-pm.c | 219
++
 include/soc/qcom/pm.h |  39 +
 3 files changed, 259 insertions(+), 1 deletion(-)
 create mode 100644 drivers/soc/qcom/msm-pm.c
 create mode 100644 include/soc/qcom/pm.h

diff --git a/drivers/soc/qcom/Makefile b/drivers/soc/qcom/Makefile
index d7ae93b..7925f83 100644
--- a/drivers/soc/qcom/Makefile
+++ b/drivers/soc/qcom/Makefile
@@ -1,5 +1,5 @@
 obj-$(CONFIG_QCOM_GSBI)+=qcom_gsbi.o
-obj-$(CONFIG_QCOM_PM) +=spm-devices.o spm.o
+obj-$(CONFIG_QCOM_PM) +=spm-devices.o spm.o msm-pm.o

 CFLAGS_scm.o :=$(call as-instr,.arch_extension sec,-DREQUIRES_SEC=1)
 obj-$(CONFIG_QCOM_SCM) += scm.o scm-boot.o
diff --git a/drivers/soc/qcom/msm-pm.c b/drivers/soc/qcom/msm-pm.c
new file mode 100644
index 000..f2f15b8
--- /dev/null
+++ b/drivers/soc/qcom/msm-pm.c
@@ -0,0 +1,219 @@
+/* Copyright (c) 2010-2014, The Linux Foundation. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 and
+ * only version 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ */
+
+#include linux/module.h
+#include linux/kernel.h
+#include linux/init.h
+#include linux/io.h
+#include linux/smp.h
+#include linux/tick.h
+#include linux/platform_device.h
+#include linux/cpu_pm.h
+#include linux/uaccess.h
+
+#include soc/qcom/spm.h
+#include soc/qcom/pm.h
+#include soc/qcom/scm.h
+#include soc/qcom/scm-boot.h
+
+#include asm/suspend.h
+#include asm/cacheflush.h
+#include asm/cputype.h
+#include asm/system_misc.h
+
+#define SCM_CMD_TERMINATE_PC(0x2)
+#define SCM_CMD_CORE_HOTPLUGGED (0x10)
+#define SCM_FLUSH_FLAG_MASK(0x3)
+
+static bool msm_pm_is_L1_writeback(void)
+{
+u32 cache_id = 0;
+
+#if defined(CONFIG_CPU_V7)
+u32 sel = 0;
+
+asm volatile (mcr p15, 2, %[ccselr], c0, c0, 0\n\t
+  isb\n\t
+  mrc p15, 1, %[ccsidr], c0, c0, 0\n\t
+  :[ccsidr]=r (cache_id)
+  :[ccselr]r (sel)
+ );
+return cache_id  BIT(30);
+#elif defined(CONFIG_ARM64)
+u32 sel = 0;
+asm volatile(msr csselr_el1, %[ccselr]\n\t
+ isb\n\t
+ mrs %[ccsidr],ccsidr_el1\n\t
+ :[ccsidr]=r (cache_id)
+ :[ccselr]r (sel)
+);
+return cache_id  BIT(30);
+#else
+#error No valid CPU arch selected
+#endif
+}
+
+static inline void msm_arch_idle(void)
+{
+/* Flush and clock-gate */
+mb();


Why is needed this memory barrier ?

Some QCOM SoCs needed this. I am not sure which one anymore. :(



+wfi();
+}
+
+static bool msm_pm_swfi(bool from_idle)
+{
+msm_arch_idle();
+return true;
+}
+
+static bool msm_pm_retention(bool from_idle)
+{
+int ret = 0;
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_RETENTION, false);
+WARN_ON(ret);
+
+msm_arch_idle();
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_CLOCK_GATING, false);
+WARN_ON(ret);


Why do you need to set the clock gating mode each time you exit the
retention mode ?

So if the SPM did not reset to clockgating, we would not do retention
when we intended to do clockgating. Btw, we dont set clockgating
everytime we do clockgating, helps reduce the latency in doing WFI.


Can you elaborate ? Or may be just describe what is the doing the 
function because I don't get the connection between your explanation and 
the code.



+return true;
+}
+
+static int msm_pm_collapse(unsigned long from_idle)
+{
+enum msm_pm_l2_scm_flag flag = MSM_SCM_L2_ON;
+
+/**
+ * Single core processors need to have L2
+ * flushed when powering down the core.
+ * Notify SCM to flush secure L2 lines.
+ */
+if (num_possible_cpus() == 1)
+flag = MSM_SCM_L2_OFF;


I am wondering if this shouldn't be handle by a mcpm driver.

Cc nico.


Well, possibly, sorry, not sure what features of the mcpm driver you
think I need here?


Please correct me if I am wrong. IIUC, this function is checking the 
number of the cpus of the cluster in order to flush the L2 cache because 
the SCM will power down the cluster if it is the last one, right ?




--
 http://www.linaro.org/ Linaro.org │ Open source software for 

Re: [PATCH v2 07/10] qcom: msm-pm: Add cpu low power mode functions

2014-08-14 Thread Lina Iyer

On Thu, Aug 14, 2014 at 04:24:10PM +0200, Daniel Lezcano wrote:

On 08/13/2014 04:16 PM, Lina Iyer wrote:

On Wed, Aug 13, 2014 at 01:18:01PM +0200, Daniel Lezcano wrote:

On 08/12/2014 09:43 PM, Lina Iyer wrote:



+static bool msm_pm_retention(bool from_idle)

+{
+int ret = 0;
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_RETENTION, false);
+WARN_ON(ret);
+
+msm_arch_idle();
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_CLOCK_GATING, false);
+WARN_ON(ret);


Why do you need to set the clock gating mode each time you exit the
retention mode ?

So if the SPM did not reset to clockgating, we would not do retention
when we intended to do clockgating. Btw, we dont set clockgating
everytime we do clockgating, helps reduce the latency in doing WFI.


Can you elaborate ? Or may be just describe what is the doing the 
function because I don't get the connection between your explanation 
and the code.




Retention still has an higher latency than clock gating. Retention gets
triggered with the core executes wfi() instruction. The entry into a
steady state retention mode is higher than just gating clocks, which may
be bad for power, if we do not stay in the low power modes for a minimum
of the residency period.

If the current idle state was retention and SPM was configured to do
retention and we came out the retention state and the next idle, we
decided to do clockgating we should configure the SPM to do clock
gating. Since we want to speed up clockgating as its one of the state
most commonly entered, we set the configuration of SPM as soon as we
come out any low power mode back to WFI.


+return true;
+}
+
+static int msm_pm_collapse(unsigned long from_idle)
+{
+enum msm_pm_l2_scm_flag flag = MSM_SCM_L2_ON;
+
+/**
+ * Single core processors need to have L2
+ * flushed when powering down the core.
+ * Notify SCM to flush secure L2 lines.
+ */
+if (num_possible_cpus() == 1)
+flag = MSM_SCM_L2_OFF;


I am wondering if this shouldn't be handle by a mcpm driver.

Cc nico.


Well, possibly, sorry, not sure what features of the mcpm driver you
think I need here?


Please correct me if I am wrong. IIUC, this function is checking the 
number of the cpus of the cluster in order to flush the L2 cache 
because the SCM will power down the cluster if it is the last one, 
right ?




--
http://www.linaro.org/ Linaro.org │ Open source software for ARM SoCs

Follow Linaro:  http://www.facebook.com/pages/Linaro Facebook |
http://twitter.com/#!/linaroorg Twitter |
http://www.linaro.org/linaro-blog/ Blog


--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v3] scsi: ufs-msm: add UFS controller support for Qualcomm MSM chips

2014-08-14 Thread Kumar Gala

On Aug 14, 2014, at 9:22 AM, Yaniv Gardi yga...@codeaurora.org wrote:

 The files in this change implement the UFS HW (controller  PHY) specific
 behavior in Qualcomm MSM chips.
 
 Signed-off-by: Yaniv Gardi yga...@codeaurora.org
 ---
 Documentation/devicetree/bindings/ufs/ufs-msm.txt  |   37 +
 .../devicetree/bindings/ufs/ufshcd-pltfrm.txt  |4 +
 drivers/scsi/ufs/Kconfig   |   12 +
 drivers/scsi/ufs/Makefile  |4 +
 drivers/scsi/ufs/ufs-msm-phy-qmp-20nm.c|  254 +
 drivers/scsi/ufs/ufs-msm-phy-qmp-20nm.h|  216 
 drivers/scsi/ufs/ufs-msm-phy-qmp-28nm.c|  368 +++
 drivers/scsi/ufs/ufs-msm-phy-qmp-28nm.h|  735 +
 drivers/scsi/ufs/ufs-msm-phy.c |  646 
 drivers/scsi/ufs/ufs-msm-phy.h |  193 

Any reason not to put the phy driver in drivers/phy ?

 drivers/scsi/ufs/ufs-msm.c | 1105 
 drivers/scsi/ufs/ufs-msm.h |  158 +++
 12 files changed, 3732 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/ufs/ufs-msm.txt
 create mode 100644 drivers/scsi/ufs/ufs-msm-phy-qmp-20nm.c
 create mode 100644 drivers/scsi/ufs/ufs-msm-phy-qmp-20nm.h
 create mode 100644 drivers/scsi/ufs/ufs-msm-phy-qmp-28nm.c
 create mode 100644 drivers/scsi/ufs/ufs-msm-phy-qmp-28nm.h
 create mode 100644 drivers/scsi/ufs/ufs-msm-phy.c
 create mode 100644 drivers/scsi/ufs/ufs-msm-phy.h
 create mode 100644 drivers/scsi/ufs/ufs-msm.c
 create mode 100644 drivers/scsi/ufs/ufs-msm.h

Seems like we should spit this into two patches, one for the phy and one for 
the UFS driver itself.  Maybe even three, one for the 20nm phy, one for the 
28nm phy, and one for ufs-msm.c,h.

 
 diff --git a/Documentation/devicetree/bindings/ufs/ufs-msm.txt 
 b/Documentation/devicetree/bindings/ufs/ufs-msm.txt
 new file mode 100644
 index 000..b5caace
 --- /dev/null
 +++ b/Documentation/devicetree/bindings/ufs/ufs-msm.txt

This should probably be bindings/phy/qcom-ufs-phy.txt

 @@ -0,0 +1,37 @@
 +* MSM Universal Flash Storage (UFS) PHY
 +
 +UFSPHY nodes are defined to describe on-chip UFS PHY hardware macro.
 +Each UFS PHY node should have its own node.
 +
 +To bind UFS PHY with UFS host controller, the controller node should
 +contain a phandle reference to UFS PHY node.
 +
 +Required properties:
 +- compatible: compatible list, contains qcom,ufs-msm-phy-qmp-28nm
 +  or qcom,ufs-msm-phy-qmp-20nm according to the 
 relevant
 +  phy in use

Do we really need ‘-msm’ in the compat name?

 +- reg   : registers mapping
 +- #phy-cells : This property shall be set to 0
 +- vdda-phy-supply   : phandle to main PHY supply for analog domain
 +- vdda-pll-supply   : phandle to PHY PLL and Power-Gen block power supply
 +
 +Optional properties:
 +- vdda-phy-max-microamp : specifies max. load that can be drawn from phy 
 supply
 +- vdda-pll-max-microamp : specifies max. load that can be drawn from pll 
 supply
 +
 +Example:
 +
 + ufsphy1: ufsphy@0xfc597000 {
 + compatible = qcom,ufs-msm-phy-qmp-28nm;
 + reg = 0xfc597000 0x800;
 + #phy-cells = 0;
 + vdda-phy-supply = pma8084_l4;
 + vdda-pll-supply = pma8084_l12;
 + vdda-phy-max-microamp = 5;
 + vdda-pll-max-microamp = 1000;
 + };
 +
 + ufshc@0xfc598000 {
 + ...
 + phys = ufsphy1;
 + };
 diff --git a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt 
 b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
 index e73a619..378585c 100644
 --- a/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
 +++ b/Documentation/devicetree/bindings/ufs/ufshcd-pltfrm.txt
 @@ -9,6 +9,9 @@ Required properties:
 - reg   : registers mapping
 
 Optional properties:
 +- phys   : phandle to UFS PHY node
 +- phy-names  : the string ufs_msm_phy when is found in a node, 
 along
 +   with phys attribute, provides phandle to UFS PHY 
 node

seems like the phy-names should be more generic like “ufsphy

 - vcc-supply: phandle to VCC supply regulator node
 - vccq-supply   : phandle to VCCQ supply regulator node
 - vccq2-supply  : phandle to VCCQ2 supply regulator node
 @@ -39,6 +42,7 @@ Example:
   reg = 0xfc598000 0x800;
   interrupts = 0 28 0;
 
 + ufs-phy = ufsphy;
   vcc-supply = xxx_reg1;
   vcc-supply-1p8;
   vccq-supply = xxx_reg2;


 diff --git a/drivers/scsi/ufs/Kconfig b/drivers/scsi/ufs/Kconfig
 index 6e07b2a..a8259e0 100644
 --- a/drivers/scsi/ufs/Kconfig
 +++ b/drivers/scsi/ufs/Kconfig
 @@ -70,3 +70,15 @@ config SCSI_UFSHCD_PLATFORM
   If you have a controller with this interface, say Y or M here.
 
 If unsure, say 

Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Kumar Gala

On Aug 12, 2014, at 2:43 PM, Lina Iyer lina.i...@linaro.org wrote:

 Qualcomm chipsets use an separate h/w block to control the logic around
 the processor cores (cpu and L2). The SPM h/w block regulates power to
 the cores and controls the power when the core enter low power modes.
 
 Each core has its own instance of SPM. The SPM has the following key
 functions
   - Configure the h/w dependencies when entering low power modes
   - Wait for interrupt and wake up on interrupt
   - Ensure the dependencies are ready before bringing the core out
 of sleep
   - Regulating voltage to the core, interfacing with the PMIC.
   - Optimize power based on runtime recommendations.
 
 The driver identifies and configures the SPMs, by reading the nodes and
 the register values from the devicetree. The SPMs need to be configured
 to allow the processor to be idled in a low power state.
 
 Signed-off-by: Praveen Chidamabram pchid...@codeaurora.org
 Signed-off-by: Murali Nalajala mnala...@codeaurora.org
 Signed-off-by: Lina Iyer lina.i...@linaro.org
 ---
 .../devicetree/bindings/arm/msm/spm-v2.txt |  62 ++
 drivers/soc/qcom/Makefile  |   2 +
 drivers/soc/qcom/spm-devices.c | 703 +
 drivers/soc/qcom/spm.c | 482 ++
 drivers/soc/qcom/spm_driver.h  | 116 
 include/soc/qcom/spm.h |  70 ++
 6 files changed, 1435 insertions(+)
 create mode 100644 Documentation/devicetree/bindings/arm/msm/spm-v2.txt
 create mode 100644 drivers/soc/qcom/spm-devices.c
 create mode 100644 drivers/soc/qcom/spm.c
 create mode 100644 drivers/soc/qcom/spm_driver.h
 create mode 100644 include/soc/qcom/spm.h
 
 diff --git a/Documentation/devicetree/bindings/arm/msm/spm-v2.txt 
 b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
 new file mode 100644
 index 000..3130f4b
 --- /dev/null
 +++ b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
 @@ -0,0 +1,62 @@
 +* MSM Subsystem Power Manager (spm-v2)
 +
 +S4 generation of MSMs have SPM hardware blocks to control the Application
 +Processor Sub-System power. These SPM blocks run individual state machine
 +to determine what the core (L2 or Krait/Scorpion) would do when the WFI
 +instruction is executed by the core.
 +
 +The devicetree representation of the SPM block should be:
 +
 +Required properties
 +
 +- compatible: Could be one of -
 + qcom,spm-v2.1
 + qcom,spm-v3.0
 +- reg: The physical address and the size of the SPM's memory mapped registers
 +- qcom,cpu: phandle for the CPU that the SPM block is attached to. On targets
 + that dont support CPU phandles the driver would support qcom,core-id.
 + This field is required on only for SPMs that control the CPU.
 +- qcom,saw2-cfg: SAW2 configuration register
 +- qcom,saw2-spm-dly: Provides the values for the SPM delay command in the SPM
 + sequence
 +- qcom,saw2-spm-ctl: The SPM control register
 +- qcom,name: The name with which a SPM device is identified by the power
 + management code.

Still not sure about this, wondering why we can’t use the node name.

 +
 +Optional properties
 +
 +- qcom,saw2-pmic-data0..7: Specify the pmic data value and the associated FTS
 + (Fast Transient Switch) index to send the PMIC data to
 +- qcom,vctl-port: The PVC (PMIC Virtual Channel) port used for changing
 + voltage
 +- qcom,phase-port: The PVC port used for changing the number of phases
 +- qcom,pfm-port: The PVC port used for enabling PWM/PFM modes
 +- qcom,saw2-spm-cmd-wfi: The WFI command sequence
 +- qcom,saw2-spm-cmd-ret: The Retention command sequence
 +- qcom,saw2-spm-cmd-spc: The Standalone PC command sequence
 +- qcom,saw2-spm-cmd-pc-no-rpm: The Power Collapse command sequence where APPS
 + proc won't inform the RPM.
 +- qcom,saw2-spm-cmd-pc: The Power Collapse command sequence. This sequence 
 may
 + turn off other SoC components.
 +- qcom,saw2-spm-cmd-gdhs: GDHS (Globally Distributed Head Switch) command
 + sequence. This sequence will retain the memory but turn off the logic.
 +- qcom,cpu-vctl-list: List of cpu node phandles, whose voltage the spm device
 + can control.
 +- qcom,vctl-timeout-us: The timeout value in microseconds to wait for 
 voltage to
 + change after sending the voltage command to the PMIC.
 +-
 +Example:
 + qcom,spm@f9089000 {
 + compatible = qcom,spm-v2;
 + #address-cells = 1;
 + #size-cells = 1;
 + reg = 0xf9089000 0x1000;
 + qcom,cpu = CPU0;
 + qcom,saw2-cfg = 0x1;
 + qcom,saw2-spm-dly= 0x2400;
 + qcom,saw2-spm-ctl = 0x1;
 + qcom,saw2-spm-cmd-wfi = [03 0b 0f];
 + qcom,saw2-spm-cmd-spc = [00 20 50 80 60 70 10 92
 + a0 b0 03 68 70 3b 92 a0 b0
 + 82 2b 50 10 30 02 22 30 0f];
 + };
 diff 

Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Lina Iyer

On Thu, Aug 14, 2014 at 06:31:09PM +0530, Pramod Gurav wrote:

On Wednesday 13 August 2014 01:13 AM, Lina Iyer wrote:

Qualcomm chipsets use an separate h/w block to control the logic around
the processor cores (cpu and L2). The SPM h/w block regulates power to
the cores and controls the power when the core enter low power modes.

Each core has its own instance of SPM. The SPM has the following key
functions
- Configure the h/w dependencies when entering low power modes
- Wait for interrupt and wake up on interrupt
- Ensure the dependencies are ready before bringing the core out
  of sleep
- Regulating voltage to the core, interfacing with the PMIC.
- Optimize power based on runtime recommendations.

The driver identifies and configures the SPMs, by reading the nodes and
the register values from the devicetree. The SPMs need to be configured
to allow the processor to be idled in a low power state.

Signed-off-by: Praveen Chidamabram pchid...@codeaurora.org
Signed-off-by: Murali Nalajala mnala...@codeaurora.org
Signed-off-by: Lina Iyer lina.i...@linaro.org
---
+


snip


 CFLAGS_scm.o :=$(call as-instr,.arch_extension sec,-DREQUIRES_SEC=1)
 obj-$(CONFIG_QCOM_SCM) += scm.o scm-boot.o
diff --git a/drivers/soc/qcom/spm-devices.c b/drivers/soc/qcom/spm-devices.c
new file mode 100644
index 000..567e9f9
--- /dev/null
+++ b/drivers/soc/qcom/spm-devices.c


snip


+   if (ret)
+   return ret;
+
+   return dev-cpu_vdd;
+}
+EXPORT_SYMBOL(msm_spm_get_vdd);
+
+static void msm_spm_config_q2s(struct msm_spm_device *dev, unsigned int mode)
+{
+   uint32_t spm_legacy_mode = 0;
+   uint32_t qchannel_ignore = 0;
+   uint32_t val = 0;

Initialization not needed for val.

+
+   if (!dev-q2s_reg)
+   return;
+
+   switch (mode) {
+   case MSM_SPM_MODE_DISABLED:
+   case MSM_SPM_MODE_CLOCK_GATING:
+   qchannel_ignore = 1;
+   spm_legacy_mode = 0;
+   break;
+   case MSM_SPM_MODE_RETENTION:
+   qchannel_ignore = 0;
+   spm_legacy_mode = 0;
+   break;
+   case MSM_SPM_MODE_GDHS:
+   case MSM_SPM_MODE_POWER_COLLAPSE:
+   qchannel_ignore = 0;
+   spm_legacy_mode = 1;
+   break;
+   default:
+   break;
+   }
+
+   val = spm_legacy_mode  2 | qchannel_ignore  1;
+   __raw_writel(val, dev-q2s_reg);
+   mb();

This may need a comment around it.

Sorry, my bad. I picked up the latest driver and this came with it. In my
next version I pruned this code.

+}
+
+static int msm_spm_dev_set_low_power_mode(struct msm_spm_device *dev,
+   unsigned int mode, bool notify_rpm)
+{
+   uint32_t i;
+   uint32_t start_addr = 0;
+   int ret = -EINVAL;
+   bool pc_mode = false;
+
+   if (!dev-initialized)
+   return -ENXIO;
+
+   if ((mode == MSM_SPM_MODE_POWER_COLLAPSE)
+   || (mode == MSM_SPM_MODE_GDHS))
+   pc_mode = true;
+
+   if (mode == MSM_SPM_MODE_DISABLED) {
+   ret = msm_spm_drv_set_spm_enable(dev-reg_data, false);
+   } else if (!msm_spm_drv_set_spm_enable(dev-reg_data, true)) {
+   for (i = 0; i  dev-num_modes; i++) {
+   if ((dev-modes[i].mode == mode) 
+   (dev-modes[i].notify_rpm == notify_rpm)) {
+   start_addr = dev-modes[i].start_addr;
+   break;
+   }
+   }
+   ret = msm_spm_drv_set_low_power_mode(dev-reg_data,
+   start_addr, pc_mode);
+   }
+
+   msm_spm_config_q2s(dev, mode);
+
+   return ret;
+}
+
+static int msm_spm_dev_init(struct msm_spm_device *dev,
+   struct msm_spm_platform_data *data)
+{
+   int i, ret = -ENOMEM;
+   uint32_t offset = 0;
+
+   dev-cpu_vdd = VDD_DEFAULT;
+   dev-num_modes = data-num_modes;
+   dev-modes = kmalloc(
+   sizeof(struct msm_spm_power_modes) * dev-num_modes,
+   GFP_KERNEL);
+
+   if (!dev-modes)
+   goto spm_failed_malloc;
+
+   dev-reg_data.major = data-major;
+   dev-reg_data.minor = data-minor;
+   ret = msm_spm_drv_init(dev-reg_data, data);
+

Please remove extra line.

+   if (ret)
+   goto spm_failed_init;
+
+   for (i = 0; i  dev-num_modes; i++) {
+
+   /* Default offset is 0 and gets updated as we write more
+* sequences into SPM
+*/
+   dev-modes[i].start_addr = offset;
+   ret = msm_spm_drv_write_seq_data(dev-reg_data,
+   data-modes[i].cmd, offset);
+   if (ret  0)
+   goto spm_failed_init;
+
+   dev-modes[i].mode = data-modes[i].mode;
+   

Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Lina Iyer

On Thu, Aug 14, 2014 at 10:16:15AM -0500, Kumar Gala wrote:


On Aug 12, 2014, at 2:43 PM, Lina Iyer lina.i...@linaro.org wrote:


Qualcomm chipsets use an separate h/w block to control the logic around
the processor cores (cpu and L2). The SPM h/w block regulates power to
the cores and controls the power when the core enter low power modes.

Each core has its own instance of SPM. The SPM has the following key
functions
- Configure the h/w dependencies when entering low power modes
- Wait for interrupt and wake up on interrupt
- Ensure the dependencies are ready before bringing the core out
  of sleep
- Regulating voltage to the core, interfacing with the PMIC.
- Optimize power based on runtime recommendations.

The driver identifies and configures the SPMs, by reading the nodes and
the register values from the devicetree. The SPMs need to be configured
to allow the processor to be idled in a low power state.

Signed-off-by: Praveen Chidamabram pchid...@codeaurora.org
Signed-off-by: Murali Nalajala mnala...@codeaurora.org
Signed-off-by: Lina Iyer lina.i...@linaro.org
---
.../devicetree/bindings/arm/msm/spm-v2.txt |  62 ++
drivers/soc/qcom/Makefile  |   2 +
drivers/soc/qcom/spm-devices.c | 703 +
drivers/soc/qcom/spm.c | 482 ++
drivers/soc/qcom/spm_driver.h  | 116 
include/soc/qcom/spm.h |  70 ++
6 files changed, 1435 insertions(+)
create mode 100644 Documentation/devicetree/bindings/arm/msm/spm-v2.txt
create mode 100644 drivers/soc/qcom/spm-devices.c
create mode 100644 drivers/soc/qcom/spm.c
create mode 100644 drivers/soc/qcom/spm_driver.h
create mode 100644 include/soc/qcom/spm.h

diff --git a/Documentation/devicetree/bindings/arm/msm/spm-v2.txt 
b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
new file mode 100644
index 000..3130f4b
--- /dev/null
+++ b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
@@ -0,0 +1,62 @@
+* MSM Subsystem Power Manager (spm-v2)
+
+S4 generation of MSMs have SPM hardware blocks to control the Application
+Processor Sub-System power. These SPM blocks run individual state machine
+to determine what the core (L2 or Krait/Scorpion) would do when the WFI
+instruction is executed by the core.
+
+The devicetree representation of the SPM block should be:
+
+Required properties
+
+- compatible: Could be one of -
+   qcom,spm-v2.1
+   qcom,spm-v3.0
+- reg: The physical address and the size of the SPM's memory mapped registers
+- qcom,cpu: phandle for the CPU that the SPM block is attached to. On targets
+   that dont support CPU phandles the driver would support qcom,core-id.
+   This field is required on only for SPMs that control the CPU.
+- qcom,saw2-cfg: SAW2 configuration register
+- qcom,saw2-spm-dly: Provides the values for the SPM delay command in the SPM
+   sequence
+- qcom,saw2-spm-ctl: The SPM control register
+- qcom,name: The name with which a SPM device is identified by the power
+   management code.


Still not sure about this, wondering why we can’t use the node name.

At this point, without the SoC Idle frameworks code, we dont need this.
I will prune this off from the next version.



+
+Optional properties
+
+- qcom,saw2-pmic-data0..7: Specify the pmic data value and the associated FTS
+   (Fast Transient Switch) index to send the PMIC data to
+- qcom,vctl-port: The PVC (PMIC Virtual Channel) port used for changing
+   voltage
+- qcom,phase-port: The PVC port used for changing the number of phases
+- qcom,pfm-port: The PVC port used for enabling PWM/PFM modes
+- qcom,saw2-spm-cmd-wfi: The WFI command sequence
+- qcom,saw2-spm-cmd-ret: The Retention command sequence
+- qcom,saw2-spm-cmd-spc: The Standalone PC command sequence
+- qcom,saw2-spm-cmd-pc-no-rpm: The Power Collapse command sequence where APPS
+   proc won't inform the RPM.
+- qcom,saw2-spm-cmd-pc: The Power Collapse command sequence. This sequence may
+   turn off other SoC components.
+- qcom,saw2-spm-cmd-gdhs: GDHS (Globally Distributed Head Switch) command
+   sequence. This sequence will retain the memory but turn off the logic.
+- qcom,cpu-vctl-list: List of cpu node phandles, whose voltage the spm device
+   can control.
+- qcom,vctl-timeout-us: The timeout value in microseconds to wait for voltage 
to
+   change after sending the voltage command to the PMIC.
+-
+Example:
+   qcom,spm@f9089000 {
+   compatible = qcom,spm-v2;
+   #address-cells = 1;
+   #size-cells = 1;
+   reg = 0xf9089000 0x1000;
+   qcom,cpu = CPU0;
+   qcom,saw2-cfg = 0x1;
+   qcom,saw2-spm-dly= 0x2400;
+   qcom,saw2-spm-ctl = 0x1;
+   qcom,saw2-spm-cmd-wfi = [03 0b 0f];
+   qcom,saw2-spm-cmd-spc = [00 20 50 80 60 70 

Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Kumar Gala

 diff --git a/drivers/soc/qcom/spm.c b/drivers/soc/qcom/spm.c
 new file mode 100644
 index 000..7dbdb64
 --- /dev/null
 +++ b/drivers/soc/qcom/spm.c
 @@ -0,0 +1,482 @@
 +/* Copyright (c) 2011-2014, The Linux Foundation. All rights reserved.
 + *
 + * This program is free software; you can redistribute it and/or modify
 + * it under the terms of the GNU General Public License version 2 and
 + * only version 2 as published by the Free Software Foundation.
 + *
 + * This program is distributed in the hope that it will be useful,
 + * but WITHOUT ANY WARRANTY; without even the implied warranty of
 + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 + * GNU General Public License for more details.
 + *
 + */
 +
 +#include linux/module.h
 +#include linux/kernel.h
 +#include linux/delay.h
 +#include linux/init.h
 +#include linux/io.h
 +#include linux/slab.h
 +
 +#include spm_driver.h
 +
 +#define MSM_SPM_PMIC_STATE_IDLE  0
 +
 +enum {
 +   MSM_SPM_DEBUG_SHADOW = 1U  0,
 +   MSM_SPM_DEBUG_VCTL = 1U  1,
 +};
 +
 +static int msm_spm_debug_mask;
 +module_param_named(
 +   debug_mask, msm_spm_debug_mask, int, S_IRUGO | S_IWUSR | S_IWGRP
 +);
 +
 +struct saw2_data {
 +   const char *ver_name;
 +   uint32_t major;
 +   uint32_t minor;
 +   uint32_t *spm_reg_offset_ptr;
 +};
 +
 +static uint32_t msm_spm_reg_offsets_saw2_v2_1[MSM_SPM_REG_NR] = {
 +   [MSM_SPM_REG_SAW2_SECURE]   = 0x00,
 +   [MSM_SPM_REG_SAW2_ID]   = 0x04,
 +   [MSM_SPM_REG_SAW2_CFG]  = 0x08,
 +   [MSM_SPM_REG_SAW2_SPM_STS]  = 0x0C,
 +   [MSM_SPM_REG_SAW2_AVS_STS]  = 0x10,
 +   [MSM_SPM_REG_SAW2_PMIC_STS] = 0x14,
 +   [MSM_SPM_REG_SAW2_RST]  = 0x18,
 +   [MSM_SPM_REG_SAW2_VCTL] = 0x1C,
 +   [MSM_SPM_REG_SAW2_AVS_CTL]  = 0x20,
 +   [MSM_SPM_REG_SAW2_AVS_LIMIT]= 0x24,
 +   [MSM_SPM_REG_SAW2_AVS_DLY]  = 0x28,
 +   [MSM_SPM_REG_SAW2_AVS_HYSTERESIS]   = 0x2C,
 +   [MSM_SPM_REG_SAW2_SPM_CTL]  = 0x30,
 +   [MSM_SPM_REG_SAW2_SPM_DLY]  = 0x34,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_0]  = 0x40,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_1]  = 0x44,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_2]  = 0x48,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_3]  = 0x4C,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_4]  = 0x50,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_5]  = 0x54,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_6]  = 0x58,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_7]  = 0x5C,
 +   [MSM_SPM_REG_SAW2_SEQ_ENTRY]= 0x80,
 +   [MSM_SPM_REG_SAW2_VERSION]  = 0xFD0,
 +};
 +
 +static uint32_t msm_spm_reg_offsets_saw2_v3_0[MSM_SPM_REG_NR] = {
 +   [MSM_SPM_REG_SAW2_SECURE]   = 0x00,
 +   [MSM_SPM_REG_SAW2_ID]   = 0x04,
 +   [MSM_SPM_REG_SAW2_CFG]  = 0x08,
 +   [MSM_SPM_REG_SAW2_SPM_STS]  = 0x0C,
 +   [MSM_SPM_REG_SAW2_AVS_STS]  = 0x10,
 +   [MSM_SPM_REG_SAW2_PMIC_STS] = 0x14,
 +   [MSM_SPM_REG_SAW2_RST]  = 0x18,
 +   [MSM_SPM_REG_SAW2_VCTL] = 0x1C,
 +   [MSM_SPM_REG_SAW2_AVS_CTL]  = 0x20,
 +   [MSM_SPM_REG_SAW2_AVS_LIMIT]= 0x24,
 +   [MSM_SPM_REG_SAW2_AVS_DLY]  = 0x28,
 +   [MSM_SPM_REG_SAW2_AVS_HYSTERESIS]   = 0x2C,
 +   [MSM_SPM_REG_SAW2_SPM_CTL]  = 0x30,
 +   [MSM_SPM_REG_SAW2_SPM_DLY]  = 0x34,
 +   [MSM_SPM_REG_SAW2_STS2] = 0x38,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_0]  = 0x40,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_1]  = 0x44,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_2]  = 0x48,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_3]  = 0x4C,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_4]  = 0x50,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_5]  = 0x54,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_6]  = 0x58,
 +   [MSM_SPM_REG_SAW2_PMIC_DATA_7]  = 0x5C,
 +   [MSM_SPM_REG_SAW2_SEQ_ENTRY]= 0x400,
 +   [MSM_SPM_REG_SAW2_VERSION]  = 0xFD0,
 +};
 
 I don’t see what having these arrays provides as the only differences are 
 that v3.0 has MSM_SPM_REG_SAW2_STS2 and the offset of 
 MSM_SPM_REG_SAW2_SEQ_ENTRY.  If so we can remove all this extra code and 
 just add a simple check in msm_spm_drv_flush_seq_entry that looks at the 
 compatible and picks the proper offset when updating 
 MSM_SPM_REG_SAW2_SEQ_ENTRY.
 
 Isnt that an hack ?

Why would it be a hack, if the only difference in the driver can be reduced 
down to 5 lines of code, versus what is currently there I don’t see that as a 
hack at all.

[ snip ]

 diff --git a/include/soc/qcom/spm.h b/include/soc/qcom/spm.h
 new file mode 100644
 index 000..f39e0c4
 --- /dev/null
 +++ b/include/soc/qcom/spm.h
 @@ -0,0 +1,70 @@
 +/* Copyright (c) 2010-2014, The Linux Foundation. All rights reserved.
 + *
 + * This program is free software; you can redistribute it and/or modify
 + * it under the terms of the GNU General Public 

Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Kumar Gala

On Aug 12, 2014, at 2:43 PM, Lina Iyer lina.i...@linaro.org wrote:

 
 diff --git a/Documentation/devicetree/bindings/arm/msm/spm-v2.txt 
 b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
 new file mode 100644
 index 000..3130f4b
 --- /dev/null
 +++ b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
 @@ -0,0 +1,62 @@
 +* MSM Subsystem Power Manager (spm-v2)
 +
 +S4 generation of MSMs have SPM hardware blocks to control the Application
 +Processor Sub-System power. These SPM blocks run individual state machine
 +to determine what the core (L2 or Krait/Scorpion) would do when the WFI
 +instruction is executed by the core.
 +
 +The devicetree representation of the SPM block should be:
 +
 +Required properties
 +
 +- compatible: Could be one of -
 + qcom,spm-v2.1
 + qcom,spm-v3.0
 +- reg: The physical address and the size of the SPM's memory mapped registers
 +- qcom,cpu: phandle for the CPU that the SPM block is attached to. On targets
 + that dont support CPU phandles the driver would support qcom,core-id.
 + This field is required on only for SPMs that control the CPU.
 +- qcom,saw2-cfg: SAW2 configuration register

Can we change this to qcom,saw2-clk-div as that is what is really getting set, 
I know there are a few other fields in the saw2-cfg register, but I’m pretty 
sure we arent ever really setting those from DT. 

 +- qcom,saw2-spm-dly: Provides the values for the SPM delay command in the SPM
 + sequence
 +- qcom,saw2-spm-ctl: The SPM control register

Can we describe this as “spm-enable”, “spm-inhibit-start-address”, 
“spm-wakeup-cfg”?

Also, I’m unclear why would we have a case that spm would be disabled?

 +- qcom,name: The name with which a SPM device is identified by the power
 + management code.
 +
 +Optional properties
 +
 +- qcom,saw2-pmic-data0..7: Specify the pmic data value and the associated FTS
 + (Fast Transient Switch) index to send the PMIC data to
 +- qcom,vctl-port: The PVC (PMIC Virtual Channel) port used for changing
 + voltage
 +- qcom,phase-port: The PVC port used for changing the number of phases
 +- qcom,pfm-port: The PVC port used for enabling PWM/PFM modes
 +- qcom,saw2-spm-cmd-wfi: The WFI command sequence
 +- qcom,saw2-spm-cmd-ret: The Retention command sequence
 +- qcom,saw2-spm-cmd-spc: The Standalone PC command sequence
 +- qcom,saw2-spm-cmd-pc-no-rpm: The Power Collapse command sequence where APPS
 + proc won't inform the RPM.
 +- qcom,saw2-spm-cmd-pc: The Power Collapse command sequence. This sequence 
 may
 + turn off other SoC components.
 +- qcom,saw2-spm-cmd-gdhs: GDHS (Globally Distributed Head Switch) command
 + sequence. This sequence will retain the memory but turn off the logic.
 +- qcom,cpu-vctl-list: List of cpu node phandles, whose voltage the spm device
 + can control.
 +- qcom,vctl-timeout-us: The timeout value in microseconds to wait for 
 voltage to
 + change after sending the voltage command to the PMIC.
 +-
 +Example:
 + qcom,spm@f9089000 {
 + compatible = qcom,spm-v2;
 + #address-cells = 1;
 + #size-cells = 1;
 + reg = 0xf9089000 0x1000;
 + qcom,cpu = CPU0;
 + qcom,saw2-cfg = 0x1;
 + qcom,saw2-spm-dly= 0x2400;
 + qcom,saw2-spm-ctl = 0x1;
 + qcom,saw2-spm-cmd-wfi = [03 0b 0f];
 + qcom,saw2-spm-cmd-spc = [00 20 50 80 60 70 10 92
 + a0 b0 03 68 70 3b 92 a0 b0
 + 82 2b 50 10 30 02 22 30 0f];
 + };

-- 
Employee of Qualcomm Innovation Center, Inc.
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by 
The Linux Foundation

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 07/10] qcom: msm-pm: Add cpu low power mode functions

2014-08-14 Thread Daniel Lezcano

On 08/13/2014 04:16 PM, Lina Iyer wrote:

On Wed, Aug 13, 2014 at 01:18:01PM +0200, Daniel Lezcano wrote:

On 08/12/2014 09:43 PM, Lina Iyer wrote:

Add interface layer to abstract and handle hardware specific
functionality for executing various cpu low power modes in QCOM
chipsets.

Signed-off-by: Venkat Devarasetty vdeva...@codeaurora.org
Signed-off-by: Mahesh Sivasubramanian msiva...@codeaurora.org
Signed-off-by: Lina Iyer lina.i...@linaro.org
---
 drivers/soc/qcom/Makefile |   2 +-
 drivers/soc/qcom/msm-pm.c | 219
++
 include/soc/qcom/pm.h |  39 +
 3 files changed, 259 insertions(+), 1 deletion(-)
 create mode 100644 drivers/soc/qcom/msm-pm.c
 create mode 100644 include/soc/qcom/pm.h

diff --git a/drivers/soc/qcom/Makefile b/drivers/soc/qcom/Makefile
index d7ae93b..7925f83 100644
--- a/drivers/soc/qcom/Makefile
+++ b/drivers/soc/qcom/Makefile
@@ -1,5 +1,5 @@
 obj-$(CONFIG_QCOM_GSBI)+=qcom_gsbi.o
-obj-$(CONFIG_QCOM_PM) +=spm-devices.o spm.o
+obj-$(CONFIG_QCOM_PM) +=spm-devices.o spm.o msm-pm.o

 CFLAGS_scm.o :=$(call as-instr,.arch_extension sec,-DREQUIRES_SEC=1)
 obj-$(CONFIG_QCOM_SCM) += scm.o scm-boot.o
diff --git a/drivers/soc/qcom/msm-pm.c b/drivers/soc/qcom/msm-pm.c
new file mode 100644
index 000..f2f15b8
--- /dev/null
+++ b/drivers/soc/qcom/msm-pm.c
@@ -0,0 +1,219 @@
+/* Copyright (c) 2010-2014, The Linux Foundation. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 and
+ * only version 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ */
+
+#include linux/module.h
+#include linux/kernel.h
+#include linux/init.h
+#include linux/io.h
+#include linux/smp.h
+#include linux/tick.h
+#include linux/platform_device.h
+#include linux/cpu_pm.h
+#include linux/uaccess.h
+
+#include soc/qcom/spm.h
+#include soc/qcom/pm.h
+#include soc/qcom/scm.h
+#include soc/qcom/scm-boot.h
+
+#include asm/suspend.h
+#include asm/cacheflush.h
+#include asm/cputype.h
+#include asm/system_misc.h
+
+#define SCM_CMD_TERMINATE_PC(0x2)
+#define SCM_CMD_CORE_HOTPLUGGED (0x10)
+#define SCM_FLUSH_FLAG_MASK(0x3)
+
+static bool msm_pm_is_L1_writeback(void)
+{
+u32 cache_id = 0;
+
+#if defined(CONFIG_CPU_V7)
+u32 sel = 0;
+
+asm volatile (mcr p15, 2, %[ccselr], c0, c0, 0\n\t
+  isb\n\t
+  mrc p15, 1, %[ccsidr], c0, c0, 0\n\t
+  :[ccsidr]=r (cache_id)
+  :[ccselr]r (sel)
+ );
+return cache_id  BIT(30);
+#elif defined(CONFIG_ARM64)
+u32 sel = 0;
+asm volatile(msr csselr_el1, %[ccselr]\n\t
+ isb\n\t
+ mrs %[ccsidr],ccsidr_el1\n\t
+ :[ccsidr]=r (cache_id)
+ :[ccselr]r (sel)
+);
+return cache_id  BIT(30);
+#else
+#error No valid CPU arch selected
+#endif
+}
+
+static inline void msm_arch_idle(void)
+{
+/* Flush and clock-gate */
+mb();


Why is needed this memory barrier ?

Some QCOM SoCs needed this. I am not sure which one anymore. :(


I guess this is to flush the L1 cache when the core is going down. 
Regarding the kernel option, it seems mb() is as dsb(), so I am 
wondering if this function could be simply replaced by cpu_do_idle().



+wfi();
+}
+
+static bool msm_pm_swfi(bool from_idle)
+{
+msm_arch_idle();
+return true;
+}


Same here, could be replaced by cpu_do_idle(), I think.


+static bool msm_pm_retention(bool from_idle)
+{
+int ret = 0;
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_RETENTION, false);
+WARN_ON(ret);
+
+msm_arch_idle();
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_CLOCK_GATING, false);
+WARN_ON(ret);


Why do you need to set the clock gating mode each time you exit the
retention mode ?

So if the SPM did not reset to clockgating, we would not do retention
when we intended to do clockgating. Btw, we dont set clockgating
everytime we do clockgating, helps reduce the latency in doing WFI.


Thanks for the explanation in the other email. So IIUC, the SCM keeps 
the last state configuration and we have to set it back to clock gating, 
right ?


I don't think it is up to this function to do this but the clock gating 
function.


Also, this function prototype looks a bit weird. Just for the sake of 
using callbacks.


And finally, the WARN_ON is not desirable here, except if the goal is to 
flood the terminal :)


What not using first simple functions ?

void qcom_do_idle(void)
{
myfirmware_call(MSM_SPM_MODE_CLOCK_GATING);
wfi();
}

void qcom_cpu_retention(void)
{
myfirmware_call(MSM_SPM_MODE_RETENTION);
dsb();
wfi();
}

void 

Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Lina Iyer

On Thu, Aug 14, 2014 at 11:09:48AM -0500, Kumar Gala wrote:


On Aug 12, 2014, at 2:43 PM, Lina Iyer lina.i...@linaro.org wrote:



diff --git a/Documentation/devicetree/bindings/arm/msm/spm-v2.txt 
b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
new file mode 100644
index 000..3130f4b
--- /dev/null
+++ b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
@@ -0,0 +1,62 @@
+* MSM Subsystem Power Manager (spm-v2)
+
+S4 generation of MSMs have SPM hardware blocks to control the Application
+Processor Sub-System power. These SPM blocks run individual state machine
+to determine what the core (L2 or Krait/Scorpion) would do when the WFI
+instruction is executed by the core.
+
+The devicetree representation of the SPM block should be:
+
+Required properties
+
+- compatible: Could be one of -
+   qcom,spm-v2.1
+   qcom,spm-v3.0
+- reg: The physical address and the size of the SPM's memory mapped registers
+- qcom,cpu: phandle for the CPU that the SPM block is attached to. On targets
+   that dont support CPU phandles the driver would support qcom,core-id.
+   This field is required on only for SPMs that control the CPU.
+- qcom,saw2-cfg: SAW2 configuration register


Can we change this to qcom,saw2-clk-div as that is what is really getting set, 
I know there are a few other fields in the saw2-cfg register, but I’m pretty 
sure we arent ever really setting those from DT.


I am pruning them off in the next revision of the patch.

+- qcom,saw2-spm-dly: Provides the values for the SPM delay command in the SPM
+   sequence
+- qcom,saw2-spm-ctl: The SPM control register


Can we describe this as “spm-enable”, “spm-inhibit-start-address”, 
“spm-wakeup-cfg”?

Also, I’m unclear why would we have a case that spm would be disabled?


Much of these registers names make it easier for developers and
debuggers to relate it to the hardware spec. Choosing different names
here though might make it readable would convolute their efforts.


+- qcom,name: The name with which a SPM device is identified by the power
+   management code.
+
+Optional properties
+
+- qcom,saw2-pmic-data0..7: Specify the pmic data value and the associated FTS
+   (Fast Transient Switch) index to send the PMIC data to
+- qcom,vctl-port: The PVC (PMIC Virtual Channel) port used for changing
+   voltage
+- qcom,phase-port: The PVC port used for changing the number of phases
+- qcom,pfm-port: The PVC port used for enabling PWM/PFM modes
+- qcom,saw2-spm-cmd-wfi: The WFI command sequence
+- qcom,saw2-spm-cmd-ret: The Retention command sequence
+- qcom,saw2-spm-cmd-spc: The Standalone PC command sequence
+- qcom,saw2-spm-cmd-pc-no-rpm: The Power Collapse command sequence where APPS
+   proc won't inform the RPM.
+- qcom,saw2-spm-cmd-pc: The Power Collapse command sequence. This sequence may
+   turn off other SoC components.
+- qcom,saw2-spm-cmd-gdhs: GDHS (Globally Distributed Head Switch) command
+   sequence. This sequence will retain the memory but turn off the logic.
+- qcom,cpu-vctl-list: List of cpu node phandles, whose voltage the spm device
+   can control.
+- qcom,vctl-timeout-us: The timeout value in microseconds to wait for voltage 
to
+   change after sending the voltage command to the PMIC.
+-
+Example:
+   qcom,spm@f9089000 {
+   compatible = qcom,spm-v2;
+   #address-cells = 1;
+   #size-cells = 1;
+   reg = 0xf9089000 0x1000;
+   qcom,cpu = CPU0;
+   qcom,saw2-cfg = 0x1;
+   qcom,saw2-spm-dly= 0x2400;
+   qcom,saw2-spm-ctl = 0x1;
+   qcom,saw2-spm-cmd-wfi = [03 0b 0f];
+   qcom,saw2-spm-cmd-spc = [00 20 50 80 60 70 10 92
+   a0 b0 03 68 70 3b 92 a0 b0
+   82 2b 50 10 30 02 22 30 0f];
+   };


--
Employee of Qualcomm Innovation Center, Inc.
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by 
The Linux Foundation


--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Kumar Gala

On Aug 14, 2014, at 11:18 AM, Lina Iyer lina.i...@linaro.org wrote:

 On Thu, Aug 14, 2014 at 11:09:48AM -0500, Kumar Gala wrote:
 
 On Aug 12, 2014, at 2:43 PM, Lina Iyer lina.i...@linaro.org wrote:
 
 
 diff --git a/Documentation/devicetree/bindings/arm/msm/spm-v2.txt 
 b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
 new file mode 100644
 index 000..3130f4b
 --- /dev/null
 +++ b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
 @@ -0,0 +1,62 @@
 +* MSM Subsystem Power Manager (spm-v2)
 +
 +S4 generation of MSMs have SPM hardware blocks to control the Application
 +Processor Sub-System power. These SPM blocks run individual state machine
 +to determine what the core (L2 or Krait/Scorpion) would do when the WFI
 +instruction is executed by the core.
 +
 +The devicetree representation of the SPM block should be:
 +
 +Required properties
 +
 +- compatible: Could be one of -
 +   qcom,spm-v2.1
 +   qcom,spm-v3.0
 +- reg: The physical address and the size of the SPM's memory mapped 
 registers
 +- qcom,cpu: phandle for the CPU that the SPM block is attached to. On 
 targets
 +   that dont support CPU phandles the driver would support qcom,core-id.
 +   This field is required on only for SPMs that control the CPU.
 +- qcom,saw2-cfg: SAW2 configuration register
 
 Can we change this to qcom,saw2-clk-div as that is what is really getting 
 set, I know there are a few other fields in the saw2-cfg register, but I’m 
 pretty sure we arent ever really setting those from DT.
 
 I am pruning them off in the next revision of the patch.
 +- qcom,saw2-spm-dly: Provides the values for the SPM delay command in the 
 SPM
 +   sequence
 +- qcom,saw2-spm-ctl: The SPM control register
 
 Can we describe this as “spm-enable”, “spm-inhibit-start-address”, 
 “spm-wakeup-cfg”?
 
 Also, I’m unclear why would we have a case that spm would be disabled?
 
 Much of these registers names make it easier for developers and
 debuggers to relate it to the hardware spec. Choosing different names
 here though might make it readable would convolute their efforts.

The point is to move away from just dumping a register value directly from DT 
into the device.  This is pretty bad form.  The names can relate to the 
register, etc, its just the fields that are really being used/set was the 
direction I was suggesting we go.

 
 +- qcom,name: The name with which a SPM device is identified by the power
 +   management code.
 +
 +Optional properties
 +
 +- qcom,saw2-pmic-data0..7: Specify the pmic data value and the associated 
 FTS
 +   (Fast Transient Switch) index to send the PMIC data to
 +- qcom,vctl-port: The PVC (PMIC Virtual Channel) port used for changing
 +   voltage
 +- qcom,phase-port: The PVC port used for changing the number of phases
 +- qcom,pfm-port: The PVC port used for enabling PWM/PFM modes
 +- qcom,saw2-spm-cmd-wfi: The WFI command sequence
 +- qcom,saw2-spm-cmd-ret: The Retention command sequence
 +- qcom,saw2-spm-cmd-spc: The Standalone PC command sequence
 +- qcom,saw2-spm-cmd-pc-no-rpm: The Power Collapse command sequence where 
 APPS
 +   proc won't inform the RPM.
 +- qcom,saw2-spm-cmd-pc: The Power Collapse command sequence. This sequence 
 may
 +   turn off other SoC components.
 +- qcom,saw2-spm-cmd-gdhs: GDHS (Globally Distributed Head Switch) command
 +   sequence. This sequence will retain the memory but turn off the logic.
 +- qcom,cpu-vctl-list: List of cpu node phandles, whose voltage the spm 
 device
 +   can control.
 +- qcom,vctl-timeout-us: The timeout value in microseconds to wait for 
 voltage to
 +   change after sending the voltage command to the PMIC.
 +-
 +Example:
 +   qcom,spm@f9089000 {
 +   compatible = qcom,spm-v2;
 +   #address-cells = 1;
 +   #size-cells = 1;
 +   reg = 0xf9089000 0x1000;
 +   qcom,cpu = CPU0;
 +   qcom,saw2-cfg = 0x1;
 +   qcom,saw2-spm-dly= 0x2400;
 +   qcom,saw2-spm-ctl = 0x1;
 +   qcom,saw2-spm-cmd-wfi = [03 0b 0f];
 +   qcom,saw2-spm-cmd-spc = [00 20 50 80 60 70 10 92
 +   a0 b0 03 68 70 3b 92 a0 b0
 +   82 2b 50 10 30 02 22 30 0f];
 +   };
 
 -- 
 Employee of Qualcomm Innovation Center, Inc.
 Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by 
 The Linux Foundation
 

- k

-- 
Employee of Qualcomm Innovation Center, Inc.
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by 
The Linux Foundation

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Fwd: Status of chipidea msm USB reset patch

2014-08-14 Thread Tim Bird
Ping.  Anybody know the status of this patch?  Is it queued in someone's tree?
Without it the USB driver for the Qualcomm 8974 (hsusb phy) doesn't
work (at least for me).
It looks like it got dropped from Ivan's original patch series, back in May.

-- Forwarded message --
From: Tim Bird tbird...@gmail.com
Date: Fri, Jul 25, 2014 at 2:38 PM
Subject: Status of chipidea msm USB reset patch
To: linux-arm-msm@vger.kernel.org, ba...@ti.com, Ivan T. Ivanov
iiva...@mm-sol.com


Ivan and Felipe,

Do you know the status of the patch below?  It was part of Ivan's
USB patch set, which got mainlined recently.  However, this patch
did not show up in Linus' tree.

Is it in another tree on it's way, or does it need a re-submission?

I was recently testing the MSM USB gadget driver on the Dragonboard 800
(with a Qualcomm 8974 processor), and without this patch the USB hardware
does not come up properly.

Thanks,
 -- Tim


Subject: [PATCH] usb: chipidea: msm: Use USB PHY API to control PHY state

PHY drivers keep track of the current state of the hardware,
so don't change PHY settings under it.

Signed-off-by: Ivan T. Ivanov iiva...@mm-sol.com
---
 drivers/usb/chipidea/ci_hdrc_msm.c | 9 ++---
 1 file changed, 2 insertions(+), 7 deletions(-)

diff --git a/drivers/usb/chipidea/ci_hdrc_msm.c
b/drivers/usb/chipidea/ci_hdrc_msm.c
index d72b9d2..81de834 100644
--- a/drivers/usb/chipidea/ci_hdrc_msm.c
+++ b/drivers/usb/chipidea/ci_hdrc_msm.c
@@ -20,13 +20,11 @@
 static void ci_hdrc_msm_notify_event(struct ci_hdrc *ci, unsigned event)
 {
  struct device *dev = ci-gadget.dev.parent;
- int val;

  switch (event) {
  case CI_HDRC_CONTROLLER_RESET_EVENT:
  dev_dbg(dev, CI_HDRC_CONTROLLER_RESET_EVENT received\n);
- writel(0, USB_AHBBURST);
- writel(0, USB_AHBMODE);
+ usb_phy_init(ci-transceiver);
  break;
  case CI_HDRC_CONTROLLER_STOPPED_EVENT:
  dev_dbg(dev, CI_HDRC_CONTROLLER_STOPPED_EVENT received\n);
@@ -34,10 +32,7 @@ static void ci_hdrc_msm_notify_event(struct ci_hdrc
*ci, unsigned event)
  * Put the transceiver in non-driving mode. Otherwise host
  * may not detect soft-disconnection.
  */
- val = usb_phy_io_read(ci-transceiver, ULPI_FUNC_CTRL);
- val = ~ULPI_FUNC_CTRL_OPMODE_MASK;
- val |= ULPI_FUNC_CTRL_OPMODE_NONDRIVING;
- usb_phy_io_write(ci-transceiver, val, ULPI_FUNC_CTRL);
+ usb_phy_notify_disconnect(ci-transceiver, USB_SPEED_UNKNOWN);
  break;
  default:
  dev_dbg(dev, unknown ci_hdrc event\n);
--
1.8.2.2
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: Fwd: Status of chipidea msm USB reset patch

2014-08-14 Thread Felipe Balbi
Hi,

On Thu, Aug 14, 2014 at 09:53:10AM -0700, Tim Bird wrote:
 Ping.  Anybody know the status of this patch?  Is it queued in someone's tree?
 Without it the USB driver for the Qualcomm 8974 (hsusb phy) doesn't
 work (at least for me).
 It looks like it got dropped from Ivan's original patch series, back in May.

I don't maintain chipidea, Peter's the guy you want

 
 -- Forwarded message --
 From: Tim Bird tbird...@gmail.com
 Date: Fri, Jul 25, 2014 at 2:38 PM
 Subject: Status of chipidea msm USB reset patch
 To: linux-arm-msm@vger.kernel.org, ba...@ti.com, Ivan T. Ivanov
 iiva...@mm-sol.com
 
 
 Ivan and Felipe,
 
 Do you know the status of the patch below?  It was part of Ivan's
 USB patch set, which got mainlined recently.  However, this patch
 did not show up in Linus' tree.
 
 Is it in another tree on it's way, or does it need a re-submission?
 
 I was recently testing the MSM USB gadget driver on the Dragonboard 800
 (with a Qualcomm 8974 processor), and without this patch the USB hardware
 does not come up properly.
 
 Thanks,
  -- Tim
 
 
 Subject: [PATCH] usb: chipidea: msm: Use USB PHY API to control PHY state
 
 PHY drivers keep track of the current state of the hardware,
 so don't change PHY settings under it.
 
 Signed-off-by: Ivan T. Ivanov iiva...@mm-sol.com
 ---
  drivers/usb/chipidea/ci_hdrc_msm.c | 9 ++---
  1 file changed, 2 insertions(+), 7 deletions(-)
 
 diff --git a/drivers/usb/chipidea/ci_hdrc_msm.c
 b/drivers/usb/chipidea/ci_hdrc_msm.c
 index d72b9d2..81de834 100644
 --- a/drivers/usb/chipidea/ci_hdrc_msm.c
 +++ b/drivers/usb/chipidea/ci_hdrc_msm.c
 @@ -20,13 +20,11 @@
  static void ci_hdrc_msm_notify_event(struct ci_hdrc *ci, unsigned event)
  {
   struct device *dev = ci-gadget.dev.parent;
 - int val;
 
   switch (event) {
   case CI_HDRC_CONTROLLER_RESET_EVENT:
   dev_dbg(dev, CI_HDRC_CONTROLLER_RESET_EVENT received\n);
 - writel(0, USB_AHBBURST);
 - writel(0, USB_AHBMODE);
 + usb_phy_init(ci-transceiver);
   break;
   case CI_HDRC_CONTROLLER_STOPPED_EVENT:
   dev_dbg(dev, CI_HDRC_CONTROLLER_STOPPED_EVENT received\n);
 @@ -34,10 +32,7 @@ static void ci_hdrc_msm_notify_event(struct ci_hdrc
 *ci, unsigned event)
   * Put the transceiver in non-driving mode. Otherwise host
   * may not detect soft-disconnection.
   */
 - val = usb_phy_io_read(ci-transceiver, ULPI_FUNC_CTRL);
 - val = ~ULPI_FUNC_CTRL_OPMODE_MASK;
 - val |= ULPI_FUNC_CTRL_OPMODE_NONDRIVING;
 - usb_phy_io_write(ci-transceiver, val, ULPI_FUNC_CTRL);
 + usb_phy_notify_disconnect(ci-transceiver, USB_SPEED_UNKNOWN);
   break;
   default:
   dev_dbg(dev, unknown ci_hdrc event\n);
 --
 1.8.2.2

-- 
balbi


signature.asc
Description: Digital signature


Re: [PATCH v2 07/10] qcom: msm-pm: Add cpu low power mode functions

2014-08-14 Thread Lina Iyer

On Thu, Aug 14, 2014 at 06:11:43PM +0200, Daniel Lezcano wrote:

On 08/13/2014 04:16 PM, Lina Iyer wrote:

On Wed, Aug 13, 2014 at 01:18:01PM +0200, Daniel Lezcano wrote:

On 08/12/2014 09:43 PM, Lina Iyer wrote:

Add interface layer to abstract and handle hardware specific
functionality for executing various cpu low power modes in QCOM
chipsets.

Signed-off-by: Venkat Devarasetty vdeva...@codeaurora.org
Signed-off-by: Mahesh Sivasubramanian msiva...@codeaurora.org
Signed-off-by: Lina Iyer lina.i...@linaro.org
---
drivers/soc/qcom/Makefile |   2 +-
drivers/soc/qcom/msm-pm.c | 219
++
include/soc/qcom/pm.h |  39 +
3 files changed, 259 insertions(+), 1 deletion(-)
create mode 100644 drivers/soc/qcom/msm-pm.c
create mode 100644 include/soc/qcom/pm.h

diff --git a/drivers/soc/qcom/Makefile b/drivers/soc/qcom/Makefile
index d7ae93b..7925f83 100644
--- a/drivers/soc/qcom/Makefile
+++ b/drivers/soc/qcom/Makefile
@@ -1,5 +1,5 @@
obj-$(CONFIG_QCOM_GSBI)+=qcom_gsbi.o
-obj-$(CONFIG_QCOM_PM) +=spm-devices.o spm.o
+obj-$(CONFIG_QCOM_PM) +=spm-devices.o spm.o msm-pm.o

CFLAGS_scm.o :=$(call as-instr,.arch_extension sec,-DREQUIRES_SEC=1)
obj-$(CONFIG_QCOM_SCM) += scm.o scm-boot.o
diff --git a/drivers/soc/qcom/msm-pm.c b/drivers/soc/qcom/msm-pm.c
new file mode 100644
index 000..f2f15b8
--- /dev/null
+++ b/drivers/soc/qcom/msm-pm.c
@@ -0,0 +1,219 @@
+/* Copyright (c) 2010-2014, The Linux Foundation. All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or modify
+ * it under the terms of the GNU General Public License version 2 and
+ * only version 2 as published by the Free Software Foundation.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+ * GNU General Public License for more details.
+ *
+ */
+
+#include linux/module.h
+#include linux/kernel.h
+#include linux/init.h
+#include linux/io.h
+#include linux/smp.h
+#include linux/tick.h
+#include linux/platform_device.h
+#include linux/cpu_pm.h
+#include linux/uaccess.h
+
+#include soc/qcom/spm.h
+#include soc/qcom/pm.h
+#include soc/qcom/scm.h
+#include soc/qcom/scm-boot.h
+
+#include asm/suspend.h
+#include asm/cacheflush.h
+#include asm/cputype.h
+#include asm/system_misc.h
+
+#define SCM_CMD_TERMINATE_PC(0x2)
+#define SCM_CMD_CORE_HOTPLUGGED (0x10)
+#define SCM_FLUSH_FLAG_MASK(0x3)
+
+static bool msm_pm_is_L1_writeback(void)
+{
+u32 cache_id = 0;
+
+#if defined(CONFIG_CPU_V7)
+u32 sel = 0;
+
+asm volatile (mcr p15, 2, %[ccselr], c0, c0, 0\n\t
+  isb\n\t
+  mrc p15, 1, %[ccsidr], c0, c0, 0\n\t
+  :[ccsidr]=r (cache_id)
+  :[ccselr]r (sel)
+ );
+return cache_id  BIT(30);
+#elif defined(CONFIG_ARM64)
+u32 sel = 0;
+asm volatile(msr csselr_el1, %[ccselr]\n\t
+ isb\n\t
+ mrs %[ccsidr],ccsidr_el1\n\t
+ :[ccsidr]=r (cache_id)
+ :[ccselr]r (sel)
+);
+return cache_id  BIT(30);
+#else
+#error No valid CPU arch selected
+#endif
+}
+
+static inline void msm_arch_idle(void)
+{
+/* Flush and clock-gate */
+mb();


Why is needed this memory barrier ?

Some QCOM SoCs needed this. I am not sure which one anymore. :(


I guess this is to flush the L1 cache when the core is going down. 
Regarding the kernel option, it seems mb() is as dsb(), so I am 
wondering if this function could be simply replaced by cpu_do_idle().



Possibly could. I will do that.


+wfi();
+}
+
+static bool msm_pm_swfi(bool from_idle)
+{
+msm_arch_idle();
+return true;
+}


Same here, could be replaced by cpu_do_idle(), I think.


+static bool msm_pm_retention(bool from_idle)
+{
+int ret = 0;
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_RETENTION, false);
+WARN_ON(ret);
+
+msm_arch_idle();
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_CLOCK_GATING, false);
+WARN_ON(ret);


Why do you need to set the clock gating mode each time you exit the
retention mode ?

So if the SPM did not reset to clockgating, we would not do retention
when we intended to do clockgating. Btw, we dont set clockgating
everytime we do clockgating, helps reduce the latency in doing WFI.


Thanks for the explanation in the other email. So IIUC, the SCM keeps 
the last state configuration and we have to set it back to clock 
gating, right ?

Correct.


I don't think it is up to this function to do this but the clock 
gating function.


Also, this function prototype looks a bit weird. Just for the sake of 
using callbacks.


And finally, the WARN_ON is not desirable here, except if the goal is 
to flood the terminal :)

Was debating the use of it myself. Will remove it.


What not using first simple functions ?

void qcom_do_idle(void)
{

Re: [PATCH] ARM: apq8064: Add pinmux and i2c pinctrl nodes

2014-08-14 Thread Bjorn Andersson
On Thu, Aug 14, 2014 at 12:20 AM, Kiran Padwal
kiran.pad...@smartplayin.com wrote:
 diff --git a/arch/arm/boot/dts/qcom-apq8064.dtsi 
 b/arch/arm/boot/dts/qcom-apq8064.dtsi
 index 92bf793..fbebf5c 100644
 --- a/arch/arm/boot/dts/qcom-apq8064.dtsi
 +++ b/arch/arm/boot/dts/qcom-apq8064.dtsi
 @@ -70,6 +70,17 @@
 ranges;
 compatible = simple-bus;

 +   qcom_pinmux: pinmux@80 {

There are (at least) three different pinmuxes in these platforms: TLMM, PMIC
GPIO, PMIC MPP. Also this is the phandle that is used to reference the gpio
chip throughout the board.

So I would like to suggest that we name it tlmm or like in the downstream
kernel msmgpio.

 +   compatible = qcom,apq8064-pinctrl;
 +   reg = 0x80 0x4000;
 +
 +   gpio-controller;
 +   #gpio-cells = 2;
 +   interrupt-controller;
 +   #interrupt-cells = 2;
 +   interrupts = 0 32 0x4;

I must have gotten this wrong in the dt binding example, sorry about that.
interrupts should be 0 16 0x4.

 +   };

Regards,
Bjorn
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Quick question to join in development

2014-08-14 Thread Christopher Latham
I am a recent member of the linux-arm-msm mailing list. I'd like to know
where the source of this project is located, and what branch, so I can
clone and contribute. Thanks. I hope this is the correct email to post to
the list, not the majordomo one. You may respond to personal, below, just
please not on the list. Thank you again!

Sincerely,
Christopher Latham

sudosuroot...@gmail.com
https://github.com/sudosurootdev

PERSONAL, without 1,000's in inbox:
SS ROOT DEV 'AT' GMAIL 'DOT' 'COM'
... WITH NO SPACES
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


[PATCH] pinctrl: qcom: apq8064: Correct interrupts in example

2014-08-14 Thread Bjorn Andersson
The example in the binding document indicates that interrupt 32 is used
for the TLMM summary IRQ. Correct this to reduce the confusion.

Signed-off-by: Bjorn Andersson bjorn.anders...@sonymobile.com
---
 .../bindings/pinctrl/qcom,apq8064-pinctrl.txt  |2 +-
 1 file changed, 1 insertion(+), 1 deletion(-)

diff --git a/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt 
b/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt
index 0211c6d..92fae82 100644
--- a/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt
+++ b/Documentation/devicetree/bindings/pinctrl/qcom,apq8064-pinctrl.txt
@@ -62,7 +62,7 @@ Example:
#gpio-cells = 2;
interrupt-controller;
#interrupt-cells = 2;
-   interrupts = 0 32 0x4;
+   interrupts = 0 16 0x4;
 
pinctrl-names = default;
pinctrl-0 = gsbi5_uart_default;
-- 
1.7.9.5

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 07/10] qcom: msm-pm: Add cpu low power mode functions

2014-08-14 Thread Daniel Lezcano

On 08/14/2014 09:22 PM, Lina Iyer wrote:

On Thu, Aug 14, 2014 at 06:11:43PM +0200, Daniel Lezcano wrote:

On 08/13/2014 04:16 PM, Lina Iyer wrote:

On Wed, Aug 13, 2014 at 01:18:01PM +0200, Daniel Lezcano wrote:

On 08/12/2014 09:43 PM, Lina Iyer wrote:

Add interface layer to abstract and handle hardware specific
functionality for executing various cpu low power modes in QCOM
chipsets.

Signed-off-by: Venkat Devarasetty vdeva...@codeaurora.org
Signed-off-by: Mahesh Sivasubramanian msiva...@codeaurora.org
Signed-off-by: Lina Iyer lina.i...@linaro.org
---


[ ... ]


+static bool msm_pm_retention(bool from_idle)
+{
+int ret = 0;
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_RETENTION, false);
+WARN_ON(ret);
+
+msm_arch_idle();
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_CLOCK_GATING,
false);
+WARN_ON(ret);


Why do you need to set the clock gating mode each time you exit the
retention mode ?

So if the SPM did not reset to clockgating, we would not do retention
when we intended to do clockgating. Btw, we dont set clockgating
everytime we do clockgating, helps reduce the latency in doing WFI.


Thanks for the explanation in the other email. So IIUC, the SCM keeps
the last state configuration and we have to set it back to clock
gating, right ?

Correct.


I don't think it is up to this function to do this but the clock
gating function.

Also, this function prototype looks a bit weird. Just for the sake of
using callbacks.

And finally, the WARN_ON is not desirable here, except if the goal is
to flood the terminal :)

Was debating the use of it myself. Will remove it.


What not using first simple functions ?

void qcom_do_idle(void)
{
myfirmware_call(MSM_SPM_MODE_CLOCK_GATING);
wfi();
}

void qcom_cpu_retention(void)
{
myfirmware_call(MSM_SPM_MODE_RETENTION);
dsb();
wfi();
}

void qcom_cpu_powerdown(int flags)
{
scm_call_atomic1(SCM_SVC_BOOT, SCM_CMD_TERMINATE_PC, flag);
}

and then you build on top of that the cpuidle driver.

Okay. Will do this


The patchset adds all the features in one shot and for someone not
used with the platform it is really hard to follow all the code.

I suggest you write a simple cpuidle driver based on the DT Lorenzo
patches bringing the clock gating, then another patchset with the
retention mode, etc ...



Do you agree with this approach ?


+return true;
+}
+
+static int msm_pm_collapse(unsigned long from_idle)
+{
+enum msm_pm_l2_scm_flag flag = MSM_SCM_L2_ON;
+
+/**
+ * Single core processors need to have L2
+ * flushed when powering down the core.
+ * Notify SCM to flush secure L2 lines.
+ */
+if (num_possible_cpus() == 1)
+flag = MSM_SCM_L2_OFF;


I am wondering if this shouldn't be handle by a mcpm driver.

Cc nico.


Well, possibly, sorry, not sure what features of the mcpm driver you
think I need here?


Please correct me if I am wrong. IIUC, this function is checking the
number of the cpus of the cluster in order to flush the L2 cache
because the SCM will power down the cluster if it is the last one,
right ?

Nope. Some QCOM variants which have a single CPU, cannot be powered down
without flushing the caches. Warm boot of the cpu resets the L2
logic as well. The cluster core is lot more complex than this :)


Ok, probably we can discuss this later when we reach this state in the 
incremental implementation.


Thanks

  -- Daniel


--
http://www.linaro.org/ Linaro.org │ Open source software for ARM SoCs

Follow Linaro:  http://www.facebook.com/pages/Linaro Facebook |
http://twitter.com/#!/linaroorg Twitter |
http://www.linaro.org/linaro-blog/ Blog




--
 http://www.linaro.org/ Linaro.org │ Open source software for ARM SoCs

Follow Linaro:  http://www.facebook.com/pages/Linaro Facebook |
http://twitter.com/#!/linaroorg Twitter |
http://www.linaro.org/linaro-blog/ Blog

--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v5 1/3] mfd: devicetree: bindings: Add Qualcomm RPM DT binding

2014-08-14 Thread Bjorn Andersson
On Tue 12 Aug 10:43 PDT 2014, Kumar Gala wrote:

 
 On Aug 11, 2014, at 5:43 PM, Bjorn Andersson bjorn.anders...@sonymobile.com 
 wrote:
 
[...]
  diff --git a/Documentation/devicetree/bindings/mfd/qcom,rpm.txt 
  b/Documentation/devicetree/bindings/mfd/qcom,rpm.txt
[...]
  +- reg:
  + Usage: required
  + Value type: prop-encoded-array
  + Definition: two entries specifying the physical address and size of 
  the
  + RPM's message ram
 
 I’m a little confused here, by ‘two entries’ do you mean two values or really 
 two regions?  A B  or  A B C D ?
 

Hmm, I agree with you, but I'm not sure what the definition of an entry is in
this context and looking around at other bindings makes me wonder even more.

How about we reduce the confusion by dropping the beginning and letting it be
the physical address and size of...?

  +
[...]
  +
  +- qcom,ipc:
  + Usage: required
  + Value type: prop-encoded-array
  + Definition: three entries specifying:
  + - phandle to a syscon node representing the apcs registers
  + - u32 representing offset to the register within the 
  syscon
  + - u32 representing the ipc bit within the register
 
 Can we clarify that this is ipc from Apps (or ARM processors to RPM)
 

Makes sense

  +
  +
  += SUBDEVICES
 
 These should not be children of RPM, but in an RPM container outside of the 
 SoC node with some phandle reference (if needed) to the RPM.  The reason is 
 there isn’t really a technical means to translate from the SoC / MMIO bus 
 address space to the RPM address space that these nodes live in.
 

I don't agree with this; the regulators, clocks and bus-scalers aren't
components on their own but just parts of the RPM. Your argument indicates that
every pmic, i2c, spi... block got this wrong, I think we should better follow
the pattern defined by the rest of these.

One thing that I think should be fixed though is to rename SUBDEVICES to
SUBNODES as devices is an implementation detail in my solution.

 Also, the binding specs should be split out into their own files.
 

Not according to Rob Herring:
https://lkml.org/lkml/2014/3/10/567

  +
  +The RPM exposes resources to its subnodes. The below bindings specify the 
  set
  +of valid subnodes that can operate on these resources.
  +
  +== Switch-mode Power Supply regulator
  +
[...]
  +- reg:
  + Usage: required
  + Value type: u32
  + Definition: resource as defined in dt-bindings/mfd/qcom,rpm.h
  +
 
 Can we spec what subset of values in qcom,rpm.h are actually valid?
 

Yes, sorry about not improving this part.

[...]
  +- qcom,switch-mode-frequency:
  + Usage: required
  + Value type: u32
  + Definition: Frequency (Hz) of the switch-mode power supply;
  + must be one of:
  + 1920, 960, 640, 480, 384, 320,
  + 274, 240, 213, 192, 175, 160,
  + 148, 137, 128, 120
  +
  +- qcom,force-mode-none:
 
 I think I asked this last time I took a look at this, but can we have 
 multiple force-mode’s set?  If no, maybe this should be an enum instead.
 

No, they are mutually exclusive. I just like the boolean representation
instead, but I can change it to an enum and provide some constants in the
header file.

Looking through msm-3.4 almost everything seems to be using force mode none,
with a few uses of auto. So if we turn it into an enum then we could specify
none in the platform dtsi (or don't specifying anything?) and only have to
override it in the very few places it needs to be anything else.

  + Usage: optional (default if no other qcom,force-mode is specified)
  + Value type: empty
  + Defintion: indicates that the regulator should not be forced to any
  +particular mode
  +
  +- qcom,force-mode-lpm:
  + Usage: optional
  + Value type: empty
  + Definition: indicates that the regulator should be forced to operate 
  in
  + low-power-mode
  +
  +- qcom,force-mode-auto:
  + Usage: optional (only available for 8960/8064)
 
 can we say only available for qcom,rpm-msm8960”, qcom,rpm-apq8064
 

Indeed.

  + Value type: empty
  + Definition: indicates that the regulator should be automatically pick
  + operating mode
  +
  +- qcom,force-mode-hpm:
  + Usage: optional (only available for 8960/8064)
 
 can we say only available for qcom,rpm-msm8960”, qcom,rpm-apq8064
 

Indeed.

  + Value type: empty
  + Definition: indicates that the regulator should be forced to operate 
  in
  + high-power-mode
  +
  +- qcom,force-mode-bypass: (only for 8960/8064)
  + Usage: optional (only available for 8960/8064)
 
 can we say only available for qcom,rpm-msm8960”, qcom,rpm-apq8064
 

Indeed.

 
  + Value type: empty
  + Definition: indicates that the regulator should be forced to operate 
  

Re: Fwd: Status of chipidea msm USB reset patch

2014-08-14 Thread Peter Chen
On Thu, Aug 14, 2014 at 11:54:02AM -0500, Felipe Balbi wrote:
 Hi,
 
 On Thu, Aug 14, 2014 at 09:53:10AM -0700, Tim Bird wrote:
  Ping.  Anybody know the status of this patch?  Is it queued in someone's 
  tree?
  Without it the USB driver for the Qualcomm 8974 (hsusb phy) doesn't
  work (at least for me).
  It looks like it got dropped from Ivan's original patch series, back in May.
 
 I don't maintain chipidea, Peter's the guy you want

Below patch was not at msm chipidea patchset Ivan sent me.

http://markmail.org/search/?q=%5BPATCH+v4+0%2F3%5D+usb%3A+chipidea%3A+msm%3A+Clean+and+fix+#query:%5BPATCH%20v4%200%2F3%5D%20usb%3A%20chipidea%3A%20msm%3A%20Clean%20and%20fix%20from%3A%22Ivan%20T.%20Ivanov%22+page:1+mid:mt7hgr7yamyzegg3+state:results

Peter
 
  
  -- Forwarded message --
  From: Tim Bird tbird...@gmail.com
  Date: Fri, Jul 25, 2014 at 2:38 PM
  Subject: Status of chipidea msm USB reset patch
  To: linux-arm-msm@vger.kernel.org, ba...@ti.com, Ivan T. Ivanov
  iiva...@mm-sol.com
  
  
  Ivan and Felipe,
  
  Do you know the status of the patch below?  It was part of Ivan's
  USB patch set, which got mainlined recently.  However, this patch
  did not show up in Linus' tree.
  
  Is it in another tree on it's way, or does it need a re-submission?
  
  I was recently testing the MSM USB gadget driver on the Dragonboard 800
  (with a Qualcomm 8974 processor), and without this patch the USB hardware
  does not come up properly.
  
  Thanks,
   -- Tim
  
  
  Subject: [PATCH] usb: chipidea: msm: Use USB PHY API to control PHY state
  
  PHY drivers keep track of the current state of the hardware,
  so don't change PHY settings under it.
  
  Signed-off-by: Ivan T. Ivanov iiva...@mm-sol.com
  ---
   drivers/usb/chipidea/ci_hdrc_msm.c | 9 ++---
   1 file changed, 2 insertions(+), 7 deletions(-)
  
  diff --git a/drivers/usb/chipidea/ci_hdrc_msm.c
  b/drivers/usb/chipidea/ci_hdrc_msm.c
  index d72b9d2..81de834 100644
  --- a/drivers/usb/chipidea/ci_hdrc_msm.c
  +++ b/drivers/usb/chipidea/ci_hdrc_msm.c
  @@ -20,13 +20,11 @@
   static void ci_hdrc_msm_notify_event(struct ci_hdrc *ci, unsigned event)
   {
struct device *dev = ci-gadget.dev.parent;
  - int val;
  
switch (event) {
case CI_HDRC_CONTROLLER_RESET_EVENT:
dev_dbg(dev, CI_HDRC_CONTROLLER_RESET_EVENT received\n);
  - writel(0, USB_AHBBURST);
  - writel(0, USB_AHBMODE);
  + usb_phy_init(ci-transceiver);
break;
case CI_HDRC_CONTROLLER_STOPPED_EVENT:
dev_dbg(dev, CI_HDRC_CONTROLLER_STOPPED_EVENT received\n);
  @@ -34,10 +32,7 @@ static void ci_hdrc_msm_notify_event(struct ci_hdrc
  *ci, unsigned event)
* Put the transceiver in non-driving mode. Otherwise host
* may not detect soft-disconnection.
*/
  - val = usb_phy_io_read(ci-transceiver, ULPI_FUNC_CTRL);
  - val = ~ULPI_FUNC_CTRL_OPMODE_MASK;
  - val |= ULPI_FUNC_CTRL_OPMODE_NONDRIVING;
  - usb_phy_io_write(ci-transceiver, val, ULPI_FUNC_CTRL);
  + usb_phy_notify_disconnect(ci-transceiver, USB_SPEED_UNKNOWN);
break;
default:
dev_dbg(dev, unknown ci_hdrc event\n);
  --
  1.8.2.2
 
 -- 
 balbi



-- 
Best Regards,
Peter Chen
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: To otg-fsm or not to otg-fsm? That is the question.

2014-08-14 Thread Peter Chen
On Tue, Aug 12, 2014 at 09:13:47AM -0700, Tim Bird wrote:
 On Mon, Aug 11, 2014 at 5:28 PM, Peter Chen peter.c...@freescale.com wrote:
  The OTG FSM at /usb/common/usb-otg-fsm.c is a software OTG FSM 
  implementation
  which follows On-The-Go and Embedded Host Supplement to the USB Revision 
  2.0 Specification
  (Revision 2.0 version 1.1a) Chapter 7 State Diagrams.
 
  If the platform doesn't support hardware otg fsm, it should follow above 
  fsm implementation since
  it follows the newest OTG  EH spec. Besides, as far as I know, the 
  qualcomm uses
  chipidea core for its usb2, then it should be easy for qualcomm using this 
  common
  otg fsm implementation.
 
 OK.  sounds good.
 
 Yes, the qualcomm chips use a chipidea core for usb2.  The main
 difficulty, IMHO, will
 be mapping the qcom charger state machine onto the generic OTG state
 machine implementation
 in usb-otg-fsm.  I'm not sure if I'll be able to embed the needed
 functionality into the existing functions
 called by the generic state machine, or if I'll need to add some new
 entries to the function table
 to handle this extra logic.
 
 I'll probably try to get the driver working without the charger stuff
 first, and then, once I have a
 better idea of how the state machines map, try adding the charger
 stuff.  If I feel like I need
 to modify the generic state machine, I'll ask on list.  I'm a newbie
 at USB stuff and I don't want
 to break anything.
 
 Thanks.
 

One remind, you may need to know which role-switch function you need,
if you only need role-switch based in ID pin, then no OTG FSM support
is needed, this is current most of OTG device supports, it is not fully
OTG compliance.

-- 
Best Regards,
Peter Chen
--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 07/10] qcom: msm-pm: Add cpu low power mode functions

2014-08-14 Thread Lina Iyer

On Fri, Aug 15, 2014 at 02:01:47AM +0200, Daniel Lezcano wrote:

On 08/14/2014 09:22 PM, Lina Iyer wrote:

On Thu, Aug 14, 2014 at 06:11:43PM +0200, Daniel Lezcano wrote:

On 08/13/2014 04:16 PM, Lina Iyer wrote:

On Wed, Aug 13, 2014 at 01:18:01PM +0200, Daniel Lezcano wrote:

On 08/12/2014 09:43 PM, Lina Iyer wrote:

Add interface layer to abstract and handle hardware specific
functionality for executing various cpu low power modes in QCOM
chipsets.

Signed-off-by: Venkat Devarasetty vdeva...@codeaurora.org
Signed-off-by: Mahesh Sivasubramanian msiva...@codeaurora.org
Signed-off-by: Lina Iyer lina.i...@linaro.org
---


[ ... ]


+static bool msm_pm_retention(bool from_idle)
+{
+int ret = 0;
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_RETENTION, false);
+WARN_ON(ret);
+
+msm_arch_idle();
+
+ret = msm_spm_set_low_power_mode(MSM_SPM_MODE_CLOCK_GATING,
false);
+WARN_ON(ret);


Why do you need to set the clock gating mode each time you exit the
retention mode ?

So if the SPM did not reset to clockgating, we would not do retention
when we intended to do clockgating. Btw, we dont set clockgating
everytime we do clockgating, helps reduce the latency in doing WFI.


Thanks for the explanation in the other email. So IIUC, the SCM keeps
the last state configuration and we have to set it back to clock
gating, right ?

Correct.


I don't think it is up to this function to do this but the clock
gating function.

Also, this function prototype looks a bit weird. Just for the sake of
using callbacks.

And finally, the WARN_ON is not desirable here, except if the goal is
to flood the terminal :)

Was debating the use of it myself. Will remove it.


What not using first simple functions ?

void qcom_do_idle(void)
{
   myfirmware_call(MSM_SPM_MODE_CLOCK_GATING);
   wfi();
}

void qcom_cpu_retention(void)
{
   myfirmware_call(MSM_SPM_MODE_RETENTION);
   dsb();
   wfi();
}

void qcom_cpu_powerdown(int flags)
{
   scm_call_atomic1(SCM_SVC_BOOT, SCM_CMD_TERMINATE_PC, flag);
}

and then you build on top of that the cpuidle driver.

Okay. Will do this


The patchset adds all the features in one shot and for someone not
used with the platform it is really hard to follow all the code.

I suggest you write a simple cpuidle driver based on the DT Lorenzo
patches bringing the clock gating, then another patchset with the
retention mode, etc ...



Do you agree with this approach ?

Yes, have a working patch with the code cleaned out as you suggested.
Looking at Lorenzo's DT changes and a few SPM driver clean ups. Will
submit a patch revision soon.




+return true;
+}
+
+static int msm_pm_collapse(unsigned long from_idle)
+{
+enum msm_pm_l2_scm_flag flag = MSM_SCM_L2_ON;
+
+/**
+ * Single core processors need to have L2
+ * flushed when powering down the core.
+ * Notify SCM to flush secure L2 lines.
+ */
+if (num_possible_cpus() == 1)
+flag = MSM_SCM_L2_OFF;


I am wondering if this shouldn't be handle by a mcpm driver.

Cc nico.


Well, possibly, sorry, not sure what features of the mcpm driver you
think I need here?


Please correct me if I am wrong. IIUC, this function is checking the
number of the cpus of the cluster in order to flush the L2 cache
because the SCM will power down the cluster if it is the last one,
right ?

Nope. Some QCOM variants which have a single CPU, cannot be powered down
without flushing the caches. Warm boot of the cpu resets the L2
logic as well. The cluster core is lot more complex than this :)


Ok, probably we can discuss this later when we reach this state in the 
incremental implementation.

Hmm, yeah.



Thanks

 -- Daniel


--
http://www.linaro.org/ Linaro.org │ Open source software for ARM SoCs

Follow Linaro:  http://www.facebook.com/pages/Linaro Facebook |
http://twitter.com/#!/linaroorg Twitter |
http://www.linaro.org/linaro-blog/ Blog




--
http://www.linaro.org/ Linaro.org │ Open source software for ARM SoCs

Follow Linaro:  http://www.facebook.com/pages/Linaro Facebook |
http://twitter.com/#!/linaroorg Twitter |
http://www.linaro.org/linaro-blog/ Blog


--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html


Re: [PATCH v2 03/10] qcom: spm: Add Subsystem Power Manager (SPM) driver for QCOM chipsets

2014-08-14 Thread Lina Iyer

On Thu, Aug 14, 2014 at 11:41:39AM -0500, Kumar Gala wrote:


On Aug 14, 2014, at 11:18 AM, Lina Iyer lina.i...@linaro.org wrote:


On Thu, Aug 14, 2014 at 11:09:48AM -0500, Kumar Gala wrote:


On Aug 12, 2014, at 2:43 PM, Lina Iyer lina.i...@linaro.org wrote:



diff --git a/Documentation/devicetree/bindings/arm/msm/spm-v2.txt 
b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
new file mode 100644
index 000..3130f4b
--- /dev/null
+++ b/Documentation/devicetree/bindings/arm/msm/spm-v2.txt
@@ -0,0 +1,62 @@
+* MSM Subsystem Power Manager (spm-v2)
+
+S4 generation of MSMs have SPM hardware blocks to control the Application
+Processor Sub-System power. These SPM blocks run individual state machine
+to determine what the core (L2 or Krait/Scorpion) would do when the WFI
+instruction is executed by the core.
+
+The devicetree representation of the SPM block should be:
+
+Required properties
+
+- compatible: Could be one of -
+   qcom,spm-v2.1
+   qcom,spm-v3.0
+- reg: The physical address and the size of the SPM's memory mapped registers
+- qcom,cpu: phandle for the CPU that the SPM block is attached to. On targets
+   that dont support CPU phandles the driver would support qcom,core-id.
+   This field is required on only for SPMs that control the CPU.
+- qcom,saw2-cfg: SAW2 configuration register


Can we change this to qcom,saw2-clk-div as that is what is really getting set, 
I know there are a few other fields in the saw2-cfg register, but I’m pretty 
sure we arent ever really setting those from DT.


I am pruning them off in the next revision of the patch.

+- qcom,saw2-spm-dly: Provides the values for the SPM delay command in the SPM
+   sequence
+- qcom,saw2-spm-ctl: The SPM control register


Can we describe this as “spm-enable”, “spm-inhibit-start-address”, 
“spm-wakeup-cfg”?

Also, I’m unclear why would we have a case that spm would be disabled?

SPM would mostly be disabled for debug reasons or if there was a version
of the hardware tht needed hardware to be disabled. In general, it
wouldnt be.



Much of these registers names make it easier for developers and
debuggers to relate it to the hardware spec. Choosing different names
here though might make it readable would convolute their efforts.


The point is to move away from just dumping a register value directly from DT 
into the device.  This is pretty bad form.  The names can relate to the 
register, etc, its just the fields that are really being used/set was the 
direction I was suggesting we go.


Hmm. I see. Let me if I can address that.. There may be some registers
where I may not have such a luxury, will give it a try.




+- qcom,name: The name with which a SPM device is identified by the power
+   management code.
+
+Optional properties
+
+- qcom,saw2-pmic-data0..7: Specify the pmic data value and the associated FTS
+   (Fast Transient Switch) index to send the PMIC data to
+- qcom,vctl-port: The PVC (PMIC Virtual Channel) port used for changing
+   voltage
+- qcom,phase-port: The PVC port used for changing the number of phases
+- qcom,pfm-port: The PVC port used for enabling PWM/PFM modes
+- qcom,saw2-spm-cmd-wfi: The WFI command sequence
+- qcom,saw2-spm-cmd-ret: The Retention command sequence
+- qcom,saw2-spm-cmd-spc: The Standalone PC command sequence
+- qcom,saw2-spm-cmd-pc-no-rpm: The Power Collapse command sequence where APPS
+   proc won't inform the RPM.
+- qcom,saw2-spm-cmd-pc: The Power Collapse command sequence. This sequence may
+   turn off other SoC components.
+- qcom,saw2-spm-cmd-gdhs: GDHS (Globally Distributed Head Switch) command
+   sequence. This sequence will retain the memory but turn off the logic.
+- qcom,cpu-vctl-list: List of cpu node phandles, whose voltage the spm device
+   can control.
+- qcom,vctl-timeout-us: The timeout value in microseconds to wait for voltage 
to
+   change after sending the voltage command to the PMIC.
+-
+Example:
+   qcom,spm@f9089000 {
+   compatible = qcom,spm-v2;
+   #address-cells = 1;
+   #size-cells = 1;
+   reg = 0xf9089000 0x1000;
+   qcom,cpu = CPU0;
+   qcom,saw2-cfg = 0x1;
+   qcom,saw2-spm-dly= 0x2400;
+   qcom,saw2-spm-ctl = 0x1;
+   qcom,saw2-spm-cmd-wfi = [03 0b 0f];
+   qcom,saw2-spm-cmd-spc = [00 20 50 80 60 70 10 92
+   a0 b0 03 68 70 3b 92 a0 b0
+   82 2b 50 10 30 02 22 30 0f];
+   };


--
Employee of Qualcomm Innovation Center, Inc.
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by 
The Linux Foundation



- k

--
Employee of Qualcomm Innovation Center, Inc.
Qualcomm Innovation Center, Inc. is a member of Code Aurora Forum, hosted by 
The Linux Foundation


--
To unsubscribe from this list: send the line unsubscribe linux-arm-msm in
the body of a message to