Source-Changes-HG archive

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]

[src/trunk]: src/sys/arch/evbarm/rpi genfb support for rpi



details:   https://anonhg.NetBSD.org/src/rev/76d2ba1b5c6a
branches:  trunk
changeset: 783797:76d2ba1b5c6a
user:      jmcneill <jmcneill%NetBSD.org@localhost>
date:      Wed Jan 09 00:24:54 2013 +0000

description:
genfb support for rpi

diffstat:

 sys/arch/evbarm/rpi/rpi_machdep.c |  314 ++++++++++++++++++++++++++++++++++++-
 1 files changed, 303 insertions(+), 11 deletions(-)

diffs (truncated from 426 to 300 lines):

diff -r 37e76faf0019 -r 76d2ba1b5c6a sys/arch/evbarm/rpi/rpi_machdep.c
--- a/sys/arch/evbarm/rpi/rpi_machdep.c Wed Jan 09 00:01:07 2013 +0000
+++ b/sys/arch/evbarm/rpi/rpi_machdep.c Wed Jan 09 00:24:54 2013 +0000
@@ -1,4 +1,4 @@
-/*     $NetBSD: rpi_machdep.c,v 1.21 2013/01/08 16:49:43 skrll Exp $   */
+/*     $NetBSD: rpi_machdep.c,v 1.22 2013/01/09 00:24:54 jmcneill Exp $        */
 
 /*-
  * Copyright (c) 2012 The NetBSD Foundation, Inc.
@@ -30,13 +30,15 @@
  */
 
 #include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: rpi_machdep.c,v 1.21 2013/01/08 16:49:43 skrll Exp $");
+__KERNEL_RCSID(0, "$NetBSD: rpi_machdep.c,v 1.22 2013/01/09 00:24:54 jmcneill Exp $");
 
 #include "opt_evbarm_boardtype.h"
 
 #include "sdhc.h"
 #include "bcmspi.h"
 #include "bsciic.h"
+#include "plcom.h"
+#include "genfb.h"
 
 #include <sys/param.h>
 #include <sys/device.h>
@@ -67,12 +69,16 @@
 
 #include <evbarm/rpi/rpi.h>
 
-#include "plcom.h"
-#if (NPLCOM > 0)
+#if NPLCOM > 0
 #include <evbarm/dev/plcomreg.h>
 #include <evbarm/dev/plcomvar.h>
 #endif
 
+#if NGENFB > 0
+#include <dev/videomode/videomode.h>
+#include <dev/videomode/edidvar.h>
+#endif
+
 #include "ksyms.h"
 
 extern int KERNEL_BASE_phys[];
@@ -94,6 +100,13 @@
 #define KERN_VTOPHYS(va) ((paddr_t)((vaddr_t)va + KERN_VTOPDIFF))
 #define KERN_PHYSTOV(pa) ((vaddr_t)((paddr_t)pa - KERN_VTOPDIFF))
 
+#ifndef RPI_FB_WIDTH
+#define RPI_FB_WIDTH   1280
+#endif
+#ifndef RPI_FB_HEIGHT
+#define RPI_FB_HEIGHT  720
+#endif
+
 #define        PLCONADDR 0x20201000
 
 #ifndef CONSDEVNAME
@@ -213,6 +226,118 @@
        }
 };
 
+#if NGENFB > 0
+static struct {
+       struct vcprop_buffer_hdr        vb_hdr;
+       struct vcprop_tag_edidblock     vbt_edid;
+       struct vcprop_tag end;
+} vb_edid __packed __aligned(16) =
+{
+       .vb_hdr = {
+               .vpb_len = sizeof(vb_edid),
+               .vpb_rcode = VCPROP_PROCESS_REQUEST,
+       },
+       .vbt_edid = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_GET_EDID_BLOCK,
+                       .vpt_len = VCPROPTAG_LEN(vb_edid.vbt_edid),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .blockno = 0,
+       },
+       .end = {
+               .vpt_tag = VCPROPTAG_NULL
+       }
+};
+
+static struct {
+       struct vcprop_buffer_hdr        vb_hdr;
+       struct vcprop_tag_fbres         vbt_res;
+       struct vcprop_tag_fbres         vbt_vres;
+       struct vcprop_tag_fbdepth       vbt_depth;
+       struct vcprop_tag_fbpixelorder  vbt_pixelorder;
+       struct vcprop_tag_fbalpha       vbt_alpha;
+       struct vcprop_tag_allocbuf      vbt_allocbuf;
+       struct vcprop_tag_blankscreen   vbt_blank;
+       struct vcprop_tag_fbpitch       vbt_pitch;
+       struct vcprop_tag end;
+} vb_setfb __packed __aligned(16) =
+{
+       .vb_hdr = {
+               .vpb_len = sizeof(vb_setfb),
+               .vpb_rcode = VCPROP_PROCESS_REQUEST,
+       },
+       .vbt_res = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_SET_FB_RES,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_res),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .width = 0,
+               .height = 0,
+       },
+       .vbt_vres = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_SET_FB_VRES,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_vres),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .width = 0,
+               .height = 0,
+       },
+       .vbt_depth = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_SET_FB_DEPTH,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_depth),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .bpp = 32,
+       },
+       .vbt_pixelorder = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_SET_FB_PIXEL_ORDER,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_pixelorder),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .state = VCPROP_PIXEL_RGB,
+       },
+       .vbt_alpha = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_SET_FB_ALPHA_MODE,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_alpha),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .state = VCPROP_ALPHA_IGNORED,
+       },
+       .vbt_allocbuf = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_ALLOCATE_BUFFER,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_allocbuf),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .address = PAGE_SIZE,   /* alignment */
+       },
+       .vbt_blank = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_BLANK_SCREEN,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_blank),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+               .state = VCPROP_BLANK_OFF,
+       },
+       .vbt_pitch = {
+               .tag = {
+                       .vpt_tag = VCPROPTAG_GET_FB_PITCH,
+                       .vpt_len = VCPROPTAG_LEN(vb_setfb.vbt_pitch),
+                       .vpt_rcode = VCPROPTAG_REQUEST,
+               },
+       },
+       .end = {
+               .vpt_tag = VCPROPTAG_NULL,
+       },
+};
+#endif
+
 static void
 rpi_bootparams(void)
 {
@@ -227,7 +352,6 @@
 #if (NPLCOM > 0)
            (1 << VCPM_POWER_UART0) |
 #endif
-
 #if (NBSCIIC > 0)
            (1 << VCPM_POWER_I2C0) | (1 << VCPM_POWER_I2C1) | 
        /*  (1 << VCPM_POWER_I2C2) | */
@@ -244,9 +368,9 @@
        /*
         * No need to invalid the cache as the memory has never been referenced
         * by the ARM.
-        * 
+        *
         * cpu_dcache_inv_range((vaddr_t)&vb, sizeof(vb));
-        * 
+        *
         */
 
        if (!vcprop_buffer_success_p(&vb.vb_hdr)) {
@@ -254,10 +378,10 @@
                bootconfig.dram[0].address = 0x0;
                bootconfig.dram[0].pages = atop(RPI_MINIMUM_SPLIT);
                return;
-       } 
+       }
 
        struct vcprop_tag_memory *vptp_mem = &vb.vbt_memory;
