Advertisement
Not a member of Pastebin yet?
Sign Up,
it unlocks many cool features!
- diff --git a/arch/arm/mach-msm/acpuclock-scorpion.c b/arch/arm/mach-msm/acpuclock-scorpion.c
- index 6d79cd7..44e9b60 100644
- --- a/arch/arm/mach-msm/acpuclock-scorpion.c
- +++ b/arch/arm/mach-msm/acpuclock-scorpion.c
- @@ -28,6 +28,7 @@
- #include "acpuclock.h"
- #include "proc_comm.h"
- +#include "clock.h"
- #if 0
- #define DEBUG(x...) pr_info(x)
- @@ -55,6 +56,7 @@ struct clkctl_acpu_speed {
- unsigned sc_l_value;
- unsigned lpj;
- int vdd;
- + unsigned axiclk_khz;
- };
- /* clock sources */
- @@ -71,27 +73,28 @@ struct clkctl_acpu_speed {
- #define SRC_PLL1 3 /* 768 MHz */
- struct clkctl_acpu_speed acpu_freq_tbl[] = {
- - { 19200, CCTL(CLK_TCXO, 1), SRC_RAW, 0, 0, 1050 },
- - { 128000, CCTL(CLK_TCXO, 1), SRC_AXI, 0, 0, 1050 },
- - { 245000, CCTL(CLK_MODEM_PLL, 1), SRC_RAW, 0, 0, 1050 },
- - { 256000, CCTL(CLK_GLOBAL_PLL, 3), SRC_RAW, 0, 0, 1050 },
- - { 384000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0A, 0, 1050 },
- - { 422400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0B, 0, 1050 },
- - { 460800, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0C, 0, 1050 },
- - { 499200, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0D, 0, 1075 },
- - { 537600, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0E, 0, 1100 },
- - { 576000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0F, 0, 1100 },
- - { 614400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x10, 0, 1125 },
- - { 652800, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x11, 0, 1150 },
- - { 691200, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x12, 0, 1175 },
- - { 729600, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x13, 0, 1200 },
- - { 768000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x14, 0, 1200 },
- - { 806400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x15, 0, 1225 },
- - { 844800, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x16, 0, 1250 },
- - { 883200, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x17, 0, 1275 },
- - { 921600, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x18, 0, 1275 },
- - { 960000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x19, 0, 1275 },
- - { 998400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x1A, 0, 1275 },
- + { 19200, CCTL(CLK_TCXO, 1), SRC_RAW, 0, 0, 1050, 14000},
- + { 128000, CCTL(CLK_TCXO, 1), SRC_AXI, 0, 0, 1050, 14000 },
- + { 245000, CCTL(CLK_MODEM_PLL, 1), SRC_RAW, 0, 0, 1050, 29000 },
- + /* Work arround for acpu resume hung, GPLL is turn off by arm9 */
- + /*{ 256000, CCTL(CLK_GLOBAL_PLL, 3), SRC_RAW, 0, 0, 1050, 29000 },*/
- + { 384000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0A, 0, 1050, 58000 },
- + { 422400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0B, 0, 1050, 117000 },
- + { 460800, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0C, 0, 1050, 117000 },
- + { 499200, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0D, 0, 1075, 117000 },
- + { 537600, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0E, 0, 1100, 117000 },
- + { 576000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x0F, 0, 1100, 117000 },
- + { 614400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x10, 0, 1125, 117000 },
- + { 652800, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x11, 0, 1150, 117000 },
- + { 691200, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x12, 0, 1175, 117000 },
- + { 729600, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x13, 0, 1200, 117000 },
- + { 768000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x14, 0, 1200, 128000 },
- + { 806400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x15, 0, 1225, 128000 },
- + { 844800, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x16, 0, 1250, 128000 },
- + { 883200, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x17, 0, 1275, 128000 },
- + { 921600, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x18, 0, 1300, 128000 },
- + { 960000, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x19, 0, 1300, 128000 },
- + { 998400, CCTL(CLK_TCXO, 1), SRC_SCPLL, 0x1A, 0, 1300, 128000 },
- { 0 },
- };
- @@ -152,11 +155,17 @@ struct clock_state {
- uint32_t vdd_switch_time_us;
- unsigned long power_collapse_khz;
- unsigned long wait_for_irq_khz;
- + struct clk* clk_ebi1;
- struct regulator *regulator;
- };
- static struct clock_state drv_state = { 0 };
- +
- +struct clk *clk_get(struct device *dev, const char *id);
- +unsigned long clk_get_rate(struct clk *clk);
- +int clk_set_rate(struct clk *clk, unsigned long rate);
- +
- static DEFINE_SPINLOCK(acpu_lock);
- #define PLLMODE_POWERDOWN 0
- @@ -288,7 +297,7 @@ static int acpuclk_set_vdd_level(int vdd)
- return regulator_set_voltage(drv_state.regulator, vdd, vdd);
- }
- -int acpuclk_set_rate(unsigned long rate, int for_power_collapse)
- +int acpuclk_set_rate(unsigned long rate, enum setrate_reason reason)
- {
- struct clkctl_acpu_speed *cur, *next;
- unsigned long flags;
- @@ -298,9 +307,9 @@ int acpuclk_set_rate(unsigned long rate, int for_power_collapse)
- /* convert to KHz */
- rate /= 1000;
- - DEBUG("acpuclk_set_rate(%d,%d)\n", (int) rate, for_power_collapse);
- + DEBUG("acpuclk_set_rate(%d,%d)\n", (int) rate, reason);
- - if (rate == 0 || rate == cur->acpu_khz)
- + if (rate == cur->acpu_khz || rate == 0)
- return 0;
- next = acpu_freq_tbl;
- @@ -312,7 +321,7 @@ int acpuclk_set_rate(unsigned long rate, int for_power_collapse)
- next++;
- }
- - if (!for_power_collapse) {
- + if (reason == SETRATE_CPUFREQ) {
- mutex_lock(&drv_state.lock);
- /* Increase VDD if needed. */
- if (next->vdd > cur->vdd) {
- @@ -331,6 +340,7 @@ int acpuclk_set_rate(unsigned long rate, int for_power_collapse)
- next->clk_sel, next->clk_cfg, next->sc_l_value);
- if (next->clk_sel == SRC_SCPLL) {
- + /* curr -> standby(MPLL speed) -> target */
- if (!IS_ACPU_STANDBY(cur))
- select_clock(acpu_stby->clk_sel, acpu_stby->clk_cfg);
- loops_per_jiffy = next->lpj;
- @@ -350,7 +360,16 @@ int acpuclk_set_rate(unsigned long rate, int for_power_collapse)
- drv_state.current_speed = next;
- spin_unlock_irqrestore(&acpu_lock, flags);
- - if (!for_power_collapse) {
- +
- +#ifndef CONFIG_AXI_SCREEN_POLICY
- + if (reason == SETRATE_CPUFREQ || reason == SETRATE_PC) {
- + if (cur->axiclk_khz != next->axiclk_khz)
- + clk_set_rate(drv_state.clk_ebi1, next->axiclk_khz * 1000);
- + DEBUG("acpuclk_set_rate switch axi to %d\n",
- + clk_get_rate(drv_state.clk_ebi1));
- + }
- +#endif
- + if (reason == SETRATE_CPUFREQ) {
- /* Drop VDD level if we can. */
- if (next->vdd < cur->vdd) {
- if (acpuclk_set_vdd_level(next->vdd))
- @@ -384,12 +403,59 @@ static unsigned __init acpuclk_find_speed(void)
- #define PCOM_MODEM_PLL 0
- static int pll_request(unsigned id, unsigned on)
- {
- -#if !defined(CONFIG_MSM_AMSS_VERSION_WINCE)
- on = !!on;
- return msm_proc_comm(PCOM_CLKCTL_RPC_PLL_REQUEST, &id, &on);
- -#else
- - return 0;
- -#endif
- +}
- +
- +/* Spare register populated with efuse data on max ACPU freq. */
- +#define CT_CSR_PHYS 0xA8700000
- +#define TCSR_SPARE2_ADDR (ct_csr_base + 0x60)
- +
- +void __init acpu_freq_tbl_fixup(void)
- +{
- + void __iomem *ct_csr_base;
- + uint32_t tcsr_spare2;
- + unsigned int max_acpu_khz;
- + unsigned int i;
- +
- + ct_csr_base = ioremap(CT_CSR_PHYS, PAGE_SIZE);
- + BUG_ON(ct_csr_base == NULL);
- +
- + tcsr_spare2 = readl(TCSR_SPARE2_ADDR);
- +
- + /* Check if the register is supported and meaningful. */
- + if ((tcsr_spare2 & 0xF000) != 0xA000) {
- + pr_info("Efuse data on Max ACPU freq not present.\n");
- + goto skip_efuse_fixup;
- + }
- +
- + switch (tcsr_spare2 & 0xF0) {
- + case 0x70:
- + max_acpu_khz = 768000;
- + break;
- + case 0x30:
- + case 0x00:
- + max_acpu_khz = 998400;
- + break;
- + case 0x10:
- + max_acpu_khz = 1267200;
- + break;
- + default:
- + pr_warning("Invalid efuse data (%x) on Max ACPU freq!\n",
- + tcsr_spare2);
- + goto skip_efuse_fixup;
- + }
- +
- + pr_info("Max ACPU freq from efuse data is %d KHz\n", max_acpu_khz);
- +
- + for (i = 0; acpu_freq_tbl[i].acpu_khz != 0; i++) {
- + if (acpu_freq_tbl[i].acpu_khz > max_acpu_khz) {
- + acpu_freq_tbl[i].acpu_khz = 0;
- + break;
- + }
- + }
- +skip_efuse_fixup:
- + iounmap(ct_csr_base);
- }
- static void __init acpuclk_init(void)
- @@ -458,11 +524,12 @@ uint32_t acpuclk_get_switch_time(void)
- return drv_state.acpu_switch_time_us;
- }
- -unsigned long acpuclk_power_collapse(void)
- +unsigned long acpuclk_power_collapse(int from_idle)
- {
- int ret = acpuclk_get_rate();
- + enum setrate_reason reason = (from_idle) ? SETRATE_PC_IDLE : SETRATE_PC;
- if (ret > drv_state.power_collapse_khz)
- - acpuclk_set_rate(drv_state.power_collapse_khz * 1000, 1);
- + acpuclk_set_rate(drv_state.power_collapse_khz * 1000, reason);
- return ret * 1000;
- }
- @@ -475,7 +542,7 @@ unsigned long acpuclk_wait_for_irq(void)
- {
- int ret = acpuclk_get_rate();
- if (ret > drv_state.wait_for_irq_khz)
- - acpuclk_set_rate(drv_state.wait_for_irq_khz * 1000, 1);
- + acpuclk_set_rate(drv_state.wait_for_irq_khz * 1000, SETRATE_SWFI);
- return ret * 1000;
- }
- @@ -493,6 +560,11 @@ void __init msm_acpu_clock_init(struct msm_acpu_clock_platform_data *clkdata)
- if (clkdata->mpll_khz)
- acpu_mpll->acpu_khz = clkdata->mpll_khz;
- + acpu_freq_tbl_fixup();
- acpuclk_init();
- acpuclk_init_cpufreq_table();
- + drv_state.clk_ebi1 = clk_get(NULL,"ebi1_clk");
- +#ifndef CONFIG_AXI_SCREEN_POLICY
- + clk_set_rate(drv_state.clk_ebi1, drv_state.current_speed->axiclk_khz * 1000);
- +#endif
- }
- diff --git a/arch/arm/mach-msm/acpuclock.h b/arch/arm/mach-msm/acpuclock.h
- index 415de2e..97fcb4f 100644
- --- a/arch/arm/mach-msm/acpuclock.h
- +++ b/arch/arm/mach-msm/acpuclock.h
- @@ -20,11 +20,23 @@
- #ifndef __ARCH_ARM_MACH_MSM_ACPUCLOCK_H
- #define __ARCH_ARM_MACH_MSM_ACPUCLOCK_H
- -int acpuclk_set_rate(unsigned long rate, int for_power_collapse);
- +enum setrate_reason {
- + SETRATE_CPUFREQ = 0,
- + SETRATE_SWFI,
- + SETRATE_PC,
- + SETRATE_PC_IDLE,
- +};
- +
- +#if defined(CONFIG_ARCH_MSM_SCORPION)
- +int acpuclk_set_rate(unsigned long rate, enum setrate_reason reason);
- +unsigned long acpuclk_power_collapse(int from_idle);
- +#else
- +int acpuclk_set_rate(unsigned long rate, enum setrate_reason reason);
- +unsigned long acpuclk_power_collapse(int from_idle);
- +#endif
- unsigned long acpuclk_get_rate(void);
- uint32_t acpuclk_get_switch_time(void);
- unsigned long acpuclk_wait_for_irq(void);
- -unsigned long acpuclk_power_collapse(void);
- unsigned long acpuclk_get_wfi_rate(void);
- diff --git a/arch/arm/mach-msm/include/mach/msm_smd.h b/arch/arm/mach-msm/include/mach/msm_smd.h
- index 2e56b82..d9418ba 100644
- --- a/arch/arm/mach-msm/include/mach/msm_smd.h
- +++ b/arch/arm/mach-msm/include/mach/msm_smd.h
- @@ -54,7 +54,6 @@ int smd_cur_packet_size(smd_channel_t *ch);
- */
- void smd_kick(smd_channel_t *ch);
- -
- #if 0
- /* these are interruptable waits which will block you until the specified
- ** number of bytes are readable or writable.
- @@ -62,6 +61,7 @@ void smd_kick(smd_channel_t *ch);
- int smd_wait_until_readable(smd_channel_t *ch, int bytes);
- int smd_wait_until_writable(smd_channel_t *ch, int bytes);
- #endif
- +int smd_wait_until_opened(smd_channel_t *ch, int timeout_us);
- typedef enum
- {
- @@ -105,11 +105,18 @@ typedef enum
- SMD_NUM_PORTS,
- } smd_port_id_type;
- -struct smd_tty_channel_desc {
- - int id;
- - const char *name;
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- +enum
- +{
- + SMD_APPS_MODEM = 0,
- + SMD_APPS_QDSP,
- + SMD_MODEM_QDSP
- };
- -
- -int smd_set_channel_list(const struct smd_tty_channel_desc *, int len);
- +#else
- +enum
- +{
- + SMD_APPS_MODEM = 0
- +};
- +#endif
- #endif
- diff --git a/arch/arm/mach-msm/irq.c b/arch/arm/mach-msm/irq.c
- index 57de269..4b4a044 100644
- --- a/arch/arm/mach-msm/irq.c
- +++ b/arch/arm/mach-msm/irq.c
- @@ -43,19 +43,38 @@ static int msm_irq_debug_mask;
- module_param_named(debug_mask, msm_irq_debug_mask, int, S_IRUGO | S_IWUSR | S_IWGRP);
- #define VIC_REG(off) (MSM_VIC_BASE + (off))
- +#if defined(CONFIG_ARCH_MSM7X30)
- +#define VIC_INT_TO_REG_ADDR(base, irq) (base + (irq / 32) * 4)
- +#define VIC_INT_TO_REG_INDEX(irq) ((irq >> 5) & 3)
- +#else
- +#define VIC_INT_TO_REG_ADDR(base, irq) (base + ((irq & 32) ? 4 : 0))
- +#define VIC_INT_TO_REG_INDEX(irq) ((irq >> 5) & 1)
- +#endif
- #define VIC_INT_SELECT0 VIC_REG(0x0000) /* 1: FIQ, 0: IRQ */
- #define VIC_INT_SELECT1 VIC_REG(0x0004) /* 1: FIQ, 0: IRQ */
- +#define VIC_INT_SELECT2 VIC_REG(0x0008) /* 1: FIQ, 0: IRQ */
- +#define VIC_INT_SELECT3 VIC_REG(0x000C) /* 1: FIQ, 0: IRQ */
- #define VIC_INT_EN0 VIC_REG(0x0010)
- #define VIC_INT_EN1 VIC_REG(0x0014)
- +#define VIC_INT_EN2 VIC_REG(0x0018)
- +#define VIC_INT_EN3 VIC_REG(0x001C)
- #define VIC_INT_ENCLEAR0 VIC_REG(0x0020)
- #define VIC_INT_ENCLEAR1 VIC_REG(0x0024)
- +#define VIC_INT_ENCLEAR2 VIC_REG(0x0028)
- +#define VIC_INT_ENCLEAR3 VIC_REG(0x002C)
- #define VIC_INT_ENSET0 VIC_REG(0x0030)
- #define VIC_INT_ENSET1 VIC_REG(0x0034)
- +#define VIC_INT_ENSET2 VIC_REG(0x0038)
- +#define VIC_INT_ENSET3 VIC_REG(0x003C)
- #define VIC_INT_TYPE0 VIC_REG(0x0040) /* 1: EDGE, 0: LEVEL */
- #define VIC_INT_TYPE1 VIC_REG(0x0044) /* 1: EDGE, 0: LEVEL */
- +#define VIC_INT_TYPE2 VIC_REG(0x0048) /* 1: EDGE, 0: LEVEL */
- +#define VIC_INT_TYPE3 VIC_REG(0x004C) /* 1: EDGE, 0: LEVEL */
- #define VIC_INT_POLARITY0 VIC_REG(0x0050) /* 1: NEG, 0: POS */
- #define VIC_INT_POLARITY1 VIC_REG(0x0054) /* 1: NEG, 0: POS */
- +#define VIC_INT_POLARITY2 VIC_REG(0x0058) /* 1: NEG, 0: POS */
- +#define VIC_INT_POLARITY3 VIC_REG(0x005C) /* 1: NEG, 0: POS */
- #define VIC_NO_PEND_VAL VIC_REG(0x0060)
- #if defined(CONFIG_ARCH_MSM_SCORPION)
- @@ -69,14 +88,24 @@ module_param_named(debug_mask, msm_irq_debug_mask, int, S_IRUGO | S_IWUSR | S_IW
- #endif
- #define VIC_IRQ_STATUS0 VIC_REG(0x0080)
- #define VIC_IRQ_STATUS1 VIC_REG(0x0084)
- +#define VIC_IRQ_STATUS2 VIC_REG(0x0088)
- +#define VIC_IRQ_STATUS3 VIC_REG(0x008C)
- #define VIC_FIQ_STATUS0 VIC_REG(0x0090)
- #define VIC_FIQ_STATUS1 VIC_REG(0x0094)
- +#define VIC_FIQ_STATUS2 VIC_REG(0x0098)
- +#define VIC_FIQ_STATUS3 VIC_REG(0x009C)
- #define VIC_RAW_STATUS0 VIC_REG(0x00A0)
- #define VIC_RAW_STATUS1 VIC_REG(0x00A4)
- +#define VIC_RAW_STATUS2 VIC_REG(0x00A8)
- +#define VIC_RAW_STATUS3 VIC_REG(0x00AC)
- #define VIC_INT_CLEAR0 VIC_REG(0x00B0)
- #define VIC_INT_CLEAR1 VIC_REG(0x00B4)
- +#define VIC_INT_CLEAR2 VIC_REG(0x00B8)
- +#define VIC_INT_CLEAR3 VIC_REG(0x00BC)
- #define VIC_SOFTINT0 VIC_REG(0x00C0)
- #define VIC_SOFTINT1 VIC_REG(0x00C4)
- +#define VIC_SOFTINT2 VIC_REG(0x00C8)
- +#define VIC_SOFTINT3 VIC_REG(0x00CC)
- #define VIC_IRQ_VEC_RD VIC_REG(0x00D0) /* pending int # */
- #define VIC_IRQ_VEC_PEND_RD VIC_REG(0x00D4) /* pending vector addr */
- #define VIC_IRQ_VEC_WR VIC_REG(0x00D8)
- @@ -100,21 +129,47 @@ module_param_named(debug_mask, msm_irq_debug_mask, int, S_IRUGO | S_IWUSR | S_IW
- #define VIC_VECTPRIORITY(n) VIC_REG(0x0200+((n) * 4))
- #define VIC_VECTADDR(n) VIC_REG(0x0400+((n) * 4))
- +#if defined(CONFIG_ARCH_MSM7X30)
- +#define VIC_NUM_REGS 4
- +#else
- +#define VIC_NUM_REGS 2
- +#endif
- +
- +#if VIC_NUM_REGS == 2
- +#define DPRINT_REGS(base_reg, format, ...) \
- + printk(KERN_INFO format " %x %x\n", ##__VA_ARGS__, \
- + readl(base_reg ## 0), readl(base_reg ## 1))
- +#define DPRINT_ARRAY(array, format, ...) \
- + printk(KERN_INFO format " %x %x\n", ##__VA_ARGS__, \
- + array[0], array[1])
- +#elif VIC_NUM_REGS == 4
- +#define DPRINT_REGS(base_reg, format, ...) \
- + printk(KERN_INFO format " %x %x %x %x\n", ##__VA_ARGS__, \
- + readl(base_reg ## 0), readl(base_reg ## 1), \
- + readl(base_reg ## 2), readl(base_reg ## 3))
- +#define DPRINT_ARRAY(array, format, ...) \
- + printk(KERN_INFO format " %x %x %x %x\n", ##__VA_ARGS__, \
- + array[0], array[1], \
- + array[2], array[3])
- +#else
- +#error "VIC_NUM_REGS set to illegal value"
- +#endif
- +
- static uint32_t msm_irq_smsm_wake_enable[2];
- static struct {
- uint32_t int_en[2];
- uint32_t int_type;
- uint32_t int_polarity;
- uint32_t int_select;
- -} msm_irq_shadow_reg[2];
- -static uint32_t msm_irq_idle_disable[2];
- +} msm_irq_shadow_reg[VIC_NUM_REGS];
- +static uint32_t msm_irq_idle_disable[VIC_NUM_REGS];
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- -#define INT_INFO_SMSM_ID SMEM_SMSM_INT_INFO
- -struct smsm_interrupt_info *smsm_int_info;
- -#else
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- #define INT_INFO_SMSM_ID SMEM_APPS_DEM_SLAVE_DATA
- struct msm_dem_slave_data *smsm_int_info;
- +#else
- +#define INT_INFO_SMSM_ID SMEM_SMSM_INT_INFO
- +struct smsm_interrupt_info *smsm_int_info;
- #endif
- @@ -143,7 +198,9 @@ static uint8_t msm_irq_to_smsm[NR_MSM_IRQS + NR_SIRC_IRQS] = {
- [INT_UART1DM_IRQ] = 17,
- [INT_UART1DM_RX] = 18,
- [INT_KEYSENSE] = 19,
- +#if !defined(CONFIG_ARCH_MSM7X30)
- [INT_AD_HSSD] = 20,
- +#endif
- [INT_NAND_WR_ER_DONE] = 21,
- [INT_NAND_OP_DONE] = 22,
- @@ -168,25 +225,32 @@ static uint8_t msm_irq_to_smsm[NR_MSM_IRQS + NR_SIRC_IRQS] = {
- [INT_A9_M2A_5] = SMSM_FAKE_IRQ,
- [INT_GP_TIMER_EXP] = SMSM_FAKE_IRQ,
- [INT_DEBUG_TIMER_EXP] = SMSM_FAKE_IRQ,
- - [INT_AD6_EXT_VFR] = SMSM_FAKE_IRQ,
- [INT_ADSP_A11] = SMSM_FAKE_IRQ,
- -#ifdef CONFIG_ARCH_MSM_SCORPION
- +#ifdef CONFIG_ARCH_QSD8X50
- [INT_SIRC_0] = SMSM_FAKE_IRQ,
- [INT_SIRC_1] = SMSM_FAKE_IRQ,
- #endif
- };
- +static inline void msm_irq_write_all_regs(void __iomem *base, unsigned int val)
- +{
- + int i;
- + /* the address must be continue */
- + for (i = 0; i < VIC_NUM_REGS; i++)
- + writel(val, base + (i * 4));
- +}
- +
- static void msm_irq_ack(unsigned int irq)
- {
- - void __iomem *reg = VIC_INT_CLEAR0 + ((irq & 32) ? 4 : 0);
- + void __iomem *reg = VIC_INT_TO_REG_ADDR(VIC_INT_CLEAR0, irq);
- irq = 1 << (irq & 31);
- writel(irq, reg);
- }
- static void msm_irq_mask(unsigned int irq)
- {
- - void __iomem *reg = VIC_INT_ENCLEAR0 + ((irq & 32) ? 4 : 0);
- - unsigned index = (irq >> 5) & 1;
- + void __iomem *reg = VIC_INT_TO_REG_ADDR(VIC_INT_ENCLEAR0, irq);
- + unsigned index = VIC_INT_TO_REG_INDEX(irq);
- uint32_t mask = 1UL << (irq & 31);
- int smsm_irq = msm_irq_to_smsm[irq];
- @@ -202,8 +266,8 @@ static void msm_irq_mask(unsigned int irq)
- static void msm_irq_unmask(unsigned int irq)
- {
- - void __iomem *reg = VIC_INT_ENSET0 + ((irq & 32) ? 4 : 0);
- - unsigned index = (irq >> 5) & 1;
- + void __iomem *reg = VIC_INT_TO_REG_ADDR(VIC_INT_ENSET0, irq);
- + unsigned index = VIC_INT_TO_REG_INDEX(irq);
- uint32_t mask = 1UL << (irq & 31);
- int smsm_irq = msm_irq_to_smsm[irq];
- @@ -220,7 +284,7 @@ static void msm_irq_unmask(unsigned int irq)
- static int msm_irq_set_wake(unsigned int irq, unsigned int on)
- {
- - unsigned index = (irq >> 5) & 1;
- + unsigned index = VIC_INT_TO_REG_INDEX(irq);
- uint32_t mask = 1UL << (irq & 31);
- int smsm_irq = msm_irq_to_smsm[irq];
- @@ -246,9 +310,9 @@ static int msm_irq_set_wake(unsigned int irq, unsigned int on)
- static int msm_irq_set_type(unsigned int irq, unsigned int flow_type)
- {
- - void __iomem *treg = VIC_INT_TYPE0 + ((irq & 32) ? 4 : 0);
- - void __iomem *preg = VIC_INT_POLARITY0 + ((irq & 32) ? 4 : 0);
- - unsigned index = (irq >> 5) & 1;
- + void __iomem *treg = VIC_INT_TO_REG_ADDR(VIC_INT_TYPE0, irq);
- + void __iomem *preg = VIC_INT_TO_REG_ADDR(VIC_INT_POLARITY0, irq);
- + unsigned index = VIC_INT_TO_REG_INDEX(irq);
- int b = 1 << (irq & 31);
- uint32_t polarity;
- uint32_t type;
- @@ -277,16 +341,24 @@ static int msm_irq_set_type(unsigned int irq, unsigned int flow_type)
- int msm_irq_pending(void)
- {
- - return readl(VIC_IRQ_STATUS0) || readl(VIC_IRQ_STATUS1);
- + int i, pending = 0;
- + /* the address must be continue */
- + for (i = 0; (i < VIC_NUM_REGS) && !pending; i++)
- + pending |= readl(VIC_IRQ_STATUS0 + (i * 4));
- +
- + return pending;
- }
- int msm_irq_idle_sleep_allowed(void)
- {
- + int i, disable = 0;
- +
- if (msm_irq_debug_mask & IRQ_DEBUG_SLEEP_REQUEST)
- - printk(KERN_INFO "msm_irq_idle_sleep_allowed: disable %x %x\n",
- - msm_irq_idle_disable[0], msm_irq_idle_disable[1]);
- - return !(msm_irq_idle_disable[0] || msm_irq_idle_disable[1] ||
- - !smsm_int_info);
- + DPRINT_ARRAY(msm_irq_idle_disable,
- + "msm_irq_idle_sleep_allowed: disable");
- + for (i = 0; i < VIC_NUM_REGS; i++)
- + disable |= msm_irq_idle_disable[i];
- + return !(disable || !smsm_int_info);
- }
- /* If arm9_wake is set: pass control to the other core.
- @@ -302,8 +374,8 @@ void msm_irq_enter_sleep1(bool arm9_wake, int from_idle)
- int msm_irq_enter_sleep2(bool arm9_wake, int from_idle)
- {
- - int limit = 10;
- - uint32_t pending0, pending1;
- + int i, limit = 10;
- + uint32_t pending[VIC_NUM_REGS];
- if (from_idle && !arm9_wake)
- return 0;
- @@ -312,23 +384,25 @@ int msm_irq_enter_sleep2(bool arm9_wake, int from_idle)
- WARN_ON_ONCE(!arm9_wake && !from_idle);
- if (msm_irq_debug_mask & IRQ_DEBUG_SLEEP)
- - printk(KERN_INFO "msm_irq_enter_sleep change irq, pend %x %x\n",
- - readl(VIC_IRQ_STATUS0), readl(VIC_IRQ_STATUS1));
- - pending0 = readl(VIC_IRQ_STATUS0);
- - pending1 = readl(VIC_IRQ_STATUS1);
- - pending0 &= msm_irq_shadow_reg[0].int_en[!from_idle];
- + DPRINT_REGS(VIC_IRQ_STATUS, "%s change irq, pend", __func__);
- +
- + for (i = 0; i < VIC_NUM_REGS; i++) {
- + pending[i] = readl(VIC_IRQ_STATUS0 + (i * 4));
- + pending[i] &= msm_irq_shadow_reg[i].int_en[!from_idle];
- + }
- /* Clear INT_A9_M2A_5 since requesting sleep triggers it */
- - pending0 &= ~(1U << INT_A9_M2A_5);
- - pending1 &= msm_irq_shadow_reg[1].int_en[!from_idle];
- - if (pending0 || pending1) {
- - if (msm_irq_debug_mask & IRQ_DEBUG_SLEEP_ABORT)
- - printk(KERN_INFO "msm_irq_enter_sleep2 abort %x %x\n",
- - pending0, pending1);
- - return -EAGAIN;
- + pending[0] &= ~(1U << INT_A9_M2A_5);
- +
- + for (i = 0; i < VIC_NUM_REGS; i++) {
- + if (pending[i]) {
- + if (msm_irq_debug_mask & IRQ_DEBUG_SLEEP_ABORT)
- + DPRINT_ARRAY(pending, "%s abort",
- + __func__);
- + return -EAGAIN;
- + }
- }
- - writel(0, VIC_INT_EN0);
- - writel(0, VIC_INT_EN1);
- + msm_irq_write_all_regs(VIC_INT_EN0, 0);
- while (limit-- > 0) {
- int pend_irq;
- @@ -346,8 +420,9 @@ int msm_irq_enter_sleep2(bool arm9_wake, int from_idle)
- msm_irq_ack(INT_A9_M2A_6);
- writel(1U << INT_A9_M2A_6, VIC_INT_ENSET0);
- } else {
- - writel(msm_irq_shadow_reg[0].int_en[1], VIC_INT_ENSET0);
- - writel(msm_irq_shadow_reg[1].int_en[1], VIC_INT_ENSET1);
- + for (i = 0; i < VIC_NUM_REGS; i++)
- + writel(msm_irq_shadow_reg[i].int_en[1],
- + VIC_INT_ENSET0 + (i * 4));
- }
- return 0;
- }
- @@ -358,7 +433,7 @@ void msm_irq_exit_sleep1(void)
- msm_irq_ack(INT_A9_M2A_6);
- msm_irq_ack(INT_PWB_I2C);
- - for (i = 0; i < 2; i++) {
- + for (i = 0; i < VIC_NUM_REGS; i++) {
- writel(msm_irq_shadow_reg[i].int_type, VIC_INT_TYPE0 + i * 4);
- writel(msm_irq_shadow_reg[i].int_polarity, VIC_INT_POLARITY0 + i * 4);
- writel(msm_irq_shadow_reg[i].int_en[0], VIC_INT_EN0 + i * 4);
- @@ -452,20 +527,16 @@ void __init msm_init_irq(void)
- unsigned n;
- /* select level interrupts */
- - writel(0, VIC_INT_TYPE0);
- - writel(0, VIC_INT_TYPE1);
- + msm_irq_write_all_regs(VIC_INT_TYPE0, 0);
- /* select highlevel interrupts */
- - writel(0, VIC_INT_POLARITY0);
- - writel(0, VIC_INT_POLARITY1);
- + msm_irq_write_all_regs(VIC_INT_POLARITY0, 0);
- /* select IRQ for all INTs */
- - writel(0, VIC_INT_SELECT0);
- - writel(0, VIC_INT_SELECT1);
- + msm_irq_write_all_regs(VIC_INT_SELECT0, 0);
- /* disable all INTs */
- - writel(0, VIC_INT_EN0);
- - writel(0, VIC_INT_EN1);
- + msm_irq_write_all_regs(VIC_INT_EN0, 0);
- /* don't use 1136 vic */
- writel(0, VIC_CONFIG);
- @@ -494,7 +565,7 @@ late_initcall(msm_init_irq_late);
- #if defined(CONFIG_MSM_FIQ_SUPPORT)
- void msm_trigger_irq(int irq)
- {
- - void __iomem *reg = VIC_SOFTINT0 + ((irq & 32) ? 4 : 0);
- + void __iomem *reg = VIC_INT_TO_REG_ADDR(VIC_SOFTINT0, irq);
- uint32_t mask = 1UL << (irq & 31);
- writel(mask, reg);
- }
- @@ -517,8 +588,8 @@ void msm_fiq_disable(int irq)
- static void _msm_fiq_select(int irq)
- {
- - void __iomem *reg = VIC_INT_SELECT0 + ((irq & 32) ? 4 : 0);
- - unsigned index = (irq >> 5) & 1;
- + void __iomem *reg = VIC_INT_TO_REG_ADDR(VIC_INT_SELECT0, irq);
- + unsigned index = VIC_INT_TO_REG_INDEX(irq);
- uint32_t mask = 1UL << (irq & 31);
- unsigned long flags;
- @@ -530,8 +601,8 @@ static void _msm_fiq_select(int irq)
- static void _msm_fiq_unselect(int irq)
- {
- - void __iomem *reg = VIC_INT_SELECT0 + ((irq & 32) ? 4 : 0);
- - unsigned index = (irq >> 5) & 1;
- + void __iomem *reg = VIC_INT_TO_REG_ADDR(VIC_INT_SELECT0, irq);
- + unsigned index = VIC_INT_TO_REG_INDEX(irq);
- uint32_t mask = 1UL << (irq & 31);
- unsigned long flags;
- diff --git a/arch/arm/mach-msm/pm.c b/arch/arm/mach-msm/pm.c
- index 6f1614d..bfcf7b5 100644
- --- a/arch/arm/mach-msm/pm.c
- +++ b/arch/arm/mach-msm/pm.c
- @@ -29,26 +29,24 @@
- #include <mach/msm_iomap.h>
- #include <mach/system.h>
- #include <asm/io.h>
- +#ifdef CONFIG_VFP
- +#include <asm/vfp.h>
- +#endif
- +
- +#ifdef CONFIG_CACHE_L2X0
- +#include <asm/hardware/cache-l2x0.h>
- +#endif
- #include "smd_private.h"
- +#include "smd_rpcrouter.h"
- #include "acpuclock.h"
- -
- +#include "proc_comm.h"
- #include "clock.h"
- +#include "spm.h"
- #ifdef CONFIG_HAS_WAKELOCK
- #include <linux/wakelock.h>
- #endif
- -#include "dex_comm.h"
- -
- -/*
- -#if defined(CONFIG_MSM_AMSS_VERSION_WINCE)
- -
- -#else
- -#include "proc_comm.h"
- -#endif
- -*/
- -
- -
- enum {
- MSM_PM_DEBUG_SUSPEND = 1U << 0,
- MSM_PM_DEBUG_POWER_COLLAPSE = 1U << 1,
- @@ -57,9 +55,10 @@ enum {
- MSM_PM_DEBUG_RESET_VECTOR = 1U << 4,
- MSM_PM_DEBUG_SMSM_STATE = 1U << 5,
- MSM_PM_DEBUG_IDLE = 1U << 6,
- - MSM_PM_DEBUG_CLOCK_VOTE = 1U << 7
- + MSM_PM_DEBUG_SLEEP_LIMIT = 1U << 7,
- + MSM_PM_DEBUG_WAKEUP_REASON = 1U << 8,
- };
- -static int msm_pm_debug_mask = MSM_PM_DEBUG_CLOCK_VOTE;
- +static int msm_pm_debug_mask = MSM_PM_DEBUG_SLEEP_LIMIT | MSM_PM_DEBUG_WAKEUP_REASON;
- module_param_named(debug_mask, msm_pm_debug_mask, int, S_IRUGO | S_IWUSR | S_IWGRP);
- enum {
- @@ -78,12 +77,18 @@ module_param_named(idle_sleep_min_time, msm_pm_idle_sleep_min_time, int, S_IRUGO
- static int msm_pm_idle_spin_time = CONFIG_MSM7X00A_IDLE_SPIN_TIME;
- module_param_named(idle_spin_time, msm_pm_idle_spin_time, int, S_IRUGO | S_IWUSR | S_IWGRP);
- +#if defined (CONFIG_ARCH_MSM7X30)
- +#define A11S_CLK_SLEEP_EN (MSM_GCC_BASE + 0x020)
- +#define A11S_PWRDOWN (MSM_ACC_BASE + 0x01C)
- +#define A11S_SECOP (MSM_TCSR_BASE + 0x38)
- +#else
- #define A11S_CLK_SLEEP_EN (MSM_CSR_BASE + 0x11c)
- #define A11S_PWRDOWN (MSM_CSR_BASE + 0x440)
- #define A11S_STANDBY_CTL (MSM_CSR_BASE + 0x108)
- +#endif
- #define A11RAMBACKBIAS (MSM_CSR_BASE + 0x508)
- -
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- #define DEM_MASTER_BITS_PER_CPU 6
- /* Power Master State Bits - Per CPU */
- @@ -112,18 +117,17 @@ module_param_named(idle_spin_time, msm_pm_idle_spin_time, int, S_IRUGO | S_IWUSR
- #define DEM_SLAVE_SMSM_RESET (0x0100)
- #define DEM_SLAVE_SMSM_PWRC_SUSPEND (0x0200)
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- -#define PM_SMSM_WRITE_STATE SMSM_STATE_APPS
- -#define PM_SMSM_READ_STATE SMSM_STATE_MODEM
- -
- -#define PM_SMSM_WRITE_RUN SMSM_RUN
- -#define PM_SMSM_READ_RUN SMSM_RUN
- -#else
- #define PM_SMSM_WRITE_STATE SMSM_STATE_APPS_DEM
- #define PM_SMSM_READ_STATE SMSM_STATE_POWER_MASTER_DEM
- #define PM_SMSM_WRITE_RUN DEM_SLAVE_SMSM_RUN
- #define PM_SMSM_READ_RUN DEM_MASTER_SMSM_RUN
- +#else
- +#define PM_SMSM_WRITE_STATE SMSM_STATE_APPS
- +#define PM_SMSM_READ_STATE SMSM_STATE_MODEM
- +
- +#define PM_SMSM_WRITE_RUN SMSM_RUN
- +#define PM_SMSM_READ_RUN SMSM_RUN
- #endif
- int msm_pm_collapse(void);
- @@ -134,7 +138,11 @@ int64_t msm_timer_enter_idle(void);
- void msm_timer_exit_idle(int low_power);
- int msm_irq_idle_sleep_allowed(void);
- int msm_irq_pending(void);
- -int clks_print_running(void);
- +int clks_allow_tcxo_locked_debug(void);
- +extern int board_mfg_mode(void);
- +extern char * board_get_mfg_sleep_gpio_table(void);
- +extern void gpio_set_diag_gpio_table(unsigned long * dwMFG_gpio_table);
- +extern void wait_rmt_final_call_back(int timeout);
- static int axi_rate;
- static int sleep_axi_rate;
- @@ -212,12 +220,32 @@ msm_pm_wait_state(uint32_t wait_all_set, uint32_t wait_all_clear,
- return -ETIMEDOUT;
- }
- +/*
- + * For speeding up boot time:
- + * During booting up, disable entering arch_idle() by disable_hlt()
- + * Enable it after booting up BOOT_LOCK_TIMEOUT sec.
- + */
- +#define BOOT_LOCK_TIMEOUT (60 * HZ)
- +static void do_expire_boot_lock(struct work_struct *work)
- +{
- + enable_hlt();
- + pr_info("Release 'boot-time' halt_lock\n");
- +}
- +static DECLARE_DELAYED_WORK(work_expire_boot_lock, do_expire_boot_lock);
- +
- #ifdef CONFIG_MSM_FIQ_SUPPORT
- void msm_fiq_exit_sleep(void);
- #else
- static inline void msm_fiq_exit_sleep(void) { }
- #endif
- +#ifdef CONFIG_HTC_POWER_COLLAPSE_MAGIC
- +/* Set magic number in SMEM for power collapse state */
- +#define HTC_POWER_COLLAPSE_ADD (MSM_SHARED_RAM_BASE + 0x000F8000 + 0x000007F8)
- +#define HTC_POWER_COLLAPSE_MAGIC_NUM (HTC_POWER_COLLAPSE_ADD - 0x04)
- +unsigned int magic_num;
- +#endif
- +
- static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- {
- uint32_t saved_vector[2];
- @@ -241,34 +269,13 @@ static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- int rv = -EINTR;
- bool invalid_inital_state = false;
- + if (board_mfg_mode() == 4) /*power test mode*/
- + gpio_set_diag_gpio_table(board_get_mfg_sleep_gpio_table());
- +
- if (msm_pm_debug_mask & MSM_PM_DEBUG_SUSPEND)
- printk(KERN_INFO "msm_sleep(): mode %d delay %u idle %d\n",
- sleep_mode, sleep_delay, from_idle);
- -
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- - switch (sleep_mode) {
- - case MSM_PM_SLEEP_MODE_POWER_COLLAPSE:
- - enter_state = SMSM_PWRC;
- - enter_wait_set = SMSM_RSA;
- - exit_state = SMSM_WFPI;
- - exit_wait_clear = SMSM_RSA;
- - break;
- - case MSM_PM_SLEEP_MODE_POWER_COLLAPSE_SUSPEND:
- - enter_state = SMSM_PWRC_SUSPEND;
- - enter_wait_set = SMSM_RSA;
- - exit_state = SMSM_WFPI;
- - exit_wait_clear = SMSM_RSA;
- - break;
- - case MSM_PM_SLEEP_MODE_APPS_SLEEP:
- - enter_state = SMSM_SLEEP;
- - exit_state = SMSM_SLEEPEXIT;
- - exit_wait_any_set = SMSM_SLEEPEXIT;
- - break;
- - default:
- - enter_state = 0;
- - exit_state = 0;
- - }
- -#else
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- switch (sleep_mode) {
- case MSM_PM_SLEEP_MODE_POWER_COLLAPSE:
- enter_state = DEM_SLAVE_SMSM_PWRC;
- @@ -294,8 +301,30 @@ static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- enter_state = 0;
- exit_state = 0;
- }
- +#else
- + switch (sleep_mode) {
- + case MSM_PM_SLEEP_MODE_POWER_COLLAPSE:
- + enter_state = SMSM_PWRC;
- + enter_wait_set = SMSM_RSA;
- + exit_state = SMSM_WFPI;
- + exit_wait_clear = SMSM_RSA;
- + break;
- + case MSM_PM_SLEEP_MODE_POWER_COLLAPSE_SUSPEND:
- + enter_state = SMSM_PWRC_SUSPEND;
- + enter_wait_set = SMSM_RSA;
- + exit_state = SMSM_WFPI;
- + exit_wait_clear = SMSM_RSA;
- + break;
- + case MSM_PM_SLEEP_MODE_APPS_SLEEP:
- + enter_state = SMSM_SLEEP;
- + exit_state = SMSM_SLEEPEXIT;
- + exit_wait_any_set = SMSM_SLEEPEXIT;
- + break;
- + default:
- + enter_state = 0;
- + exit_state = 0;
- + }
- #endif
- -
- clk_enter_sleep(from_idle);
- msm_irq_enter_sleep1(!!enter_state, from_idle);
- msm_gpio_enter_sleep(from_idle);
- @@ -316,9 +345,9 @@ static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- enter_state = 0;
- exit_state = 0;
- }
- - if ((!from_idle && (msm_pm_debug_mask & MSM_PM_DEBUG_CLOCK_VOTE)) ||
- - (from_idle && (msm_pm_debug_mask & MSM_PM_DEBUG_IDLE)))
- - clks_print_running();
- + if ((!from_idle && msm_pm_debug_mask & MSM_PM_DEBUG_SLEEP_LIMIT) ||
- + (from_idle && msm_pm_debug_mask & MSM_PM_DEBUG_IDLE))
- + clks_allow_tcxo_locked_debug();
- ret = smsm_change_state(PM_SMSM_WRITE_STATE, PM_SMSM_WRITE_RUN, enter_state);
- if (ret) {
- @@ -336,15 +365,16 @@ static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- goto enter_failed;
- if (enter_state) {
- -#ifdef CONFIG_ARCH_MSM_SCORPION
- - writel(0x1b, A11S_CLK_SLEEP_EN);
- +#if defined (CONFIG_ARCH_MSM7X30)
- + writel(1, A11S_PWRDOWN);
- + writel(4, A11S_SECOP);
- #else
- writel(0x1f, A11S_CLK_SLEEP_EN);
- -#endif
- writel(1, A11S_PWRDOWN);
- writel(0, A11S_STANDBY_CTL);
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- +#endif
- +#if !defined(CONFIG_MSM_N_WAY_SMD)
- writel(0, A11RAMBACKBIAS);
- #endif
- @@ -356,20 +386,26 @@ static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- }
- if (sleep_mode <= MSM_PM_SLEEP_MODE_RAMP_DOWN_AND_WAIT_FOR_INTERRUPT) {
- - pm_saved_acpu_clk_rate = acpuclk_power_collapse();
- + pm_saved_acpu_clk_rate = acpuclk_power_collapse(from_idle);
- if (msm_pm_debug_mask & MSM_PM_DEBUG_CLOCK)
- printk(KERN_INFO "msm_sleep(): %ld enter power collapse"
- "\n", pm_saved_acpu_clk_rate);
- if (pm_saved_acpu_clk_rate == 0)
- goto ramp_down_failed;
- +#ifdef CONFIG_AXI_SCREEN_POLICY
- /* Drop AXI request when the screen is on */
- if (axi_rate)
- clk_set_rate(axi_clk, sleep_axi_rate);
- +#endif
- }
- +#ifdef CONFIG_HTC_POWER_COLLAPSE_MAGIC
- + magic_num = 0xAAAA1111;
- + writel(magic_num, HTC_POWER_COLLAPSE_MAGIC_NUM);
- +#endif
- if (sleep_mode < MSM_PM_SLEEP_MODE_APPS_SLEEP) {
- if (msm_pm_debug_mask & MSM_PM_DEBUG_SMSM_STATE)
- - smsm_print_sleep_info();
- + smsm_print_sleep_info(0);
- saved_vector[0] = msm_pm_reset_vector[0];
- saved_vector[1] = msm_pm_reset_vector[1];
- msm_pm_reset_vector[0] = 0xE51FF004; /* ldr pc, 4 */
- @@ -378,10 +414,29 @@ static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- printk(KERN_INFO "msm_sleep(): vector %x %x -> "
- "%x %x\n", saved_vector[0], saved_vector[1],
- msm_pm_reset_vector[0], msm_pm_reset_vector[1]);
- +#ifdef CONFIG_VFP
- + if (from_idle)
- + vfp_flush_context();
- +#endif
- +
- +#ifdef CONFIG_CACHE_L2X0
- + l2x0_suspend();
- +#endif
- + if (!from_idle) printk(KERN_INFO "[R] suspend end\n");
- + /* reset idle sleep mode when suspend. */
- + if (!from_idle) msm_pm_idle_sleep_mode = CONFIG_MSM7X00A_IDLE_SLEEP_MODE;
- collapsed = msm_pm_collapse();
- + if (!from_idle) printk(KERN_INFO "[R] resume start\n");
- +#ifdef CONFIG_CACHE_L2X0
- + l2x0_resume(collapsed);
- +#endif
- msm_pm_reset_vector[0] = saved_vector[0];
- msm_pm_reset_vector[1] = saved_vector[1];
- if (collapsed) {
- +#ifdef CONFIG_VFP
- + if (from_idle)
- + vfp_reinit();
- +#endif
- cpu_init();
- __asm__("cpsie a");
- msm_fiq_exit_sleep();
- @@ -392,23 +447,33 @@ static int msm_sleep(int sleep_mode, uint32_t sleep_delay, int from_idle)
- printk(KERN_INFO "msm_pm_collapse(): returned %d\n",
- collapsed);
- if (msm_pm_debug_mask & MSM_PM_DEBUG_SMSM_STATE)
- - smsm_print_sleep_info();
- + smsm_print_sleep_info(0);
- } else {
- msm_arch_idle();
- rv = 0;
- }
- -
- +#ifdef CONFIG_HTC_POWER_COLLAPSE_MAGIC
- + magic_num = 0xBBBB9999;
- + writel(magic_num, HTC_POWER_COLLAPSE_MAGIC_NUM);
- +#endif
- if (sleep_mode <= MSM_PM_SLEEP_MODE_RAMP_DOWN_AND_WAIT_FOR_INTERRUPT) {
- if (msm_pm_debug_mask & MSM_PM_DEBUG_CLOCK)
- printk(KERN_INFO "msm_sleep(): exit power collapse %ld"
- "\n", pm_saved_acpu_clk_rate);
- +#if defined(CONFIG_ARCH_QSD8X50)
- if (acpuclk_set_rate(pm_saved_acpu_clk_rate, 1) < 0)
- +#else
- + if (acpuclk_set_rate(pm_saved_acpu_clk_rate,
- + from_idle ? SETRATE_PC_IDLE : SETRATE_PC) < 0)
- +#endif
- printk(KERN_ERR "msm_sleep(): clk_set_rate %ld "
- "failed\n", pm_saved_acpu_clk_rate);
- +#ifdef CONFIG_AXI_SCREEN_POLICY
- /* Restore axi rate if needed */
- if (axi_rate)
- clk_set_rate(axi_clk, axi_rate);
- +#endif
- }
- if (msm_pm_debug_mask & MSM_PM_DEBUG_STATE)
- printk(KERN_INFO "msm_sleep(): exit A11S_CLK_SLEEP_EN %x, "
- @@ -419,8 +484,14 @@ ramp_down_failed:
- msm_irq_exit_sleep1();
- enter_failed:
- if (enter_state) {
- +#if defined (CONFIG_ARCH_MSM7X30)
- + writel(0, A11S_SECOP);
- + writel(0, A11S_PWRDOWN);
- + msm_spm_reinit();
- +#else
- writel(0x00, A11S_CLK_SLEEP_EN);
- writel(0, A11S_PWRDOWN);
- +#endif
- smsm_change_state(PM_SMSM_WRITE_STATE, enter_state, exit_state);
- msm_pm_wait_state(0, exit_wait_clear, exit_wait_any_set, 0);
- if (msm_pm_debug_mask & MSM_PM_DEBUG_STATE)
- @@ -429,7 +500,9 @@ enter_failed:
- "smsm_get_state %x\n", readl(A11S_CLK_SLEEP_EN),
- readl(A11S_PWRDOWN), smsm_get_state(PM_SMSM_READ_STATE));
- if (msm_pm_debug_mask & MSM_PM_DEBUG_SMSM_STATE)
- - smsm_print_sleep_info();
- + smsm_print_sleep_info(0);
- + if (msm_pm_debug_mask & MSM_PM_DEBUG_WAKEUP_REASON && !from_idle)
- + smsm_print_sleep_info(1);
- }
- msm_irq_exit_sleep2();
- if (enter_state) {
- @@ -463,7 +536,6 @@ static int msm_pm_idle_spin(void)
- void arch_idle(void)
- {
- -#if 1
- int ret;
- int64_t sleep_time;
- int low_power = 0;
- @@ -492,6 +564,7 @@ void arch_idle(void)
- sleep_time, allow_sleep);
- if (sleep_time < msm_pm_idle_sleep_min_time || !allow_sleep) {
- unsigned long saved_rate;
- + /* only spin while trying wfi ramp down */
- if (acpuclk_get_wfi_rate() && msm_pm_idle_spin() < 0) {
- #ifdef CONFIG_MSM_IDLE_STATS
- exit_stat = MSM_PM_STAT_IDLE_SPIN;
- @@ -518,13 +591,18 @@ void arch_idle(void)
- if (msm_pm_debug_mask & MSM_PM_DEBUG_CLOCK)
- printk(KERN_DEBUG "msm_sleep: clk swfi -> %ld\n",
- saved_rate);
- - if (acpuclk_set_rate(saved_rate, 1) < 0)
- +#if defined(CONFIG_ARCH_QSD8X50)
- + if (saved_rate && acpuclk_set_rate(saved_rate, 1) < 0)
- +#else
- + if (saved_rate
- + && acpuclk_set_rate(saved_rate, SETRATE_SWFI) < 0)
- +#endif
- printk(KERN_ERR "msm_sleep(): clk_set_rate %ld "
- "failed\n", saved_rate);
- #ifdef CONFIG_MSM_IDLE_STATS
- exit_stat = MSM_PM_STAT_IDLE_WFI;
- #endif
- - } else {
- + } else {
- if (msm_pm_idle_spin() < 0) {
- #ifdef CONFIG_MSM_IDLE_STATS
- exit_stat = MSM_PM_STAT_IDLE_SPIN;
- @@ -552,8 +630,6 @@ abort_idle:
- t2 = ktime_to_ns(ktime_get());
- msm_pm_add_stat(exit_stat, t2 - t1);
- #endif
- -
- -#endif
- }
- static int msm_pm_enter(suspend_state_t state)
- @@ -567,16 +643,44 @@ static struct platform_suspend_ops msm_pm_ops = {
- .valid = suspend_valid_only_mem,
- };
- -#if defined(CONFIG_ARCH_MSM7X00A)
- static uint32_t restart_reason = 0x776655AA;
- -#else
- -static uint32_t restart_reason = 0;
- -#endif
- +
- +static int msm_wakeup_after; /* default, no wakeup by alarm */
- +static int msm_power_wakeup_after(const char *val, struct kernel_param *kp)
- +{
- + int ret;
- + struct uart_port *port;
- + struct msm_port *msm_port;
- +
- + ret = param_set_int(val, kp);
- + printk(KERN_INFO "+msm_power_wakeup_after, ret=%d\r\n", ret);
- +
- + if (!ret) {
- + printk(KERN_INFO "msm_wakeup_after=%d\r\n", msm_wakeup_after);
- + if (msm_wakeup_after < 0)
- + msm_wakeup_after = 0; /* invalid, no wakeup */
- + }
- + printk(KERN_INFO "-msm_power_wakeup_after, msm_wakeup_after=%d\r\n", msm_wakeup_after);
- + return ret;
- +}
- +
- +module_param_call(wakeup_after, msm_power_wakeup_after, param_get_int,
- + &msm_wakeup_after, S_IWUSR | S_IRUGO);
- static void msm_pm_power_off(void)
- {
- -// msm_proc_comm(PCOM_POWER_DOWN, 0, 0);
- - dex_comm(DEX_POWER_DOWN, 0, 0);
- + printk(KERN_INFO "msm_pm_power_off:wakeup after %d\r\n", msm_wakeup_after);
- +
- + if (msm_wakeup_after)
- + msm_proc_comm(PCOM_SET_RTC_ALARM, &msm_wakeup_after, 0);
- +
- + msm_proc_comm(PCOM_POWER_DOWN, 0, 0);
- +
- +#if CONFIG_MSM_RMT_STORAGE_SERVER
- + printk(KERN_INFO "from %s\r\n", __func__);
- + wait_rmt_final_call_back(10);
- + printk(KERN_INFO "back %s\r\n", __func__);
- +#endif
- for (;;) ;
- }
- @@ -609,22 +713,29 @@ static void msm_pm_restart(char str)
- {
- msm_pm_flush_console();
- - /* If there's a hard reset hook and the restart_reason
- - * is the default, prefer that to the (slower) proc_comm
- - * reset command.
- - */
- -#ifdef CONFIG_MSM_AMSS_VERSION_WINCE
- - if (msm_hw_reset_hook)
- - msm_hw_reset_hook();
- + /* always reboot device through proc comm */
- + if (restart_reason == 0x6f656d99)
- + msm_proc_comm(PCOM_RESET_CHIP_IMM, &restart_reason, 0);
- else
- - printk(KERN_ERR "No msm_hw_reset_hook() available! System halted.\n");
- + msm_proc_comm(PCOM_RESET_CHIP, &restart_reason, 0);
- +
- +#if CONFIG_MSM_RMT_STORAGE_SERVER
- + printk(KERN_INFO "from %s\r\n", __func__);
- + wait_rmt_final_call_back(10);
- + printk(KERN_INFO "back %s\r\n", __func__);
- + /* wait 2 seconds to let radio reset device after the final EFS sync*/
- + mdelay(2000);
- #else
- - if ((restart_reason == 0x776655AA) && msm_hw_reset_hook) {
- + /* In case Radio is dead, reset device after notify Radio 5 seconds */
- + mdelay(5000);
- +#endif
- +
- + /* hard reboot if possible */
- + if (msm_hw_reset_hook) {
- + printk(KERN_INFO "%s : Do HW_RESET by APP not by RADIO\r\n", __func__);
- msm_hw_reset_hook();
- - } else {
- - msm_proc_comm(PCOM_RESET_CHIP, &restart_reason, 0);
- }
- -#endif
- +
- for (;;) ;
- }
- @@ -723,16 +834,18 @@ void msm_pm_set_max_sleep_time(int64_t max_sleep_time_ns)
- }
- EXPORT_SYMBOL(msm_pm_set_max_sleep_time);
- -#if defined(CONFIG_EARLYSUSPEND) && defined(CONFIG_ARCH_MSM_SCORPION)
- +#ifdef CONFIG_EARLYSUSPEND
- /* axi 128 screen on, 61mhz screen off */
- -static void axi_early_suspend(struct early_suspend *handler) {
- +static void axi_early_suspend(struct early_suspend *handler)
- +{
- axi_rate = 0;
- clk_set_rate(axi_clk, axi_rate);
- }
- -static void axi_late_resume(struct early_suspend *handler) {
- +static void axi_late_resume(struct early_suspend *handler)
- +{
- axi_rate = 128000000;
- - sleep_axi_rate = 120000000;
- + sleep_axi_rate = 117000000;
- clk_set_rate(axi_clk, axi_rate);
- }
- @@ -744,7 +857,7 @@ static struct early_suspend axi_screen_suspend = {
- static void __init msm_pm_axi_init(void)
- {
- -#if defined(CONFIG_EARLYSUSPEND) && defined(CONFIG_ARCH_MSM_SCORPION)
- +#ifdef CONFIG_EARLYSUSPEND
- axi_clk = clk_get(NULL, "ebi1_clk");
- if (IS_ERR(axi_clk)) {
- int result = PTR_ERR(axi_clk);
- @@ -752,7 +865,7 @@ static void __init msm_pm_axi_init(void)
- return;
- }
- axi_rate = 128000000;
- - sleep_axi_rate = 120000000;
- + sleep_axi_rate = 117000000;
- clk_set_rate(axi_clk, axi_rate);
- register_early_suspend(&axi_screen_suspend);
- #else
- @@ -765,11 +878,15 @@ static int __init msm_pm_init(void)
- pm_power_off = msm_pm_power_off;
- arm_pm_restart = msm_pm_restart;
- msm_pm_max_sleep_time = 0;
- +#if defined(CONFIG_ARCH_MSM_SCORPION)
- +#ifdef CONFIG_AXI_SCREEN_POLICY
- msm_pm_axi_init();
- +#endif
- +#endif
- register_reboot_notifier(&msm_reboot_notifier);
- + msm_pm_reset_vector = ioremap(0x0, PAGE_SIZE);
- - msm_pm_reset_vector = ioremap(0, PAGE_SIZE);
- if (msm_pm_reset_vector == NULL) {
- printk(KERN_ERR "msm_pm_init: failed to map reset vector\n");
- return -ENODEV;
- @@ -781,6 +898,12 @@ static int __init msm_pm_init(void)
- create_proc_read_entry("msm_pm_stats", S_IRUGO,
- NULL, msm_pm_read_proc, NULL);
- #endif
- +
- + if ((board_mfg_mode() == 0) || (board_mfg_mode() == 1)) {
- + disable_hlt();
- + schedule_delayed_work(&work_expire_boot_lock, BOOT_LOCK_TIMEOUT);
- + pr_info("Acquire 'boot-time' halt_lock\n");
- + }
- return 0;
- }
- diff --git a/arch/arm/mach-msm/smd.c b/arch/arm/mach-msm/smd.c
- index 861b7b9..4df7c09 100644
- --- a/arch/arm/mach-msm/smd.c
- +++ b/arch/arm/mach-msm/smd.c
- @@ -61,6 +61,11 @@ static struct shared_info smd_info = {
- .state = (unsigned) &dummy_state,
- };
- +#ifdef CONFIG_BUILD_CIQ
- +static int msm_smd_ciq_info;
- +module_param_named(ciq_info, msm_smd_ciq_info,
- + int, S_IRUGO | S_IWUSR | S_IWGRP);
- +#endif
- module_param_named(debug_mask, msm_smd_debug_mask,
- int, S_IRUGO | S_IWUSR | S_IWGRP);
- @@ -71,9 +76,18 @@ static unsigned last_heap_free = 0xffffffff;
- #define MSM_A2M_INT(n) (MSM_CSR_BASE + 0x400 + (n) * 4)
- +#if defined(CONFIG_ARCH_MSM7X30)
- +#define MSM_TRIG_A2M_INT(n) (writel(1 << n, MSM_GCC_BASE + 0x8))
- +#endif
- +
- static inline void notify_other_smsm(void)
- {
- +#if defined(CONFIG_ARCH_MSM7X30)
- + MSM_TRIG_A2M_INT(5);
- +#else
- writel(1, MSM_A2M_INT(5));
- +#endif
- +
- #ifdef CONFIG_QDSP6
- writel(1, MSM_A2M_INT(8));
- #endif
- @@ -81,12 +95,20 @@ static inline void notify_other_smsm(void)
- static inline void notify_modem_smd(void)
- {
- +#if defined(CONFIG_ARCH_MSM7X30)
- + MSM_TRIG_A2M_INT(0);
- +#else
- writel(1, MSM_A2M_INT(0));
- +#endif
- }
- static inline void notify_dsp_smd(void)
- {
- +#if defined(CONFIG_ARCH_MSM7X30)
- + MSM_TRIG_A2M_INT(8);
- +#else
- writel(1, MSM_A2M_INT(8));
- +#endif
- }
- static void smd_diag(void)
- @@ -100,17 +122,15 @@ static void smd_diag(void)
- }
- }
- -#if defined(CONFIG_PM)
- void msm_pm_flush_console(void);
- -#endif
- +
- /* call when SMSM_RESET flag is set in the A9's smsm_state */
- static void handle_modem_crash(void)
- {
- pr_err("ARM9 has CRASHED\n");
- smd_diag();
- -#if defined(CONFIG_PM)
- msm_pm_flush_console();
- -#endif
- +
- /* hard reboot if possible */
- if (msm_hw_reset_hook)
- msm_hw_reset_hook();
- @@ -151,6 +171,69 @@ static DEFINE_MUTEX(smd_creation_mutex);
- static int smd_initialized;
- +struct smd_alloc_elm {
- + char name[20];
- + uint32_t cid;
- + uint32_t ctype;
- + uint32_t ref_count;
- +};
- +
- +struct smd_half_channel {
- + unsigned state;
- + unsigned char fDSR;
- + unsigned char fCTS;
- + unsigned char fCD;
- + unsigned char fRI;
- + unsigned char fHEAD;
- + unsigned char fTAIL;
- + unsigned char fSTATE;
- + unsigned char fUNUSED;
- + unsigned tail;
- + unsigned head;
- +};
- +
- +struct smd_shared_v1 {
- + struct smd_half_channel ch0;
- + unsigned char data0[SMD_BUF_SIZE];
- + struct smd_half_channel ch1;
- + unsigned char data1[SMD_BUF_SIZE];
- +};
- +
- +struct smd_shared_v2 {
- + struct smd_half_channel ch0;
- + struct smd_half_channel ch1;
- +};
- +
- +struct smd_channel {
- + volatile struct smd_half_channel *send;
- + volatile struct smd_half_channel *recv;
- + unsigned char *send_data;
- + unsigned char *recv_data;
- +
- + unsigned fifo_mask;
- + unsigned fifo_size;
- + unsigned current_packet;
- + unsigned n;
- +
- + struct list_head ch_list;
- +
- + void *priv;
- + void (*notify)(void *priv, unsigned flags);
- +
- + int (*read)(struct smd_channel *ch, void *data, int len);
- + int (*write)(struct smd_channel *ch, const void *data, int len);
- + int (*read_avail)(struct smd_channel *ch);
- + int (*write_avail)(struct smd_channel *ch);
- +
- + void (*update_state)(struct smd_channel *ch);
- + unsigned last_state;
- + void (*notify_other_cpu)(void);
- + unsigned type;
- +
- + char name[32];
- + struct platform_device pdev;
- +};
- +
- LIST_HEAD(smd_ch_closed_list);
- LIST_HEAD(smd_ch_list_modem);
- LIST_HEAD(smd_ch_list_dsp);
- @@ -158,7 +241,7 @@ LIST_HEAD(smd_ch_list_dsp);
- static unsigned char smd_ch_allocated[64];
- static struct work_struct probe_work;
- -static int smd_alloc_channel(const char *name, uint32_t cid, uint32_t type);
- +static unsigned smd_alloc_channel(const char *name, uint32_t cid, uint32_t type);
- static void smd_channel_probe_worker(struct work_struct *work)
- {
- @@ -166,6 +249,7 @@ static void smd_channel_probe_worker(struct work_struct *work)
- unsigned ctype;
- unsigned type;
- unsigned n;
- + unsigned ret = -EAGAIN;
- shared = smem_find(ID_CH_ALLOC_TBL, sizeof(*shared) * 64);
- if (!shared) {
- @@ -191,8 +275,9 @@ static void smd_channel_probe_worker(struct work_struct *work)
- type = shared[n].ctype & SMD_TYPE_MASK;
- if ((type == SMD_TYPE_APPS_MODEM) ||
- (type == SMD_TYPE_APPS_DSP))
- - if (!smd_alloc_channel(shared[n].name, shared[n].cid, ctype))
- - smd_ch_allocated[n] = 1;
- + ret = smd_alloc_channel(shared[n].name, shared[n].cid, ctype);
- + if (!ret)
- + smd_ch_allocated[n] = 1;
- }
- }
- @@ -229,8 +314,9 @@ static int smd_packet_write_avail(struct smd_channel *ch)
- static int ch_is_open(struct smd_channel *ch)
- {
- - return (ch->recv->state == SMD_SS_OPENED) &&
- - (ch->send->state == SMD_SS_OPENED);
- + return (ch->recv->state == SMD_SS_OPENED ||
- + ch->recv->state == SMD_SS_FLUSHING)
- + && (ch->send->state == SMD_SS_OPENED);
- }
- /* provide a pointer and length to readable data in the fifo */
- @@ -272,6 +358,7 @@ static int ch_read(struct smd_channel *ch, void *_data, int len)
- if (n > len)
- n = len;
- +
- if (_data)
- memcpy(data, ptr, n);
- @@ -368,20 +455,31 @@ static void smd_state_change(struct smd_channel *ch,
- switch (next) {
- case SMD_SS_OPENING:
- - ch->recv->tail = 0;
- + if (ch->send->state == SMD_SS_CLOSING ||
- + ch->send->state == SMD_SS_CLOSED) {
- + ch->recv->tail = 0;
- + ch->send->head = 0;
- + ch_set_state(ch, SMD_SS_OPENING);
- + }
- + break;
- case SMD_SS_OPENED:
- - if (ch->send->state != SMD_SS_OPENED)
- + if (ch->send->state == SMD_SS_OPENING) {
- ch_set_state(ch, SMD_SS_OPENED);
- - ch->notify(ch->priv, SMD_EVENT_OPEN);
- + ch->notify(ch->priv, SMD_EVENT_OPEN);
- + }
- break;
- case SMD_SS_FLUSHING:
- case SMD_SS_RESET:
- /* we should force them to close? */
- - default:
- - ch->notify(ch->priv, SMD_EVENT_CLOSE);
- + break;
- + case SMD_SS_CLOSED:
- + if (ch->send->state == SMD_SS_OPENED) {
- + ch_set_state(ch, SMD_SS_CLOSING);
- + ch->notify(ch->priv, SMD_EVENT_CLOSE);
- + }
- + break;
- }
- }
- -
- static void handle_smd_irq(struct list_head *list, void (*notify)(void))
- {
- unsigned long flags;
- @@ -389,7 +487,11 @@ static void handle_smd_irq(struct list_head *list, void (*notify)(void))
- int do_notify = 0;
- unsigned ch_flags;
- unsigned tmp;
- -
- +#ifdef CONFIG_BUILD_CIQ
- + /* put here to make sure we got the disable/enable index */
- + if (!msm_smd_ciq_info)
- + msm_smd_ciq_info = (*(volatile uint32_t *)(MSM_SHARED_RAM_BASE + 0xFC11C));
- +#endif
- spin_lock_irqsave(&smd_lock, flags);
- list_for_each_entry(ch, list, ch_list) {
- ch_flags = 0;
- @@ -430,11 +532,13 @@ static irqreturn_t smd_modem_irq_handler(int irq, void *data)
- return IRQ_HANDLED;
- }
- +#if defined(CONFIG_QDSP6)
- static irqreturn_t smd_dsp_irq_handler(int irq, void *data)
- {
- handle_smd_irq(&smd_ch_list_dsp, notify_dsp_smd);
- return IRQ_HANDLED;
- }
- +#endif
- static void smd_fake_irq_handler(unsigned long arg)
- {
- @@ -514,6 +618,14 @@ static int smd_is_packet(int chn, unsigned type)
- return 0;
- /* older AMSS reports SMD_KIND_UNKNOWN always */
- +#if defined(CONFIG_ARCH_MSM7225)
- + if (chn == 1)
- + return 0;
- +#endif
- +#ifdef CONFIG_BUILD_CIQ
- + if (chn == 26)
- + return 0;
- +#endif
- if ((chn > 4) || (chn == 1))
- return 1;
- else
- @@ -552,7 +664,7 @@ static int smd_packet_write(smd_channel_t *ch, const void *_data, int len)
- {
- unsigned hdr[5];
- - if (len < 0)
- + if (len <= 0)
- return -EINVAL;
- if (smd_stream_write_avail(ch) < (len + SMD_HEADER_SIZE))
- @@ -611,10 +723,16 @@ static int smd_alloc_v2(struct smd_channel *ch)
- unsigned buffer_sz;
- shared2 = smem_alloc(SMEM_SMD_BASE_ID + ch->n, sizeof(*shared2));
- + if (!shared2) {
- + pr_err("smd_alloc_v2: cid %d does not exist\n", ch->n);
- + return -1;
- + }
- buffer = smem_item(SMEM_SMD_FIFO_BASE_ID + ch->n, &buffer_sz);
- - if (!buffer)
- + if (!buffer) {
- + pr_err("smd_alloc_v2: ch%d buffer allocate fail\n", ch->n);
- return -1;
- + }
- /* buffer must be a power-of-two size */
- if (buffer_sz & (buffer_sz - 1))
- @@ -634,7 +752,7 @@ static int smd_alloc_v1(struct smd_channel *ch)
- struct smd_shared_v1 *shared1;
- shared1 = smem_alloc(ID_SMD_CHANNELS + ch->n, sizeof(*shared1));
- if (!shared1) {
- - pr_err("smd_alloc_channel() cid %d does not exist\n", ch->n);
- + pr_err("smd_alloc_v1: cid %d does not exist\n", ch->n);
- return -1;
- }
- ch->send = &shared1->ch0;
- @@ -646,26 +764,26 @@ static int smd_alloc_v1(struct smd_channel *ch)
- }
- -static int smd_alloc_channel(const char *name, uint32_t cid, uint32_t type)
- +static unsigned smd_alloc_channel(const char *name, uint32_t cid, uint32_t type)
- {
- struct smd_channel *ch;
- ch = kzalloc(sizeof(struct smd_channel), GFP_KERNEL);
- if (ch == 0) {
- pr_err("smd_alloc_channel() out of memory\n");
- - return -1;
- + return -EAGAIN;
- }
- ch->n = cid;
- if (smd_alloc_v2(ch) && smd_alloc_v1(ch)) {
- kfree(ch);
- - return -1;
- + return -EAGAIN;
- }
- ch->fifo_mask = ch->fifo_size - 1;
- - ch->type = type;
- + ch->type = type & SMD_TYPE_MASK;
- - if ((type & SMD_TYPE_MASK) == SMD_TYPE_APPS_MODEM)
- + if (ch->type == SMD_TYPE_APPS_MODEM)
- ch->notify_other_cpu = notify_modem_smd;
- else
- ch->notify_other_cpu = notify_dsp_smd;
- @@ -684,14 +802,16 @@ static int smd_alloc_channel(const char *name, uint32_t cid, uint32_t type)
- ch->update_state = update_stream_state;
- }
- - if ((type & 0xff) == 0)
- + if (ch->type == SMD_TYPE_APPS_MODEM)
- memcpy(ch->name, "SMD_", 4);
- else
- memcpy(ch->name, "DSP_", 4);
- +
- memcpy(ch->name + 4, name, 20);
- ch->name[23] = 0;
- +
- ch->pdev.name = ch->name;
- - ch->pdev.id = -1;
- + ch->pdev.id = ch->type;
- pr_info("smd_alloc_channel() cid=%02d size=%05d '%s'\n",
- ch->n, ch->fifo_size, ch->name);
- @@ -737,8 +857,10 @@ int smd_open(const char *name, smd_channel_t **_ch,
- }
- ch = smd_get_channel(name);
- - if (!ch)
- + if (!ch){
- + pr_info("smd_open() fail, because radio no open %s smd chnnel\n",name);
- return -ENODEV;
- + }
- if (notify == 0)
- notify = do_nothing_notify;
- @@ -752,27 +874,14 @@ int smd_open(const char *name, smd_channel_t **_ch,
- spin_lock_irqsave(&smd_lock, flags);
- - if ((ch->type & SMD_TYPE_MASK) == SMD_TYPE_APPS_MODEM)
- + if (ch->type == SMD_APPS_MODEM)
- list_add(&ch->ch_list, &smd_ch_list_modem);
- else
- list_add(&ch->ch_list, &smd_ch_list_dsp);
- - /* If the remote side is CLOSING, we need to get it to
- - * move to OPENING (which we'll do by moving from CLOSED to
- - * OPENING) and then get it to move from OPENING to
- - * OPENED (by doing the same state change ourselves).
- - *
- - * Otherwise, it should be OPENING and we can move directly
- - * to OPENED so that it will follow.
- - */
- - if (ch->recv->state == SMD_SS_CLOSING) {
- - ch->send->head = 0;
- - ch_set_state(ch, SMD_SS_OPENING);
- - } else {
- - ch_set_state(ch, SMD_SS_OPENED);
- - }
- + smd_state_change(ch, ch->last_state, SMD_SS_OPENING);
- +
- spin_unlock_irqrestore(&smd_lock, flags);
- - smd_kick(ch);
- return 0;
- }
- @@ -786,6 +895,9 @@ int smd_close(smd_channel_t *ch)
- if (ch == 0)
- return -1;
- + ch->recv->head = 0;
- + ch->recv->tail = 0;
- +
- spin_lock_irqsave(&smd_lock, flags);
- ch->notify = do_nothing_notify;
- list_del(&ch->ch_list);
- @@ -839,6 +951,26 @@ int smd_wait_until_writable(smd_channel_t *ch, int bytes)
- return -1;
- }
- +int smd_wait_until_opened(smd_channel_t *ch, int timeout_us)
- +{
- +#define POLL_INTERVAL_USEC 200
- + int count = 0;
- +
- + if (timeout_us)
- + count = timeout_us / (POLL_INTERVAL_USEC + 1) + 1;
- +
- + do {
- + if (ch_is_open(ch))
- + return 0;
- + if (count--)
- + udelay(POLL_INTERVAL_USEC);
- + else
- + break;
- + } while (1);
- +
- + return -1;
- +}
- +
- int smd_cur_packet_size(smd_channel_t *ch)
- {
- return ch->current_packet;
- @@ -954,8 +1086,7 @@ uint32_t smsm_get_state(enum smsm_state_item item)
- return rv;
- }
- -#ifdef CONFIG_ARCH_MSM_SCORPION
- -
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- int smsm_set_sleep_duration(uint32_t delay)
- {
- struct msm_dem_slave_data *ptr;
- @@ -972,8 +1103,23 @@ int smsm_set_sleep_duration(uint32_t delay)
- return 0;
- }
- -#else
- +int smsm_set_sleep_limit(uint32_t sleep_limit)
- +{
- + struct msm_dem_slave_data *ptr;
- +
- + ptr = smem_find(SMEM_APPS_DEM_SLAVE_DATA, sizeof(*ptr));
- + if (ptr == NULL) {
- + pr_err("smsm_set_sleep_limit <SM NO APPS_DEM_SLAVE_DATA>\n");
- + return -EIO;
- + }
- + if (msm_smd_debug_mask & MSM_SMSM_DEBUG)
- + pr_info("smsm_set_sleep_limit %d -> %d\n",
- + ptr->resources_used, sleep_limit);
- + ptr->resources_used = sleep_limit;
- + return 0;
- +}
- +#else
- int smsm_set_sleep_duration(uint32_t delay)
- {
- uint32_t *ptr;
- @@ -990,6 +1136,10 @@ int smsm_set_sleep_duration(uint32_t delay)
- return 0;
- }
- +inline int smsm_set_sleep_limit(uint32_t sleep_limit)
- +{
- + return 0;
- +}
- #endif
- int smd_core_init(void)
- @@ -1030,12 +1180,16 @@ int smd_core_init(void)
- #if defined(CONFIG_QDSP6)
- r = request_irq(INT_ADSP_A11, smd_dsp_irq_handler,
- - IRQF_TRIGGER_RISING, "smd_dsp", 0);
- + IRQF_TRIGGER_RISING | IRQF_SHARED, "smd_dev", smd_dsp_irq_handler);
- if (r < 0) {
- free_irq(INT_A9_M2A_0, 0);
- free_irq(INT_A9_M2A_5, 0);
- return r;
- }
- + r = enable_irq_wake(INT_ADSP_A11);
- + if (r < 0)
- + printk(KERN_ERR "smd_core_init: "
- + "enable_irq_wake failed for INT_ADSP_A11\n");
- #endif
- /* check for any SMD channels that may already exist */
- @@ -1044,7 +1198,7 @@ int smd_core_init(void)
- /* indicate that we're up and running */
- smsm_change_state(SMSM_STATE_APPS,
- ~0, SMSM_INIT | SMSM_SMDINIT | SMSM_RPCINIT | SMSM_RUN);
- -#ifdef CONFIG_ARCH_MSM_SCORPION
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- smsm_change_state(SMSM_STATE_APPS_DEM, ~0, 0);
- #endif
- diff --git a/arch/arm/mach-msm/smd_debug.c b/arch/arm/mach-msm/smd_debug.c
- index e2bfa7e..9246a45 100644
- --- a/arch/arm/mach-msm/smd_debug.c
- +++ b/arch/arm/mach-msm/smd_debug.c
- @@ -16,10 +16,105 @@
- #include <linux/debugfs.h>
- #include <linux/list.h>
- +#include <linux/io.h>
- +#include <linux/earlysuspend.h>
- +#include <linux/rtc.h>
- +#include <linux/suspend.h>
- #include <mach/msm_iomap.h>
- #include "smd_private.h"
- +#include "smd_debug.h"
- +
- +
- +#if CONFIG_SMD_OFFSET_TCXO_STAT
- +enum {
- + F_SCREEN_OFF = 0,
- + F_SUSPEND,
- + F_RESUME,
- + F_SCREEN_ON,
- +};
- +
- +struct smem_sleep_stat {
- + uint32_t tcxo_time;
- + uint32_t tcxo_cnt;
- + uint32_t suspend_tcxo_time;
- + uint32_t suspend_tcxo_cnt;
- + uint32_t garbage_pkt_cnt;
- + uint32_t zone_based_reg_cnt;
- + uint32_t idle_hand_off_cnt;
- + uint32_t mo_2g_probe_cnt;
- + uint32_t mo_3g_probe_cnt;
- + uint32_t reserved[5];
- +};
- +static struct smem_sleep_stat *sleep_stat;
- +static struct smem_sleep_stat *get_smem_sleep_stat(void)
- +{
- + return (struct smem_sleep_stat *)
- + (MSM_SHARED_RAM_BASE + CONFIG_SMD_OFFSET_TCXO_STAT);
- +}
- +
- +static void print_sleep_stat(int flag)
- +{
- + struct timespec ts;
- + struct rtc_time tm;
- + getnstimeofday(&ts);
- + rtc_time_to_tm(ts.tv_sec, &tm);
- +
- + if (!sleep_stat)
- + return;
- +
- + pr_info("sleep_stat.%d: %ds %d %ds %d - "
- + "%d %d %d - %d %d - %d %d %d %d %d"
- + "(%d-%02d-%02d %02d:%02d:%02d.%09lu UTC)\n",
- + flag, sleep_stat->tcxo_time, sleep_stat->tcxo_cnt,
- + sleep_stat->suspend_tcxo_time, sleep_stat->suspend_tcxo_cnt,
- + sleep_stat->garbage_pkt_cnt, sleep_stat->zone_based_reg_cnt,
- + sleep_stat->idle_hand_off_cnt, sleep_stat->mo_2g_probe_cnt,
- + sleep_stat->mo_3g_probe_cnt, sleep_stat->reserved[0],
- + sleep_stat->reserved[1], sleep_stat->reserved[2],
- + sleep_stat->reserved[3], sleep_stat->reserved[4],
- + tm.tm_year + 1900, tm.tm_mon + 1, tm.tm_mday,
- + tm.tm_hour, tm.tm_min, tm.tm_sec, ts.tv_nsec);
- +
- +}
- +
- +static int sleep_stat_suspend_notifier(struct notifier_block *nb,
- + unsigned long event, void *dummy)
- +{
- + switch (event) {
- + /* enter suspend */
- + case PM_SUSPEND_PREPARE:
- + print_sleep_stat(F_SUSPEND);
- + return NOTIFY_OK;
- + /* exit suspend */
- + case PM_POST_SUSPEND:
- + print_sleep_stat(F_RESUME);
- + return NOTIFY_OK;
- + default:
- + return NOTIFY_DONE;
- + }
- +}
- +
- +static struct notifier_block sleep_stat_notif_block = {
- + .notifier_call = sleep_stat_suspend_notifier,
- +};
- +
- +static void sleep_stat_early_suspend(struct early_suspend *handler)
- +{
- + print_sleep_stat(F_SCREEN_OFF);
- +}
- +
- +static void sleep_stat_late_resume(struct early_suspend *handler)
- +{
- + print_sleep_stat(F_SCREEN_ON);
- +}
- +
- +static struct early_suspend sleep_stat_screen_hdl = {
- + .suspend = sleep_stat_early_suspend,
- + .resume = sleep_stat_late_resume,
- +};
- +#endif
- #if defined(CONFIG_DEBUG_FS)
- @@ -103,6 +198,29 @@ static int debug_read_stat(char *buf, int max)
- msg[SZ_DIAG_ERR_MSG - 1] = 0;
- i += scnprintf(buf + i, max - i, "diag: '%s'\n", msg);
- }
- +
- +#if CONFIG_SMD_OFFSET_TCXO_STAT
- + if (sleep_stat) {
- + i += scnprintf(buf + i, max - i,
- + "tcxo_time: 0x%x (%ds) tcxo_cnt: %d\n"
- + "suspend_tcxo_time: 0x%x (%ds) suspend_tcxo_cnt: %d\n"
- + "garbage_pkt_cnt: %d "
- + "zone_based_reg_cnt: %d "
- + "idle_hand_off_cnt: %d "
- + "mo_2g_probe_cnt: %d "
- + "mo_3g_probe_cnt: %d\n",
- + sleep_stat->tcxo_time, sleep_stat->tcxo_time >> 15,
- + sleep_stat->tcxo_cnt, sleep_stat->suspend_tcxo_time,
- + sleep_stat->suspend_tcxo_time >> 15,
- + sleep_stat->suspend_tcxo_cnt,
- + sleep_stat->garbage_pkt_cnt,
- + sleep_stat->zone_based_reg_cnt,
- + sleep_stat->idle_hand_off_cnt,
- + sleep_stat->mo_2g_probe_cnt,
- + sleep_stat->mo_3g_probe_cnt);
- + }
- +#endif
- +
- return i;
- }
- @@ -176,6 +294,10 @@ static int debug_read_alloc_tbl(char *buf, int max)
- int n, i = 0;
- shared = smem_find(ID_CH_ALLOC_TBL, sizeof(*shared) * 64);
- + if (!shared) {
- + pr_err("smd: cannot find allocation table\n");
- + return 0;
- + }
- for (n = 0; n < 64; n++) {
- if (shared[n].ref_count == 0)
- @@ -221,13 +343,13 @@ static void debug_create(const char *name, mode_t mode,
- debugfs_create_file(name, mode, dent, fill, &debug_ops);
- }
- -static int smd_debugfs_init(void)
- +static int __init smd_debugfs_init(void)
- {
- struct dentry *dent;
- dent = debugfs_create_dir("smd", 0);
- if (IS_ERR(dent))
- - return PTR_ERR(dent);
- + return -1;
- debug_create("ch", 0444, dent, debug_read_ch);
- debug_create("stat", 0444, dent, debug_read_stat);
- @@ -235,7 +357,13 @@ static int smd_debugfs_init(void)
- debug_create("version", 0444, dent, debug_read_version);
- debug_create("tbl", 0444, dent, debug_read_alloc_tbl);
- debug_create("build", 0444, dent, debug_read_build_id);
- -
- +#if CONFIG_SMD_OFFSET_TCXO_STAT
- + sleep_stat = get_smem_sleep_stat();
- + register_early_suspend(&sleep_stat_screen_hdl);
- + register_pm_notifier(&sleep_stat_notif_block);
- +#else
- + pr_info("No sleep statistics\n");
- +#endif
- return 0;
- }
- @@ -265,30 +393,33 @@ struct tramp_gpio_smem {
- };
- -void smsm_print_sleep_info(void)
- +void smsm_print_sleep_info(unsigned wakeup_reason_only)
- {
- unsigned long flags;
- uint32_t *ptr;
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- + struct msm_dem_slave_data *smd_int_info;
- +#else
- struct tramp_gpio_smem *gpio;
- struct smsm_interrupt_info *int_info;
- #endif
- spin_lock_irqsave(&smem_lock, flags);
- - ptr = smem_alloc(SMEM_SMSM_SLEEP_DELAY, sizeof(*ptr));
- - if (ptr)
- - pr_info("SMEM_SMSM_SLEEP_DELAY: %x\n", *ptr);
- -
- - ptr = smem_alloc(SMEM_SMSM_LIMIT_SLEEP, sizeof(*ptr));
- - if (ptr)
- - pr_info("SMEM_SMSM_LIMIT_SLEEP: %x\n", *ptr);
- + if (!wakeup_reason_only) {
- + ptr = smem_alloc(SMEM_SMSM_SLEEP_DELAY, sizeof(*ptr));
- + if (ptr)
- + pr_info("SMEM_SMSM_SLEEP_DELAY: %x\n", *ptr);
- - ptr = smem_alloc(SMEM_SLEEP_POWER_COLLAPSE_DISABLED, sizeof(*ptr));
- - if (ptr)
- - pr_info("SMEM_SLEEP_POWER_COLLAPSE_DISABLED: %x\n", *ptr);
- + ptr = smem_alloc(SMEM_SMSM_LIMIT_SLEEP, sizeof(*ptr));
- + if (ptr)
- + pr_info("SMEM_SMSM_LIMIT_SLEEP: %x\n", *ptr);
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- + ptr = smem_alloc(SMEM_SLEEP_POWER_COLLAPSE_DISABLED, sizeof(*ptr));
- + if (ptr)
- + pr_info("SMEM_SLEEP_POWER_COLLAPSE_DISABLED: %x\n", *ptr);
- + }
- +#if !defined(CONFIG_MSM_N_WAY_SMD)
- int_info = smem_alloc(SMEM_SMSM_INT_INFO, sizeof(*int_info));
- if (int_info)
- pr_info("SMEM_SMSM_INT_INFO %x %x %x\n",
- @@ -299,17 +430,32 @@ void smsm_print_sleep_info(void)
- gpio = smem_alloc(SMEM_GPIO_INT, sizeof(*gpio));
- if (gpio) {
- int i;
- - for (i = 0; i < NUM_GPIO_INT_REGISTERS; i++)
- - pr_info("SMEM_GPIO_INT: %d: e %x d %x p %x\n",
- - i, gpio->enabled[i], gpio->detection[i],
- - gpio->polarity[i]);
- -
- + if (!wakeup_reason_only) {
- + for (i = 0; i < NUM_GPIO_INT_REGISTERS; i++)
- + pr_info("SMEM_GPIO_INT: %d: e %x d %x p %x\n",
- + i, gpio->enabled[i], gpio->detection[i],
- + gpio->polarity[i]);
- + }
- for (i = 0; i < GPIO_SMEM_NUM_GROUPS; i++)
- pr_info("SMEM_GPIO_INT: %d: f %d: %d %d...\n",
- i, gpio->num_fired[i], gpio->fired[i][0],
- gpio->fired[i][1]);
- }
- #else
- + smd_int_info = smem_find(SMEM_APPS_DEM_SLAVE_DATA, sizeof(*smd_int_info));
- + if (smd_int_info) {
- + pr_info("SMEM_APPS_DEM_SLAVE_DATA: %ds %x %x %x %x %x %x %x %s %x\n",
- + smd_int_info->sleep_time / 32768,
- + smd_int_info->interrupt_mask,
- + smd_int_info->resources_used,
- + smd_int_info->reserved1,
- + smd_int_info->wakeup_reason,
- + smd_int_info->pending_interrupts,
- + smd_int_info->rpc_prog,
- + smd_int_info->rpc_proc,
- + smd_int_info->smd_port_name,
- + smd_int_info->reserved2);
- + }
- #endif
- spin_unlock_irqrestore(&smem_lock, flags);
- }
- diff --git a/arch/arm/mach-msm/smd_private.h b/arch/arm/mach-msm/smd_private.h
- index 2da758e..7094783 100644
- --- a/arch/arm/mach-msm/smd_private.h
- +++ b/arch/arm/mach-msm/smd_private.h
- @@ -16,28 +16,21 @@
- #ifndef _ARCH_ARM_MACH_MSM_MSM_SMD_PRIVATE_H_
- #define _ARCH_ARM_MACH_MSM_MSM_SMD_PRIVATE_H_
- -#include <linux/platform_device.h>
- -#include <linux/spinlock.h>
- -#include <linux/list.h>
- -
- -struct smem_heap_info
- -{
- +struct smem_heap_info {
- unsigned initialized;
- unsigned free_offset;
- unsigned heap_remaining;
- unsigned reserved;
- };
- -struct smem_heap_entry
- -{
- +struct smem_heap_entry {
- unsigned allocated;
- unsigned offset;
- unsigned size;
- unsigned reserved;
- };
- -struct smem_proc_comm
- -{
- +struct smem_proc_comm {
- unsigned command;
- unsigned status;
- unsigned data1;
- @@ -54,8 +47,7 @@ struct smem_proc_comm
- #define VERSION_APPS 8
- #define VERSION_MODEM 9
- -struct smem_shared
- -{
- +struct smem_shared {
- struct smem_proc_comm proc_comm[4];
- unsigned version[32];
- struct smem_heap_info heap_info;
- @@ -65,14 +57,7 @@ struct smem_shared
- #define SMSM_V1_SIZE (sizeof(unsigned) * 8)
- #define SMSM_V2_SIZE (sizeof(unsigned) * 4)
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- -struct smsm_interrupt_info
- -{
- - uint32_t interrupt_mask;
- - uint32_t pending_interrupts;
- - uint32_t wakeup_reason;
- -};
- -#else
- +#if defined(CONFIG_MSM_N_WAY_SMD)
- #define DEM_MAX_PORT_NAME_LEN (20)
- struct msm_dem_slave_data {
- uint32_t sleep_time;
- @@ -87,6 +72,21 @@ struct msm_dem_slave_data {
- char smd_port_name[DEM_MAX_PORT_NAME_LEN];
- uint32_t reserved2;
- };
- +#else
- +#define SMSM_MAX_PORT_NAME_LEN 20
- +struct smsm_interrupt_info {
- + uint32_t interrupt_mask;
- + uint32_t pending_interrupts;
- + uint32_t wakeup_reason;
- + uint32_t aArm_rpc_prog;
- + uint32_t aArm_rpc_proc;
- + char aArm_smd_port_name[SMSM_MAX_PORT_NAME_LEN];
- + /* If the wakeup reason is GPIO then send the gpio info */
- + uint32_t aArm_gpio_info;
- + /*uint32_t interrupt_mask;
- + uint32_t pending_interrupts;
- + uint32_t wakeup_reason;*/
- +};
- #endif
- #define SZ_DIAG_ERR_MSG 0xC8
- @@ -96,7 +96,10 @@ struct msm_dem_slave_data {
- #define ID_CH_ALLOC_TBL SMEM_CHANNEL_ALLOC_TBL
- #define SMSM_INIT 0x00000001
- +#define SMSM_OSENTERED 0x00000002
- +#define SMSM_SMDWAIT 0x00000004
- #define SMSM_SMDINIT 0x00000008
- +#define SMSM_RPCWAIT 0x00000010
- #define SMSM_RPCINIT 0x00000020
- #define SMSM_RESET 0x00000040
- #define SMSM_RSA 0x00000080
- @@ -108,6 +111,7 @@ struct msm_dem_slave_data {
- #define SMSM_WFPI 0x00002000
- #define SMSM_SLEEP 0x00004000
- #define SMSM_SLEEPEXIT 0x00008000
- +#define SMSM_OEMSBL_RELEASE 0x00010000
- #define SMSM_APPS_REBOOT 0x00020000
- #define SMSM_SYSTEM_POWER_DOWN 0x00040000
- #define SMSM_SYSTEM_REBOOT 0x00080000
- @@ -128,13 +132,7 @@ struct msm_dem_slave_data {
- #define SMSM_WKUP_REASON_ALARM 0x00000010
- #define SMSM_WKUP_REASON_RESET 0x00000020
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- -enum smsm_state_item {
- - SMSM_STATE_APPS = 1,
- - SMSM_STATE_MODEM = 3,
- - SMSM_STATE_COUNT,
- -};
- -#else
- +//#if defined(CONFIG_MSM_N_WAY_SMD)
- enum smsm_state_item {
- SMSM_STATE_APPS,
- SMSM_STATE_MODEM,
- @@ -146,18 +144,24 @@ enum smsm_state_item {
- SMSM_STATE_TIME_MASTER_DEM,
- SMSM_STATE_COUNT,
- };
- -#endif
- +//#else
- +//enum smsm_state_item {
- +// SMSM_STATE_APPS = 1,
- +// SMSM_STATE_MODEM = 3,
- +// SMSM_STATE_COUNT,
- +//};
- +//#endif
- void *smem_alloc(unsigned id, unsigned size);
- int smsm_change_state(enum smsm_state_item item, uint32_t clear_mask, uint32_t set_mask);
- uint32_t smsm_get_state(enum smsm_state_item item);
- int smsm_set_sleep_duration(uint32_t delay);
- -void smsm_print_sleep_info(void);
- +int smsm_set_sleep_limit(uint32_t sleep_limit);
- +void smsm_print_sleep_info(unsigned wakeup_reason_only);
- #define SMEM_NUM_SMD_CHANNELS 64
- -typedef enum
- -{
- +typedef enum {
- /* fixed items */
- SMEM_PROC_COMM = 0,
- SMEM_HEAP_INFO,
- @@ -213,6 +217,7 @@ typedef enum
- SMEM_ID_VENDOR1,
- SMEM_ID_VENDOR2,
- SMEM_HW_SW_BUILD_ID,
- +//#if defined(CONFIG_MSM_N_WAY_SMD)
- SMEM_SMD_BLOCK_PORT_BASE_ID,
- SMEM_SMD_BLOCK_PORT_PROC0_HEAP = SMEM_SMD_BLOCK_PORT_BASE_ID + SMEM_NUM_SMD_CHANNELS,
- SMEM_SMD_BLOCK_PORT_PROC1_HEAP = SMEM_SMD_BLOCK_PORT_PROC0_HEAP + SMEM_NUM_SMD_CHANNELS,
- @@ -232,7 +237,16 @@ typedef enum
- SMEM_SMEM_LOG_POWER_WRAP,
- SMEM_SMEM_LOG_POWER_EVENTS,
- SMEM_ERR_CRASH_LOG,
- - SMEM_ERR_F3_TRACE_LOG,
- + SMEM_ERR_F3_TRACE_LOG,
- + SMEM_SMD_BRIDGE_ALLOC_TABLE,
- + SMEM_SMDLITE_TABLE,
- + SMEM_SD_IMG_UPGRADE_STATUS,
- + SMEM_SEFS_INFO,
- +//#else
- +// SMEM_SMD_FIFO_BASE_ID,
- +// SMEM_SMEM_LAST = SMEM_SMD_FIFO_BASE_ID + SMEM_NUM_SMD_CHANNELS,
- +//#endif
- +
- SMEM_NUM_ITEMS,
- } smem_mem_type;
- @@ -250,69 +264,6 @@ typedef enum
- #define SMD_HEADER_SIZE 20
- -struct smd_alloc_elm {
- - char name[20];
- - uint32_t cid;
- - uint32_t ctype;
- - uint32_t ref_count;
- -};
- -
- -struct smd_half_channel {
- - unsigned state;
- - unsigned char fDSR;
- - unsigned char fCTS;
- - unsigned char fCD;
- - unsigned char fRI;
- - unsigned char fHEAD;
- - unsigned char fTAIL;
- - unsigned char fSTATE;
- - unsigned char fUNUSED;
- - unsigned tail;
- - unsigned head;
- -} __attribute__(( aligned(4), packed ));
- -
- -struct smd_shared_v1 {
- - struct smd_half_channel ch0;
- - unsigned char data0[SMD_BUF_SIZE];
- - struct smd_half_channel ch1;
- - unsigned char data1[SMD_BUF_SIZE];
- -};
- -
- -struct smd_shared_v2 {
- - struct smd_half_channel ch0;
- - struct smd_half_channel ch1;
- -};
- -
- -struct smd_channel {
- - volatile struct smd_half_channel *send;
- - volatile struct smd_half_channel *recv;
- - unsigned char *send_data;
- - unsigned char *recv_data;
- -
- - unsigned fifo_mask;
- - unsigned fifo_size;
- - unsigned current_packet;
- - unsigned n;
- -
- - struct list_head ch_list;
- -
- - void *priv;
- - void (*notify)(void *priv, unsigned flags);
- -
- - int (*read)(struct smd_channel *ch, void *data, int len);
- - int (*write)(struct smd_channel *ch, const void *data, int len);
- - int (*read_avail)(struct smd_channel *ch);
- - int (*write_avail)(struct smd_channel *ch);
- -
- - void (*update_state)(struct smd_channel *ch);
- - unsigned last_state;
- - void (*notify_other_cpu)(void);
- - unsigned type;
- -
- - char name[32];
- - struct platform_device pdev;
- -};
- -
- #define SMD_TYPE_MASK 0x0FF
- #define SMD_TYPE_APPS_MODEM 0x000
- #define SMD_TYPE_APPS_DSP 0x001
- @@ -323,13 +274,6 @@ struct smd_channel {
- #define SMD_KIND_STREAM 0x100
- #define SMD_KIND_PACKET 0x200
- -extern struct list_head smd_ch_closed_list;
- -extern struct list_head smd_ch_list_modem;
- -extern struct list_head smd_ch_list_dsp;
- -
- -extern spinlock_t smd_lock;
- -extern spinlock_t smem_lock;
- -
- void *smem_find(unsigned id, unsigned size);
- void *smem_item(unsigned id, unsigned *size);
- uint32_t raw_smsm_get_state(enum smsm_state_item item);
- diff --git a/arch/arm/mach-msm/smd_qmi.c b/arch/arm/mach-msm/smd_qmi.c
- index 50411df..3d47fbc 100644
- --- a/arch/arm/mach-msm/smd_qmi.c
- +++ b/arch/arm/mach-msm/smd_qmi.c
- @@ -324,6 +324,18 @@ static void qmi_process_unicast_wds_msg(struct qmi_ctxt *ctxt,
- if (qmi_get_status(msg, &err)) {
- printk(KERN_ERR
- "qmi: wds: network start failed (%04x)\n", err);
- + if (msg->size == 0x000c && (msg->tlv)[10] == 0x0b) {
- + printk(KERN_ERR
- + "qmi: wds: pdp activation collided with CCFC\n");
- + ctxt->state = STATE_OFFLINE;
- + ctxt->state_dirty = 1;
- + }
- + if (msg->size == 0x000c && (msg->tlv)[10] == 0x0c) {
- + printk(KERN_ERR
- + "qmi: wds: pdp activation failed. Cause: Operator-determined barring\n");
- + ctxt->state = STATE_OFFLINE;
- + ctxt->state_dirty = 1;
- + }
- } else if (qmi_get_tlv(msg, 0x01, sizeof(ctxt->wds_handle), &ctxt->wds_handle)) {
- printk(KERN_INFO
- "qmi: wds no handle?\n");
- @@ -648,7 +660,7 @@ static int qmi_print_state(struct qmi_ctxt *ctxt, char *buf, int max)
- }
- i = scnprintf(buf, max, "STATE=%s\n", statename);
- - i += scnprintf(buf + i, max - i, "CID=%d\n",ctxt->wds_client_id);
- + i += scnprintf(buf + i, max - i, "CID=%d\n",ctxt->misc.minor);
- if (ctxt->state != STATE_ONLINE){
- return i;
- diff --git a/arch/arm/mach-msm/smd_rpcrouter.c b/arch/arm/mach-msm/smd_rpcrouter.c
- index d2f66c1..ba180dc 100644
- --- a/arch/arm/mach-msm/smd_rpcrouter.c
- +++ b/arch/arm/mach-msm/smd_rpcrouter.c
- @@ -137,13 +137,7 @@ static int rpcrouter_send_control_msg(union rr_control_msg *msg)
- unsigned long flags;
- int need;
- - RR("send control message cmd=%d srv.cmd=%d prog=%08x:%x id=%d:%08x\n", msg->cmd, msg->srv.cmd, msg->srv.prog, msg->srv.vers, msg->srv.pid, msg->srv.cid);
- -
- - if (!(msg->cmd == RPCROUTER_CTRL_CMD_HELLO
- -#if defined(CONFIG_MSM_AMSS_VERSION_WINCE)
- - || msg->cmd == RPCROUTER_CTRL_CMD_BYE
- -#endif
- - ) && !initialized) {
- + if (!(msg->cmd == RPCROUTER_CTRL_CMD_HELLO) && !initialized) {
- printk(KERN_ERR "rpcrouter_send_control_msg(): Warning, "
- "router not initialized\n");
- return -EINVAL;
- @@ -400,10 +394,9 @@ static int process_control_msg(union rr_control_msg *msg, int len)
- RR("x HELLO\n");
- memset(&ctl, 0, sizeof(ctl));
- -#if !defined(CONFIG_MSM_AMSS_VERSION_WINCE)
- ctl.cmd = RPCROUTER_CTRL_CMD_HELLO;
- rpcrouter_send_control_msg(&ctl);
- -#endif
- +
- initialized = 1;
- /* Send list of servers one at a time */
- @@ -1248,12 +1241,15 @@ int msm_rpc_unregister_server(struct msm_rpc_endpoint *ept,
- return 0;
- }
- +int msm_rpcrouter_close(void)
- +{
- + return smd_close(smd_channel);
- +}
- +
- static int msm_rpcrouter_probe(struct platform_device *pdev)
- {
- int rc;
- - union rr_control_msg msg = { 0 };
- - pr_info("RPC Probe\n");
- -
- +
- /* Initialize what we need to start processing */
- INIT_LIST_HEAD(&local_endpoints);
- INIT_LIST_HEAD(&remote_endpoints);
- @@ -1270,8 +1266,6 @@ static int msm_rpcrouter_probe(struct platform_device *pdev)
- if (rc < 0)
- goto fail_destroy_workqueue;
- - pr_info("RPC Init done\n");
- -
- /* Open up SMD channel 2 */
- initialized = 0;
- rc = smd_open("SMD_RPCCALL", &smd_channel, NULL, rpcrouter_smdnotify);
- @@ -1279,22 +1273,6 @@ static int msm_rpcrouter_probe(struct platform_device *pdev)
- goto fail_remove_devices;
- queue_work(rpcrouter_workqueue, &work_read_data);
- -
- -#if defined(CONFIG_MSM_AMSS_VERSION_WINCE)
- - msg.cmd = RPCROUTER_CTRL_CMD_BYE;
- - rpcrouter_send_control_msg(&msg);
- - msleep(50);
- -
- - /* wince rpc init */
- - msg.cmd = RPCROUTER_CTRL_CMD_HELLO;
- - rpcrouter_send_control_msg(&msg);
- - msleep(50);
- -
- -
- - process_control_msg(&msg, sizeof(msg));
- - msleep(100);
- -#endif
- -
- return 0;
- fail_remove_devices:
- diff --git a/arch/arm/mach-msm/smd_rpcrouter.h b/arch/arm/mach-msm/smd_rpcrouter.h
- index a7416a2..aaf49f7 100644
- --- a/arch/arm/mach-msm/smd_rpcrouter.h
- +++ b/arch/arm/mach-msm/smd_rpcrouter.h
- @@ -32,6 +32,9 @@
- #define RPCROUTER_VERSION 1
- #define RPCROUTER_PROCESSORS_MAX 4
- #define RPCROUTER_MSGSIZE_MAX 512
- +#if defined(CONFIG_ARCH_MSM7X30)
- +#define RPCROUTER_PEND_REPLIES_MAX 32
- +#endif
- #define RPCROUTER_CLIENT_BCAST_ID 0xffffffff
- #define RPCROUTER_ROUTER_ADDRESS 0xfffffffe
- @@ -129,12 +132,26 @@ struct rr_remote_endpoint {
- uint32_t cid;
- int tx_quota_cntr;
- +#if defined(CONFIG_ARCH_MSM7X30)
- + int quota_restart_state;
- +#endif
- spinlock_t quota_lock;
- wait_queue_head_t quota_wait;
- struct list_head list;
- };
- +#if defined(CONFIG_ARCH_MSM7X30)
- +struct msm_rpc_reply {
- + struct list_head list;
- + uint32_t pid;
- + uint32_t cid;
- + uint32_t prog; /* be32 */
- + uint32_t vers; /* be32 */
- + uint32_t xid; /* be32 */
- +};
- +#endif
- +
- struct msm_rpc_endpoint {
- struct list_head list;
- @@ -147,7 +164,12 @@ struct msm_rpc_endpoint {
- struct wake_lock read_q_wake_lock;
- wait_queue_head_t wait_q;
- unsigned flags;
- -
- +#if defined(CONFIG_ARCH_MSM7X30)
- + /* restart handling */
- + int restart_state;
- + spinlock_t restart_lock;
- + wait_queue_head_t restart_wait;
- +#endif
- /* endpoint address */
- uint32_t pid;
- uint32_t cid;
- @@ -171,6 +193,14 @@ struct msm_rpc_endpoint {
- uint32_t reply_xid; /* be32 */
- uint32_t next_pm; /* Pacmark sequence */
- +#if defined(CONFIG_ARCH_MSM7X30)
- + /* reply queue for inbound messages */
- + struct list_head reply_pend_q;
- + struct list_head reply_avail_q;
- + spinlock_t reply_q_lock;
- + uint32_t reply_cnt;
- + struct wake_lock reply_q_wake_lock;
- +#endif
- /* device node if this endpoint is accessed via userspace */
- dev_t dev;
- };
- @@ -181,6 +211,7 @@ int __msm_rpc_read(struct msm_rpc_endpoint *ept,
- struct rr_fragment **frag,
- unsigned len, long timeout);
- +int msm_rpcrouter_close(void);
- struct msm_rpc_endpoint *msm_rpcrouter_create_local_endpoint(dev_t dev);
- int msm_rpcrouter_destroy_local_endpoint(struct msm_rpc_endpoint *ept);
- @@ -190,6 +221,18 @@ int msm_rpcrouter_create_server_pdev(struct rr_server *server);
- int msm_rpcrouter_init_devices(void);
- void msm_rpcrouter_exit_devices(void);
- +#if defined(CONFIG_ARCH_MSM7X30)
- +void get_requesting_client(struct msm_rpc_endpoint *ept, uint32_t xid,
- + struct msm_rpc_client_info *clnt_info);
- +#endif
- +
- extern dev_t msm_rpcrouter_devno;
- extern struct class *msm_rpcrouter_class;
- +
- +void xdr_init(struct msm_rpc_xdr *xdr);
- +void xdr_init_input(struct msm_rpc_xdr *xdr, void *buf, uint32_t size);
- +void xdr_init_output(struct msm_rpc_xdr *xdr, void *buf, uint32_t size);
- +void xdr_clean_input(struct msm_rpc_xdr *xdr);
- +void xdr_clean_output(struct msm_rpc_xdr *xdr);
- +uint32_t xdr_read_avail(struct msm_rpc_xdr *xdr);
- #endif
- diff --git a/arch/arm/mach-msm/smd_rpcrouter_device.c b/arch/arm/mach-msm/smd_rpcrouter_device.c
- index 16604ba..bdea3d0 100644
- --- a/arch/arm/mach-msm/smd_rpcrouter_device.c
- +++ b/arch/arm/mach-msm/smd_rpcrouter_device.c
- @@ -246,7 +246,7 @@ int msm_rpcrouter_create_server_cdev(struct rr_server *server)
- return -ENOBUFS;
- }
- -#if CONFIG_MSM_AMSS_VERSION >= 6350 || defined(CONFIG_ARCH_QSD8X50)
- +#if CONFIG_MSM_AMSS_VERSION >= 6350 || defined(CONFIG_ARCH_QSD8X50) || defined(CONFIG_ARCH_MSM7X30)
- /* Servers with bit 31 set are remote msm servers with hashkey version.
- * Servers with bit 31 not set are remote msm servers with
- * backwards compatible version type in which case the minor number
- @@ -296,7 +296,7 @@ int msm_rpcrouter_create_server_pdev(struct rr_server *server)
- {
- sprintf(server->pdev_name, "rs%.8x:%.8x",
- server->prog,
- -#if CONFIG_MSM_AMSS_VERSION >= 6350 || defined(CONFIG_ARCH_QSD8X50)
- +#if CONFIG_MSM_AMSS_VERSION >= 6350 || defined(CONFIG_ARCH_QSD8X50) || defined(CONFIG_ARCH_MSM7X30)
- (server->vers & RPC_VERSION_MODE_MASK) ? server->vers :
- (server->vers & RPC_VERSION_MAJOR_MASK));
- #else
- diff --git a/arch/arm/mach-msm/smd_tty.c b/arch/arm/mach-msm/smd_tty.c
- index ef12bca..33af0d4 100644
- --- a/arch/arm/mach-msm/smd_tty.c
- +++ b/arch/arm/mach-msm/smd_tty.c
- @@ -36,81 +36,111 @@ struct smd_tty_info {
- struct tty_struct *tty;
- struct wake_lock wake_lock;
- int open_count;
- + struct work_struct tty_work;
- };
- static struct smd_tty_info smd_tty[MAX_SMD_TTYS];
- +static struct workqueue_struct *smd_tty_wq;
- -static const struct smd_tty_channel_desc smd_default_tty_channels[] = {
- - { .id = 0, .name = "SMD_DS" },
- -#if defined(CONFIG_MSM_AMSS_VERSION_WINCE)
- - { .id = 1, .name = "SMD_DATA1" },
- -#endif
- - { .id = 27, .name = "SMD_GPSNMEA" },
- -};
- -
- -static const struct smd_tty_channel_desc *smd_tty_channels =
- - smd_default_tty_channels;
- -static int smd_tty_channels_len = ARRAY_SIZE(smd_default_tty_channels);
- -
- -int smd_set_channel_list(const struct smd_tty_channel_desc *channels, int len)
- -{
- - smd_tty_channels = channels;
- - smd_tty_channels_len = len;
- - return 0;
- -}
- -
- -static void smd_tty_notify(void *priv, unsigned event)
- +static void smd_tty_work_func(struct work_struct *work)
- {
- unsigned char *ptr;
- int avail;
- - struct smd_tty_info *info = priv;
- +
- + struct smd_tty_info *info = container_of(work,
- + struct smd_tty_info,
- + tty_work);
- struct tty_struct *tty = info->tty;
- if (!tty)
- return;
- - if (event != SMD_EVENT_DATA)
- - return;
- +
- + mutex_lock(&smd_tty_lock);
- for (;;) {
- - if (test_bit(TTY_THROTTLED, &tty->flags)) break;
- - avail = smd_read_avail(info->ch);
- - if (avail == 0) break;
- + if (test_bit(TTY_THROTTLED, &tty->flags))
- + break;
- - avail = tty_prepare_flip_string(tty, &ptr, avail);
- + if (info->ch == 0) {
- + printk(KERN_ERR "smd_tty_work_func: info->ch null\n");
- + break;
- + }
- - if (smd_read(info->ch, ptr, avail) != avail) {
- - /* shouldn't be possible since we're in interrupt
- - ** context here and nobody else could 'steal' our
- - ** characters.
- - */
- - printk(KERN_ERR "OOPS - smd_tty_buffer mismatch?!");
- + avail = smd_read_avail(info->ch);
- + if (avail == 0) {
- + tty->low_latency = 0;
- + tty_flip_buffer_push(tty);
- + break;
- }
- - wake_lock_timeout(&info->wake_lock, HZ / 2);
- - tty_flip_buffer_push(tty);
- + ptr = NULL;
- + avail = tty_prepare_flip_string(tty, &ptr, avail);
- +
- + if (avail && ptr) {
- + if (smd_read(info->ch, ptr, avail) != avail) {
- + /* shouldn't be possible since we're in interrupt
- + * context here and nobody else could 'steal' our
- + * characters.
- + */
- + printk(KERN_ERR "OOPS - smd_tty_buffer mismatch?!");
- + }
- + wake_lock_timeout(&info->wake_lock, HZ / 2);
- + tty->low_latency = 1;
- + tty_flip_buffer_push(tty);
- + } else
- + printk(KERN_ERR "smd_tty_work_func: tty_prepare_flip_string fail\n");
- }
- + mutex_unlock(&smd_tty_lock);
- +
- /* XXX only when writable and necessary */
- tty_wakeup(tty);
- }
- +static void smd_tty_notify(void *priv, unsigned event)
- +{
- + struct smd_tty_info *info = priv;
- +
- + if (event != SMD_EVENT_DATA)
- + return;
- +
- + queue_work(smd_tty_wq, &info->tty_work);
- +}
- +
- static int smd_tty_open(struct tty_struct *tty, struct file *f)
- {
- int res = 0;
- int n = tty->index;
- struct smd_tty_info *info;
- - const char *name = NULL;
- - int i;
- + const char *name;
- +
- + if (n == 0) {
- + name = "SMD_DS";
- + } else if (n == 1) {
- + name = "SMD_DIAG";
- + } else if (n == 9) {
- +#if defined(CONFIG_MACH_DESIREC) || defined(CONFIG_ARCH_MSM7X30)
- + name = "SMD_DATA4";
- +#else
- + name = "SMD_DATA9";
- +#endif
- - for (i = 0; i < smd_tty_channels_len; i++) {
- - if (smd_tty_channels[i].id == n) {
- - name = smd_tty_channels[i].name;
- - break;
- - }
- - }
- - if (!name)
- + } else if (n == 27) {
- + name = "SMD_GPSNMEA";
- +#ifdef CONFIG_BUILD_OMA_DM
- + } else if (n == 19) {
- + /* MASD requested OMA_DM AT-channel */
- + name = "SMD_DATA3";
- +#endif
- +#ifdef CONFIG_BUILD_CIQ
- + } else if (n == 26) {
- + /* CIQ Master/Slaver Bridge */
- + name = "SMD_DATA20";
- +#endif
- + } else {
- return -ENODEV;
- + }
- info = smd_tty + n;
- @@ -124,6 +154,12 @@ static int smd_tty_open(struct tty_struct *tty, struct file *f)
- smd_kick(info->ch);
- } else {
- res = smd_open(name, &info->ch, info, smd_tty_notify);
- +#ifdef CONFIG_ARCH_QSD8X50
- + /* 8x50 smd bug: channel open is too late to handle
- + * smd write request */
- + if (n == 19)
- + smd_wait_until_opened(info->ch, 200);
- +#endif
- }
- }
- mutex_unlock(&smd_tty_lock);
- @@ -137,6 +173,8 @@ static void smd_tty_close(struct tty_struct *tty, struct file *f)
- if (info == 0)
- return;
- + /* wait for the work in workqueue to complete */
- + flush_work(&info->tty_work);
- mutex_lock(&smd_tty_lock);
- if (--info->open_count == 0) {
- @@ -151,20 +189,25 @@ static void smd_tty_close(struct tty_struct *tty, struct file *f)
- mutex_unlock(&smd_tty_lock);
- }
- -static int smd_tty_write(struct tty_struct *tty, const unsigned char *buf, int len)
- +static int smd_tty_write(struct tty_struct *tty,
- + const unsigned char *buf, int len)
- {
- struct smd_tty_info *info = tty->driver_data;
- int avail;
- + int ret;
- /* if we're writing to a packet channel we will
- ** never be able to write more data than there
- ** is currently space for
- */
- + mutex_lock(&smd_tty_lock);
- avail = smd_write_avail(info->ch);
- if (len > avail)
- len = avail;
- + ret = smd_write(info->ch, buf, len);
- + mutex_unlock(&smd_tty_lock);
- - return smd_write(info->ch, buf, len);
- + return ret;
- }
- static int smd_tty_write_room(struct tty_struct *tty)
- @@ -182,7 +225,8 @@ static int smd_tty_chars_in_buffer(struct tty_struct *tty)
- static void smd_tty_unthrottle(struct tty_struct *tty)
- {
- struct smd_tty_info *info = tty->driver_data;
- - smd_kick(info->ch);
- + queue_work(smd_tty_wq, &info->tty_work);
- + return;
- }
- static struct tty_operations smd_tty_ops = {
- @@ -198,11 +242,17 @@ static struct tty_driver *smd_tty_driver;
- static int __init smd_tty_init(void)
- {
- - int ret, i;
- + int ret;
- +
- + smd_tty_wq = create_singlethread_workqueue("smd_tty");
- + if (smd_tty_wq == 0)
- + return -ENOMEM;
- smd_tty_driver = alloc_tty_driver(MAX_SMD_TTYS);
- - if (smd_tty_driver == 0)
- + if (smd_tty_driver == 0) {
- + destroy_workqueue(smd_tty_wq);
- return -ENOMEM;
- + }
- smd_tty_driver->owner = THIS_MODULE;
- smd_tty_driver->driver_name = "smd_tty_driver";
- @@ -214,17 +264,34 @@ static int __init smd_tty_init(void)
- smd_tty_driver->init_termios = tty_std_termios;
- smd_tty_driver->init_termios.c_iflag = 0;
- smd_tty_driver->init_termios.c_oflag = 0;
- - smd_tty_driver->init_termios.c_cflag = B38400 | CS8 | CREAD;
- + smd_tty_driver->init_termios.c_cflag = B115200 | CS8 | CREAD;
- smd_tty_driver->init_termios.c_lflag = 0;
- smd_tty_driver->flags = TTY_DRIVER_RESET_TERMIOS |
- TTY_DRIVER_REAL_RAW | TTY_DRIVER_DYNAMIC_DEV;
- tty_set_operations(smd_tty_driver, &smd_tty_ops);
- ret = tty_register_driver(smd_tty_driver);
- - if (ret) return ret;
- -
- - for (i = 0; i < smd_tty_channels_len; i++)
- - tty_register_device(smd_tty_driver, smd_tty_channels[i].id, 0);
- + if (ret)
- + return ret;
- +
- + /* this should be dynamic */
- + tty_register_device(smd_tty_driver, 0, 0);
- + INIT_WORK(&smd_tty[0].tty_work, smd_tty_work_func);
- + tty_register_device(smd_tty_driver, 1, 0);
- + INIT_WORK(&smd_tty[1].tty_work, smd_tty_work_func);
- + tty_register_device(smd_tty_driver, 9, 0);
- + INIT_WORK(&smd_tty[9].tty_work, smd_tty_work_func);
- + tty_register_device(smd_tty_driver, 27, 0);
- + INIT_WORK(&smd_tty[27].tty_work, smd_tty_work_func);
- +#ifdef CONFIG_BUILD_OMA_DM
- + /* MASD requested OMA_DM AT-channel */
- + tty_register_device(smd_tty_driver, 19, 0);
- + INIT_WORK(&smd_tty[19].tty_work, smd_tty_work_func);
- +#endif
- +#ifdef CONFIG_BUILD_CIQ
- + tty_register_device(smd_tty_driver, 26, 0);
- + INIT_WORK(&smd_tty[26].tty_work, smd_tty_work_func);
- +#endif
- return 0;
- }
- diff --git a/arch/arm/mach-msm/timer.c b/arch/arm/mach-msm/timer.c
- index 1523987..a1ed7a1 100644
- --- a/arch/arm/mach-msm/timer.c
- +++ b/arch/arm/mach-msm/timer.c
- @@ -27,7 +27,6 @@
- #include "smd_private.h"
- -
- enum {
- MSM_TIMER_DEBUG_SYNC_STATE = 1U << 0,
- MSM_TIMER_DEBUG_SYNC_UPDATE = 1U << 1,
- @@ -36,7 +35,11 @@ enum {
- static int msm_timer_debug_mask;
- module_param_named(debug_mask, msm_timer_debug_mask, int, S_IRUGO | S_IWUSR | S_IWGRP);
- +#ifdef CONFIG_ARCH_MSM7X30
- +#define MSM_DGT_BASE (MSM_TMR_BASE + 0x24)
- +#else
- #define MSM_DGT_BASE (MSM_GPT_BASE + 0x10)
- +#endif
- #define TIMER_MATCH_VAL 0x0000
- #define TIMER_COUNT_VAL 0x0004
- @@ -50,7 +53,10 @@ module_param_named(debug_mask, msm_timer_debug_mask, int, S_IRUGO | S_IWUSR | S_
- #define GPT_HZ 32768
- -#ifdef CONFIG_ARCH_MSM_SCORPION
- +#ifdef CONFIG_ARCH_MSM7X30
- +#define DGT_HZ 6144000 /* Uses LPXO/4 (24.576 MHz / 4) */
- +#define MSM_DGT_SHIFT (0)
- +#elif CONFIG_ARCH_MSM_SCORPION
- #define DGT_HZ (19200000 / 4) /* 19.2 MHz / 4 by default */
- #define MSM_DGT_SHIFT (0)
- #else
- @@ -215,7 +221,7 @@ static inline int check_timeout(struct msm_clock *clock, uint32_t timeout)
- return (int32_t)(msm_read_timer_count(clock) - timeout) <= 0;
- }
- -#ifndef CONFIG_ARCH_MSM_SCORPION
- +#ifndef CONFIG_MSM_N_WAY_SMD
- static uint32_t msm_timer_sync_smem_clock(int exit_sleep)
- {
- @@ -457,23 +463,20 @@ int64_t msm_timer_enter_idle(void)
- uint32_t count;
- int32_t delta;
- -// CotullaTODO: - disable idle...workaround for now?
- - return 0;
- -
- if (clock != &msm_clocks[MSM_CLOCK_GPT] || msm_fast_timer_enabled)
- return 0;
- -// msm_timer_sync_smem_clock(0);
- + msm_timer_sync_smem_clock(0);
- count = msm_read_timer_count(clock);
- if (clock->stopped++ == 0)
- clock->stopped_tick = (count + clock->offset) >> clock->shift;
- alarm = clock->alarm_vtime - clock->offset;
- delta = alarm - count;
- - if (delta <= -(int32_t)((clock->freq << clock->shift) >> 10))
- - {
- + if (delta <= -(int32_t)((clock->freq << clock->shift) >> 10)) {
- /* timer should have triggered 1ms ago */
- - printk(KERN_ERR "msm_timer_enter_idle: timer late %d, reprogram it\n", delta);
- + printk(KERN_ERR "msm_timer_enter_idle: timer late %d, "
- + "reprogram it\n", delta);
- msm_timer_reactivate_alarm(clock);
- }
- if (delta <= 0)
- @@ -487,16 +490,13 @@ void msm_timer_exit_idle(int low_power)
- struct msm_clock *clock = msm_active_clock;
- uint32_t smem_clock;
- -// Cotulla - disable idle...workaround for now?
- - return;
- -
- if (clock != &msm_clocks[MSM_CLOCK_GPT])
- return;
- if (low_power) {
- if (!(readl(clock->regbase + TIMER_ENABLE) & TIMER_ENABLE_EN)) {
- writel(TIMER_ENABLE_EN, clock->regbase + TIMER_ENABLE);
- -// smem_clock = msm_timer_sync_smem_clock(1);
- + smem_clock = msm_timer_sync_smem_clock(1);
- }
- msm_timer_reactivate_alarm(clock);
- }
- @@ -543,19 +543,11 @@ unsigned long long sched_clock(void)
- return result;
- }
- -/*
- #ifdef CONFIG_MSM7X00A_USE_GP_TIMER
- #define DG_TIMER_RATING 100
- #else
- #define DG_TIMER_RATING 300
- #endif
- -*/
- -
- -// for DGT timer
- -#define DG_TIMER_RATING 300
- -
- -// for GPT timer
- -//#define DG_TIMER_RATING 100
- static struct msm_clock msm_clocks[] = {
- [MSM_CLOCK_GPT] = {
- @@ -583,15 +575,16 @@ static struct msm_clock msm_clocks[] = {
- .dev_id = &msm_clocks[0].clockevent,
- .irq = INT_GP_TIMER_EXP
- },
- +#if defined(CONFIG_ARCH_MSM7X30)
- + .regbase = MSM_TMR_BASE + 4,
- +#else
- .regbase = MSM_GPT_BASE,
- +#endif
- .freq = GPT_HZ,
- -
- -
- -/* .flags =
- + .flags =
- MSM_CLOCK_FLAGS_UNSTABLE_COUNT |
- MSM_CLOCK_FLAGS_ODD_MATCH_WRITE |
- MSM_CLOCK_FLAGS_DELAYED_WRITE_POST,
- -*/
- .write_delay = 9,
- },
- [MSM_CLOCK_DGT] = {
- @@ -689,38 +682,35 @@ static void __init msm_timer_init(void)
- {
- int i;
- int res;
- -
- - printk("msm_timer_init $$$\n");
- -
- - printk(" 1DIV = %08X\n", readl(MSM_GPT_BASE + 0x20));
- - writel(3, MSM_GPT_BASE + 0x20);
- - printk(" 2DIV = %08X\n", readl(MSM_GPT_BASE + 0x20));
- -
- - for (i = 0; i < ARRAY_SIZE(msm_clocks); i++)
- - {
- +
- + for (i = 0; i < ARRAY_SIZE(msm_clocks); i++) {
- struct msm_clock *clock = &msm_clocks[i];
- struct clock_event_device *ce = &clock->clockevent;
- struct clocksource *cs = &clock->clocksource;
- writel(0, clock->regbase + TIMER_ENABLE);
- - writel(1, clock->regbase + TIMER_CLEAR);
- + writel(0, clock->regbase + TIMER_CLEAR);
- writel(~0, clock->regbase + TIMER_MATCH_VAL);
- while (msm_read_timer_count(clock)) ; /* wait for clock to clear */
- ce->mult = div_sc(clock->freq, NSEC_PER_SEC, ce->shift);
- /* allow at least 10 seconds to notice that the timer wrapped */
- - ce->max_delta_ns = clockevent_delta2ns(0xf0000000 >> clock->shift, ce);
- + ce->max_delta_ns =
- + clockevent_delta2ns(0xf0000000 >> clock->shift, ce);
- /* ticks gets rounded down by one */
- - ce->min_delta_ns = clockevent_delta2ns(clock->write_delay + 4, ce);
- + ce->min_delta_ns =
- + clockevent_delta2ns(clock->write_delay + 4, ce);
- ce->cpumask = cpumask_of(0);
- cs->mult = clocksource_hz2mult(clock->freq, cs->shift);
- res = clocksource_register(cs);
- if (res)
- - printk(KERN_ERR "msm_timer_init: clocksource_register failed for %s\n", cs->name);
- + printk(KERN_ERR "msm_timer_init: clocksource_register "
- + "failed for %s\n", cs->name);
- res = setup_irq(clock->irq.irq, &clock->irq);
- if (res)
- - printk(KERN_ERR "msm_timer_init: setup_irq failed for %s\n", cs->name);
- + printk(KERN_ERR "msm_timer_init: setup_irq "
- + "failed for %s\n", cs->name);
- clockevents_register_device(ce);
- }
Advertisement
Add Comment
Please, Sign In to add comment
Advertisement