aboutsummaryrefslogtreecommitdiff
path: root/chips/sfb_hdw.c
diff options
context:
space:
mode:
Diffstat (limited to 'chips/sfb_hdw.c')
-rw-r--r--chips/sfb_hdw.c253
1 files changed, 253 insertions, 0 deletions
diff --git a/chips/sfb_hdw.c b/chips/sfb_hdw.c
new file mode 100644
index 00000000..ff2b1f6d
--- /dev/null
+++ b/chips/sfb_hdw.c
@@ -0,0 +1,253 @@
+/*
+ * Mach Operating System
+ * Copyright (c) 1992 Carnegie Mellon University
+ * All Rights Reserved.
+ *
+ * Permission to use, copy, modify and distribute this software and its
+ * documentation is hereby granted, provided that both the copyright
+ * notice and this permission notice appear in all copies of the
+ * software, derivative works or modified versions, and any portions
+ * thereof, and that both notices appear in supporting documentation.
+ *
+ * CARNEGIE MELLON ALLOWS FREE USE OF THIS SOFTWARE IN ITS "AS IS"
+ * CONDITION. CARNEGIE MELLON DISCLAIMS ANY LIABILITY OF ANY KIND FOR
+ * ANY DAMAGES WHATSOEVER RESULTING FROM THE USE OF THIS SOFTWARE.
+ *
+ * Carnegie Mellon requests users of this software to return to
+ *
+ * Software Distribution Coordinator or Software.Distribution@CS.CMU.EDU
+ * School of Computer Science
+ * Carnegie Mellon University
+ * Pittsburgh PA 15213-3890
+ *
+ * any improvements or extensions that they make and grant Carnegie Mellon
+ * the rights to redistribute these changes.
+ */
+/*
+ * File: sfb_hdw.c
+ * Author: Alessandro Forin, Carnegie Mellon University
+ * Date: 11/92
+ *
+ * Driver for the Smart Color Frame Buffer Display,
+ * hardware-level operations.
+ */
+
+#include <sfb.h>
+#if (NSFB > 0)
+#include <platforms.h>
+
+#include <machine/machspl.h>
+#include <mach/std_types.h>
+#include <chips/busses.h>
+#include <chips/screen_defs.h>
+#include <chips/pm_defs.h>
+#include <machine/machspl.h>
+
+typedef pm_softc_t sfb_softc_t;
+
+#ifdef DECSTATION
+#include <mips/PMAX/pmagb_ba.h>
+#include <mips/PMAX/tc.h>
+#endif
+
+#ifdef FLAMINGO
+#include <mips/PMAX/pmagb_ba.h> /* XXXX fixme */
+#include <alpha/DEC/tc.h>
+#define sparsify(x) ((1L << 28) | (((x) & 0x7ffffff) << 1) | \
+ ((x) & ~0x7ffffffL))
+#endif
+
+#ifndef sparsify
+#define sparsify(x) x
+#endif
+
+/*
+ * Definition of the driver for the auto-configuration program.
+ */
+
+int sfb_probe(), sfb_intr();
+void sfb_attach();
+
+vm_offset_t sfb_std[NSFB] = { 0 };
+struct bus_device *sfb_info[NSFB];
+struct bus_driver sfb_driver =
+ { sfb_probe, 0, sfb_attach, 0, sfb_std, "sfb", sfb_info,
+ 0, 0, BUS_INTR_DISABLED};
+
+/*
+ * Probe/Attach functions
+ */
+
+sfb_probe(
+ vm_offset_t addr,
+ struct bus_device *device)
+{
+ static probed_once = 0;
+
+ /*
+ * Probing was really done sweeping the TC long ago
+ */
+ if (tc_probe("sfb") == 0)
+ return 0;
+ if (probed_once++ > 1) {
+ printf("[mappable] ");
+ device->address = addr;
+ }
+ return 1;
+}
+
+void sfb_attach(
+ struct bus_device *ui)
+{
+ /* ... */
+ printf(": smart frame buffer");
+}
+
+
+/*
+ * Interrupt routine
+ */
+
+sfb_intr(
+ int unit,
+ spl_t spllevel)
+{
+ register volatile char *ack;
+
+ /* acknowledge interrupt */
+ ack = (volatile char *) sfb_info[unit]->address + SFB_OFFSET_ICLR;
+ *ack = 0;
+
+#if mips
+ splx(spllevel);
+#endif
+ lk201_led(unit);
+}
+
+sfb_vretrace(
+ sfb_softc_t *sfb,
+ boolean_t on)
+{
+ sfb_regs *regs;
+
+ regs = (sfb_regs *) ((char *)sfb->framebuffer - SFB_OFFSET_VRAM + SFB_OFFSET_REGS);
+
+ regs->intr_enable = (on) ? 1 : 0;
+}
+
+/*
+ * Boot time initialization: must make device
+ * usable as console asap.
+ */
+#define sfb_set_status cfb_set_status
+
+extern int
+ sfb_soft_reset(), sfb_set_status(),
+ sfb_pos_cursor(), bt459_video_on(),
+ bt459_video_off(), sfb_vretrace(),
+ pm_get_status(), pm_char_paint(),
+ pm_insert_line(), pm_remove_line(),
+ pm_clear_bitmap(), pm_map_page();
+
+static struct screen_switch sfb_sw = {
+ screen_noop, /* graphic_open */
+ sfb_soft_reset, /* graphic_close */
+ sfb_set_status, /* set_status */
+ pm_get_status, /* get_status */
+ pm_char_paint, /* char_paint */
+ sfb_pos_cursor, /* pos_cursor */
+ pm_insert_line, /* insert_line */
+ pm_remove_line, /* remove_line */
+ pm_clear_bitmap, /* clear_bitmap */
+ bt459_video_on, /* video_on */
+ bt459_video_off, /* video_off */
+ sfb_vretrace, /* intr_enable */
+ pm_map_page /* map_page */
+};
+
+sfb_cold_init(
+ int unit,
+ user_info_t *up)
+{
+ sfb_softc_t *sfb;
+ screen_softc_t sc = screen(unit);
+ vm_offset_t base = tc_probe("sfb");
+ int hor_p, ver_p;
+ boolean_t makes_sense;
+
+ bcopy(&sfb_sw, &sc->sw, sizeof(sc->sw));
+ sc->flags |= COLOR_SCREEN;
+
+ /*
+ * I am confused here by the documentation. One document
+ * sez there are three boards:
+ * "PMAGB-BA" can do 1280x1024 @66Hz or @72Hz
+ * "PMAGB-BC" can do 1024x864 @60Hz or 1280x1024 @72Hz
+ * "PMAGB-BE" can do 1024x768 @72Hz or 1280x1024 @72Hz
+ * Another document sez things differently:
+ * "PMAGB-BB" can do 1024x768 @72Hz
+ * "PMAGB-BD" can do 1024x864 @60Hz or 1280x1024 @72Hz
+ *
+ * I would be inclined to believe the first one, which came
+ * with an actual piece of hardware attached (a PMAGB-BA).
+ * But I could swear I got a first board (which blew up
+ * instantly) and it was calling itself PMAGB-BB...
+ *
+ * Since I have not seen any other hardware I will make
+ * this code as hypothetical as I can. Should work :-))
+ */
+
+ makes_sense = FALSE;
+
+ {
+ sfb_regs *regs;
+
+ regs = (sfb_regs *) ((char *)base + SFB_OFFSET_REGS);
+ hor_p = (regs->vhor_setup & 0x1ff) * 4;
+ ver_p = regs->vvert_setup & 0x7ff;
+
+ if (((hor_p == 1280) && (ver_p == 1024)) ||
+ ((hor_p == 1024) && (ver_p == 864)) ||
+ ((hor_p == 1024) && (ver_p == 768)))
+ makes_sense = TRUE;
+ }
+
+ if (makes_sense) {
+ sc->frame_scanline_width = hor_p;
+ sc->frame_height = ver_p;
+ sc->frame_visible_width = hor_p;
+ sc->frame_visible_height = ver_p;
+ } else {
+ sc->frame_scanline_width = 1280;
+ sc->frame_height = 1024;
+ sc->frame_visible_width = 1280;
+ sc->frame_visible_height = 1024;
+ }
+
+ pm_init_screen_params(sc,up);
+ (void) screen_up(unit, up);
+
+ sfb = pm_alloc( unit, sparsify(base + SFB_OFFSET_BT459),
+ base + SFB_OFFSET_VRAM, -1);
+
+ screen_default_colors(up);
+
+ sfb_soft_reset(sc);
+
+ /*
+ * Clearing the screen at boot saves from scrolling
+ * much, and speeds up booting quite a bit.
+ */
+ screen_blitc( unit, 'C'-'@');/* clear screen */
+}
+
+#if 0 /* this is how you find out about a new screen */
+fill(addr,n,c)
+ char *addr;
+{
+ while (n-- > 0) *addr++ = c;
+}
+#endif
+
+
+#endif (NSFB > 0)