-       
+
        if (vcprop_tag_success_p(&vptp_mem->tag)) {
                size_t n = vcprop_tag_resplen(&vptp_mem->tag) /
                    sizeof(struct vcprop_memory);
@@ -270,7 +394,7 @@
                        bootconfig.dramblocks++;
                }
        }
-       
+
        if (vcprop_tag_success_p(&vb.vbt_armclockrate.tag))
                curcpu()->ci_data.cpu_cc_freq = vb.vbt_armclockrate.rate;
 
@@ -290,6 +414,7 @@
        if (vcprop_tag_success_p(&vb.vbt_serial.tag))
                printf("%s: board serial %llx\n", __func__,
                    vb.vbt_serial.sn);
+
        if (vcprop_tag_success_p(&vb.vbt_cmdline.tag))
                printf("%s: cmdline      %s\n", __func__,
                    vb.vbt_cmdline.cmdline);
@@ -365,6 +490,12 @@
 
        rpi_bootparams();
 
+       if (vcprop_tag_success_p(&vb.vbt_armclockrate.tag)) {
+               curcpu()->ci_data.cpu_cc_freq = vb.vbt_armclockrate.rate;
+               printf("%s: arm clock   %d\n", __func__,
+                   vb.vbt_armclockrate.rate);
+       }
+
 #ifdef VERBOSE_INIT_ARM
        printf("initarm: Configuring system ...\n");
 #endif
@@ -422,22 +553,183 @@
         * This allows a means of generating output during initarm().
         */
        rpi_pi.pi_iobase = consaddr;
-       
+
        plcomcnattach(&rpi_pi, plcomcnspeed, BCM2835_UART0_CLK,
            plcomcnmode, PLCOMCNUNIT);
 
 #endif
 }
 
+#if NGENFB > 0
+static bool
+rpi_fb_parse_mode(const char *s, uint32_t *pwidth, uint32_t *pheight)
+{
+       if (strncmp(s, "fb", 2) != 0)
+               return false;
+
+       if (strncmp(s, "fb:", 3) == 0) {
+               char *x = strchr(s + 3, 'x');
+               if (x) {
+                       *pwidth = strtoul(s + 3, NULL, 10);
+                       *pheight = strtoul(x + 1, NULL, 10);
+               }        
+       }
+
+       return true;
+}
+
+static bool
+rpi_fb_get_edid_mode(uint32_t *pwidth, uint32_t *pheight)
+{
+       struct edid_info ei;
+       uint8_t edid_data[1024];
+       uint32_t res;
+       int error;
+       
+       error = bcmmbox_request(BCMMBOX_CHANARM2VC, &vb_edid,
+           sizeof(vb_edid), &res);
+       if (error) {
+               printf("%s: mbox request failed (%d)\n", __func__, error);
+               return false;
+       }
+
+       if (!vcprop_buffer_success_p(&vb_edid.vb_hdr) ||
+           !vcprop_tag_success_p(&vb_edid.vbt_edid.tag))
+               return false;
+
+       memset(edid_data, 0, sizeof(edid_data));
+       memcpy(edid_data, vb_edid.vbt_edid.data,
+           sizeof(vb_edid.vbt_edid.data));
+       edid_parse(edid_data, &ei);
+#ifdef VERBOSE_INIT_ARM
+       edid_print(&ei);
+#endif
+
+       *pwidth = ei.edid_preferred_mode->hdisplay;
+       *pheight = ei.edid_preferred_mode->vdisplay;



Home | Main Index | Thread Index | Old Index