summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJihoon Bang <jbang@nvidia.com>2011-09-27 11:23:55 -0700
committerVarun Colbert <vcolbert@nvidia.com>2011-10-13 12:58:47 -0700
commit6609c0ec7d52f7656e3c520e36ae836cbc63aa6a (patch)
tree98abe15fabbd45767120fd5bc4adfaa65ca43d3b
parentff32585e71fdb9b66180d6f1940736c505aaf51c (diff)
arm: tegra: enterprise: add I2C mux driver instance
Add I2C mux driver instance to support two rear sensors. Add new GPIO pin to control reset for I2C mux. If board doesn't have I2C mux, it falls back to previous I2C tree. Bug 871860 Reviewed-on: http://git-master/r/54763 (cherry picked from commit c53f8fc9d5d05427684aafb4ad6552eb6cff7ff7) Reviewed-on: http://git-master/r/55799 (cherry picked from commit c5fe68c1b4b1ed1e283526c8ac057efb3a2af5af) Change-Id: I40a35cbd301e53a8d70700043142d5cac0655b5c Reviewed-on: http://git-master/r/57414 Reviewed-by: Jihoon Bang <jbang@nvidia.com> Tested-by: Jihoon Bang <jbang@nvidia.com> Reviewed-by: Dan Willemsen <dwillemsen@nvidia.com>
-rw-r--r--arch/arm/mach-tegra/board-enterprise-pinmux.c3
-rw-r--r--arch/arm/mach-tegra/board-enterprise-power.c18
-rw-r--r--arch/arm/mach-tegra/board-enterprise-sensors.c88
-rw-r--r--arch/arm/mach-tegra/board-enterprise.h18
4 files changed, 107 insertions, 20 deletions
diff --git a/arch/arm/mach-tegra/board-enterprise-pinmux.c b/arch/arm/mach-tegra/board-enterprise-pinmux.c
index 3d91cc76018b..44a33aa9eb18 100644
--- a/arch/arm/mach-tegra/board-enterprise-pinmux.c
+++ b/arch/arm/mach-tegra/board-enterprise-pinmux.c
@@ -205,6 +205,7 @@ static __initdata struct tegra_pingroup_config enterprise_pinmux[] = {
DEFAULT_PINMUX(LCD_D7, RSVD1, NORMAL, NORMAL, OUTPUT),
DEFAULT_PINMUX(LCD_D8, DISPLAYA, NORMAL, NORMAL, INPUT),
DEFAULT_PINMUX(LCD_D9, DISPLAYA, NORMAL, NORMAL, INPUT),
+ DEFAULT_PINMUX(LCD_D11, DISPLAYA, NORMAL, NORMAL, INPUT),
DEFAULT_PINMUX(LCD_D12, DISPLAYA, NORMAL, NORMAL, INPUT),
DEFAULT_PINMUX(LCD_D13, DISPLAYA, NORMAL, NORMAL, INPUT),
DEFAULT_PINMUX(LCD_D14, DISPLAYA, NORMAL, NORMAL, INPUT),
@@ -381,7 +382,6 @@ static __initdata struct tegra_pingroup_config enterprise_unused_pinmux[] = {
DEFAULT_PINMUX(LCD_HSYNC, DISPLAYA, PULL_DOWN, TRISTATE, OUTPUT),
DEFAULT_PINMUX(LCD_VSYNC, DISPLAYA, PULL_DOWN, TRISTATE, OUTPUT),
DEFAULT_PINMUX(LCD_D10, DISPLAYA, PULL_DOWN, TRISTATE, OUTPUT),
- DEFAULT_PINMUX(LCD_D11, DISPLAYA, PULL_DOWN, TRISTATE, OUTPUT),
DEFAULT_PINMUX(LCD_PWR0, DISPLAYA, PULL_DOWN, TRISTATE, OUTPUT),
DEFAULT_PINMUX(LCD_SCK, DISPLAYA, PULL_DOWN, TRISTATE, OUTPUT),
DEFAULT_PINMUX(LCD_SDOUT, DISPLAYA, PULL_DOWN, TRISTATE, OUTPUT),
@@ -459,7 +459,6 @@ static __initdata struct pin_info_low_power_mode enterprise_unused_gpio_pins[] =
PIN_GPIO_LPM("LCD_HSYNC", TEGRA_GPIO_PJ3, 0, 0),
PIN_GPIO_LPM("LCD_VSYNC", TEGRA_GPIO_PJ4, 0, 0),
PIN_GPIO_LPM("LCD_D10", TEGRA_GPIO_PF2, 0, 0),
- PIN_GPIO_LPM("LCD_D12", TEGRA_GPIO_PF3, 0, 0),
PIN_GPIO_LPM("LCD_PWR0", TEGRA_GPIO_PB2, 0, 0),
PIN_GPIO_LPM("LCD_SCK", TEGRA_GPIO_PZ4, 0, 0),
PIN_GPIO_LPM("LCD_SDOUT", TEGRA_GPIO_PN5, 0, 0),
diff --git a/arch/arm/mach-tegra/board-enterprise-power.c b/arch/arm/mach-tegra/board-enterprise-power.c
index 4ccedb2b4f5d..96f0403391b1 100644
--- a/arch/arm/mach-tegra/board-enterprise-power.c
+++ b/arch/arm/mach-tegra/board-enterprise-power.c
@@ -346,24 +346,38 @@ static struct regulator_consumer_supply gpio_switch_sdmmc3_vdd_sel_supply[] = {
static int gpio_switch_sdmmc3_vdd_sel_voltages[] = {2850};
/* LCD-D23 (GPIO M7) from T30*/
-/* 2-0036 is dev_name of ar0832 */
+/* 2-0036 is dev_name of ar0832 in Enterprise A01*/
+/* 2-0032 is alternative dev_name of ar0832 Enterprise A01*/
/* 2-0010 is dev_name of ov9726 */
+/* 2-0070 is dev_name of PCA9546 in Enterprise A02*/
+/* 6-0036 is dev_name of ar0832 in Enterprise A02 */
+/* 7-0036 is dev_name of ar0832 in Enterprise A02 */
static struct regulator_consumer_supply gpio_switch_cam_ldo_2v8_en_supply[] = {
REGULATOR_SUPPLY("vaa", "2-0036"),
REGULATOR_SUPPLY("vaa", "2-0032"),
REGULATOR_SUPPLY("avdd", "2-0010"),
REGULATOR_SUPPLY("vdd_2v8_cam", NULL),
+ REGULATOR_SUPPLY("vcc", "2-0070"),
+ REGULATOR_SUPPLY("vaa", "6-0036"),
+ REGULATOR_SUPPLY("vaa", "7-0036"),
};
static int gpio_switch_cam_ldo_2v8_en_voltages[] = {2800};
/* LCD-D9 (GPIO F1) from T30*/
-/* 2-0036 is dev_name of ar0832 */
+/* 2-0036 is dev_name of ar0832 in Enterprise A01*/
+/* 2-0032 is alternative dev_name of ar0832 Enterprise A01*/
/* 2-0010 is dev_name of ov9726 */
+/* 2-0070 is dev_name of PCA9546 in Enterprise A02*/
+/* 6-0036 is dev_name of ar0832 in Enterprise A02 */
+/* 7-0036 is dev_name of ar0832 in Enterprise A02 */
static struct regulator_consumer_supply gpio_switch_cam_ldo_1v8_en_supply[] = {
REGULATOR_SUPPLY("vdd", "2-0036"),
REGULATOR_SUPPLY("vdd", "2-0032"),
REGULATOR_SUPPLY("dovdd", "2-0010"),
REGULATOR_SUPPLY("vdd_1v8_cam", NULL),
+ REGULATOR_SUPPLY("vcc_i2c", "2-0070"),
+ REGULATOR_SUPPLY("vdd", "6-0036"),
+ REGULATOR_SUPPLY("vdd", "7-0036"),
};
static int gpio_switch_cam_ldo_1v8_en_voltages[] = {1800};
diff --git a/arch/arm/mach-tegra/board-enterprise-sensors.c b/arch/arm/mach-tegra/board-enterprise-sensors.c
index 287497161fc8..c60f2596b92a 100644
--- a/arch/arm/mach-tegra/board-enterprise-sensors.c
+++ b/arch/arm/mach-tegra/board-enterprise-sensors.c
@@ -33,6 +33,7 @@
#include <linux/i2c.h>
#include <linux/delay.h>
+#include <linux/i2c/pca954x.h>
#include <linux/err.h>
#include <linux/mpu.h>
#include <linux/nct1008.h>
@@ -45,6 +46,7 @@
#include "cpu-tegra.h"
#include "gpio-names.h"
#include "board-enterprise.h"
+#include "board.h"
static struct nct1008_platform_data enterprise_nct1008_pdata = {
.supported_hwrev = true,
@@ -280,6 +282,7 @@ static int enterprise_ar0832_ri_power_on(int is_stereo)
{
int ret = 0;
+ pr_info("%s: ++\n", __func__);
ret = enterprise_cam_pwr(CAM_REAR_RIGHT, true);
/* Release Reset */
@@ -394,26 +397,25 @@ static int enterprise_tps61050_pm(int pwr)
pr_info("%s: ++%d\n", __func__, pwr);
switch (pwr) {
case TPS61050_PWR_OFF:
- if (enterprise_flash_reg) {
+ if (enterprise_flash_reg)
regulator_disable(enterprise_flash_reg);
- regulator_put(enterprise_flash_reg);
- enterprise_flash_reg = NULL;
- }
break;
case TPS61050_PWR_STDBY:
case TPS61050_PWR_COMM:
case TPS61050_PWR_ON:
- enterprise_flash_reg = regulator_get(NULL, "vdd_1v8_cam");
- if (IS_ERR_OR_NULL(enterprise_flash_reg)) {
- pr_err("%s: failed to get flash pwr\n", __func__);
- return PTR_ERR(enterprise_flash_reg);
+ if (!enterprise_flash_reg) {
+ enterprise_flash_reg = regulator_get(NULL, "vdd_1v8_cam");
+ if (IS_ERR_OR_NULL(enterprise_flash_reg)) {
+ pr_err("%s: failed to get flash pwr\n", __func__);
+ return PTR_ERR(enterprise_flash_reg);
+ }
}
ret = regulator_enable(enterprise_flash_reg);
if (ret) {
pr_err("%s: failed to enable flash pwr\n", __func__);
goto fail_regulator_flash_reg;
}
- enterprise_msleep(10);
+ enterprise_msleep(1);
break;
default:
ret = -1;
@@ -447,6 +449,19 @@ static struct enterprise_cam_gpio enterprise_cam_gpio_data[] = {
[3] = TEGRA_CAMERA_GPIO(CAM3_RST_L_GPIO, "cam3_rst_lo", 0),
[4] = TEGRA_CAMERA_GPIO(CAM3_PWDN_GPIO, "cam3_pwdn", 1),
[5] = TEGRA_CAMERA_GPIO(CAM_FLASH_EN_GPIO, "flash_en", 1),
+ [6] = TEGRA_CAMERA_GPIO(CAM_I2C_MUX_RST_EXP, "cam_i2c_mux_rst", 1),
+};
+
+static struct pca954x_platform_mode enterprise_pca954x_modes[] = {
+ { .adap_id = PCA954x_I2C_BUS0, .deselect_on_exit = true, },
+ { .adap_id = PCA954x_I2C_BUS1, .deselect_on_exit = true, },
+ { .adap_id = PCA954x_I2C_BUS2, .deselect_on_exit = true, },
+ { .adap_id = PCA954x_I2C_BUS3, .deselect_on_exit = true, },
+};
+
+static struct pca954x_platform_data enterprise_pca954x_data = {
+ .modes = enterprise_pca954x_modes,
+ .num_modes = ARRAY_SIZE(enterprise_pca954x_modes),
};
static struct ar0832_platform_data enterprise_ar0832_ri_data = {
@@ -474,6 +489,21 @@ static struct tps61050_platform_data enterprise_tps61050_data = {
.gpio_sync = NULL,
};
+static const struct i2c_board_info enterprise_i2c2_boardinfo[] = {
+ {
+ I2C_BOARD_INFO("pca9546", 0x70),
+ .platform_data = &enterprise_pca954x_data,
+ },
+ {
+ I2C_BOARD_INFO("tps61050", 0x33),
+ .platform_data = &enterprise_tps61050_data,
+ },
+ {
+ I2C_BOARD_INFO("ov9726", OV9726_I2C_ADDR >> 1),
+ .platform_data = &enterprise_ov9726_data,
+ },
+};
+
/*
* Since ar0832 driver should support multiple devices, slave
* address should be changed after it is open. Default slave
@@ -482,12 +512,12 @@ static struct tps61050_platform_data enterprise_tps61050_data = {
*/
static struct i2c_board_info ar0832_i2c2_boardinfo[] = {
{
- /* 0x30: alternative slave address */
+ /* 0x36: alternative slave address */
I2C_BOARD_INFO("ar0832", 0x36),
.platform_data = &enterprise_ar0832_ri_data,
},
{
- /* 0x31: alternative slave address */
+ /* 0x32: alternative slave address */
I2C_BOARD_INFO("ar0832", 0x32),
.platform_data = &enterprise_ar0832_le_data,
},
@@ -501,13 +531,27 @@ static struct i2c_board_info ar0832_i2c2_boardinfo[] = {
},
};
+static struct i2c_board_info enterprise_i2c6_boardinfo[] = {
+ {
+ I2C_BOARD_INFO("ar0832", 0x36),
+ .platform_data = &enterprise_ar0832_le_data,
+ },
+};
+
+static struct i2c_board_info enterprise_i2c7_boardinfo[] = {
+ {
+ I2C_BOARD_INFO("ar0832", 0x36),
+ .platform_data = &enterprise_ar0832_ri_data,
+ },
+};
+
static int enterprise_cam_init(void)
{
int ret;
int i;
+ struct board_info bi;
pr_info("%s:++\n", __func__);
-
memset(ent_vicsi_pwr, 0, sizeof(ent_vicsi_pwr));
for (i = 0; i < ARRAY_SIZE(enterprise_cam_gpio_data); i++) {
ret = gpio_request(enterprise_cam_gpio_data[i].gpio,
@@ -523,8 +567,23 @@ static int enterprise_cam_init(void)
tegra_gpio_enable(enterprise_cam_gpio_data[i].gpio);
}
- i2c_register_board_info(2, ar0832_i2c2_boardinfo,
- ARRAY_SIZE(ar0832_i2c2_boardinfo));
+ tegra_get_board_info(&bi);
+
+ if (bi.fab == BOARD_FAB_A01)
+ i2c_register_board_info(2, ar0832_i2c2_boardinfo,
+ ARRAY_SIZE(ar0832_i2c2_boardinfo));
+ else if (bi.fab == BOARD_FAB_A02) {
+ i2c_register_board_info(2, enterprise_i2c2_boardinfo,
+ ARRAY_SIZE(enterprise_i2c2_boardinfo));
+ /*
+ * Right camera is on PCA954x's I2C BUS1,
+ * Left camera is on BUS0
+ */
+ i2c_register_board_info(PCA954x_I2C_BUS0, enterprise_i2c6_boardinfo,
+ ARRAY_SIZE(enterprise_i2c6_boardinfo));
+ i2c_register_board_info(PCA954x_I2C_BUS1, enterprise_i2c7_boardinfo,
+ ARRAY_SIZE(enterprise_i2c7_boardinfo));
+ }
return 0;
@@ -538,6 +597,7 @@ fail_free_gpio:
int __init enterprise_sensors_init(void)
{
int ret;
+
enterprise_isl_init();
enterprise_nct1008_init();
enterprise_mpuirq_init();
diff --git a/arch/arm/mach-tegra/board-enterprise.h b/arch/arm/mach-tegra/board-enterprise.h
index 26e63208cb89..dcc24a0a5a98 100644
--- a/arch/arm/mach-tegra/board-enterprise.h
+++ b/arch/arm/mach-tegra/board-enterprise.h
@@ -25,6 +25,14 @@
#include <mach/irqs.h>
#include <linux/mfd/tps80031.h>
+/* Processor Board ID */
+#define BOARD_E1205 0x0C05
+
+/* Board Fab version */
+#define BOARD_FAB_A00 0x0
+#define BOARD_FAB_A01 0x1
+#define BOARD_FAB_A02 0x2
+
int enterprise_charge_init(void);
int enterprise_sdhci_init(void);
int enterprise_pinmux_init(void);
@@ -39,6 +47,13 @@ int enterprise_suspend_init(void);
int enterprise_edp_init(void);
void __init enterprise_tsensor_init(void);
+/* PCA954x I2C bus expander bus addresses */
+#define PCA954x_I2C_BUS_BASE 6
+#define PCA954x_I2C_BUS0 (PCA954x_I2C_BUS_BASE + 0)
+#define PCA954x_I2C_BUS1 (PCA954x_I2C_BUS_BASE + 1)
+#define PCA954x_I2C_BUS2 (PCA954x_I2C_BUS_BASE + 2)
+#define PCA954x_I2C_BUS3 (PCA954x_I2C_BUS_BASE + 3)
+
/*****************External GPIO tables ******************/
/* External peripheral gpio base. */
#define ENT_TPS80031_GPIO_BASE TEGRA_NR_GPIOS
@@ -58,9 +73,7 @@ void __init enterprise_tsensor_init(void);
#define CAM_CSI_MUX_SEL_FRONT 0
#define CAM1_RST_L_GPIO TEGRA_GPIO_PM5 /*REAR RIGHT*/
-#define CAM1_PWDN_GPIO TEGRA_GPIO_PF3 /*REAR RIGHT*/
#define CAM2_RST_L_GPIO TEGRA_GPIO_PF4 /*REAR LEFT*/
-#define CAM2_PWDN_GPIO TEGRA_GPIO_PF2 /*REAR LEFT*/
#define CAM3_RST_L_GPIO TEGRA_GPIO_PM2 /*FRONT*/
#define CAM3_RST_L_TRUE 0
#define CAM3_RST_L_FALSE 1
@@ -70,6 +83,7 @@ void __init enterprise_tsensor_init(void);
#define CAM_FLASH_EN_GPIO TEGRA_GPIO_PBB3
#define CAM_FLASH_MAX_TORCH_AMP 7
#define CAM_FLASH_MAX_FLASH_AMP 7
+#define CAM_I2C_MUX_RST_EXP TEGRA_GPIO_PF3 /*I2C Mux Reset*/
/* Audio-related GPIOs */
#define TEGRA_GPIO_HP_DET TEGRA_GPIO_PW3