summaryrefslogtreecommitdiff
path: root/drivers/video
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/video')
-rw-r--r--drivers/video/console/vgacon.c17
-rw-r--r--drivers/video/of_display_timing.c6
-rw-r--r--drivers/video/uvesafb.c70
3 files changed, 34 insertions, 59 deletions
diff --git a/drivers/video/console/vgacon.c b/drivers/video/console/vgacon.c
index 5855d17d19ac..9d8feac67637 100644
--- a/drivers/video/console/vgacon.c
+++ b/drivers/video/console/vgacon.c
@@ -42,6 +42,7 @@
#include <linux/kd.h>
#include <linux/slab.h>
#include <linux/vt_kern.h>
+#include <linux/sched.h>
#include <linux/selection.h>
#include <linux/spinlock.h>
#include <linux/ioport.h>
@@ -1124,11 +1125,15 @@ static int vgacon_do_font_op(struct vgastate *state,char *arg,int set,int ch512)
if (arg) {
if (set)
- for (i = 0; i < cmapsz; i++)
+ for (i = 0; i < cmapsz; i++) {
vga_writeb(arg[i], charmap + i);
+ cond_resched();
+ }
else
- for (i = 0; i < cmapsz; i++)
+ for (i = 0; i < cmapsz; i++) {
arg[i] = vga_readb(charmap + i);
+ cond_resched();
+ }
/*
* In 512-character mode, the character map is not contiguous if
@@ -1139,11 +1144,15 @@ static int vgacon_do_font_op(struct vgastate *state,char *arg,int set,int ch512)
charmap += 2 * cmapsz;
arg += cmapsz;
if (set)
- for (i = 0; i < cmapsz; i++)
+ for (i = 0; i < cmapsz; i++) {
vga_writeb(arg[i], charmap + i);
+ cond_resched();
+ }
else
- for (i = 0; i < cmapsz; i++)
+ for (i = 0; i < cmapsz; i++) {
arg[i] = vga_readb(charmap + i);
+ cond_resched();
+ }
}
}
diff --git a/drivers/video/of_display_timing.c b/drivers/video/of_display_timing.c
index 9c0f17b2e6fb..171821ddd78d 100644
--- a/drivers/video/of_display_timing.c
+++ b/drivers/video/of_display_timing.c
@@ -23,7 +23,7 @@
* Every display_timing can be specified with either just the typical value or
* a range consisting of min/typ/max. This function helps handling this
**/
-static int parse_timing_property(struct device_node *np, const char *name,
+static int parse_timing_property(const struct device_node *np, const char *name,
struct timing_entry *result)
{
struct property *prop;
@@ -56,7 +56,7 @@ static int parse_timing_property(struct device_node *np, const char *name,
* of_parse_display_timing - parse display_timing entry from device_node
* @np: device_node with the properties
**/
-static int of_parse_display_timing(struct device_node *np,
+static int of_parse_display_timing(const struct device_node *np,
struct display_timing *dt)
{
u32 val = 0;
@@ -92,6 +92,8 @@ static int of_parse_display_timing(struct device_node *np,
dt->flags |= DISPLAY_FLAGS_INTERLACED;
if (of_property_read_bool(np, "doublescan"))
dt->flags |= DISPLAY_FLAGS_DOUBLESCAN;
+ if (of_property_read_bool(np, "doubleclk"))
+ dt->flags |= DISPLAY_FLAGS_DOUBLECLK;
if (ret) {
pr_err("%s: error reading timing properties\n",
diff --git a/drivers/video/uvesafb.c b/drivers/video/uvesafb.c
index 10138b60fd70..b963ea12d175 100644
--- a/drivers/video/uvesafb.c
+++ b/drivers/video/uvesafb.c
@@ -24,9 +24,6 @@
#ifdef CONFIG_X86
#include <video/vga.h>
#endif
-#ifdef CONFIG_MTRR
-#include <asm/mtrr.h>
-#endif
#include "edid.h"
static struct cb_id uvesafb_cn_id = {
@@ -1540,67 +1537,30 @@ static void uvesafb_init_info(struct fb_info *info, struct vbe_mode_ib *mode)
static void uvesafb_init_mtrr(struct fb_info *info)
{
-#ifdef CONFIG_MTRR
+ struct uvesafb_par *par = info->par;
+
if (mtrr && !(info->fix.smem_start & (PAGE_SIZE - 1))) {
int temp_size = info->fix.smem_len;
- unsigned int type = 0;
- switch (mtrr) {
- case 1:
- type = MTRR_TYPE_UNCACHABLE;
- break;
- case 2:
- type = MTRR_TYPE_WRBACK;
- break;
- case 3:
- type = MTRR_TYPE_WRCOMB;
- break;
- case 4:
- type = MTRR_TYPE_WRTHROUGH;
- break;
- default:
- type = 0;
- break;
- }
+ int rc;
- if (type) {
- int rc;
+ /* Find the largest power-of-two */
+ temp_size = roundup_pow_of_two(temp_size);
- /* Find the largest power-of-two */
- temp_size = roundup_pow_of_two(temp_size);
+ /* Try and find a power of two to add */
+ do {
+ rc = arch_phys_wc_add(info->fix.smem_start, temp_size);
+ temp_size >>= 1;
+ } while (temp_size >= PAGE_SIZE && rc == -EINVAL);
- /* Try and find a power of two to add */
- do {
- rc = mtrr_add(info->fix.smem_start,
- temp_size, type, 1);
- temp_size >>= 1;
- } while (temp_size >= PAGE_SIZE && rc == -EINVAL);
- }
+ if (rc >= 0)
+ par->mtrr_handle = rc;
}
-#endif /* CONFIG_MTRR */
}
static void uvesafb_ioremap(struct fb_info *info)
{
-#ifdef CONFIG_X86
- switch (mtrr) {
- case 1: /* uncachable */
- info->screen_base = ioremap_nocache(info->fix.smem_start, info->fix.smem_len);
- break;
- case 2: /* write-back */
- info->screen_base = ioremap_cache(info->fix.smem_start, info->fix.smem_len);
- break;
- case 3: /* write-combining */
- info->screen_base = ioremap_wc(info->fix.smem_start, info->fix.smem_len);
- break;
- case 4: /* write-through */
- default:
- info->screen_base = ioremap(info->fix.smem_start, info->fix.smem_len);
- break;
- }
-#else
- info->screen_base = ioremap(info->fix.smem_start, info->fix.smem_len);
-#endif /* CONFIG_X86 */
+ info->screen_base = ioremap_wc(info->fix.smem_start, info->fix.smem_len);
}
static ssize_t uvesafb_show_vbe_ver(struct device *dev,
@@ -1851,6 +1811,7 @@ static int uvesafb_remove(struct platform_device *dev)
unregister_framebuffer(info);
release_region(0x3c0, 32);
iounmap(info->screen_base);
+ arch_phys_wc_del(par->mtrr_handle);
release_mem_region(info->fix.smem_start, info->fix.smem_len);
fb_destroy_modedb(info->monspecs.modedb);
fb_dealloc_cmap(&info->cmap);
@@ -1930,6 +1891,9 @@ static int uvesafb_setup(char *options)
}
}
+ if (mtrr != 3 && mtrr != 1)
+ pr_warn("uvesafb: mtrr should be set to 0 or 3; %d is unsupported", mtrr);
+
return 0;
}
#endif /* !MODULE */