static int evitareul_s5k6a1gx03_power_off(void) { pr_info("[CAM] %s ++", __func__); int pcbid = htc_get_pcbid_info(); #if defined(CONFIG_RAWCHIP_ENABLE) if ((pcbid >= PROJECT_PHASE_XB) || (pcbid == PROJECT_PHASE_EVM)) { /* set gpio output low : O(L) */ tegra_gpio_enable(MCAM_SPI_CLK); ENR_msleep(1); tegra_gpio_enable(MCAM_SPI_DO); tegra_gpio_enable(MCAM_SPI_DI); tegra_gpio_enable(MCAM_SPI_CS0); tegra_pinmux_set_pullupdown(TEGRA_PINGROUP_KB_ROW0, TEGRA_PUPD_PULL_DOWN); tegra_pinmux_set_pullupdown(TEGRA_PINGROUP_CLK3_REQ, TEGRA_PUPD_PULL_DOWN); ENR_msleep(1); /* RAW RSTN*/ gpio_direction_output(RAW_RSTN, 0); ENR_msleep(3); } #endif tegra_gpio_enable(CAM_MCLK); ENR_msleep(1); /* CAM SEL */ gpio_direction_output(CAM_SEL, 0); ENR_msleep(1); /* vcm */ regulator_disable(cam_vcm2v85_en); ENR_msleep(1); /* digital */ gpio_direction_output(CAM2_D1V2_EN, 0); ENR_msleep(1); /* RSTN */ gpio_direction_output(FRONT_CAM_RST, 0); ENR_msleep(1); #if defined(CONFIG_RAWCHIP_ENABLE) if ((pcbid >= PROJECT_PHASE_XB) || (pcbid == PROJECT_PHASE_EVM)) { /* core */ gpio_direction_output(CAM_D1V2_EN, 0); ENR_msleep(1); /* RAW_1V8_EN */ gpio_direction_output(RAW_1V8_EN, 0); ENR_msleep(1); rawchip_spi_clock_control(0); } #endif /* analog */ regulator_disable(cam_a2v85_en); ENR_msleep(5); /* IO */ tegra_gpio_enable(CAM_I2C_SCL); tegra_gpio_enable(CAM_I2C_SDA); gpio_direction_output(CAMIO_1V8_EN, 0); ENR_msleep(10); tegra_pinmux_set_pullupdown(TEGRA_PINGROUP_KB_ROW6, TEGRA_PUPD_PULL_DOWN); pr_info("[CAM] %s --", __func__); return 0; }
static long aic3008_ioctl(struct file *file, unsigned int cmd, unsigned long argc) { struct AIC3008_PARAM para; void *table; int ret = 0, i = 0, mem_size, volume = 0; CODEC_SPI_CMD reg[4]; unsigned char data; int len= 0; /* for dump dsp length. */ int pcbid = 0; AUD_DBG("IOCTL command:0x%02X, argc:%ld\n", cmd, argc); if (aic3008_uplink == NULL || aic3008_downlink == NULL || aic3008_minidsp == NULL) { AUD_ERR("cmd 0x%x, invalid pointers\n", cmd); return -EFAULT; } switch (cmd) { /* first IO command from HAL */ case AIC3008_IO_SET_TX_PARAM: /* second IO command from HAL */ case AIC3008_IO_SET_RX_PARAM: if (copy_from_user(¶, (void *) argc, sizeof(para))) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } AUD_DBG("parameters(%d, %d, %p)\n", para.row_num, para.col_num, para.cmd_data); if (cmd == AIC3008_IO_SET_TX_PARAM) table = aic3008_uplink[0]; else table = aic3008_downlink[0]; /* confirm indicated size doesn't exceed the allocated one */ if (para.row_num > IO_CTL_ROW_MAX || para.col_num != IO_CTL_COL_MAX) { AUD_ERR("data size mismatch with allocated memory (%d,%d)\n", IO_CTL_ROW_MAX, IO_CTL_COL_MAX); return -EFAULT; } mem_size = para.row_num * para.col_num * sizeof(CODEC_SPI_CMD); if (copy_from_user(table, para.cmd_data, mem_size)) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } /* invoking initialization procedure of AIC3008 */ if (cmd == AIC3008_IO_SET_TX_PARAM) aic3008_tx_config(INITIAL); AUD_INFO("update RX/TX tables(%d, %d) successfully\n", para.row_num, para.col_num); break; /* third io command from HAL */ case AIC3008_IO_SET_DSP_PARAM: if (copy_from_user(¶, (void *) argc, sizeof(para))) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } AUD_DBG("parameters(%d, %d, %p)\n", para.row_num, para.col_num, para.cmd_data); table = aic3008_minidsp[0]; /* confirm indicated size doesn't exceed the allocated one */ if (para.row_num > MINIDSP_ROW_MAX || para.col_num != MINIDSP_COL_MAX) { AUD_ERR("data size mismatch with allocated memory (%d, %d)\n", MINIDSP_ROW_MAX, MINIDSP_COL_MAX); return -EFAULT; } mem_size = para.row_num * para.col_num * sizeof(CODEC_SPI_CMD); if (copy_from_user(table, para.cmd_data, mem_size)) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } AUD_INFO("update dsp table(%d, %d) successfully\n", para.row_num, para.col_num); break; /* these IO commands are called to set path */ case AIC3008_IO_CONFIG_TX: case AIC3008_IO_CONFIG_RX: case AIC3008_IO_CONFIG_MEDIA: if (copy_from_user(&i, (void *) argc, sizeof(int))) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } /* call aic3008_set_config() to issue SPI commands */ ret = aic3008_set_config(cmd, i, 1); if (ret < 0) AUD_ERR("configure(%d) error %d\n", i, ret); break; case AIC3008_IO_CONFIG_VOLUME_L: if (copy_from_user(&volume, (void *) argc, sizeof(int))) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } if (volume < -127 || volume > 48) { AUD_ERR("volume out of range\n"); return -EFAULT; } AUD_DBG("AIC3008 config left volume %d\n", volume); CODEC_SET_VOLUME_L[1].data = volume; /* call extended aic3008_config_ex() to set up volume */ aic3008_config_ex(CODEC_SET_VOLUME_L, ARRAY_SIZE(CODEC_SET_VOLUME_L)); break; case AIC3008_IO_CONFIG_VOLUME_R: if (copy_from_user(&volume, (void *) argc, sizeof(int))) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } if (volume < -127 || volume > 48) { AUD_ERR("volume out of range\n"); return -EFAULT; } AUD_DBG("AIC3008 config right volume %d\n", volume); CODEC_SET_VOLUME_R[1].data = volume; /* call extended aic3008_config_ex() to set up volume */ aic3008_config_ex(CODEC_SET_VOLUME_R, ARRAY_SIZE(CODEC_SET_VOLUME_R)); break; /* dump specific audio codec page */ case AIC3008_IO_DUMP_PAGES: if (copy_from_user(&i, (void *) argc, sizeof(int))) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } if (i > AIC3008_MAX_PAGES) { AUD_ERR("invalid page number %d\n", i); return -EINVAL; } AUD_DBG("========== dump page %d ==========\n", i); /* indicated page number of AIC3008 */ codec_spi_write(0x00, i, true); for (i = 0; i < AIC3008_MAX_REGS; i++) { ret = codec_spi_read(i, &data, true); if (ret < 0) { AUD_ERR("read fail on register 0x%X\n", i); 0; } else { AUD_DBG("(addr:0x%02X, data:0x%02X)\n", i, data); 0; } } AUD_DBG("=============================================\n"); break; case AIC3008_IO_DUMP_DSP: AUD_DBG("========== dump dsp %d ==========\n", aic3008_dsp_mode); /* indicated dsp number of AIC3008 */ len = (aic3008_minidsp[aic3008_dsp_mode][0].reg << 8) | aic3008_minidsp[aic3008_dsp_mode][0].data; AUD_DBG("len = %d", len); spi_read_list(&aic3008_minidsp[aic3008_dsp_mode][1], len); AUD_DBG("=============================================\n"); break; /* write specific audio codec register */ case AIC3008_IO_WRITE_REG: AUD_INFO("========== WRITE_REG ==========\n"); if (copy_from_user(®, (void *) argc, sizeof(CODEC_SPI_CMD) * 4)) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } AUD_DBG("command list (%c,%02X,%02X) (%c,%02X,%02X) (%c,%02X,%02X) (%c,%02X,%02X)\n", reg[0].act, reg[0].reg, reg[0].data, reg[1].act, reg[1].reg, reg[1].data, reg[2].act, reg[2].reg, reg[2].data, reg[3].act, reg[3].reg, reg[3].data); // aic3008_config_ex(reg, 4); for (i = 0; i < 4; i++) { if (reg[i].act == 'r' || reg[i].act == 'R') codec_spi_read(reg[i].reg, ®[i].data, true); else if (reg[i].act == 'w' || reg[i].act == 'W') codec_spi_write(reg[i].reg, reg[i].data, true); else return -EINVAL; } AUD_INFO("========== WRITE_REG end ==========\n"); break; /* read specific audio codec register */ case AIC3008_IO_READ_REG: AUD_INFO("========== READ_REG ==========\n"); if (copy_from_user(®, (void *) argc, sizeof(CODEC_SPI_CMD) * 4)) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } for (i = 0; i < 4; i++) { if (reg[i].act == 'r' || reg[i].act == 'R') codec_spi_read(reg[i].reg, ®[i].data, true); else if (reg[i].act == 'w' || reg[i].act == 'W') codec_spi_write(reg[i].reg, reg[i].data, true); else return -EINVAL; } if (copy_to_user((void *) argc, ®, sizeof(CODEC_SPI_CMD) * 2)) { AUD_ERR("failed on copy_to_user\n"); return -EFAULT; } AUD_INFO("========== READ_REG end==========\n"); break; case AIC3008_IO_POWERDOWN: /* power down IO command */ mutex_lock(&lock); aic3008_powerdown(); mutex_unlock(&lock); break; case AIC3008_IO_LOOPBACK: /* loopback IO command */ if (copy_from_user(&i, (void *) argc, sizeof(int))) { AUD_ERR("failed on copy_from_user\n"); return -EFAULT; } AUD_DBG("index %d for LOOPBACK\n", i); /* set up the loopback with specific id */ aic3008_set_loopback(i); break; case AIC3008_IO_GET_PCBID: /* get pcbid */ pcbid = htc_get_pcbid_info(); if (copy_to_user((void *) argc, &pcbid, sizeof(int))) { AUD_ERR("failed on copy_to_user\n"); return -EFAULT; } break; default: AUD_ERR("invalid command %d\n", _IOC_NR(cmd)); ret = -EINVAL; } return ret; }
static int evitareul_s5k6a1gx03_power_on(void) { int ret; int pcbid = htc_get_pcbid_info(); pr_info("[CAM] %s ++", __func__); enrc2u_set_regulator(); gpio_direction_output(CAM_MCLK, 0); #if defined(CONFIG_RAWCHIP_ENABLE) if ((pcbid >= PROJECT_PHASE_XB) || (pcbid == PROJECT_PHASE_EVM)) { tegra_gpio_disable(MCAM_SPI_CLK); tegra_gpio_disable(MCAM_SPI_DO); tegra_gpio_disable(MCAM_SPI_DI); tegra_gpio_disable(MCAM_SPI_CS0); tegra_pinmux_set_pullupdown(TEGRA_PINGROUP_KB_ROW0, TEGRA_PUPD_NORMAL); tegra_pinmux_set_pullupdown(TEGRA_PINGROUP_CLK3_REQ, TEGRA_PUPD_NORMAL); } #endif tegra_gpio_disable(CAM_I2C_SCL); tegra_gpio_disable(CAM_I2C_SDA); gpio_direction_output(CAM1_PWDN, 0); gpio_direction_output(FRONT_CAM_RST, 0); gpio_direction_output(CAM1_VCM_PD, 0); #if defined(CONFIG_RAWCHIP_ENABLE) if ((pcbid >= PROJECT_PHASE_XB) || (pcbid == PROJECT_PHASE_EVM)) { gpio_direction_output(RAW_RSTN, 0); } #endif gpio_direction_output(CAM_SEL, 0); #if defined(CONFIG_RAWCHIP_ENABLE) if ((pcbid >= PROJECT_PHASE_XB) || (pcbid == PROJECT_PHASE_EVM)) { /* RAW_1V8_EN */ gpio_direction_output(RAW_1V8_EN, 1); ENR_usleep(200); } #endif /* vcm */ ret = regulator_enable(cam_vcm2v85_en); if (ret < 0) { pr_err("[CAM] couldn't enable regulator cam_vcm2v85_en\n"); regulator_put(cam_vcm2v85_en); cam_vcm2v85_en = NULL; return ret; } ENR_usleep(200); /* analog */ ret = regulator_enable(cam_a2v85_en); if (ret < 0) { pr_err("[CAM] couldn't enable regulator cam_a2v85_en\n"); regulator_put(cam_a2v85_en); cam_a2v85_en = NULL; return ret; } ENR_usleep(200); #if defined(CONFIG_RAWCHIP_ENABLE) if ((pcbid >= PROJECT_PHASE_XB) || (pcbid == PROJECT_PHASE_EVM)) { /* main camera core */ gpio_direction_output(CAM_D1V2_EN, 1); ENR_usleep(200); } #endif /* IO */ gpio_direction_output(CAMIO_1V8_EN, 1); ENR_usleep(200); tegra_pinmux_set_pullupdown(TEGRA_PINGROUP_KB_ROW6, TEGRA_PUPD_NORMAL); /* RSTN */ gpio_direction_output(FRONT_CAM_RST, 1); /* digital */ gpio_direction_output(CAM2_D1V2_EN, 1); ENR_usleep(200); /* CAM SEL */ gpio_direction_output(CAM_SEL, 1); ENR_msleep(1); tegra_gpio_disable(CAM_MCLK); ENR_msleep(1); #if defined(CONFIG_RAWCHIP_ENABLE) if ((pcbid >= PROJECT_PHASE_XB) || (pcbid == PROJECT_PHASE_EVM)) { /* RAW_RSTN */ ret = gpio_direction_output(RAW_RSTN, 1); ENR_msleep(1); rawchip_spi_clock_control(1); /* SPI send command to configure RAWCHIP here! */ yushan_spi_write(0x0008, 0x7f); ENR_msleep(1); } #endif pr_info("[CAM] %s --", __func__); return 0; }