apply.c revision 1f3f53ae5179ba7f24b4a429bc41773f1f4857ca
158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen/* 258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * Copyright (C) 2011 Texas Instruments 358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * Author: Tomi Valkeinen <tomi.valkeinen@ti.com> 458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * This program is free software; you can redistribute it and/or modify it 658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * under the terms of the GNU General Public License version 2 as published by 758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * the Free Software Foundation. 858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * This program is distributed in the hope that it will be useful, but WITHOUT 1058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or 1158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for 1258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * more details. 1358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 1458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * You should have received a copy of the GNU General Public License along with 1558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * this program. If not, see <http://www.gnu.org/licenses/>. 1658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen */ 1758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 1858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#define DSS_SUBSYS_NAME "APPLY" 1958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 2058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#include <linux/kernel.h> 2158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#include <linux/slab.h> 2258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#include <linux/spinlock.h> 2358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#include <linux/jiffies.h> 2458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 2558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#include <video/omapdss.h> 2658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 2758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#include "dss.h" 2858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#include "dss_features.h" 2958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 3058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen/* 3158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * We have 4 levels of cache for the dispc settings. First two are in SW and 3258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * the latter two in HW. 3358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 340b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen * set_info() 350b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen * v 3658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 370b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen * | user_info | 3858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 3958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * v 4058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * apply() 4158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * v 4258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 43d09c7aa8989caf44e8754e8aa81ce80217a0e98aTomi Valkeinen * | info | 4458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 4558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * v 46f6a5e0871f22428a7c74c07ddd791197c5f5d38fTomi Valkeinen * write_regs() 4758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * v 4858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 4958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * | shadow registers | 5058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 5158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * v 5258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * VFP or lcd/digit_enable 5358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * v 5458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 5558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * | registers | 5658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * +--------------------+ 5758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen */ 5858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 59c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinenstruct ovl_priv_data { 60c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 61c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen bool user_info_dirty; 62c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen struct omap_overlay_info user_info; 63c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 640b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen bool info_dirty; 6558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen struct omap_overlay_info info; 6658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 670b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen bool shadow_info_dirty; 680b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen 69aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen bool extra_info_dirty; 70aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen bool shadow_extra_info_dirty; 71aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 72aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen bool enabled; 735d5a97a6fbf98f82ae50c837eba3ebcfea0902f8Tomi Valkeinen enum omap_channel channel; 746dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen u32 fifo_low, fifo_high; 7582153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen 7682153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen /* 7782153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen * True if overlay is to be enabled. Used to check and calculate configs 7882153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen * for the overlay before it is enabled in the HW. 7982153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen */ 8082153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen bool enabling; 8158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen}; 8258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 83af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinenstruct mgr_priv_data { 84388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen 85388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen bool user_info_dirty; 86388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen struct omap_overlay_manager_info user_info; 87388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen 880b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen bool info_dirty; 8958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen struct omap_overlay_manager_info info; 9058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 910b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen bool shadow_info_dirty; 920b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen 9343a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen /* If true, GO bit is up and shadow registers cannot be written. 9443a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen * Never true for manual update displays */ 9543a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen bool busy; 9643a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen 9734861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen /* If true, dispc output is enabled */ 9834861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen bool updating; 9934861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen 100bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen /* If true, a display is enabled using this manager */ 101bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen bool enabled; 10258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen}; 10358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 10458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenstatic struct { 105c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen struct ovl_priv_data ovl_priv_data_array[MAX_DSS_OVERLAYS]; 106af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen struct mgr_priv_data mgr_priv_data_array[MAX_DSS_MANAGERS]; 10758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 10858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen bool irq_enabled; 109d09c7aa8989caf44e8754e8aa81ce80217a0e98aTomi Valkeinen} dss_data; 11058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 111d09c7aa8989caf44e8754e8aa81ce80217a0e98aTomi Valkeinen/* protects dss_data */ 112063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinenstatic spinlock_t data_lock; 1135558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen/* lock for blocking functions */ 1145558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinenstatic DEFINE_MUTEX(apply_lock); 115f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinenstatic DECLARE_COMPLETION(extra_updated_completion); 116063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen 11775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinenstatic void dss_register_vsync_isr(void); 11875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 119c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinenstatic struct ovl_priv_data *get_ovl_priv(struct omap_overlay *ovl) 120c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen{ 121d09c7aa8989caf44e8754e8aa81ce80217a0e98aTomi Valkeinen return &dss_data.ovl_priv_data_array[ovl->id]; 122c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen} 123c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen 124af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinenstatic struct mgr_priv_data *get_mgr_priv(struct omap_overlay_manager *mgr) 125af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen{ 126d09c7aa8989caf44e8754e8aa81ce80217a0e98aTomi Valkeinen return &dss_data.mgr_priv_data_array[mgr->id]; 127af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen} 128af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen 12958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenvoid dss_apply_init(void) 13058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 131c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen const int num_ovls = dss_feat_get_num_ovls(); 132c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen int i; 133c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 134063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen spin_lock_init(&data_lock); 135c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 136c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen for (i = 0; i < num_ovls; ++i) { 137c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen struct ovl_priv_data *op; 138c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 139c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op = &dss_data.ovl_priv_data_array[i]; 140c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 141c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->info.global_alpha = 255; 142c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 143c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen switch (i) { 144c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen case 0: 145c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->info.zorder = 0; 146c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen break; 147c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen case 1: 148c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->info.zorder = 149c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen dss_has_feature(FEAT_ALPHA_FREE_ZORDER) ? 3 : 0; 150c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen break; 151c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen case 2: 152c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->info.zorder = 153c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen dss_has_feature(FEAT_ALPHA_FREE_ZORDER) ? 2 : 0; 154c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen break; 155c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen case 3: 156c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->info.zorder = 157c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen dss_has_feature(FEAT_ALPHA_FREE_ZORDER) ? 1 : 0; 158c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen break; 159c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen } 160c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen 161c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->user_info = op->info; 162c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen } 16358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 16458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 16558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenstatic bool ovl_manual_update(struct omap_overlay *ovl) 16658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 16758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return ovl->manager->device->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE; 16858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 16958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 17058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenstatic bool mgr_manual_update(struct omap_overlay_manager *mgr) 17158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 17258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return mgr->device->caps & OMAP_DSS_DISPLAY_CAP_MANUAL_UPDATE; 17358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 17458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 17539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinenstatic int dss_check_settings_low(struct omap_overlay_manager *mgr, 17639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct omap_dss_device *dssdev, bool applying) 17739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen{ 17839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct omap_overlay_info *oi; 17939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct omap_overlay_manager_info *mi; 18039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct omap_overlay *ovl; 18139518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct omap_overlay_info *ois[MAX_DSS_OVERLAYS]; 18239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct ovl_priv_data *op; 18339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct mgr_priv_data *mp; 18439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 18539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen mp = get_mgr_priv(mgr); 18639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 18739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen if (applying && mp->user_info_dirty) 18839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen mi = &mp->user_info; 18939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen else 19039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen mi = &mp->info; 19139518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 19239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen /* collect the infos to be tested into the array */ 19339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen list_for_each_entry(ovl, &mgr->overlays, list) { 19439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen op = get_ovl_priv(ovl); 19539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 19682153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen if (!op->enabled && !op->enabling) 19739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen oi = NULL; 19839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen else if (applying && op->user_info_dirty) 19939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen oi = &op->user_info; 20039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen else 20139518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen oi = &op->info; 20239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 20339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen ois[ovl->id] = oi; 20439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen } 20539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 20639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen return dss_mgr_check(mgr, dssdev, mi, ois); 20739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen} 20839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 20939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen/* 21039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen * check manager and overlay settings using overlay_info from data->info 21139518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen */ 21239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinenstatic int dss_check_settings(struct omap_overlay_manager *mgr, 21339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct omap_dss_device *dssdev) 21439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen{ 21539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen return dss_check_settings_low(mgr, dssdev, false); 21639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen} 21739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 21839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen/* 21939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen * check manager and overlay settings using overlay_info from ovl->info if 22039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen * dirty and from data->info otherwise 22139518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen */ 22239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinenstatic int dss_check_settings_apply(struct omap_overlay_manager *mgr, 22339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen struct omap_dss_device *dssdev) 22439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen{ 22539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen return dss_check_settings_low(mgr, dssdev, true); 22639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen} 22739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 22875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinenstatic bool need_isr(void) 22975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen{ 23075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen const int num_mgrs = dss_feat_get_num_mgrs(); 23175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen int i; 23275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 23375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen for (i = 0; i < num_mgrs; ++i) { 23475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct omap_overlay_manager *mgr; 23575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct mgr_priv_data *mp; 23675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct omap_overlay *ovl; 23775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 23875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen mgr = omap_dss_get_overlay_manager(i); 23975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen mp = get_mgr_priv(mgr); 24075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 24175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen if (!mp->enabled) 24275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen continue; 24375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 24434861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (mgr_manual_update(mgr)) { 24534861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen /* to catch FRAMEDONE */ 24634861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (mp->updating) 24734861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen return true; 24834861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen } else { 24934861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen /* to catch GO bit going down */ 25034861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (mp->busy) 25134861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen return true; 25275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 25334861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen /* to write new values to registers */ 2540b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen if (mp->info_dirty) 25534861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen return true; 25675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 2579f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen /* to set GO bit */ 2589f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen if (mp->shadow_info_dirty) 2599f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen return true; 2609f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen 26134861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen list_for_each_entry(ovl, &mgr->overlays, list) { 26234861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen struct ovl_priv_data *op; 26375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 26434861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen op = get_ovl_priv(ovl); 26575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 2669f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen /* 2679f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen * NOTE: we check extra_info flags even for 2689f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen * disabled overlays, as extra_infos need to be 2699f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen * always written. 2709f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen */ 2719f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen 2729f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen /* to write new values to registers */ 2739f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen if (op->extra_info_dirty) 2749f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen return true; 2759f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen 2769f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen /* to set GO bit */ 2779f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen if (op->shadow_extra_info_dirty) 2789f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen return true; 2799f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen 28034861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (!op->enabled) 28134861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen continue; 28275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 28334861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen /* to write new values to registers */ 2849f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen if (op->info_dirty) 2859f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen return true; 2869f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen 2879f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen /* to set GO bit */ 2889f808956d3cd07c8dc69e213931b19bad56344fbTomi Valkeinen if (op->shadow_info_dirty) 28934861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen return true; 29034861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen } 29175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen } 29275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen } 29375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 29475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return false; 29575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen} 29675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 29775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinenstatic bool need_go(struct omap_overlay_manager *mgr) 29875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen{ 29975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct omap_overlay *ovl; 30075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct mgr_priv_data *mp; 30175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct ovl_priv_data *op; 30275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 30375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen mp = get_mgr_priv(mgr); 30475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 3050b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen if (mp->shadow_info_dirty) 30675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return true; 30775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 30875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen list_for_each_entry(ovl, &mgr->overlays, list) { 30975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen op = get_ovl_priv(ovl); 3100b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen if (op->shadow_info_dirty || op->shadow_extra_info_dirty) 31175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return true; 31275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen } 31375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 31475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return false; 31575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen} 31675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 317f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen/* returns true if an extra_info field is currently being updated */ 318f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinenstatic bool extra_info_update_ongoing(void) 319f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen{ 320f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen const int num_ovls = omap_dss_get_num_overlays(); 321f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen struct ovl_priv_data *op; 322f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen struct omap_overlay *ovl; 323f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen struct mgr_priv_data *mp; 324f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen int i; 325f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 326f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen for (i = 0; i < num_ovls; ++i) { 327f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen ovl = omap_dss_get_overlay(i); 328f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen op = get_ovl_priv(ovl); 329f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 3301f3f53ae5179ba7f24b4a429bc41773f1f4857caRob Clark if (!ovl->manager) 3311f3f53ae5179ba7f24b4a429bc41773f1f4857caRob Clark continue; 3321f3f53ae5179ba7f24b4a429bc41773f1f4857caRob Clark 333f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen mp = get_mgr_priv(ovl->manager); 334f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 335f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen if (!mp->enabled) 336f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen continue; 337f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 338153b6e7357778267e6914f2370a059e79a751371Tomi Valkeinen if (!mp->updating) 339f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen continue; 340f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 341153b6e7357778267e6914f2370a059e79a751371Tomi Valkeinen if (op->extra_info_dirty || op->shadow_extra_info_dirty) 342153b6e7357778267e6914f2370a059e79a751371Tomi Valkeinen return true; 343f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen } 344f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 345f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen return false; 346f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen} 347f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 348f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen/* wait until no extra_info updates are pending */ 349f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinenstatic void wait_pending_extra_info_updates(void) 350f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen{ 351f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen bool updating; 352f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen unsigned long flags; 353f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen unsigned long t; 354f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 355f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 356f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 357f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen updating = extra_info_update_ongoing(); 358f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 359f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen if (!updating) { 360f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 361f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen return; 362f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen } 363f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 364f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen init_completion(&extra_updated_completion); 365f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 366f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 367f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 368f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen t = msecs_to_jiffies(500); 369f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen wait_for_completion_timeout(&extra_updated_completion, t); 370f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 371f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen updating = extra_info_update_ongoing(); 372f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 373f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen WARN_ON(updating); 374f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen} 375f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 37658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenint dss_mgr_wait_for_go(struct omap_overlay_manager *mgr) 37758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 37858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen unsigned long timeout = msecs_to_jiffies(500); 379af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen struct mgr_priv_data *mp; 38058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen u32 irq; 38158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen int r; 38258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen int i; 38358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen struct omap_dss_device *dssdev = mgr->device; 38458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 38558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (!dssdev || dssdev->state != OMAP_DSS_DISPLAY_ACTIVE) 38658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return 0; 38758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 38858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (mgr_manual_update(mgr)) 38958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return 0; 39058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 391bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen irq = dispc_mgr_get_vsync_irq(mgr->id); 39258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 393af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen mp = get_mgr_priv(mgr); 39458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen i = 0; 39558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen while (1) { 39658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen unsigned long flags; 39758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen bool shadow_dirty, dirty; 39858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 399063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 4000b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen dirty = mp->info_dirty; 4010b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen shadow_dirty = mp->shadow_info_dirty; 402063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 40358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 40458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (!dirty && !shadow_dirty) { 40558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen r = 0; 40658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 40758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 40858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 40958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen /* 4 iterations is the worst case: 41058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 1 - initial iteration, dirty = true (between VFP and VSYNC) 41158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 2 - first VSYNC, dirty = true 41258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 3 - dirty = false, shadow_dirty = true 41358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 4 - shadow_dirty = false */ 41458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (i++ == 3) { 41558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen DSSERR("mgr(%d)->wait_for_go() not finishing\n", 41658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen mgr->id); 41758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen r = 0; 41858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 41958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 42058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 42158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen r = omap_dispc_wait_for_irq_interruptible_timeout(irq, timeout); 42258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (r == -ERESTARTSYS) 42358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 42458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 42558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (r) { 42658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen DSSERR("mgr(%d)->wait_for_go() timeout\n", mgr->id); 42758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 42858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 42958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 43058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 43158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return r; 43258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 43358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 43458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenint dss_mgr_wait_for_go_ovl(struct omap_overlay *ovl) 43558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 43658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen unsigned long timeout = msecs_to_jiffies(500); 437c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen struct ovl_priv_data *op; 43858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen struct omap_dss_device *dssdev; 43958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen u32 irq; 44058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen int r; 44158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen int i; 44258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 44358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (!ovl->manager) 44458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return 0; 44558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 44658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen dssdev = ovl->manager->device; 44758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 44858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (!dssdev || dssdev->state != OMAP_DSS_DISPLAY_ACTIVE) 44958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return 0; 45058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 45158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (ovl_manual_update(ovl)) 45258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return 0; 45358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 454bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen irq = dispc_mgr_get_vsync_irq(ovl->manager->id); 45558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 456c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen op = get_ovl_priv(ovl); 45758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen i = 0; 45858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen while (1) { 45958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen unsigned long flags; 46058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen bool shadow_dirty, dirty; 46158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 462063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 4630b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen dirty = op->info_dirty; 4640b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen shadow_dirty = op->shadow_info_dirty; 465063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 46658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 46758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (!dirty && !shadow_dirty) { 46858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen r = 0; 46958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 47058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 47158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 47258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen /* 4 iterations is the worst case: 47358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 1 - initial iteration, dirty = true (between VFP and VSYNC) 47458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 2 - first VSYNC, dirty = true 47558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 3 - dirty = false, shadow_dirty = true 47658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen * 4 - shadow_dirty = false */ 47758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (i++ == 3) { 47858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen DSSERR("ovl(%d)->wait_for_go() not finishing\n", 47958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen ovl->id); 48058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen r = 0; 48158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 48258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 48358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 48458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen r = omap_dispc_wait_for_irq_interruptible_timeout(irq, timeout); 48558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (r == -ERESTARTSYS) 48658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 48758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 48858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (r) { 48958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen DSSERR("ovl(%d)->wait_for_go() timeout\n", ovl->id); 49058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 49158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 49258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 49358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 49458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return r; 49558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 49658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 49775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinenstatic void dss_ovl_write_regs(struct omap_overlay *ovl) 49858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 49975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 50058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen struct omap_overlay_info *oi; 50158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen bool ilace, replication; 50234861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen struct mgr_priv_data *mp; 50358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen int r; 50458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 505f6a5e0871f22428a7c74c07ddd791197c5f5d38fTomi Valkeinen DSSDBGF("%d", ovl->id); 50658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 5070b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen if (!op->enabled || !op->info_dirty) 50875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return; 50958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 51075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen oi = &op->info; 51158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 51258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen replication = dss_use_replication(ovl->manager->device, oi->color_mode); 51358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 51458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen ilace = ovl->manager->device->type == OMAP_DISPLAY_TYPE_VENC; 51558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 516f6a5e0871f22428a7c74c07ddd791197c5f5d38fTomi Valkeinen r = dispc_ovl_setup(ovl->id, oi, ilace, replication); 51758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen if (r) { 51875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen /* 51975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen * We can't do much here, as this function can be called from 52075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen * vsync interrupt. 52175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen */ 522f6a5e0871f22428a7c74c07ddd791197c5f5d38fTomi Valkeinen DSSERR("dispc_ovl_setup failed for ovl %d\n", ovl->id); 52375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 52475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen /* This will leave fifo configurations in a nonoptimal state */ 52575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen op->enabled = false; 52675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dispc_ovl_enable(ovl->id, false); 52775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return; 52858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 52958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 53034861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen mp = get_mgr_priv(ovl->manager); 53134861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen 5320b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen op->info_dirty = false; 53334861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (mp->updating) 5340b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen op->shadow_info_dirty = true; 53558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 53658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 537aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinenstatic void dss_ovl_write_regs_extra(struct omap_overlay *ovl) 538aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen{ 539aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 54034861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen struct mgr_priv_data *mp; 541aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 542aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen DSSDBGF("%d", ovl->id); 543aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 54475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen if (!op->extra_info_dirty) 54575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return; 54675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 547aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen /* note: write also when op->enabled == false, so that the ovl gets 548aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen * disabled */ 549aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 550aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen dispc_ovl_enable(ovl->id, op->enabled); 5515d5a97a6fbf98f82ae50c837eba3ebcfea0902f8Tomi Valkeinen dispc_ovl_set_channel_out(ovl->id, op->channel); 5526dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen dispc_ovl_set_fifo_threshold(ovl->id, op->fifo_low, op->fifo_high); 55375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 55434861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen mp = get_mgr_priv(ovl->manager); 55534861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen 55675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen op->extra_info_dirty = false; 55734861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (mp->updating) 55834861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen op->shadow_extra_info_dirty = true; 559aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen} 560aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 561f6a5e0871f22428a7c74c07ddd791197c5f5d38fTomi Valkeinenstatic void dss_mgr_write_regs(struct omap_overlay_manager *mgr) 56258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 56375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct mgr_priv_data *mp = get_mgr_priv(mgr); 56475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct omap_overlay *ovl; 56558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 566f6a5e0871f22428a7c74c07ddd791197c5f5d38fTomi Valkeinen DSSDBGF("%d", mgr->id); 56758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 56875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen if (!mp->enabled) 56975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen return; 57058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 57175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen WARN_ON(mp->busy); 57258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 57358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen /* Commit overlay settings */ 57475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen list_for_each_entry(ovl, &mgr->overlays, list) { 57575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_ovl_write_regs(ovl); 576aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen dss_ovl_write_regs_extra(ovl); 577aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen } 578aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 5790b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen if (mp->info_dirty) { 58075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dispc_mgr_setup(mgr->id, &mp->info); 58158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 5820b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen mp->info_dirty = false; 58334861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (mp->updating) 5840b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen mp->shadow_info_dirty = true; 58558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 58675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen} 58775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 58875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinenstatic void dss_write_regs(void) 58975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen{ 59075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen const int num_mgrs = omap_dss_get_num_overlay_managers(); 59175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen int i; 59258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 59358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen for (i = 0; i < num_mgrs; ++i) { 59475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct omap_overlay_manager *mgr; 59575c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen struct mgr_priv_data *mp; 59639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen int r; 59775c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 598af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen mgr = omap_dss_get_overlay_manager(i); 599af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen mp = get_mgr_priv(mgr); 60058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 60175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen if (!mp->enabled || mgr_manual_update(mgr) || mp->busy) 60258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen continue; 60358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 60439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen r = dss_check_settings(mgr, mgr->device); 60539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen if (r) { 60639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen DSSERR("cannot write registers for manager %s: " 60739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen "illegal configuration\n", mgr->name); 60839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen continue; 60939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen } 61039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 61175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_mgr_write_regs(mgr); 6123ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen } 6133ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen} 61475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 6153ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinenstatic void dss_set_go_bits(void) 6163ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen{ 6173ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen const int num_mgrs = omap_dss_get_num_overlay_managers(); 6183ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen int i; 61958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 6203ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen for (i = 0; i < num_mgrs; ++i) { 6213ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen struct omap_overlay_manager *mgr; 6223ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen struct mgr_priv_data *mp; 62358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 6243ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen mgr = omap_dss_get_overlay_manager(i); 6253ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen mp = get_mgr_priv(mgr); 6263ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen 6273ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen if (!mp->enabled || mgr_manual_update(mgr) || mp->busy) 6283ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen continue; 6293ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen 6303ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen if (!need_go(mgr)) 6313ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen continue; 6323ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen 6333ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen mp->busy = true; 6343ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen 6353ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen if (!dss_data.irq_enabled && need_isr()) 6363ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen dss_register_vsync_isr(); 6373ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen 6383ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen dispc_mgr_go(mgr->id); 63975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen } 6403ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen 64158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 64258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 64358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenvoid dss_mgr_start_update(struct omap_overlay_manager *mgr) 64458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 645af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen struct mgr_priv_data *mp = get_mgr_priv(mgr); 646e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen unsigned long flags; 64739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen int r; 648e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 649e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 65058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 65134861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen WARN_ON(mp->updating); 65234861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen 65339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen r = dss_check_settings(mgr, mgr->device); 65439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen if (r) { 65539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen DSSERR("cannot start manual update: illegal configuration\n"); 65639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 65739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen return; 65839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen } 65939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 66075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_mgr_write_regs(mgr); 66158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 66234861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen mp->updating = true; 66358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 66434861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (!dss_data.irq_enabled && need_isr()) 66534861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen dss_register_vsync_isr(); 66658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 6677797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinen dispc_mgr_enable(mgr->id, true); 668e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 669e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 67058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 67158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 672dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinenstatic void dss_apply_irq_handler(void *data, u32 mask); 673dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 674dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinenstatic void dss_register_vsync_isr(void) 675dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen{ 676bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen const int num_mgrs = dss_feat_get_num_mgrs(); 677dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen u32 mask; 678bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen int r, i; 679dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 680bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen mask = 0; 681bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen for (i = 0; i < num_mgrs; ++i) 682bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen mask |= dispc_mgr_get_vsync_irq(i); 683dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 68434861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen for (i = 0; i < num_mgrs; ++i) 68534861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen mask |= dispc_mgr_get_framedone_irq(i); 68634861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen 687dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen r = omap_dispc_register_isr(dss_apply_irq_handler, NULL, mask); 688dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen WARN_ON(r); 689dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 690d09c7aa8989caf44e8754e8aa81ce80217a0e98aTomi Valkeinen dss_data.irq_enabled = true; 691dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen} 692dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 693dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinenstatic void dss_unregister_vsync_isr(void) 694dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen{ 695bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen const int num_mgrs = dss_feat_get_num_mgrs(); 696dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen u32 mask; 697bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen int r, i; 698dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 699bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen mask = 0; 700bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen for (i = 0; i < num_mgrs; ++i) 701bc1a95181f7069920c13fcef0159ffa7d61160f1Tomi Valkeinen mask |= dispc_mgr_get_vsync_irq(i); 702dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 70334861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen for (i = 0; i < num_mgrs; ++i) 70434861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen mask |= dispc_mgr_get_framedone_irq(i); 70534861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen 706dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen r = omap_dispc_unregister_isr(dss_apply_irq_handler, NULL, mask); 707dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen WARN_ON(r); 708dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 709d09c7aa8989caf44e8754e8aa81ce80217a0e98aTomi Valkeinen dss_data.irq_enabled = false; 710dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen} 711dbce0160af31d2ea323656c201d8debf5af789bfTomi Valkeinen 7127609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinenstatic void mgr_clear_shadow_dirty(struct omap_overlay_manager *mgr) 71358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 714c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen struct omap_overlay *ovl; 715af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen struct mgr_priv_data *mp; 716c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen struct ovl_priv_data *op; 7177609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen 7187609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen mp = get_mgr_priv(mgr); 7190b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen mp->shadow_info_dirty = false; 7207609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen 7217609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen list_for_each_entry(ovl, &mgr->overlays, list) { 7227609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen op = get_ovl_priv(ovl); 7230b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen op->shadow_info_dirty = false; 7247609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen op->shadow_extra_info_dirty = false; 7257609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen } 7267609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen} 7277609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen 7287609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinenstatic void dss_apply_irq_handler(void *data, u32 mask) 7297609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen{ 73058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen const int num_mgrs = dss_feat_get_num_mgrs(); 73175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen int i; 732f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen bool extra_updating; 73358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 734063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen spin_lock(&data_lock); 73558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 7367609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen /* clear busy, updating flags, shadow_dirty flags */ 73743a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen for (i = 0; i < num_mgrs; i++) { 7387609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen struct omap_overlay_manager *mgr; 7397609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen struct mgr_priv_data *mp; 7405b2141719aa8a14ebd242c60b4ce6a580276f7cdTomi Valkeinen bool was_updating; 7417609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen 74243a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen mgr = omap_dss_get_overlay_manager(i); 74343a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen mp = get_mgr_priv(mgr); 74443a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen 7457609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen if (!mp->enabled) 74643a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen continue; 74743a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen 7485b2141719aa8a14ebd242c60b4ce6a580276f7cdTomi Valkeinen was_updating = mp->updating; 7497609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen mp->updating = dispc_mgr_is_enabled(i); 75058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 7517609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen if (!mgr_manual_update(mgr)) { 7525b2141719aa8a14ebd242c60b4ce6a580276f7cdTomi Valkeinen bool was_busy = mp->busy; 7537609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen mp->busy = dispc_mgr_go_busy(i); 75443a972d96b6ea2b9e3d6b55b9724c9f61d802c68Tomi Valkeinen 7555b2141719aa8a14ebd242c60b4ce6a580276f7cdTomi Valkeinen if (was_busy && !mp->busy) 7567609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen mgr_clear_shadow_dirty(mgr); 7577609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen } else { 7585b2141719aa8a14ebd242c60b4ce6a580276f7cdTomi Valkeinen if (was_updating && !mp->updating) 7597609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen mgr_clear_shadow_dirty(mgr); 7607609893c637b422eec88b57d204f02d8798cfc65Tomi Valkeinen } 76158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 76258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 76375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_write_regs(); 7643ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen dss_set_go_bits(); 76558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 766f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen extra_updating = extra_info_update_ongoing(); 767f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen if (!extra_updating) 768f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen complete_all(&extra_updated_completion); 769f1577ce18004337ec2f6f48109ca14cac10a0a4fTomi Valkeinen 77075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen if (!need_isr()) 77175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_unregister_vsync_isr(); 77258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 773063fd701abba3b58c36b6043d5feacf0fdc76cbdTomi Valkeinen spin_unlock(&data_lock); 77458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 77558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 7765738b633136a41923b4ba75e6b1a160d08539c99Tomi Valkeinenstatic void omap_dss_mgr_apply_ovl(struct omap_overlay *ovl) 77758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 778c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen struct ovl_priv_data *op; 77958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 780c10c6f042b6a5940c522a334a716d57b40f7dec9Tomi Valkeinen op = get_ovl_priv(ovl); 78158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 782c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen if (!op->user_info_dirty) 7835738b633136a41923b4ba75e6b1a160d08539c99Tomi Valkeinen return; 78458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 785c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->user_info_dirty = false; 7860b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen op->info_dirty = true; 787c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->info = op->user_info; 78858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 78958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 79058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinenstatic void omap_dss_mgr_apply_mgr(struct omap_overlay_manager *mgr) 79158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 792af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen struct mgr_priv_data *mp; 79358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 794af3d64b2c674bc6246bb04654b484f34287fbbc3Tomi Valkeinen mp = get_mgr_priv(mgr); 79558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 796388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen if (!mp->user_info_dirty) 79758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen return; 79858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 799388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen mp->user_info_dirty = false; 8000b53f17971700f673492e2e91b5069893e5f2d0bTomi Valkeinen mp->info_dirty = true; 801388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen mp->info = mp->user_info; 80258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 80358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 8046dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinenint omap_dss_mgr_apply(struct omap_overlay_manager *mgr) 80558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 8066dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen unsigned long flags; 8076dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen struct omap_overlay *ovl; 80839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen int r; 8096dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 8106dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen DSSDBG("omap_dss_mgr_apply(%s)\n", mgr->name); 8116dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 8126dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 8136dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 81439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen r = dss_check_settings_apply(mgr, mgr->device); 81539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen if (r) { 81639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 81739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen DSSERR("failed to apply settings: illegal configuration.\n"); 81839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen return r; 81939518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen } 82039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 8216dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen /* Configure overlays */ 8226dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen list_for_each_entry(ovl, &mgr->overlays, list) 8236dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen omap_dss_mgr_apply_ovl(ovl); 8246dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 8256dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen /* Configure manager */ 8266dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen omap_dss_mgr_apply_mgr(mgr); 8276dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 8286dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen dss_write_regs(); 8293ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen dss_set_go_bits(); 8306dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 8316dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 8326dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 833e70f98acaa84ec9ad55e544d0dc8b2d0a36bbecaTomi Valkeinen return 0; 8346dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen} 8356dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 836841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinenstatic void dss_apply_ovl_enable(struct omap_overlay *ovl, bool enable) 837841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen{ 838841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen struct ovl_priv_data *op; 839841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen 840841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen op = get_ovl_priv(ovl); 841841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen 842841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen if (op->enabled == enable) 843841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen return; 844841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen 845841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen op->enabled = enable; 846841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen op->extra_info_dirty = true; 847841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen} 848841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen 84904576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinenstatic void dss_apply_ovl_fifo_thresholds(struct omap_overlay *ovl, 85004576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen u32 fifo_low, u32 fifo_high) 85104576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen{ 85204576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 85304576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen 85404576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen if (op->fifo_low == fifo_low && op->fifo_high == fifo_high) 85504576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen return; 85604576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen 85704576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen op->fifo_low = fifo_low; 85804576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen op->fifo_high = fifo_high; 85904576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen op->extra_info_dirty = true; 86004576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen} 86104576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen 8626dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinenstatic void dss_ovl_setup_fifo(struct omap_overlay *ovl) 8636dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen{ 8646dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 86558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen struct omap_dss_device *dssdev; 86658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen u32 size, burst_size; 8676dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen u32 fifo_low, fifo_high; 86858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 86975ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen if (!op->enabled && !op->enabling) 87075ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen return; 87175ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen 87258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen dssdev = ovl->manager->device; 87358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 87458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen size = dispc_ovl_get_fifo_size(ovl->id); 87558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 87658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen burst_size = dispc_ovl_get_burst_size(ovl->id); 87758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 87858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen switch (dssdev->type) { 87958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen case OMAP_DISPLAY_TYPE_DPI: 88058f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen case OMAP_DISPLAY_TYPE_DBI: 88158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen case OMAP_DISPLAY_TYPE_SDI: 88258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen case OMAP_DISPLAY_TYPE_VENC: 88358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen case OMAP_DISPLAY_TYPE_HDMI: 88458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen default_get_overlay_fifo_thresholds(ovl->id, size, 8856dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen burst_size, &fifo_low, &fifo_high); 88658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 88758f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#ifdef CONFIG_OMAP2_DSS_DSI 88858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen case OMAP_DISPLAY_TYPE_DSI: 88958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen dsi_get_overlay_fifo_thresholds(ovl->id, size, 8906dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen burst_size, &fifo_low, &fifo_high); 89158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen break; 89258f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen#endif 89358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen default: 89458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen BUG(); 89558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen } 8966dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 89704576d415e01aa08752bf3884db9862cfbba9115Tomi Valkeinen dss_apply_ovl_fifo_thresholds(ovl, fifo_low, fifo_high); 89858f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 89958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 9006dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinenstatic void dss_mgr_setup_fifos(struct omap_overlay_manager *mgr) 90158f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen{ 90207e327c9c18b382656bf455051759be8182627aeTomi Valkeinen struct omap_overlay *ovl; 9036dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen struct mgr_priv_data *mp; 90458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 9056dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen mp = get_mgr_priv(mgr); 90658f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 9076dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen if (!mp->enabled) 9086dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen return; 90958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 91075ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen list_for_each_entry(ovl, &mgr->overlays, list) 91175ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen dss_ovl_setup_fifo(ovl); 91275ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen} 91358f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 91475ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinenstatic void dss_setup_fifos(void) 91575ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen{ 91675ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen const int num_mgrs = omap_dss_get_num_overlay_managers(); 91775ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen struct omap_overlay_manager *mgr; 91875ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen int i; 91958f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 92075ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen for (i = 0; i < num_mgrs; ++i) { 92175ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen mgr = omap_dss_get_overlay_manager(i); 92275ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen dss_mgr_setup_fifos(mgr); 9236dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen } 92458f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen} 92558f2554807a7dc627f1583d1d4363b85758cf685Tomi Valkeinen 9262a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinenint dss_mgr_enable(struct omap_overlay_manager *mgr) 9277797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinen{ 928bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen struct mgr_priv_data *mp = get_mgr_priv(mgr); 929bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen unsigned long flags; 93039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen int r; 931bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen 9325558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_lock(&apply_lock); 9335558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 934e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen if (mp->enabled) 935e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen goto out; 936e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen 937bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 938bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen 939bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen mp->enabled = true; 940a6b24f83601530f69ee36ac48527336e3c79bea8Tomi Valkeinen 94139518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen r = dss_check_settings(mgr, mgr->device); 94239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen if (r) { 94339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen DSSERR("failed to enable manager %d: check_settings failed\n", 94439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen mgr->id); 9452a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinen goto err; 94639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen } 94739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 94875ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen dss_setup_fifos(); 9496dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 95075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_write_regs(); 9513ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen dss_set_go_bits(); 95275c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 95334861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen if (!mgr_manual_update(mgr)) 95434861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen mp->updating = true; 95534861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen 956bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 9575558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 95875c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen if (!mgr_manual_update(mgr)) 95975c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dispc_mgr_enable(mgr->id, true); 96075c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 961e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinenout: 9625558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 9632a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinen 9642a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinen return 0; 9652a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinen 9662a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinenerr: 967a6b24f83601530f69ee36ac48527336e3c79bea8Tomi Valkeinen mp->enabled = false; 9682a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 9692a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinen mutex_unlock(&apply_lock); 9702a4ee7ee685f3bf996461ed0d148857ce85a00e2Tomi Valkeinen return r; 9717797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinen} 9727797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinen 9737797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinenvoid dss_mgr_disable(struct omap_overlay_manager *mgr) 9747797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinen{ 975bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen struct mgr_priv_data *mp = get_mgr_priv(mgr); 976bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen unsigned long flags; 977bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen 9785558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_lock(&apply_lock); 9795558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 980e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen if (!mp->enabled) 981e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen goto out; 982e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen 9839a147a65de1ac89e506ef90413f41ebd96e03fd3Tomi Valkeinen if (!mgr_manual_update(mgr)) 9849a147a65de1ac89e506ef90413f41ebd96e03fd3Tomi Valkeinen dispc_mgr_enable(mgr->id, false); 985bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen 986bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 987bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen 98834861378a54e3fcac0eb87317ded2554b087494eTomi Valkeinen mp->updating = false; 989bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen mp->enabled = false; 990bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen 991bf213523fe9708572a0b0a9149f7196a4f058564Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 9925558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 993e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinenout: 9945558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 9957797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinen} 9967797c6da64852b06b585b7eca8d3f657bfc9fa47Tomi Valkeinen 997eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinenint dss_mgr_set_info(struct omap_overlay_manager *mgr, 998eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen struct omap_overlay_manager_info *info) 999eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen{ 1000388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen struct mgr_priv_data *mp = get_mgr_priv(mgr); 1001e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen unsigned long flags; 1002f17d04fbbb201c05700359e94e2747c210f99852Tomi Valkeinen int r; 1003f17d04fbbb201c05700359e94e2747c210f99852Tomi Valkeinen 1004f17d04fbbb201c05700359e94e2747c210f99852Tomi Valkeinen r = dss_mgr_simple_check(mgr, info); 1005f17d04fbbb201c05700359e94e2747c210f99852Tomi Valkeinen if (r) 1006f17d04fbbb201c05700359e94e2747c210f99852Tomi Valkeinen return r; 1007e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1008e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1009e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1010388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen mp->user_info = *info; 1011388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen mp->user_info_dirty = true; 1012eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1013e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1014e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1015eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen return 0; 1016eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen} 1017eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1018eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinenvoid dss_mgr_get_info(struct omap_overlay_manager *mgr, 1019eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen struct omap_overlay_manager_info *info) 1020eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen{ 1021388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen struct mgr_priv_data *mp = get_mgr_priv(mgr); 1022e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen unsigned long flags; 1023e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1024e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1025e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1026388c4c6cbb335e69fe23c8d18bd4b0e8dd66901bTomi Valkeinen *info = mp->user_info; 1027e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1028e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1029eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen} 1030eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1031eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinenint dss_mgr_set_device(struct omap_overlay_manager *mgr, 1032eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen struct omap_dss_device *dssdev) 1033eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen{ 1034eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen int r; 1035eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 10365558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_lock(&apply_lock); 10375558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1038eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen if (dssdev->manager) { 1039eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen DSSERR("display '%s' already has a manager '%s'\n", 1040eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen dssdev->name, dssdev->manager->name); 10415558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 10425558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 1043eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen } 1044eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1045eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen if ((mgr->supported_displays & dssdev->type) == 0) { 1046eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen DSSERR("display '%s' does not support manager '%s'\n", 1047eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen dssdev->name, mgr->name); 10485558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 10495558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 1050eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen } 1051eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1052eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen dssdev->manager = mgr; 1053eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen mgr->device = dssdev; 1054eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 10555558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 10565558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1057eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen return 0; 10585558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinenerr: 10595558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 10605558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen return r; 1061eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen} 1062eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1063eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinenint dss_mgr_unset_device(struct omap_overlay_manager *mgr) 1064eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen{ 10655558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen int r; 10665558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 10675558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_lock(&apply_lock); 10685558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1069eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen if (!mgr->device) { 1070eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen DSSERR("failed to unset display, display not set.\n"); 10715558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 10725558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 1073eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen } 1074eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1075eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen /* 1076eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen * Don't allow currently enabled displays to have the overlay manager 1077eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen * pulled out from underneath them 1078eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen */ 10795558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen if (mgr->device->state != OMAP_DSS_DISPLAY_DISABLED) { 10805558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 10815558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 10825558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen } 1083eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1084eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen mgr->device->manager = NULL; 1085eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen mgr->device = NULL; 1086eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 10875558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 10885558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1089eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen return 0; 10905558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinenerr: 10915558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 10925558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen return r; 1093eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen} 1094eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1095eb70d739adf2266e744a784a1272f1c92a257b81Tomi Valkeinen 1096f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinenint dss_ovl_set_info(struct omap_overlay *ovl, 1097f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen struct omap_overlay_info *info) 1098f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen{ 1099c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 1100e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen unsigned long flags; 1101fcc764dca80ead39b7391ff2c67a6b78de16d7a9Tomi Valkeinen int r; 1102fcc764dca80ead39b7391ff2c67a6b78de16d7a9Tomi Valkeinen 1103fcc764dca80ead39b7391ff2c67a6b78de16d7a9Tomi Valkeinen r = dss_ovl_simple_check(ovl, info); 1104fcc764dca80ead39b7391ff2c67a6b78de16d7a9Tomi Valkeinen if (r) 1105fcc764dca80ead39b7391ff2c67a6b78de16d7a9Tomi Valkeinen return r; 1106e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1107e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1108e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1109c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->user_info = *info; 1110c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen op->user_info_dirty = true; 1111f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1112e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1113e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1114f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen return 0; 1115f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen} 1116f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1117f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinenvoid dss_ovl_get_info(struct omap_overlay *ovl, 1118f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen struct omap_overlay_info *info) 1119f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen{ 1120c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 1121e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen unsigned long flags; 1122e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1123e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1124e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1125c1a9febfafa2a9a9ac09b2de4c80aa96b41a03d1Tomi Valkeinen *info = op->user_info; 1126e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen 1127e0a2aa5b3d1a26969ba906447c816d44c018969dTomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1128f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen} 1129f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1130f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinenint dss_ovl_set_manager(struct omap_overlay *ovl, 1131f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen struct omap_overlay_manager *mgr) 1132f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen{ 1133aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 1134aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen unsigned long flags; 11355558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen int r; 11365558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1137f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen if (!mgr) 1138f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen return -EINVAL; 1139f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 11405558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_lock(&apply_lock); 11415558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1142f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen if (ovl->manager) { 1143f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen DSSERR("overlay '%s' already has a manager '%s'\n", 1144f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen ovl->name, ovl->manager->name); 11455558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 11465558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 1147f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen } 1148f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1149aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1150aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1151aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen if (op->enabled) { 1152aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1153f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen DSSERR("overlay has to be disabled to change the manager\n"); 11545558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 11555558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 1156f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen } 1157f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 11585d5a97a6fbf98f82ae50c837eba3ebcfea0902f8Tomi Valkeinen op->channel = mgr->id; 11595d5a97a6fbf98f82ae50c837eba3ebcfea0902f8Tomi Valkeinen op->extra_info_dirty = true; 11605d5a97a6fbf98f82ae50c837eba3ebcfea0902f8Tomi Valkeinen 1161f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen ovl->manager = mgr; 1162f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen list_add_tail(&ovl->list, &mgr->overlays); 1163f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1164aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1165aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1166f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen /* XXX: When there is an overlay on a DSI manual update display, and 1167f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * the overlay is first disabled, then moved to tv, and enabled, we 1168f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * seem to get SYNC_LOST_DIGIT error. 1169f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * 1170f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * Waiting doesn't seem to help, but updating the manual update display 1171f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * after disabling the overlay seems to fix this. This hints that the 1172f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * overlay is perhaps somehow tied to the LCD output until the output 1173f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * is updated. 1174f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * 1175f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * Userspace workaround for this is to update the LCD after disabling 1176f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen * the overlay, but before moving the overlay to TV. 1177f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen */ 1178f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 11795558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 11805558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1181f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen return 0; 11825558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinenerr: 11835558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 11845558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen return r; 1185f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen} 1186f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1187f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinenint dss_ovl_unset_manager(struct omap_overlay *ovl) 1188f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen{ 1189aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 1190aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen unsigned long flags; 11915558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen int r; 11925558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 11935558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_lock(&apply_lock); 11945558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1195f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen if (!ovl->manager) { 1196f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen DSSERR("failed to detach overlay: manager not set\n"); 11975558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 11985558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 1199f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen } 1200f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1201aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1202aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1203aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen if (op->enabled) { 1204aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1205f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen DSSERR("overlay has to be disabled to unset the manager\n"); 12065558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen r = -EINVAL; 12075558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen goto err; 1208f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen } 1209f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 12105d5a97a6fbf98f82ae50c837eba3ebcfea0902f8Tomi Valkeinen op->channel = -1; 12115d5a97a6fbf98f82ae50c837eba3ebcfea0902f8Tomi Valkeinen 1212f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen ovl->manager = NULL; 1213f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen list_del(&ovl->list); 1214f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1215aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1216aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1217aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen mutex_unlock(&apply_lock); 1218aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1219aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen return 0; 1220aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinenerr: 1221aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen mutex_unlock(&apply_lock); 1222aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen return r; 1223aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen} 1224aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1225aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinenbool dss_ovl_is_enabled(struct omap_overlay *ovl) 1226aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen{ 1227aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 1228aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen unsigned long flags; 1229aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen bool e; 1230aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1231aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1232aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1233aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen e = op->enabled; 1234aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1235aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1236aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1237aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen return e; 1238aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen} 1239aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1240aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinenint dss_ovl_enable(struct omap_overlay *ovl) 1241aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen{ 1242aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 1243aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen unsigned long flags; 1244aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen int r; 1245aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1246aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen mutex_lock(&apply_lock); 1247aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1248e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen if (op->enabled) { 1249e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen r = 0; 125039518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen goto err1; 1251e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen } 1252e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen 1253aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen if (ovl->manager == NULL || ovl->manager->device == NULL) { 1254aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen r = -EINVAL; 125539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen goto err1; 1256aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen } 1257aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1258aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1259aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 126082153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen op->enabling = true; 126182153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen 126239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen r = dss_check_settings(ovl->manager, ovl->manager->device); 126339518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen if (r) { 126439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen DSSERR("failed to enable overlay %d: check_settings failed\n", 126539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen ovl->id); 126639518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen goto err2; 126739518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen } 126839518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen 126975ae118a0028810f93a746c25f4bb018fb044323Tomi Valkeinen dss_setup_fifos(); 12706dc802e2901d33e02efad3c90bb2034fd20c79e7Tomi Valkeinen 127182153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen op->enabling = false; 127282153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen dss_apply_ovl_enable(ovl, true); 127382153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen 127475c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_write_regs(); 12753ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen dss_set_go_bits(); 127675c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 1277aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1278aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1279aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen mutex_unlock(&apply_lock); 1280aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1281aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen return 0; 128239518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinenerr2: 128382153eda076ee4df434bb1008f24e46590f76dfcTomi Valkeinen op->enabling = false; 128439518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 128539518356ccd6e439abae24e1a24d84dcd12ff207Tomi Valkeinenerr1: 1286aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen mutex_unlock(&apply_lock); 1287aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen return r; 1288aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen} 1289aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1290aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinenint dss_ovl_disable(struct omap_overlay *ovl) 1291aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen{ 1292aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen struct ovl_priv_data *op = get_ovl_priv(ovl); 1293aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen unsigned long flags; 1294aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen int r; 1295aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1296aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen mutex_lock(&apply_lock); 1297aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1298e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen if (!op->enabled) { 1299e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen r = 0; 1300e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen goto err; 1301e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen } 1302e4f7ad702ef271d2b0c03e9904b05f9bcbf0808bTomi Valkeinen 1303aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen if (ovl->manager == NULL || ovl->manager->device == NULL) { 1304aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen r = -EINVAL; 1305aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen goto err; 1306aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen } 1307aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1308aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_lock_irqsave(&data_lock, flags); 1309aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 1310841c09c7975c67fe7741564d98265de28a5764d0Tomi Valkeinen dss_apply_ovl_enable(ovl, false); 131175c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen dss_write_regs(); 13123ab15b2aa70369e0360f12e35e47bca1a269138bTomi Valkeinen dss_set_go_bits(); 131375c949653fdf77a17753ffb8462a3c458c476271Tomi Valkeinen 1314aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen spin_unlock_irqrestore(&data_lock, flags); 1315aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 13165558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 13175558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen 1318f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen return 0; 1319aaa874a985158383c4b394c687c716ef26288741Tomi Valkeinen 13205558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinenerr: 13215558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen mutex_unlock(&apply_lock); 13225558db3fdd52e3928d5eaabe363e1576dc5fe473Tomi Valkeinen return r; 1323f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen} 1324f77b30700e5c0a6b5220b3a964bf6c40d5e71416Tomi Valkeinen 1325