static void aat2870_bl_enable(struct backlight_device *bd) { struct aat2870_bl_driver_data *drvdata = dev_get_drvdata(&bd->dev); int i; dbg("enable\n"); if (drvdata->en_pin >= 0) { // #ifdef CONFIG_MACH_LGE gpio_set_value(drvdata->en_pin, 0); mdelay(1); #endif // gpio_set_value(drvdata->en_pin, 1); // #ifdef CONFIG_MACH_LGE udelay(100); if (als_enabled == false) { dbg("Debugging Here : Default Flows\n"); /* Non ALC mode */ aat2870_bl_write(bd, AAT2870_BL_ALSF_, 0x00); /* backlight magnitude */ aat2870_bl_write(bd, AAT2870_BL_BLM, calc_brightness(bd, bd->props.brightness)); // set backlight magnitude because this function // can be called from aat2870_bl_set_ldo() // which does not perform magnitude setting } else { /* Auto Brightness Mode */ #if defined(FEATURE_ALC_TABLE_SELECTION)// int marked_id = get_panel_info(); for (i=0 ; init_alc_currents[marked_id][i].addr != 0xFF ; i++) { aat2870_bl_write(bd, init_alc_currents[marked_id][i].addr, init_alc_currents[marked_id][i].data); udelay(10); #else for (i=0 ; init_alc_currents[i].addr != 0xFF ; i++) { aat2870_bl_write(bd, init_alc_currents[i].addr, init_alc_currents[i].data); udelay(10); #endif /* FEATURE_ALC_TABLE_SELECTION */ } /* ALS Function, Log Scale, Rset 4K/16K, High gain input setting */ aat2870_bl_write(bd, AAT2870_BL_ALSF_, 0x71); /* SBIAS 3.0V, Offset No adjustment */ aat2870_bl_write(bd, AAT2870_BL_SBIAS, 0x01); /* Auto gain control, polling time 2sec, ALC gain -18.25% adjustment */ aat2870_bl_write(bd, AAT2870_BL_ALS_G, 0x07); } /* enable chennel */ aat2870_bl_write(bd, AAT2870_BL_EN, drvdata->avail_ch); if(drvdata->op_mode == AAT2870_OP_MODE_ALC) { dbg("Debugging op_mode [%d]\n", drvdata->op_mode); aat2870_bl_switch_mode(AAT2870_OP_MODE_ALC); dbg("Debugging ALC:ON\n"); } mdelay(1); #endif // } } static void aat2870_bl_disable(struct backlight_device *bd) { struct aat2870_bl_driver_data *drvdata = dev_get_drvdata(&bd->dev); dbg("disable\n"); if (drvdata->en_pin >= 0) { gpio_set_value(drvdata->en_pin, 0); // #ifdef CONFIG_MACH_LGE // to trigger enable during resume drvdata->brightness = 0; #endif // } } int aat2870_bl_set_ldo(enum aat2870_bl_ldo ldo, enum aat2870_bl_ldo_voltage volt, int en) { struct aat2870_bl_driver_data *drvdata; struct backlight_device *bd; int addr, data, shift; int ret = 0; if (!aat2870_bl_drvdata) { pr_err("%s: aat2870_bl_drvdata points NULL\n", AAT2870_BL_DRV_NAME); ret = -ENXIO; goto out; } drvdata = aat2870_bl_drvdata; bd = drvdata->bd; if ((volt < AAT2870_BL_LDO_1_2V) || (volt > AAT2870_BL_LDO_3_3V)) { dev_err(&bd->dev, "invalid LDO voltage: 0x%x\n", volt); ret = -EINVAL; goto out; } switch (ldo) { case AAT2870_BL_LDOA: addr = AAT2870_BL_LDO_AB; shift = 4; break; case AAT2870_BL_LDOB: addr = AAT2870_BL_LDO_AB; shift = 0; break; case AAT2870_BL_LDOC: addr = AAT2870_BL_LDO_CD; shift = 4; break; case AAT2870_BL_LDOD: addr = AAT2870_BL_LDO_CD; shift = 0; break; default: dev_err(&drvdata->bd->dev, "invalid LDO ID: %d\n", ldo); ret = -EINVAL; goto out; } if (drvdata->brightness == 0) aat2870_bl_enable(bd); data = aat2870_bl_read(bd, addr); data &= ~(AAT2870_BL_LDO_MASK << shift); data |= (volt << shift); if (aat2870_bl_write(bd, addr, data) < 0) { ret = -EIO; goto out; } addr = AAT2870_BL_EN_LDO; data = aat2870_bl_read(bd, addr); if (en) data |= (1 << ldo); else data &= ~(1 << ldo); if (aat2870_bl_write(bd, addr, data) < 0) { ret = -EIO; goto out; } out: return ret; } EXPORT_SYMBOL(aat2870_bl_set_ldo); static int aat2870_bl_get_brightness(struct backlight_device *bd) { return bd->props.brightness; } // MOBII_S [[email protected]] 2012-05-07 : Auto Brightness Setting From P990. #if defined(CONFIG_MACH_STAR_P990) || defined(CONFIG_MACH_STAR_SU660) static int aat2870_bl_update_modestatus(struct backlight_device *bd) { //MOBII_CHNANGE_S 20120819 [email protected] : Modify ALS table value struct aat2870_bl_driver_data *drvdata = dev_get_drvdata(&bd->dev); int brightness_mode = bd->props.brightness_mode; int next_mode; static struct aat2870_bl_driver_data *drv; drv = aat2870_bl_drvdata; if(brightness_mode == 1) { next_mode = AAT2870_OP_MODE_ALC; if (drv->lsensor_enable) { schedule_delayed_work(&drv->delayed_work_bl, drv->lsensor_poll_time); } } else { next_mode = AAT2870_OP_MODE_NORMAL; } aat2870_bl_switch_mode(next_mode); drv->op_mode = next_mode; //MOBII_CHNANGE_E 20120819 [email protected] : Modify ALS table value } #endif // MOBII_E [[email protected]] 2012-05-07 : Auto Brightness Setting From P990. static int aat2870_bl_update_status(struct backlight_device *bd) { struct aat2870_bl_driver_data *drvdata = dev_get_drvdata(&bd->dev); int brightness = bd->props.brightness; int ret = 0; if(is_suspended == true) { return 0; } if ((brightness < 0) || (brightness > bd->props.max_brightness)) { dev_err(&bd->dev, "invalid brightness: %d(0 <= brightness <= %d)\n", brightness, bd->props.max_brightness); ret = -EINVAL; goto out; } #if defined (CONFIG_PANICRPT) if( panicrpt_ispanic() == 1) goto out; #endif dbg("props: brightness=%d, power=%d, state=%d\n", bd->props.brightness, bd->props.power, bd->props.state); if ((bd->props.power != FB_BLANK_UNBLANK) || (bd->props.state & BL_CORE_FBBLANK) || (bd->props.state & BL_CORE_SUSPENDED)) { brightness = 0; } if (brightness == 0) { aat2870_bl_disable(bd); } else { if (drvdata->brightness == 0) { dbg("SEQ3 : enabled Funk!\n"); aat2870_bl_enable(bd); } if (aat2870_bl_write(bd, AAT2870_BL_BLM, calc_brightness(bd, brightness)) < 0) { ret = -EIO; goto out; } // // channel enable is done during aat2870_bl_enable() #ifndef CONFIG_MACH_LGE if (drvdata->brightness == 0) { if (aat2870_bl_write(bd, AAT2870_BL_EN, drvdata->avail_ch) < 0) { ret = -EIO; goto out; } } #endif // } drvdata->brightness = brightness; out: return ret; } static int aat2870_bl_check_fb(struct backlight_device *bd, struct fb_info *fi) { return 1; } static const struct backlight_ops aat2870_bl_ops = { .get_brightness = aat2870_bl_get_brightness, .update_status = aat2870_bl_update_status, // MOBII_S [[email protected]] 2012-05-07 : Auto Brightness Setting From P990. #if defined(CONFIG_MACH_STAR_P990) || defined(CONFIG_MACH_STAR_SU660) .update_modestatus = aat2870_bl_update_modestatus, #endif // MOBII_E [[email protected]] 2012-05-07 : Auto Brightness Setting From P990. .check_fb = aat2870_bl_check_fb, }; static unsigned int aat2870_bl_conv_to_lux(int lev) { struct aat2870_lux_tbl_t *tbl; unsigned val = 0; tbl = aat2870_lux_tbl; for (;;) { if (tbl->lev == lev) { val = tbl->lux; break; } else if (tbl->lev >= 0x1f) { break; } tbl++; } return val; } static int aat2870_bl_send_cmd(struct aat2870_bl_driver_data *drv, struct aat2870_ctl_tbl_t *tbl) { unsigned long delay = 0; if (tbl == NULL) { dbg("input ptr is null\n"); return -EIO; } mutex_lock(&drv->cmd_lock); for( ;;) { if (tbl->reg == 0xFF) { if (tbl->val != 0xFE) { delay = (unsigned long)tbl->val; } else break; } else { if (aat2870_bl_write(drv->bd, tbl->reg, tbl->val) != 0) dbg("i2c failed addr:%d, value:%d\n", tbl->reg, tbl->val); } tbl++; } mutex_unlock(&drv->cmd_lock); return 0; }
static void tegra_overlay_flip_worker(struct work_struct *work) { struct tegra_overlay_flip_data *data = container_of(work, struct tegra_overlay_flip_data, work); struct tegra_overlay_info *overlay = data->overlay; struct tegra_dc_win *win; struct tegra_dc_win *wins[TEGRA_FB_FLIP_N_WINDOWS]; struct nvmap_handle_ref *unpin_handles[TEGRA_FB_FLIP_N_WINDOWS]; int i, nr_win = 0, nr_unpin = 0; /* * 2011.07.27 [email protected] "for kernel panic" */ #if defined (CONFIG_PANICRPT) if (panicrpt_ispanic ()) return; #endif /* CONFIG_PANICRPT */ data = container_of(work, struct tegra_overlay_flip_data, work); for (i = 0; i < TEGRA_FB_FLIP_N_WINDOWS; i++) { struct tegra_overlay_flip_win *flip_win = &data->win[i]; int idx = flip_win->attr.index; if (idx == -1) continue; win = tegra_dc_get_window(overlay->dc, idx); if (!win) continue; if (win->flags && win->cur_handle && !data->didim_work) unpin_handles[nr_unpin++] = win->cur_handle; tegra_overlay_set_windowattr(overlay, win, &data->win[i]); wins[nr_win++] = win; #if 0 if (flip_win->attr.pre_syncpt_id < 0) continue; printk("%08x %08x\n", flip_win->attr.pre_syncpt_id, flip_win->attr.pre_syncpt_val); nvhost_syncpt_wait_timeout(&overlay->ndev->host->syncpt, flip_win->attr.pre_syncpt_id, flip_win->attr.pre_syncpt_val, msecs_to_jiffies(500)); #endif } if (data->flags & TEGRA_OVERLAY_FLIP_FLAG_BLEND_REORDER) { struct tegra_dc_win *dcwins[DC_N_WINDOWS]; for (i = 0; i < DC_N_WINDOWS; i++) dcwins[i] = tegra_dc_get_window(overlay->dc, i); tegra_overlay_blend_reorder(&overlay->blend, dcwins); tegra_dc_update_windows(dcwins, DC_N_WINDOWS); tegra_dc_sync_windows(dcwins, DC_N_WINDOWS); } else { tegra_dc_update_windows(wins, nr_win); /* TODO: implement swapinterval here */ tegra_dc_sync_windows(wins, nr_win); } if ((overlay->dc->out->flags & TEGRA_DC_OUT_ONE_SHOT_MODE) && (overlay->dc->out->flags & TEGRA_DC_OUT_N_SHOT_MODE)) { tegra_overlay_n_shot(data, unpin_handles, &nr_unpin); } else { tegra_dc_incr_syncpt_min(overlay->dc, 0, data->syncpt_max); /* unpin and deref previous front buffers */ for (i = 0; i < nr_unpin; i++) { nvmap_unpin(overlay->overlay_nvmap, unpin_handles[i]); nvmap_free(overlay->overlay_nvmap, unpin_handles[i]); } kfree(data); } }