aboutsummaryrefslogtreecommitdiff
path: root/vgasrc/bochsdisplay.c
diff options
context:
space:
mode:
authorGerd Hoffmann <kraxel@redhat.com>2017-11-15 14:43:10 +0100
committerGerd Hoffmann <kraxel@redhat.com>2018-06-22 07:44:07 +0200
commit77404b450d30a1d7860e717e98762b8a4745341d (patch)
tree1baf51c0af23cf05f75813323b171c6a670fe1a9 /vgasrc/bochsdisplay.c
parent4d70b24b86012e382cf551ce72c2dd6c92a6d1fa (diff)
downloadseabios-hppa-77404b450d30a1d7860e717e98762b8a4745341d.zip
seabios-hppa-77404b450d30a1d7860e717e98762b8a4745341d.tar.gz
seabios-hppa-77404b450d30a1d7860e717e98762b8a4745341d.tar.bz2
qemu: add bochs-display support
Use coreboot text mode emulation to also support the qemu bochs-display device. This is a new display device supporting simple linear framebuffers, using the bochs register interface. No support for legacy vga (text modes, planar modes, cga modes, 8bpp palette modes all dropped). The bochs interface is compatible with the qemu stdvga. Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
Diffstat (limited to 'vgasrc/bochsdisplay.c')
-rw-r--r--vgasrc/bochsdisplay.c59
1 files changed, 59 insertions, 0 deletions
diff --git a/vgasrc/bochsdisplay.c b/vgasrc/bochsdisplay.c
new file mode 100644
index 0000000..e1f90f9
--- /dev/null
+++ b/vgasrc/bochsdisplay.c
@@ -0,0 +1,59 @@
+#include "biosvar.h" // GET_BDA
+#include "output.h" // dprintf
+#include "string.h" // memset16_far
+#include "bochsvga.h" // VBE_BOCHS_*
+#include "hw/pci.h" // pci_config_readl
+#include "hw/pci_regs.h" // PCI_BASE_ADDRESS_0
+#include "vgautil.h" // VBE_total_memory
+
+#define FRAMEBUFFER_WIDTH 1024
+#define FRAMEBUFFER_HEIGHT 768
+#define FRAMEBUFFER_BPP 4
+#define FRAMEBUFFER_STRIDE (FRAMEBUFFER_BPP * FRAMEBUFFER_WIDTH)
+#define FRAMEBUFFER_SIZE (FRAMEBUFFER_STRIDE * FRAMEBUFFER_HEIGHT)
+
+int
+bochs_display_setup(void)
+{
+ dprintf(1, "bochs-display: setup called\n");
+
+ if (GET_GLOBAL(HaveRunInit))
+ return 0;
+
+ int bdf = GET_GLOBAL(VgaBDF);
+ if (bdf == 0)
+ return 0;
+
+ u32 bar = pci_config_readl(bdf, PCI_BASE_ADDRESS_0);
+ u32 lfb_addr = bar & PCI_BASE_ADDRESS_MEM_MASK;
+ bar = pci_config_readl(bdf, PCI_BASE_ADDRESS_2);
+ u32 io_addr = bar & PCI_BASE_ADDRESS_IO_MASK;
+ dprintf(1, "bochs-display: bdf %02x:%02x.%x, bar 0 at 0x%x, bar 1 at 0x%x\n"
+ , pci_bdf_to_bus(bdf) , pci_bdf_to_dev(bdf), pci_bdf_to_fn(bdf),
+ lfb_addr, io_addr);
+
+ u16 *dispi = (void*)(io_addr + 0x500);
+ u8 *vga = (void*)(io_addr + 0x400);
+ u16 id = readw(dispi + VBE_DISPI_INDEX_ID);
+ dprintf(1, "bochs-display: id is 0x%x, %s\n", id
+ , id == VBE_DISPI_ID5 ? "good" : "FAIL");
+ if (id != VBE_DISPI_ID5)
+ return 0;
+
+ dprintf(1, "bochs-display: using %dx%d, %d bpp (%d stride)\n"
+ , FRAMEBUFFER_WIDTH, FRAMEBUFFER_HEIGHT
+ , FRAMEBUFFER_BPP * 8, FRAMEBUFFER_STRIDE);
+
+ cbvga_setup_modes(lfb_addr, FRAMEBUFFER_BPP * 8,
+ FRAMEBUFFER_WIDTH, FRAMEBUFFER_HEIGHT,
+ FRAMEBUFFER_STRIDE);
+
+ writew(dispi + VBE_DISPI_INDEX_XRES, FRAMEBUFFER_WIDTH);
+ writew(dispi + VBE_DISPI_INDEX_YRES, FRAMEBUFFER_HEIGHT);
+ writew(dispi + VBE_DISPI_INDEX_BPP, FRAMEBUFFER_BPP * 8);
+ writew(dispi + VBE_DISPI_INDEX_ENABLE, VBE_DISPI_ENABLED);
+
+ writeb(vga, 0x20); /* unblank (for qemu -device VGA) */
+
+ return 0;
+}