summaryrefslogtreecommitdiffstats
path: root/sys/dev/vt
diff options
context:
space:
mode:
authornwhitehorn <nwhitehorn@FreeBSD.org>2016-01-09 21:28:56 +0000
committernwhitehorn <nwhitehorn@FreeBSD.org>2016-01-09 21:28:56 +0000
commit78f9dfd7201229521e6590d6bd27e58db143279d (patch)
tree0be07ef725d9e6b141f63387da77591027a526fa /sys/dev/vt
parente706df7b9aabea4208d9f836f591eae7b4424987 (diff)
downloadFreeBSD-src-78f9dfd7201229521e6590d6bd27e58db143279d.zip
FreeBSD-src-78f9dfd7201229521e6590d6bd27e58db143279d.tar.gz
Make graphical consoles work under PowerKVM. Without using hypercalls, it is
not possible to write the framebuffer before pmap is up. Solve this by deferring initialization until that happens, like on PS3. MFC after: 1 week
Diffstat (limited to 'sys/dev/vt')
-rw-r--r--sys/dev/vt/hw/ofwfb/ofwfb.c25
1 files changed, 23 insertions, 2 deletions
diff --git a/sys/dev/vt/hw/ofwfb/ofwfb.c b/sys/dev/vt/hw/ofwfb/ofwfb.c
index acad5d4..c3ac185 100644
--- a/sys/dev/vt/hw/ofwfb/ofwfb.c
+++ b/sys/dev/vt/hw/ofwfb/ofwfb.c
@@ -57,6 +57,7 @@ struct ofwfb_softc {
int iso_palette;
};
+static void ofwfb_initialize(struct vt_device *vd);
static vd_probe_t ofwfb_probe;
static vd_init_t ofwfb_init;
static vd_bitblt_text_t ofwfb_bitblt_text;
@@ -124,6 +125,18 @@ ofwfb_bitblt_bitmap(struct vt_device *vd, const struct vt_window *vw,
uint8_t c[4];
} ch1, ch2;
+#ifdef __powerpc__
+ /* Deal with unmapped framebuffers */
+ if (sc->fb_flags & FB_FLAG_NOWRITE) {
+ if (pmap_bootstrapped) {
+ sc->fb_flags &= ~FB_FLAG_NOWRITE;
+ ofwfb_initialize(vd);
+ } else {
+ return;
+ }
+ }
+#endif
+
fgc = sc->fb_cmap[fg];
bgc = sc->fb_cmap[bg];
b = m = 0;
@@ -271,6 +284,11 @@ ofwfb_initialize(struct vt_device *vd)
cell_t retval;
uint32_t oldpix;
+ sc->fb.fb_cmsize = 16;
+
+ if (sc->fb.fb_flags & FB_FLAG_NOWRITE)
+ return;
+
/*
* Set up the color map
*/
@@ -318,8 +336,6 @@ ofwfb_initialize(struct vt_device *vd)
panic("Unknown color space depth %d", sc->fb.fb_bpp);
break;
}
-
- sc->fb.fb_cmsize = 16;
}
static int
@@ -466,6 +482,11 @@ ofwfb_init(struct vt_device *vd)
#if defined(__powerpc__)
OF_decode_addr(node, fb_phys, &sc->sc_memt, &sc->fb.fb_vbase);
sc->fb.fb_pbase = sc->fb.fb_vbase; /* 1:1 mapped */
+ #ifdef __powerpc64__
+ /* Real mode under a hypervisor probably doesn't cover FB */
+ if (!(mfmsr() & (PSL_HV | PSL_DR)))
+ sc->fb.fb_flags |= FB_FLAG_NOWRITE;
+ #endif
#else
/* No ability to interpret assigned-addresses otherwise */
return (CN_DEAD);
OpenPOWER on IntegriCloud