android_kernel_google_msm/arch/arm/mach-msm/msm_cpr.h
Pankaj Kumar 0ae4c556a7 msm: cpr: Add support for CPR in 8625
CPR (Core Power Reduction) is a new technology to reduce
the power consumption of SOC using sensors inside the SOC.
Based on the feedback by the CPR controller, we can adjust
the voltage requirement for the SOC.

Add initial driver support for CPR.

Change-Id: I4b59438deb2635c45e45c5efe850c050c14a9165
Signed-off-by: Pankaj Kumar <pakuma@codeaurora.org>
Signed-off-by: Sravan Kumar Ambapuram <asravan@codeaurora.org>
Signed-off-by: Kaushal Kumar <kaushalk@codeaurora.org>
2013-02-27 18:21:30 -08:00

226 lines
5.7 KiB
C

/*
* Copyright (c) 2012, Code Aurora Forum. 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.
*
*/
#ifndef __ARCH_ARM_MACH_MSM_CPR_H
#define __ARCH_ARM_MACH_MSM_CPR_H
/* Register Offsets for RBCPR */
/* RBCPR Gate Count and Target Registers */
#define RBCPR_GCNT_TARGET(n) (0x60 + 4 * n)
/* RBCPR Timer Control */
#define RBCPR_TIMER_INTERVAL 0x44
#define RBIF_TIMER_ADJUST 0x4C
/* RBCPR Config Register */
#define RBIF_LIMIT 0x48
#define RBCPR_STEP_QUOT 0X80
#define RBCPR_CTL 0x90
#define RBIF_SW_VLEVEL 0x94
#define RBIF_CONT_ACK_CMD 0x98
#define RBIF_CONT_NACK_CMD 0x9C
/* RBCPR Result status Register */
#define RBCPR_RESULT_0 0xA0
#define RBCPR_RESULT_1 0xA4
#define RBCPR_QUOT_AVG 0x118
/* RBCPR DEBUG Register */
#define RBCPR_DEBUG1 0x120
/* RBCPR Interrupt Control Register */
#define RBIF_IRQ_EN(n) (0x100 + 4 * n)
#define RBIF_IRQ_CLEAR 0x110
#define RBIF_IRQ_STATUS 0x114
/* Bit Mask Values */
#define GCNT_M 0x003FF000
#define TARGET_M 0x00000FFF
#define SW_VLEVEL_M 0x0000003F
#define UP_FLAG_M 0x00000010
#define DOWN_FLAG_M 0x00000004
#define CEILING_M 0x00000FC0
#define FLOOR_M 0x0000003F
#define LOOP_EN_M 0x00000001
#define TIMER_M 0x00000008
#define SW_AUTO_CONT_ACK_EN_M 0x00000020
#define SW_AUTO_CONT_NACK_DN_EN_M 0x00000040
#define HW_TO_PMIC_EN_M BIT(4)
#define BUSY_M BIT(19)
#define QUOT_SLOW_M 0x00FFF000
#define UP_THRESHOLD_M 0x0F000000
#define DN_THRESHOLD_M 0xF0000000
/* Bit Values */
#define ENABLE_CPR BIT(0)
#define DISABLE_CPR 0x0
#define ENABLE_TIMER BIT(3)
#define DISABLE_TIMER 0x0
#define SW_MODE 0x0
#define SW_AUTO_CONT_ACK_EN BIT(5)
#define SW_AUTO_CONT_NACK_DN_EN BIT(6)
/* Test values for RBCPR RUMI Testing */
#define GNT_CNT 0xC0
#define TARGET 0xEFF
#define CEILING_V 0x30
#define FLOOR_V 0x15
#define SW_LEVEL 0x20
/* Interrupt Mask for All interrupt flags */
#define INT_MASK (MIN_INT | DOWN_INT | MID_INT | UP_INT | MAX_INT)
/* Number of oscilator in each sensor */
#define NUM_OSC 8
#define CPR_MODE 2
/**
* enum cpr_mode - Modes in which cpr is used
*/
enum cpr_mode {
NORMAL_MODE = 0,
TURBO_MODE,
SVS_MODE,
};
/**
* enum cpr_action - Cpr actions to be taken
*/
enum cpr_action {
DOWN = 0,
UP,
};
/**
* enum cpr_interrupt
*/
enum cpr_interrupt {
DONE_INT = BIT(0),
MIN_INT = BIT(1),
DOWN_INT = BIT(2),
MID_INT = BIT(3),
UP_INT = BIT(4),
MAX_INT = BIT(5),
};
/**
* struct msm_vp_data - structure for VP configuration
* @min_volt_mV: minimum milivolt level for VP
* @max_volt_mV: maximum milivolt level for VP
* @default_volt_mV: default milivolt for VP
* @step_size_mV: step size of voltage
*/
struct msm_cpr_vp_data {
int min_volt;
int max_volt;
int default_volt;
int step_size;
};
/**
* struct msm_cpr_osc - Data for CPR ring oscillator
* @gcnt: gate count value for the oscillator
* @target_count: target value for ring oscillator
*/
struct msm_cpr_osc {
int gcnt;
uint32_t target_count;
};
/**
* struct msm_cpr_mode - Data for CPR modes of operation
* @msm_cpr_osc: structure for oscillator data
* @ring_osc: ring oscillator of the sensor
* @tgt_volt_offset: inital voltage offset from default value
* @step_quot: step Quot for CPR calcuation
*/
struct msm_cpr_mode {
struct msm_cpr_osc ring_osc_data[NUM_OSC];
int ring_osc;
int32_t tgt_volt_offset;
uint32_t step_quot;
uint32_t Vmax;
uint32_t Vmin;
uint32_t calibrated_mV;
};
/**
* struct msm_cpr_config - Platform data for CPR configuration
* @ref_clk_khz: clock value of CPR in KHz
* @delay_us: timer delay in micro second
* @irq_line: irq line to be use (0 or 1 or 2)
* @msm_cpr_mode: structure for CPR mode data
*/
struct msm_cpr_config {
unsigned long ref_clk_khz;
unsigned long delay_us;
int irq_line;
struct msm_cpr_mode *cpr_mode_data;
int min_down_step;
uint32_t tgt_count_div_N; /* Target Cnt(Nom) = Target Cnt(Turbo) / N */
uint32_t floor;
uint32_t ceiling;
uint32_t sw_vlevel;
uint32_t up_threshold;
uint32_t dn_threshold;
uint32_t up_margin;
uint32_t dn_margin;
uint32_t nom_freq_limit;
struct msm_cpr_vp_data *vp_data;
};
/**
* struct msm_cpr_config - CPR Registers
*/
struct msm_cpr_reg {
uint32_t rbif_timer_interval;
uint32_t rbif_int_en;
uint32_t rbif_limit;
uint32_t rbif_timer_adjust;
uint32_t rbcpr_gcnt_target;
uint32_t rbcpr_step_quot;
uint32_t rbif_sw_level;
uint32_t rbcpr_ctl;
};
#if defined(CONFIG_MSM_CPR) || defined(CONFIG_MSM_CPR_MODULE)
/* msm_cpr_pm_resume: Used by Power Manager for Idle Power Collapse */
void msm_cpr_pm_resume(void);
/* msm_cpr_pm_suspend: Used by Power Manager for Idle Power Collapse */
void msm_cpr_pm_suspend(void);
/* msm_cpr_enable: Used by Power Manager for GDFS */
void msm_cpr_enable(void);
/* msm_cpr_disable: Used by Power Manager for GDFS */
void msm_cpr_disable(void);
#else
/* msm_cpr_pm_resume: Used by Power Manager for Idle Power Collapse */
void msm_cpr_pm_resume(void) { }
/* msm_cpr_pm_suspend: Used by Power Manager for Idle Power Collapse */
void msm_cpr_pm_suspend(void) { }
/* msm_cpr_enable: Used by Power Manager for GDFS */
void msm_cpr_enable(void) { }
/* msm_cpr_disable: Used by Power Manager for GDFS */
void msm_cpr_disable(void) { }
#endif
#ifdef CONFIG_DEBUG_FS
int msm_cpr_debug_init(void *);
#else
static inline int msm_cpr_debug_init(void *) { return 0; }
#endif
#endif /* __ARCH_ARM_MACH_MSM_CPR_H */