uboot/drivers/video/sm501.c
<<
>>
Prefs
   1/*
   2 * (C) Copyright 2002
   3 * Stäubli Faverges - <www.staubli.com>
   4 * Pierre AUBERT  p.aubert@staubli.com
   5 *
   6 * (C) Copyright 2005
   7 * Martin Krause TQ-Systems GmbH martin.krause@tqs.de
   8 *
   9 * SPDX-License-Identifier:     GPL-2.0+
  10 */
  11
  12/*
  13 * Basic video support for SMI SM501 "Voyager" graphic controller
  14 */
  15
  16#include <common.h>
  17
  18#include <asm/io.h>
  19#include <video_fb.h>
  20#include <sm501.h>
  21
  22#define read8(ptrReg)                \
  23    *(volatile unsigned char *)(sm501.isaBase + ptrReg)
  24
  25#define write8(ptrReg,value) \
  26    *(volatile unsigned char *)(sm501.isaBase + ptrReg) = value
  27
  28#define read16(ptrReg) \
  29    (*(volatile unsigned short *)(sm501.isaBase + ptrReg))
  30
  31#define write16(ptrReg,value) \
  32    (*(volatile unsigned short *)(sm501.isaBase + ptrReg) = value)
  33
  34#define read32(ptrReg) \
  35    (*(volatile unsigned int *)(sm501.isaBase + ptrReg))
  36
  37#define write32(ptrReg, value) \
  38    (*(volatile unsigned int *)(sm501.isaBase + ptrReg) = value)
  39
  40GraphicDevice sm501;
  41
  42void write_be32(int off, unsigned int val)
  43{
  44        out_be32((unsigned __iomem *)(sm501.isaBase + off), val);
  45}
  46
  47void write_le32(int off, unsigned int val)
  48{
  49        out_le32((unsigned __iomem *)(sm501.isaBase + off), val);
  50}
  51
  52void (*write_reg32)(int off, unsigned int val) = write_be32;
  53
  54/*-----------------------------------------------------------------------------
  55 * SmiSetRegs --
  56 *-----------------------------------------------------------------------------
  57 */
  58static void SmiSetRegs (void)
  59{
  60        /*
  61         * The content of the chipset register depends on the board (clocks,
  62         * ...)
  63         */
  64        const SMI_REGS *preg = board_get_regs ();
  65        while (preg->Index) {
  66                write_reg32 (preg->Index, preg->Value);
  67                /*
  68                 * Insert a delay between
  69                 */
  70                udelay (1000);
  71                preg ++;
  72        }
  73}
  74
  75#ifdef CONFIG_VIDEO_SM501_PCI
  76static struct pci_device_id sm501_pci_tbl[] = {
  77        { PCI_VENDOR_ID_SMI, PCI_DEVICE_ID_SMI_501 },
  78        {}
  79};
  80#endif
  81
  82/*
  83 * We do not enforce board code to provide empty/unused
  84 * functions for this driver and define weak default
  85 * functions here.
  86 */
  87unsigned int __board_video_init (void)
  88{
  89        return 0;
  90}
  91
  92unsigned int board_video_init (void)
  93                        __attribute__((weak, alias("__board_video_init")));
  94
  95unsigned int __board_video_get_fb (void)
  96{
  97        return 0;
  98}
  99
 100unsigned int board_video_get_fb (void)
 101                        __attribute__((weak, alias("__board_video_get_fb")));
 102
 103void __board_validate_screen (unsigned int base)
 104{
 105}
 106
 107void board_validate_screen (unsigned int base)
 108                        __attribute__((weak, alias("__board_validate_screen")));
 109
 110/*-----------------------------------------------------------------------------
 111 * video_hw_init --
 112 *-----------------------------------------------------------------------------
 113 */
 114void *video_hw_init (void)
 115{
 116#ifdef CONFIG_VIDEO_SM501_PCI
 117        unsigned int pci_mem_base, pci_mmio_base;
 118        unsigned int id;
 119        unsigned short device_id;
 120        pci_dev_t devbusfn;
 121        int mem;
 122#endif
 123        unsigned int *vm, i;
 124
 125        memset (&sm501, 0, sizeof (GraphicDevice));
 126
 127#ifdef CONFIG_VIDEO_SM501_PCI
 128        printf("Video: ");
 129
 130        /* Look for SM501/SM502 chips */
 131        devbusfn = pci_find_devices(sm501_pci_tbl, 0);
 132        if (devbusfn < 0) {
 133                printf ("PCI Controller not found.\n");
 134                goto not_pci;
 135        }
 136
 137        /* Setup */
 138        pci_write_config_dword (devbusfn, PCI_COMMAND,
 139                                (PCI_COMMAND_MEMORY | PCI_COMMAND_IO));
 140        pci_read_config_word (devbusfn, PCI_DEVICE_ID, &device_id);
 141        pci_read_config_dword (devbusfn, PCI_REVISION_ID, &id);
 142        pci_read_config_dword (devbusfn, PCI_BASE_ADDRESS_0, &pci_mem_base);
 143        pci_read_config_dword (devbusfn, PCI_BASE_ADDRESS_1, &pci_mmio_base);
 144        sm501.frameAdrs = pci_mem_to_phys (devbusfn, pci_mem_base);
 145        sm501.isaBase = pci_mem_to_phys (devbusfn, pci_mmio_base);
 146
 147        if (sm501.isaBase)
 148                write_reg32 = write_le32;
 149
 150        mem = in_le32 ((unsigned __iomem *)(sm501.isaBase + 0x10));
 151        mem = (mem & 0x0000e000) >> 13;
 152        switch (mem) {
 153        case 1:
 154                mem = 8;
 155                break;
 156        case 2:
 157                mem = 16;
 158                break;
 159        case 3:
 160                mem = 32;
 161                break;
 162        case 4:
 163                mem = 64;
 164                break;
 165        case 5:
 166                mem = 2;
 167                break;
 168        case 0:
 169        default:
 170                mem = 4;
 171        }
 172        printf ("PCI SM50%d %d MB\n", ((id & 0xff) == 0xC0) ? 2 : 1, mem);
 173not_pci:
 174#endif
 175        /*
 176         * Initialization of the access to the graphic chipset Retreive base
 177         * address of the chipset (see board/RPXClassic/eccx.c)
 178         */
 179        if (!sm501.isaBase) {
 180                sm501.isaBase = board_video_init ();
 181                if (!sm501.isaBase)
 182                        return NULL;
 183        }
 184
 185        if (!sm501.frameAdrs) {
 186                sm501.frameAdrs = board_video_get_fb ();
 187                if (!sm501.frameAdrs)
 188                        return NULL;
 189        }
 190
 191        sm501.winSizeX = board_get_width ();
 192        sm501.winSizeY = board_get_height ();
 193
 194#if defined(CONFIG_VIDEO_SM501_8BPP)
 195        sm501.gdfIndex = GDF__8BIT_INDEX;
 196        sm501.gdfBytesPP = 1;
 197
 198#elif defined(CONFIG_VIDEO_SM501_16BPP)
 199        sm501.gdfIndex = GDF_16BIT_565RGB;
 200        sm501.gdfBytesPP = 2;
 201
 202#elif defined(CONFIG_VIDEO_SM501_32BPP)
 203        sm501.gdfIndex = GDF_32BIT_X888RGB;
 204        sm501.gdfBytesPP = 4;
 205#else
 206#error Unsupported SM501 BPP
 207#endif
 208
 209        sm501.memSize = sm501.winSizeX * sm501.winSizeY * sm501.gdfBytesPP;
 210
 211        /* Load Smi registers */
 212        SmiSetRegs ();
 213
 214        /* (see board/RPXClassic/RPXClassic.c) */
 215        board_validate_screen (sm501.isaBase);
 216
 217        /* Clear video memory */
 218        i = sm501.memSize/4;
 219        vm = (unsigned int *)sm501.frameAdrs;
 220        while(i--)
 221                *vm++ = 0;
 222
 223        return (&sm501);
 224}
 225