summaryrefslogtreecommitdiff
path: root/drivers/video
diff options
context:
space:
mode:
authorMarcel Ziswiler <marcel.ziswiler@toradex.com>2013-03-03 00:51:24 +0100
committerMarcel Ziswiler <marcel.ziswiler@toradex.com>2013-03-03 00:51:24 +0100
commitd6fa4ec20db6bd0b403d2d99fd9423e6c0f3f845 (patch)
treee9ddb16309d2b546a400593afc07846ce9ed6746 /drivers/video
parentdc1cfc34b2a07c5441d68ca21ae4296822ee4df6 (diff)
parent1ff6b9489fbc737e3e2bc7660b92cebbfaea5247 (diff)
Conflicts:
arch/arm/mach-tegra/common.c drivers/ata/ahci-tegra.c
Diffstat (limited to 'drivers/video')
-rw-r--r--drivers/video/tegra/dc/dc.c61
-rw-r--r--drivers/video/tegra/dc/dc_config.c24
-rw-r--r--drivers/video/tegra/fb.c85
-rw-r--r--drivers/video/tegra/host/bus_client.c12
-rw-r--r--drivers/video/tegra/host/bus_client.h1
-rw-r--r--drivers/video/tegra/nvmap/nvmap.c13
6 files changed, 77 insertions, 119 deletions
diff --git a/drivers/video/tegra/dc/dc.c b/drivers/video/tegra/dc/dc.c
index ca2103f73c8a..d4c3f8bc9a49 100644
--- a/drivers/video/tegra/dc/dc.c
+++ b/drivers/video/tegra/dc/dc.c
@@ -58,21 +58,6 @@
#define DC_COM_PIN_OUTPUT_POLARITY1_INIT_VAL 0x01000000
#define DC_COM_PIN_OUTPUT_POLARITY3_INIT_VAL 0x0
-static struct fb_videomode tegra_dc_hdmi_fallback_mode = {
- .refresh = 60,
- .xres = 640,
- .yres = 480,
- .pixclock = KHZ2PICOS(25200),
- .hsync_len = 96, /* h_sync_width */
- .vsync_len = 2, /* v_sync_width */
- .left_margin = 48, /* h_back_porch */
- .upper_margin = 33, /* v_back_porch */
- .right_margin = 16, /* h_front_porch */
- .lower_margin = 10, /* v_front_porch */
- .vmode = 0,
- .sync = 0,
-};
-
static struct tegra_dc_mode override_disp_mode[3];
static void _tegra_dc_controller_disable(struct tegra_dc *dc);
@@ -1462,34 +1447,6 @@ static bool _tegra_dc_controller_reset_enable(struct tegra_dc *dc)
}
#endif
-static int _tegra_dc_set_default_videomode(struct tegra_dc *dc)
-{
- if (dc->mode.pclk == 0) {
- switch (dc->out->type) {
- case TEGRA_DC_OUT_HDMI:
- /* DC enable called but no videomode is loaded.
- Check if HDMI is connected, then set fallback mdoe */
- if (tegra_dc_hpd(dc)) {
- return tegra_dc_set_fb_mode(dc,
- &tegra_dc_hdmi_fallback_mode, 0);
- } else
- return false;
-
- break;
-
- /* Do nothing for other outputs for now */
- case TEGRA_DC_OUT_RGB:
-
- case TEGRA_DC_OUT_DSI:
-
- default:
- return false;
- }
- }
-
- return false;
-}
-
static bool _tegra_dc_enable(struct tegra_dc *dc)
{
if (dc->mode.pclk == 0)
@@ -1881,13 +1838,6 @@ static int tegra_dc_probe(struct nvhost_device *ndev,
dc->ext = NULL;
}
- mutex_lock(&dc->lock);
- if (dc->pdata->flags & TEGRA_DC_FLAG_ENABLED) {
- _tegra_dc_set_default_videomode(dc);
- dc->enabled = _tegra_dc_enable(dc);
- }
- mutex_unlock(&dc->lock);
-
/* interrupt handler must be registered before tegra_fb_register() */
if (request_irq(irq, tegra_dc_irq, 0,
dev_name(&ndev->dev), dc)) {
@@ -1895,6 +1845,12 @@ static int tegra_dc_probe(struct nvhost_device *ndev,
ret = -EBUSY;
goto err_put_emc_clk;
}
+ disable_dc_irq(irq);
+
+ mutex_lock(&dc->lock);
+ if (dc->pdata->flags & TEGRA_DC_FLAG_ENABLED)
+ dc->enabled = _tegra_dc_enable(dc);
+ mutex_unlock(&dc->lock);
tegra_dc_create_debugfs(dc);
@@ -1919,6 +1875,7 @@ static int tegra_dc_probe(struct nvhost_device *ndev,
}
dc->fb = tegra_fb_register(ndev, dc, dc->pdata->fb, fb_mem);
+
if (IS_ERR_OR_NULL(dc->fb))
dc->fb = NULL;
}
@@ -2033,10 +1990,8 @@ static int tegra_dc_resume(struct nvhost_device *ndev)
mutex_lock(&dc->lock);
dc->suspended = false;
- if (dc->enabled) {
- _tegra_dc_set_default_videomode(dc);
+ if (dc->enabled)
_tegra_dc_enable(dc);
- }
if (dc->out && dc->out->hotplug_init)
dc->out->hotplug_init();
diff --git a/drivers/video/tegra/dc/dc_config.c b/drivers/video/tegra/dc/dc_config.c
index f238faddab12..90f505bba28a 100644
--- a/drivers/video/tegra/dc/dc_config.c
+++ b/drivers/video/tegra/dc/dc_config.c
@@ -23,7 +23,7 @@
static struct tegra_dc_feature_entry t20_feature_entries_a[] = {
{ 0, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_A,} },
{ 0, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 0, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 0, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 0,} },
{ 0, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -32,7 +32,7 @@ static struct tegra_dc_feature_entry t20_feature_entries_a[] = {
{ 1, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_PREFERRED_FORMATS, {TEGRA_WIN_PREF_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 1, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 1, TEGRA_DC_FEATURE_FILTER_TYPE, {1, 1,} },
{ 1, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -40,7 +40,7 @@ static struct tegra_dc_feature_entry t20_feature_entries_a[] = {
{ 2, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_C,} },
{ 2, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 2, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 2, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 1,} },
{ 2, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -50,7 +50,7 @@ static struct tegra_dc_feature_entry t20_feature_entries_a[] = {
static struct tegra_dc_feature_entry t20_feature_entries_b[] = {
{ 0, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_A,} },
{ 0, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 0, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 0, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 0,} },
{ 0, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -59,7 +59,7 @@ static struct tegra_dc_feature_entry t20_feature_entries_b[] = {
{ 1, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_PREFERRED_FORMATS, {TEGRA_WIN_PREF_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 1, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 1, TEGRA_DC_FEATURE_FILTER_TYPE, {1, 1,} },
{ 1, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -67,7 +67,7 @@ static struct tegra_dc_feature_entry t20_feature_entries_b[] = {
{ 2, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_C,} },
{ 2, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 2, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 2, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 1,} },
{ 2, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -85,7 +85,7 @@ struct tegra_dc_feature t20_feature_table_b = {
static struct tegra_dc_feature_entry t30_feature_entries_a[] = {
{ 0, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_A,} },
{ 0, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 0, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 0, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 0,} },
{ 0, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1} },
@@ -94,7 +94,7 @@ static struct tegra_dc_feature_entry t30_feature_entries_a[] = {
{ 1, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_PREFERRED_FORMATS, {TEGRA_WIN_PREF_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 1, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 1, TEGRA_DC_FEATURE_FILTER_TYPE, {1, 1,} },
{ 1, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1} },
@@ -102,7 +102,7 @@ static struct tegra_dc_feature_entry t30_feature_entries_a[] = {
{ 2, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_C,} },
{ 2, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 2, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 2, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 1,} },
{ 2, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1} },
@@ -112,7 +112,7 @@ static struct tegra_dc_feature_entry t30_feature_entries_a[] = {
static struct tegra_dc_feature_entry t30_feature_entries_b[] = {
{ 0, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_A,} },
{ 0, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 0, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 0, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 0, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 0,} },
{ 0, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -121,7 +121,7 @@ static struct tegra_dc_feature_entry t30_feature_entries_b[] = {
{ 1, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_PREFERRED_FORMATS, {TEGRA_WIN_PREF_FMT_WIN_B,} },
{ 1, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 1, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 1, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 1, TEGRA_DC_FEATURE_FILTER_TYPE, {1, 1,} },
{ 1, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
@@ -129,7 +129,7 @@ static struct tegra_dc_feature_entry t30_feature_entries_b[] = {
{ 2, TEGRA_DC_FEATURE_FORMATS, {TEGRA_WIN_FMT_WIN_C,} },
{ 2, TEGRA_DC_FEATURE_BLEND_TYPE, {1,} },
- { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 16, 4095, 16,} },
+ { 2, TEGRA_DC_FEATURE_MAXIMUM_SIZE, {4095, 1, 4095, 1,} },
{ 2, TEGRA_DC_FEATURE_MAXIMUM_SCALE, {2, 2, 2, 2,} },
{ 2, TEGRA_DC_FEATURE_FILTER_TYPE, {0, 1,} },
{ 2, TEGRA_DC_FEATURE_LAYOUT_TYPE, {1, 1,} },
diff --git a/drivers/video/tegra/fb.c b/drivers/video/tegra/fb.c
index 59c162bb3b4c..f69048f62cc2 100644
--- a/drivers/video/tegra/fb.c
+++ b/drivers/video/tegra/fb.c
@@ -126,12 +126,9 @@ static int tegra_fb_set_par(struct fb_info *info)
return -EINVAL;
}
/* if line_length unset, then pad the stride */
- if (!info->fix.line_length) {
- info->fix.line_length = var->xres * var->bits_per_pixel
- / 8;
- info->fix.line_length = round_up(info->fix.line_length,
- TEGRA_LINEAR_PITCH_ALIGNMENT);
- }
+ info->fix.line_length = var->xres * var->bits_per_pixel / 8;
+ info->fix.line_length = round_up(info->fix.line_length,
+ TEGRA_LINEAR_PITCH_ALIGNMENT);
tegra_fb->win->stride = info->fix.line_length;
tegra_fb->win->stride_uv = 0;
tegra_fb->win->phys_addr_u = 0;
@@ -496,33 +493,15 @@ const struct fb_videomode *tegra_fb_find_best_mode(
return best;
}
-static int tegra_fb_activate_mode(struct tegra_fb_info *fb_info,
- struct fb_var_screeninfo *var)
-{
- int err;
- struct fb_info *info = fb_info->info;
-
- var->activate |= FB_ACTIVATE_FORCE;
- console_lock();
- info->flags |= FBINFO_MISC_USEREVENT;
- err = fb_set_var(info, var);
- info->flags &= ~FBINFO_MISC_USEREVENT;
- console_unlock();
- if (err)
- return err;
- return 0;
-}
-
void tegra_fb_update_monspecs(struct tegra_fb_info *fb_info,
struct fb_monspecs *specs,
bool (*mode_filter)(const struct tegra_dc *dc,
struct fb_videomode *mode))
{
int i;
- int ret = 0;
+ bool first = false;
struct fb_event event;
struct fb_info *info = fb_info->info;
- const struct fb_videomode *best_mode = NULL;
struct fb_var_screeninfo var = {0,};
mutex_lock(&fb_info->info->lock);
@@ -561,6 +540,13 @@ void tegra_fb_update_monspecs(struct tegra_fb_info *fb_info,
fb_var_to_videomode(&m, &var);
fb_add_videomode(&m,
&fb_info->info->modelist);
+ /* EDID stds recommend first detailed mode
+ to be applied as default,but if first mode
+ doesn't pass mode filter, we have to select
+ and apply other mode. So flag on if first
+ mode passes mode filter */
+ if (!i)
+ first = true;
}
} else {
fb_add_videomode(&specs->modedb[i],
@@ -568,36 +554,31 @@ void tegra_fb_update_monspecs(struct tegra_fb_info *fb_info,
}
}
- /* Get the best mode from modedb and apply on fb */
- var.xres = 0;
- var.yres = 0;
- best_mode = tegra_fb_find_best_mode(&var, &info->modelist);
-
- /* Update framebuffer with best mode */
- fb_videomode_to_var(&var, best_mode);
-
- /* TODO: Get proper way of getting rid of a 0 bpp */
- if (!var.bits_per_pixel)
- var.bits_per_pixel = 32;
-
- memcpy(&info->var, &var, sizeof(struct fb_var_screeninfo));
-
- ret = tegra_fb_activate_mode(fb_info, &var);
- if (ret)
- return;
+ /* We can't apply first detailed mode, so get the best mode
+ based on resolution and apply on fb */
+ if (!first) {
+ var.xres = 0;
+ var.yres = 0;
+ info->mode = (struct fb_videomode *)
+ tegra_fb_find_best_mode(&var, &info->modelist);
+ }
+ /* Prepare fb info with new mode details */
+ fb_videomode_to_var(&info->var, info->mode);
event.info = fb_info->info;
#ifdef CONFIG_FRAMEBUFFER_CONSOLE
-/* Lock the console before sending the noti. Fbconsole
- * on HDMI might be using console
- */
+ /* Send a noti to change fb_display[].mode for all vc's */
+ console_lock();
+ fb_notifier_call_chain(FB_EVENT_MODE_CHANGE_ALL, &event);
+ console_unlock();
+
+ /* Notify framebuffer console about mode change */
console_lock();
-#endif
fb_notifier_call_chain(FB_EVENT_NEW_MODELIST, &event);
-#ifdef CONFIG_FRAMEBUFFER_CONSOLE
-/* Unlock the console */
console_unlock();
+#else
+ fb_notifier_call_chain(FB_EVENT_NEW_MODELIST, &event);
#endif
mutex_unlock(&fb_info->info->lock);
@@ -649,12 +630,8 @@ struct tegra_fb_info *tegra_fb_register(struct nvhost_device *ndev,
tegra_fb->valid = true;
}
- info->fix.line_length = fb_data->xres * fb_data->bits_per_pixel / 8;
-
- stride = tegra_dc_get_stride(dc, 0);
- if (!stride) /* default to pad the stride */
- stride = round_up(info->fix.line_length,
- TEGRA_LINEAR_PITCH_ALIGNMENT);
+ stride = fb_data->xres * fb_data->bits_per_pixel / 8;
+ stride = round_up(stride, TEGRA_LINEAR_PITCH_ALIGNMENT);
info->fbops = &tegra_fb_ops;
info->pseudo_palette = pseudo_palette;
diff --git a/drivers/video/tegra/host/bus_client.c b/drivers/video/tegra/host/bus_client.c
index aaa038221971..4614689ec37c 100644
--- a/drivers/video/tegra/host/bus_client.c
+++ b/drivers/video/tegra/host/bus_client.c
@@ -658,3 +658,15 @@ fail:
return -ENXIO;
}
+
+void nvhost_client_device_put_resources(struct nvhost_device *dev)
+{
+ struct resource *r;
+
+ r = nvhost_get_resource(dev, IORESOURCE_MEM, 0);
+ BUG_ON(!r);
+
+ iounmap(dev->aperture);
+
+ release_mem_region(r->start, resource_size(r));
+}
diff --git a/drivers/video/tegra/host/bus_client.h b/drivers/video/tegra/host/bus_client.h
index e95ea0bc3401..8c7bdc9faefe 100644
--- a/drivers/video/tegra/host/bus_client.h
+++ b/drivers/video/tegra/host/bus_client.h
@@ -37,5 +37,6 @@ int nvhost_client_device_init(struct nvhost_device *dev);
int nvhost_client_device_suspend(struct nvhost_device *dev);
int nvhost_client_device_get_resources(struct nvhost_device *dev);
+void nvhost_client_device_put_resources(struct nvhost_device *dev);
#endif
diff --git a/drivers/video/tegra/nvmap/nvmap.c b/drivers/video/tegra/nvmap/nvmap.c
index a0dcf26337f8..19b821d41284 100644
--- a/drivers/video/tegra/nvmap/nvmap.c
+++ b/drivers/video/tegra/nvmap/nvmap.c
@@ -605,3 +605,16 @@ void nvmap_free(struct nvmap_client *client, struct nvmap_handle_ref *r)
nvmap_free_handle_id(client, nvmap_ref_to_id(r));
}
+
+int nvmap_mark_global(struct nvmap_client *client, struct nvmap_handle_ref *r)
+{
+ struct nvmap_handle *h;
+
+ h = nvmap_get_handle_id(client, (unsigned long)r->handle);
+ if (!h)
+ return -EINVAL;
+ r->handle->global = true;
+ nvmap_handle_put(h);
+
+ return 0;
+}