Back to home page

OSCL-LXR

 
 

    


0001 /*
0002  * linux/drivers/video/riva/fbdev.c - nVidia RIVA 128/TNT/TNT2 fb driver
0003  *
0004  * Maintained by Ani Joshi <ajoshi@shell.unixbox.com>
0005  *
0006  * Copyright 1999-2000 Jeff Garzik
0007  *
0008  * Contributors:
0009  *
0010  *  Ani Joshi:  Lots of debugging and cleanup work, really helped
0011  *  get the driver going
0012  *
0013  *  Ferenc Bakonyi:  Bug fixes, cleanup, modularization
0014  *
0015  *  Jindrich Makovicka:  Accel code help, hw cursor, mtrr
0016  *
0017  *  Paul Richards:  Bug fixes, updates
0018  *
0019  * Initial template from skeletonfb.c, created 28 Dec 1997 by Geert Uytterhoeven
0020  * Includes riva_hw.c from nVidia, see copyright below.
0021  * KGI code provided the basis for state storage, init, and mode switching.
0022  *
0023  * This file is subject to the terms and conditions of the GNU General Public
0024  * License.  See the file COPYING in the main directory of this archive
0025  * for more details.
0026  *
0027  * Known bugs and issues:
0028  *  restoring text mode fails
0029  *  doublescan modes are broken
0030  */
0031 
0032 #include <linux/module.h>
0033 #include <linux/kernel.h>
0034 #include <linux/errno.h>
0035 #include <linux/string.h>
0036 #include <linux/mm.h>
0037 #include <linux/slab.h>
0038 #include <linux/delay.h>
0039 #include <linux/fb.h>
0040 #include <linux/init.h>
0041 #include <linux/pci.h>
0042 #include <linux/backlight.h>
0043 #include <linux/bitrev.h>
0044 #ifdef CONFIG_PMAC_BACKLIGHT
0045 #include <asm/machdep.h>
0046 #include <asm/backlight.h>
0047 #endif
0048 
0049 #include "rivafb.h"
0050 #include "nvreg.h"
0051 
0052 /* version number of this driver */
0053 #define RIVAFB_VERSION "0.9.5b"
0054 
0055 /* ------------------------------------------------------------------------- *
0056  *
0057  * various helpful macros and constants
0058  *
0059  * ------------------------------------------------------------------------- */
0060 #ifdef CONFIG_FB_RIVA_DEBUG
0061 #define NVTRACE          printk
0062 #else
0063 #define NVTRACE          if(0) printk
0064 #endif
0065 
0066 #define NVTRACE_ENTER(...)  NVTRACE("%s START\n", __func__)
0067 #define NVTRACE_LEAVE(...)  NVTRACE("%s END\n", __func__)
0068 
0069 #ifdef CONFIG_FB_RIVA_DEBUG
0070 #define assert(expr) \
0071     if(!(expr)) { \
0072     printk( "Assertion failed! %s,%s,%s,line=%d\n",\
0073     #expr,__FILE__,__func__,__LINE__); \
0074     BUG(); \
0075     }
0076 #else
0077 #define assert(expr)
0078 #endif
0079 
0080 #define PFX "rivafb: "
0081 
0082 /* macro that allows you to set overflow bits */
0083 #define SetBitField(value,from,to) SetBF(to,GetBF(value,from))
0084 #define SetBit(n)       (1<<(n))
0085 #define Set8Bits(value)     ((value)&0xff)
0086 
0087 /* HW cursor parameters */
0088 #define MAX_CURS        32
0089 
0090 /* ------------------------------------------------------------------------- *
0091  *
0092  * prototypes
0093  *
0094  * ------------------------------------------------------------------------- */
0095 
0096 static int rivafb_blank(int blank, struct fb_info *info);
0097 
0098 /* ------------------------------------------------------------------------- *
0099  *
0100  * card identification
0101  *
0102  * ------------------------------------------------------------------------- */
0103 
0104 static const struct pci_device_id rivafb_pci_tbl[] = {
0105     { PCI_VENDOR_ID_NVIDIA_SGS, PCI_DEVICE_ID_NVIDIA_SGS_RIVA128,
0106       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0107     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_TNT,
0108       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0109     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_TNT2,
0110       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0111     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_UTNT2,
0112       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0113     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_VTNT2,
0114       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0115     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_UVTNT2,
0116       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0117     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_ITNT2,
0118       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0119     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE_SDR,
0120       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0121     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE_DDR,
0122       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0123     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO,
0124       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0125     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_MX,
0126       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0127     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_MX2,
0128       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0129     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_GO,
0130       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0131     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO2_MXR,
0132       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0133     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_GTS,
0134       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0135     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_GTS2,
0136       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0137     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE2_ULTRA,
0138       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0139     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO2_PRO,
0140       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0141     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_460,
0142       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0143     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_440,
0144       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0145     // NF2/IGP version, GeForce 4 MX, NV18
0146     { PCI_VENDOR_ID_NVIDIA, 0x01f0,
0147       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0148     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_MX_420,
0149       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0150     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_440_GO,
0151       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0152     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_420_GO,
0153       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0154     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_420_GO_M32,
0155       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0156     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO4_500XGL,
0157       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0158     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_440_GO_M64,
0159       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0160     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO4_200,
0161       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0162     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO4_550XGL,
0163       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0164     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO4_500_GOGL,
0165       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0166     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_IGEFORCE2,
0167       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0168     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE3,
0169       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0170     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE3_1,
0171       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0172     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE3_2,
0173       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0174     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO_DDC,
0175       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0176     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_TI_4600,
0177       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0178     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_TI_4400,
0179       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0180     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE4_TI_4200,
0181       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0182     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO4_900XGL,
0183       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0184     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO4_750XGL,
0185       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0186     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_QUADRO4_700XGL,
0187       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0188     { PCI_VENDOR_ID_NVIDIA, PCI_DEVICE_ID_NVIDIA_GEFORCE_FX_GO_5200,
0189       PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0 },
0190     { 0, } /* terminate list */
0191 };
0192 MODULE_DEVICE_TABLE(pci, rivafb_pci_tbl);
0193 
0194 /* ------------------------------------------------------------------------- *
0195  *
0196  * global variables
0197  *
0198  * ------------------------------------------------------------------------- */
0199 
0200 /* command line data, set in rivafb_setup() */
0201 static int flatpanel = -1; /* Autodetect later */
0202 static int forceCRTC = -1;
0203 static bool noaccel  = 0;
0204 static bool nomtrr = 0;
0205 static int backlight = IS_BUILTIN(CONFIG_PMAC_BACKLIGHT);
0206 
0207 static char *mode_option = NULL;
0208 static bool strictmode       = 0;
0209 
0210 static struct fb_fix_screeninfo rivafb_fix = {
0211     .type       = FB_TYPE_PACKED_PIXELS,
0212     .xpanstep   = 1,
0213     .ypanstep   = 1,
0214 };
0215 
0216 static struct fb_var_screeninfo rivafb_default_var = {
0217     .xres       = 640,
0218     .yres       = 480,
0219     .xres_virtual   = 640,
0220     .yres_virtual   = 480,
0221     .bits_per_pixel = 8,
0222     .red        = {0, 8, 0},
0223     .green      = {0, 8, 0},
0224     .blue       = {0, 8, 0},
0225     .transp     = {0, 0, 0},
0226     .activate   = FB_ACTIVATE_NOW,
0227     .height     = -1,
0228     .width      = -1,
0229     .pixclock   = 39721,
0230     .left_margin    = 40,
0231     .right_margin   = 24,
0232     .upper_margin   = 32,
0233     .lower_margin   = 11,
0234     .hsync_len  = 96,
0235     .vsync_len  = 2,
0236     .vmode      = FB_VMODE_NONINTERLACED
0237 };
0238 
0239 /* from GGI */
0240 static const struct riva_regs reg_template = {
0241     {0x00, 0x01, 0x02, 0x03, 0x04, 0x05, 0x06, 0x07,    /* ATTR */
0242      0x08, 0x09, 0x0A, 0x0B, 0x0C, 0x0D, 0x0E, 0x0F,
0243      0x41, 0x01, 0x0F, 0x00, 0x00},
0244     {0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,    /* CRT  */
0245      0x00, 0x00, 0x20, 0x00, 0x00, 0x00, 0x00, 0x00,
0246      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0xE3,    /* 0x10 */
0247      0xFF, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0248      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,    /* 0x20 */
0249      0x40, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0250      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,    /* 0x30 */
0251      0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,
0252      0x00,                          /* 0x40 */
0253      },
0254     {0x00, 0x00, 0x00, 0x00, 0x00, 0x40, 0x05, 0x0F,    /* GRA  */
0255      0xFF},
0256     {0x03, 0x01, 0x0F, 0x00, 0x0E},             /* SEQ  */
0257     0xEB                            /* MISC */
0258 };
0259 
0260 /*
0261  * Backlight control
0262  */
0263 #ifdef CONFIG_FB_RIVA_BACKLIGHT
0264 /* We do not have any information about which values are allowed, thus
0265  * we used safe values.
0266  */
0267 #define MIN_LEVEL 0x158
0268 #define MAX_LEVEL 0x534
0269 #define LEVEL_STEP ((MAX_LEVEL - MIN_LEVEL) / FB_BACKLIGHT_MAX)
0270 
0271 static int riva_bl_get_level_brightness(struct riva_par *par,
0272         int level)
0273 {
0274     struct fb_info *info = pci_get_drvdata(par->pdev);
0275     int nlevel;
0276 
0277     /* Get and convert the value */
0278     /* No locking on bl_curve since accessing a single value */
0279     nlevel = MIN_LEVEL + info->bl_curve[level] * LEVEL_STEP;
0280 
0281     if (nlevel < 0)
0282         nlevel = 0;
0283     else if (nlevel < MIN_LEVEL)
0284         nlevel = MIN_LEVEL;
0285     else if (nlevel > MAX_LEVEL)
0286         nlevel = MAX_LEVEL;
0287 
0288     return nlevel;
0289 }
0290 
0291 static int riva_bl_update_status(struct backlight_device *bd)
0292 {
0293     struct riva_par *par = bl_get_data(bd);
0294     U032 tmp_pcrt, tmp_pmc;
0295     int level;
0296 
0297     if (bd->props.power != FB_BLANK_UNBLANK ||
0298         bd->props.fb_blank != FB_BLANK_UNBLANK)
0299         level = 0;
0300     else
0301         level = bd->props.brightness;
0302 
0303     tmp_pmc = NV_RD32(par->riva.PMC, 0x10F0) & 0x0000FFFF;
0304     tmp_pcrt = NV_RD32(par->riva.PCRTC0, 0x081C) & 0xFFFFFFFC;
0305     if(level > 0) {
0306         tmp_pcrt |= 0x1;
0307         tmp_pmc |= (1 << 31); /* backlight bit */
0308         tmp_pmc |= riva_bl_get_level_brightness(par, level) << 16; /* level */
0309     }
0310     NV_WR32(par->riva.PCRTC0, 0x081C, tmp_pcrt);
0311     NV_WR32(par->riva.PMC, 0x10F0, tmp_pmc);
0312 
0313     return 0;
0314 }
0315 
0316 static const struct backlight_ops riva_bl_ops = {
0317     .update_status  = riva_bl_update_status,
0318 };
0319 
0320 static void riva_bl_init(struct riva_par *par)
0321 {
0322     struct backlight_properties props;
0323     struct fb_info *info = pci_get_drvdata(par->pdev);
0324     struct backlight_device *bd;
0325     char name[12];
0326 
0327     if (!par->FlatPanel)
0328         return;
0329 
0330 #ifdef CONFIG_PMAC_BACKLIGHT
0331     if (!machine_is(powermac) ||
0332         !pmac_has_backlight_type("mnca"))
0333         return;
0334 #endif
0335 
0336     snprintf(name, sizeof(name), "rivabl%d", info->node);
0337 
0338     memset(&props, 0, sizeof(struct backlight_properties));
0339     props.type = BACKLIGHT_RAW;
0340     props.max_brightness = FB_BACKLIGHT_LEVELS - 1;
0341     bd = backlight_device_register(name, info->dev, par, &riva_bl_ops,
0342                        &props);
0343     if (IS_ERR(bd)) {
0344         info->bl_dev = NULL;
0345         printk(KERN_WARNING "riva: Backlight registration failed\n");
0346         goto error;
0347     }
0348 
0349     info->bl_dev = bd;
0350     fb_bl_default_curve(info, 0,
0351         MIN_LEVEL * FB_BACKLIGHT_MAX / MAX_LEVEL,
0352         FB_BACKLIGHT_MAX);
0353 
0354     bd->props.brightness = bd->props.max_brightness;
0355     bd->props.power = FB_BLANK_UNBLANK;
0356     backlight_update_status(bd);
0357 
0358     printk("riva: Backlight initialized (%s)\n", name);
0359 
0360     return;
0361 
0362 error:
0363     return;
0364 }
0365 
0366 static void riva_bl_exit(struct fb_info *info)
0367 {
0368     struct backlight_device *bd = info->bl_dev;
0369 
0370     backlight_device_unregister(bd);
0371     printk("riva: Backlight unloaded\n");
0372 }
0373 #else
0374 static inline void riva_bl_init(struct riva_par *par) {}
0375 static inline void riva_bl_exit(struct fb_info *info) {}
0376 #endif /* CONFIG_FB_RIVA_BACKLIGHT */
0377 
0378 /* ------------------------------------------------------------------------- *
0379  *
0380  * MMIO access macros
0381  *
0382  * ------------------------------------------------------------------------- */
0383 
0384 static inline void CRTCout(struct riva_par *par, unsigned char index,
0385                unsigned char val)
0386 {
0387     VGA_WR08(par->riva.PCIO, 0x3d4, index);
0388     VGA_WR08(par->riva.PCIO, 0x3d5, val);
0389 }
0390 
0391 static inline unsigned char CRTCin(struct riva_par *par,
0392                    unsigned char index)
0393 {
0394     VGA_WR08(par->riva.PCIO, 0x3d4, index);
0395     return (VGA_RD08(par->riva.PCIO, 0x3d5));
0396 }
0397 
0398 static inline void GRAout(struct riva_par *par, unsigned char index,
0399               unsigned char val)
0400 {
0401     VGA_WR08(par->riva.PVIO, 0x3ce, index);
0402     VGA_WR08(par->riva.PVIO, 0x3cf, val);
0403 }
0404 
0405 static inline unsigned char GRAin(struct riva_par *par,
0406                   unsigned char index)
0407 {
0408     VGA_WR08(par->riva.PVIO, 0x3ce, index);
0409     return (VGA_RD08(par->riva.PVIO, 0x3cf));
0410 }
0411 
0412 static inline void SEQout(struct riva_par *par, unsigned char index,
0413               unsigned char val)
0414 {
0415     VGA_WR08(par->riva.PVIO, 0x3c4, index);
0416     VGA_WR08(par->riva.PVIO, 0x3c5, val);
0417 }
0418 
0419 static inline unsigned char SEQin(struct riva_par *par,
0420                   unsigned char index)
0421 {
0422     VGA_WR08(par->riva.PVIO, 0x3c4, index);
0423     return (VGA_RD08(par->riva.PVIO, 0x3c5));
0424 }
0425 
0426 static inline void ATTRout(struct riva_par *par, unsigned char index,
0427                unsigned char val)
0428 {
0429     VGA_WR08(par->riva.PCIO, 0x3c0, index);
0430     VGA_WR08(par->riva.PCIO, 0x3c0, val);
0431 }
0432 
0433 static inline unsigned char ATTRin(struct riva_par *par,
0434                    unsigned char index)
0435 {
0436     VGA_WR08(par->riva.PCIO, 0x3c0, index);
0437     return (VGA_RD08(par->riva.PCIO, 0x3c1));
0438 }
0439 
0440 static inline void MISCout(struct riva_par *par, unsigned char val)
0441 {
0442     VGA_WR08(par->riva.PVIO, 0x3c2, val);
0443 }
0444 
0445 static inline unsigned char MISCin(struct riva_par *par)
0446 {
0447     return (VGA_RD08(par->riva.PVIO, 0x3cc));
0448 }
0449 
0450 static inline void reverse_order(u32 *l)
0451 {
0452     u8 *a = (u8 *)l;
0453     a[0] = bitrev8(a[0]);
0454     a[1] = bitrev8(a[1]);
0455     a[2] = bitrev8(a[2]);
0456     a[3] = bitrev8(a[3]);
0457 }
0458 
0459 /* ------------------------------------------------------------------------- *
0460  *
0461  * cursor stuff
0462  *
0463  * ------------------------------------------------------------------------- */
0464 
0465 /**
0466  * rivafb_load_cursor_image - load cursor image to hardware
0467  * @data8: address to monochrome bitmap (1 = foreground color, 0 = background)
0468  * @par:  pointer to private data
0469  * @w:    width of cursor image in pixels
0470  * @h:    height of cursor image in scanlines
0471  * @bg:   background color (ARGB1555) - alpha bit determines opacity
0472  * @fg:   foreground color (ARGB1555)
0473  *
0474  * DESCRIPTiON:
0475  * Loads cursor image based on a monochrome source and mask bitmap.  The
0476  * image bits determines the color of the pixel, 0 for background, 1 for
0477  * foreground.  Only the affected region (as determined by @w and @h 
0478  * parameters) will be updated.
0479  *
0480  * CALLED FROM:
0481  * rivafb_cursor()
0482  */
0483 static void rivafb_load_cursor_image(struct riva_par *par, u8 *data8,
0484                      u16 bg, u16 fg, u32 w, u32 h)
0485 {
0486     int i, j, k = 0;
0487     u32 b, tmp;
0488     u32 *data = (u32 *)data8;
0489     bg = le16_to_cpu(bg);
0490     fg = le16_to_cpu(fg);
0491 
0492     w = (w + 1) & ~1;
0493 
0494     for (i = 0; i < h; i++) {
0495         b = *data++;
0496         reverse_order(&b);
0497         
0498         for (j = 0; j < w/2; j++) {
0499             tmp = 0;
0500 #if defined (__BIG_ENDIAN)
0501             tmp = (b & (1 << 31)) ? fg << 16 : bg << 16;
0502             b <<= 1;
0503             tmp |= (b & (1 << 31)) ? fg : bg;
0504             b <<= 1;
0505 #else
0506             tmp = (b & 1) ? fg : bg;
0507             b >>= 1;
0508             tmp |= (b & 1) ? fg << 16 : bg << 16;
0509             b >>= 1;
0510 #endif
0511             writel(tmp, &par->riva.CURSOR[k++]);
0512         }
0513         k += (MAX_CURS - w)/2;
0514     }
0515 }
0516 
0517 /* ------------------------------------------------------------------------- *
0518  *
0519  * general utility functions
0520  *
0521  * ------------------------------------------------------------------------- */
0522 
0523 /**
0524  * riva_wclut - set CLUT entry
0525  * @chip: pointer to RIVA_HW_INST object
0526  * @regnum: register number
0527  * @red: red component
0528  * @green: green component
0529  * @blue: blue component
0530  *
0531  * DESCRIPTION:
0532  * Sets color register @regnum.
0533  *
0534  * CALLED FROM:
0535  * rivafb_setcolreg()
0536  */
0537 static void riva_wclut(RIVA_HW_INST *chip,
0538                unsigned char regnum, unsigned char red,
0539                unsigned char green, unsigned char blue)
0540 {
0541     VGA_WR08(chip->PDIO, 0x3c8, regnum);
0542     VGA_WR08(chip->PDIO, 0x3c9, red);
0543     VGA_WR08(chip->PDIO, 0x3c9, green);
0544     VGA_WR08(chip->PDIO, 0x3c9, blue);
0545 }
0546 
0547 /**
0548  * riva_rclut - read fromCLUT register
0549  * @chip: pointer to RIVA_HW_INST object
0550  * @regnum: register number
0551  * @red: red component
0552  * @green: green component
0553  * @blue: blue component
0554  *
0555  * DESCRIPTION:
0556  * Reads red, green, and blue from color register @regnum.
0557  *
0558  * CALLED FROM:
0559  * rivafb_setcolreg()
0560  */
0561 static void riva_rclut(RIVA_HW_INST *chip,
0562                unsigned char regnum, unsigned char *red,
0563                unsigned char *green, unsigned char *blue)
0564 {
0565     
0566     VGA_WR08(chip->PDIO, 0x3c7, regnum);
0567     *red = VGA_RD08(chip->PDIO, 0x3c9);
0568     *green = VGA_RD08(chip->PDIO, 0x3c9);
0569     *blue = VGA_RD08(chip->PDIO, 0x3c9);
0570 }
0571 
0572 /**
0573  * riva_save_state - saves current chip state
0574  * @par: pointer to riva_par object containing info for current riva board
0575  * @regs: pointer to riva_regs object
0576  *
0577  * DESCRIPTION:
0578  * Saves current chip state to @regs.
0579  *
0580  * CALLED FROM:
0581  * rivafb_probe()
0582  */
0583 /* from GGI */
0584 static void riva_save_state(struct riva_par *par, struct riva_regs *regs)
0585 {
0586     int i;
0587 
0588     NVTRACE_ENTER();
0589     par->riva.LockUnlock(&par->riva, 0);
0590 
0591     par->riva.UnloadStateExt(&par->riva, &regs->ext);
0592 
0593     regs->misc_output = MISCin(par);
0594 
0595     for (i = 0; i < NUM_CRT_REGS; i++)
0596         regs->crtc[i] = CRTCin(par, i);
0597 
0598     for (i = 0; i < NUM_ATC_REGS; i++)
0599         regs->attr[i] = ATTRin(par, i);
0600 
0601     for (i = 0; i < NUM_GRC_REGS; i++)
0602         regs->gra[i] = GRAin(par, i);
0603 
0604     for (i = 0; i < NUM_SEQ_REGS; i++)
0605         regs->seq[i] = SEQin(par, i);
0606     NVTRACE_LEAVE();
0607 }
0608 
0609 /**
0610  * riva_load_state - loads current chip state
0611  * @par: pointer to riva_par object containing info for current riva board
0612  * @regs: pointer to riva_regs object
0613  *
0614  * DESCRIPTION:
0615  * Loads chip state from @regs.
0616  *
0617  * CALLED FROM:
0618  * riva_load_video_mode()
0619  * rivafb_probe()
0620  * rivafb_remove()
0621  */
0622 /* from GGI */
0623 static void riva_load_state(struct riva_par *par, struct riva_regs *regs)
0624 {
0625     RIVA_HW_STATE *state = &regs->ext;
0626     int i;
0627 
0628     NVTRACE_ENTER();
0629     CRTCout(par, 0x11, 0x00);
0630 
0631     par->riva.LockUnlock(&par->riva, 0);
0632 
0633     par->riva.LoadStateExt(&par->riva, state);
0634 
0635     MISCout(par, regs->misc_output);
0636 
0637     for (i = 0; i < NUM_CRT_REGS; i++) {
0638         switch (i) {
0639         case 0x19:
0640         case 0x20 ... 0x40:
0641             break;
0642         default:
0643             CRTCout(par, i, regs->crtc[i]);
0644         }
0645     }
0646 
0647     for (i = 0; i < NUM_ATC_REGS; i++)
0648         ATTRout(par, i, regs->attr[i]);
0649 
0650     for (i = 0; i < NUM_GRC_REGS; i++)
0651         GRAout(par, i, regs->gra[i]);
0652 
0653     for (i = 0; i < NUM_SEQ_REGS; i++)
0654         SEQout(par, i, regs->seq[i]);
0655     NVTRACE_LEAVE();
0656 }
0657 
0658 /**
0659  * riva_load_video_mode - calculate timings
0660  * @info: pointer to fb_info object containing info for current riva board
0661  *
0662  * DESCRIPTION:
0663  * Calculate some timings and then send em off to riva_load_state().
0664  *
0665  * CALLED FROM:
0666  * rivafb_set_par()
0667  */
0668 static int riva_load_video_mode(struct fb_info *info)
0669 {
0670     int bpp, width, hDisplaySize, hDisplay, hStart,
0671         hEnd, hTotal, height, vDisplay, vStart, vEnd, vTotal, dotClock;
0672     int hBlankStart, hBlankEnd, vBlankStart, vBlankEnd;
0673     int rc;
0674     struct riva_par *par = info->par;
0675     struct riva_regs newmode;
0676     
0677     NVTRACE_ENTER();
0678     /* time to calculate */
0679     rivafb_blank(FB_BLANK_NORMAL, info);
0680 
0681     bpp = info->var.bits_per_pixel;
0682     if (bpp == 16 && info->var.green.length == 5)
0683         bpp = 15;
0684     width = info->var.xres_virtual;
0685     hDisplaySize = info->var.xres;
0686     hDisplay = (hDisplaySize / 8) - 1;
0687     hStart = (hDisplaySize + info->var.right_margin) / 8 - 1;
0688     hEnd = (hDisplaySize + info->var.right_margin +
0689         info->var.hsync_len) / 8 - 1;
0690     hTotal = (hDisplaySize + info->var.right_margin +
0691           info->var.hsync_len + info->var.left_margin) / 8 - 5;
0692     hBlankStart = hDisplay;
0693     hBlankEnd = hTotal + 4;
0694 
0695     height = info->var.yres_virtual;
0696     vDisplay = info->var.yres - 1;
0697     vStart = info->var.yres + info->var.lower_margin - 1;
0698     vEnd = info->var.yres + info->var.lower_margin +
0699            info->var.vsync_len - 1;
0700     vTotal = info->var.yres + info->var.lower_margin +
0701          info->var.vsync_len + info->var.upper_margin + 2;
0702     vBlankStart = vDisplay;
0703     vBlankEnd = vTotal + 1;
0704     dotClock = 1000000000 / info->var.pixclock;
0705 
0706     memcpy(&newmode, &reg_template, sizeof(struct riva_regs));
0707 
0708     if ((info->var.vmode & FB_VMODE_MASK) == FB_VMODE_INTERLACED)
0709         vTotal |= 1;
0710 
0711     if (par->FlatPanel) {
0712         vStart = vTotal - 3;
0713         vEnd = vTotal - 2;
0714         vBlankStart = vStart;
0715         hStart = hTotal - 3;
0716         hEnd = hTotal - 2;
0717         hBlankEnd = hTotal + 4;
0718     }
0719 
0720     newmode.crtc[0x0] = Set8Bits (hTotal); 
0721     newmode.crtc[0x1] = Set8Bits (hDisplay);
0722     newmode.crtc[0x2] = Set8Bits (hBlankStart);
0723     newmode.crtc[0x3] = SetBitField (hBlankEnd, 4: 0, 4:0) | SetBit (7);
0724     newmode.crtc[0x4] = Set8Bits (hStart);
0725     newmode.crtc[0x5] = SetBitField (hBlankEnd, 5: 5, 7:7)
0726         | SetBitField (hEnd, 4: 0, 4:0);
0727     newmode.crtc[0x6] = SetBitField (vTotal, 7: 0, 7:0);
0728     newmode.crtc[0x7] = SetBitField (vTotal, 8: 8, 0:0)
0729         | SetBitField (vDisplay, 8: 8, 1:1)
0730         | SetBitField (vStart, 8: 8, 2:2)
0731         | SetBitField (vBlankStart, 8: 8, 3:3)
0732         | SetBit (4)
0733         | SetBitField (vTotal, 9: 9, 5:5)
0734         | SetBitField (vDisplay, 9: 9, 6:6)
0735         | SetBitField (vStart, 9: 9, 7:7);
0736     newmode.crtc[0x9] = SetBitField (vBlankStart, 9: 9, 5:5)
0737         | SetBit (6);
0738     newmode.crtc[0x10] = Set8Bits (vStart);
0739     newmode.crtc[0x11] = SetBitField (vEnd, 3: 0, 3:0)
0740         | SetBit (5);
0741     newmode.crtc[0x12] = Set8Bits (vDisplay);
0742     newmode.crtc[0x13] = (width / 8) * ((bpp + 1) / 8);
0743     newmode.crtc[0x15] = Set8Bits (vBlankStart);
0744     newmode.crtc[0x16] = Set8Bits (vBlankEnd);
0745 
0746     newmode.ext.screen = SetBitField(hBlankEnd,6:6,4:4)
0747         | SetBitField(vBlankStart,10:10,3:3)
0748         | SetBitField(vStart,10:10,2:2)
0749         | SetBitField(vDisplay,10:10,1:1)
0750         | SetBitField(vTotal,10:10,0:0);
0751     newmode.ext.horiz  = SetBitField(hTotal,8:8,0:0) 
0752         | SetBitField(hDisplay,8:8,1:1)
0753         | SetBitField(hBlankStart,8:8,2:2)
0754         | SetBitField(hStart,8:8,3:3);
0755     newmode.ext.extra  = SetBitField(vTotal,11:11,0:0)
0756         | SetBitField(vDisplay,11:11,2:2)
0757         | SetBitField(vStart,11:11,4:4)
0758         | SetBitField(vBlankStart,11:11,6:6); 
0759 
0760     if ((info->var.vmode & FB_VMODE_MASK) == FB_VMODE_INTERLACED) {
0761         int tmp = (hTotal >> 1) & ~1;
0762         newmode.ext.interlace = Set8Bits(tmp);
0763         newmode.ext.horiz |= SetBitField(tmp, 8:8,4:4);
0764     } else 
0765         newmode.ext.interlace = 0xff; /* interlace off */
0766 
0767     if (par->riva.Architecture >= NV_ARCH_10)
0768         par->riva.CURSOR = (U032 __iomem *)(info->screen_base + par->riva.CursorStart);
0769 
0770     if (info->var.sync & FB_SYNC_HOR_HIGH_ACT)
0771         newmode.misc_output &= ~0x40;
0772     else
0773         newmode.misc_output |= 0x40;
0774     if (info->var.sync & FB_SYNC_VERT_HIGH_ACT)
0775         newmode.misc_output &= ~0x80;
0776     else
0777         newmode.misc_output |= 0x80;    
0778 
0779     rc = CalcStateExt(&par->riva, &newmode.ext, par->pdev, bpp, width,
0780               hDisplaySize, height, dotClock);
0781     if (rc)
0782         goto out;
0783 
0784     newmode.ext.scale = NV_RD32(par->riva.PRAMDAC, 0x00000848) &
0785         0xfff000ff;
0786     if (par->FlatPanel == 1) {
0787         newmode.ext.pixel |= (1 << 7);
0788         newmode.ext.scale |= (1 << 8);
0789     }
0790     if (par->SecondCRTC) {
0791         newmode.ext.head  = NV_RD32(par->riva.PCRTC0, 0x00000860) &
0792             ~0x00001000;
0793         newmode.ext.head2 = NV_RD32(par->riva.PCRTC0, 0x00002860) |
0794             0x00001000;
0795         newmode.ext.crtcOwner = 3;
0796         newmode.ext.pllsel |= 0x20000800;
0797         newmode.ext.vpll2 = newmode.ext.vpll;
0798     } else if (par->riva.twoHeads) {
0799         newmode.ext.head  =  NV_RD32(par->riva.PCRTC0, 0x00000860) |
0800             0x00001000;
0801         newmode.ext.head2 =  NV_RD32(par->riva.PCRTC0, 0x00002860) &
0802             ~0x00001000;
0803         newmode.ext.crtcOwner = 0;
0804         newmode.ext.vpll2 = NV_RD32(par->riva.PRAMDAC0, 0x00000520);
0805     }
0806     if (par->FlatPanel == 1) {
0807         newmode.ext.pixel |= (1 << 7);
0808         newmode.ext.scale |= (1 << 8);
0809     }
0810     newmode.ext.cursorConfig = 0x02000100;
0811     par->current_state = newmode;
0812     riva_load_state(par, &par->current_state);
0813     par->riva.LockUnlock(&par->riva, 0); /* important for HW cursor */
0814 
0815 out:
0816     rivafb_blank(FB_BLANK_UNBLANK, info);
0817     NVTRACE_LEAVE();
0818 
0819     return rc;
0820 }
0821 
0822 static void riva_update_var(struct fb_var_screeninfo *var,
0823                 const struct fb_videomode *modedb)
0824 {
0825     NVTRACE_ENTER();
0826     var->xres = var->xres_virtual = modedb->xres;
0827     var->yres = modedb->yres;
0828         if (var->yres_virtual < var->yres)
0829         var->yres_virtual = var->yres;
0830         var->xoffset = var->yoffset = 0;
0831         var->pixclock = modedb->pixclock;
0832         var->left_margin = modedb->left_margin;
0833         var->right_margin = modedb->right_margin;
0834         var->upper_margin = modedb->upper_margin;
0835         var->lower_margin = modedb->lower_margin;
0836         var->hsync_len = modedb->hsync_len;
0837         var->vsync_len = modedb->vsync_len;
0838         var->sync = modedb->sync;
0839         var->vmode = modedb->vmode;
0840     NVTRACE_LEAVE();
0841 }
0842 
0843 /**
0844  * rivafb_do_maximize - 
0845  * @info: pointer to fb_info object containing info for current riva board
0846  * @var: standard kernel fb changeable data
0847  * @nom: nom
0848  * @den: den
0849  *
0850  * DESCRIPTION:
0851  * .
0852  *
0853  * RETURNS:
0854  * -EINVAL on failure, 0 on success
0855  * 
0856  *
0857  * CALLED FROM:
0858  * rivafb_check_var()
0859  */
0860 static int rivafb_do_maximize(struct fb_info *info,
0861                   struct fb_var_screeninfo *var,
0862                   int nom, int den)
0863 {
0864     static struct {
0865         int xres, yres;
0866     } modes[] = {
0867         {1600, 1280},
0868         {1280, 1024},
0869         {1024, 768},
0870         {800, 600},
0871         {640, 480},
0872         {-1, -1}
0873     };
0874     int i;
0875 
0876     NVTRACE_ENTER();
0877     /* use highest possible virtual resolution */
0878     if (var->xres_virtual == -1 && var->yres_virtual == -1) {
0879         printk(KERN_WARNING PFX
0880                "using maximum available virtual resolution\n");
0881         for (i = 0; modes[i].xres != -1; i++) {
0882             if (modes[i].xres * nom / den * modes[i].yres <
0883                 info->fix.smem_len)
0884                 break;
0885         }
0886         if (modes[i].xres == -1) {
0887             printk(KERN_ERR PFX
0888                    "could not find a virtual resolution that fits into video memory!!\n");
0889             NVTRACE("EXIT - EINVAL error\n");
0890             return -EINVAL;
0891         }
0892         var->xres_virtual = modes[i].xres;
0893         var->yres_virtual = modes[i].yres;
0894 
0895         printk(KERN_INFO PFX
0896                "virtual resolution set to maximum of %dx%d\n",
0897                var->xres_virtual, var->yres_virtual);
0898     } else if (var->xres_virtual == -1) {
0899         var->xres_virtual = (info->fix.smem_len * den /
0900             (nom * var->yres_virtual)) & ~15;
0901         printk(KERN_WARNING PFX
0902                "setting virtual X resolution to %d\n", var->xres_virtual);
0903     } else if (var->yres_virtual == -1) {
0904         var->xres_virtual = (var->xres_virtual + 15) & ~15;
0905         var->yres_virtual = info->fix.smem_len * den /
0906             (nom * var->xres_virtual);
0907         printk(KERN_WARNING PFX
0908                "setting virtual Y resolution to %d\n", var->yres_virtual);
0909     } else {
0910         var->xres_virtual = (var->xres_virtual + 15) & ~15;
0911         if (var->xres_virtual * nom / den * var->yres_virtual > info->fix.smem_len) {
0912             printk(KERN_ERR PFX
0913                    "mode %dx%dx%d rejected...resolution too high to fit into video memory!\n",
0914                    var->xres, var->yres, var->bits_per_pixel);
0915             NVTRACE("EXIT - EINVAL error\n");
0916             return -EINVAL;
0917         }
0918     }
0919     
0920     if (var->xres_virtual * nom / den >= 8192) {
0921         printk(KERN_WARNING PFX
0922                "virtual X resolution (%d) is too high, lowering to %d\n",
0923                var->xres_virtual, 8192 * den / nom - 16);
0924         var->xres_virtual = 8192 * den / nom - 16;
0925     }
0926     
0927     if (var->xres_virtual < var->xres) {
0928         printk(KERN_ERR PFX
0929                "virtual X resolution (%d) is smaller than real\n", var->xres_virtual);
0930         return -EINVAL;
0931     }
0932 
0933     if (var->yres_virtual < var->yres) {
0934         printk(KERN_ERR PFX
0935                "virtual Y resolution (%d) is smaller than real\n", var->yres_virtual);
0936         return -EINVAL;
0937     }
0938     if (var->yres_virtual > 0x7fff/nom)
0939         var->yres_virtual = 0x7fff/nom;
0940     if (var->xres_virtual > 0x7fff/nom)
0941         var->xres_virtual = 0x7fff/nom;
0942     NVTRACE_LEAVE();
0943     return 0;
0944 }
0945 
0946 static void
0947 riva_set_pattern(struct riva_par *par, int clr0, int clr1, int pat0, int pat1)
0948 {
0949     RIVA_FIFO_FREE(par->riva, Patt, 4);
0950     NV_WR32(&par->riva.Patt->Color0, 0, clr0);
0951     NV_WR32(&par->riva.Patt->Color1, 0, clr1);
0952     NV_WR32(par->riva.Patt->Monochrome, 0, pat0);
0953     NV_WR32(par->riva.Patt->Monochrome, 4, pat1);
0954 }
0955 
0956 /* acceleration routines */
0957 static inline void wait_for_idle(struct riva_par *par)
0958 {
0959     while (par->riva.Busy(&par->riva));
0960 }
0961 
0962 /*
0963  * Set ROP.  Translate X rop into ROP3.  Internal routine.
0964  */
0965 static void
0966 riva_set_rop_solid(struct riva_par *par, int rop)
0967 {
0968     riva_set_pattern(par, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF, 0xFFFFFFFF);
0969         RIVA_FIFO_FREE(par->riva, Rop, 1);
0970         NV_WR32(&par->riva.Rop->Rop3, 0, rop);
0971 
0972 }
0973 
0974 static void riva_setup_accel(struct fb_info *info)
0975 {
0976     struct riva_par *par = info->par;
0977 
0978     RIVA_FIFO_FREE(par->riva, Clip, 2);
0979     NV_WR32(&par->riva.Clip->TopLeft, 0, 0x0);
0980     NV_WR32(&par->riva.Clip->WidthHeight, 0,
0981         (info->var.xres_virtual & 0xffff) |
0982         (info->var.yres_virtual << 16));
0983     riva_set_rop_solid(par, 0xcc);
0984     wait_for_idle(par);
0985 }
0986 
0987 /**
0988  * riva_get_cmap_len - query current color map length
0989  * @var: standard kernel fb changeable data
0990  *
0991  * DESCRIPTION:
0992  * Get current color map length.
0993  *
0994  * RETURNS:
0995  * Length of color map
0996  *
0997  * CALLED FROM:
0998  * rivafb_setcolreg()
0999  */
1000 static int riva_get_cmap_len(const struct fb_var_screeninfo *var)
1001 {
1002     int rc = 256;       /* reasonable default */
1003 
1004     switch (var->green.length) {
1005     case 8:
1006         rc = 256;   /* 256 entries (2^8), 8 bpp and RGB8888 */
1007         break;
1008     case 5:
1009         rc = 32;    /* 32 entries (2^5), 16 bpp, RGB555 */
1010         break;
1011     case 6:
1012         rc = 64;    /* 64 entries (2^6), 16 bpp, RGB565 */
1013         break;      
1014     default:
1015         /* should not occur */
1016         break;
1017     }
1018     return rc;
1019 }
1020 
1021 /* ------------------------------------------------------------------------- *
1022  *
1023  * framebuffer operations
1024  *
1025  * ------------------------------------------------------------------------- */
1026 
1027 static int rivafb_open(struct fb_info *info, int user)
1028 {
1029     struct riva_par *par = info->par;
1030 
1031     NVTRACE_ENTER();
1032     mutex_lock(&par->open_lock);
1033     if (!par->ref_count) {
1034 #ifdef CONFIG_X86
1035         memset(&par->state, 0, sizeof(struct vgastate));
1036         par->state.flags = VGA_SAVE_MODE  | VGA_SAVE_FONTS;
1037         /* save the DAC for Riva128 */
1038         if (par->riva.Architecture == NV_ARCH_03)
1039             par->state.flags |= VGA_SAVE_CMAP;
1040         save_vga(&par->state);
1041 #endif
1042         /* vgaHWunlock() + riva unlock (0x7F) */
1043         CRTCout(par, 0x11, 0xFF);
1044         par->riva.LockUnlock(&par->riva, 0);
1045     
1046         riva_save_state(par, &par->initial_state);
1047     }
1048     par->ref_count++;
1049     mutex_unlock(&par->open_lock);
1050     NVTRACE_LEAVE();
1051     return 0;
1052 }
1053 
1054 static int rivafb_release(struct fb_info *info, int user)
1055 {
1056     struct riva_par *par = info->par;
1057 
1058     NVTRACE_ENTER();
1059     mutex_lock(&par->open_lock);
1060     if (!par->ref_count) {
1061         mutex_unlock(&par->open_lock);
1062         return -EINVAL;
1063     }
1064     if (par->ref_count == 1) {
1065         par->riva.LockUnlock(&par->riva, 0);
1066         par->riva.LoadStateExt(&par->riva, &par->initial_state.ext);
1067         riva_load_state(par, &par->initial_state);
1068 #ifdef CONFIG_X86
1069         restore_vga(&par->state);
1070 #endif
1071         par->riva.LockUnlock(&par->riva, 1);
1072     }
1073     par->ref_count--;
1074     mutex_unlock(&par->open_lock);
1075     NVTRACE_LEAVE();
1076     return 0;
1077 }
1078 
1079 static int rivafb_check_var(struct fb_var_screeninfo *var, struct fb_info *info)
1080 {
1081     const struct fb_videomode *mode;
1082     struct riva_par *par = info->par;
1083     int nom, den;       /* translating from pixels->bytes */
1084     int mode_valid = 0;
1085     
1086     NVTRACE_ENTER();
1087     if (!var->pixclock)
1088         return -EINVAL;
1089 
1090     switch (var->bits_per_pixel) {
1091     case 1 ... 8:
1092         var->red.offset = var->green.offset = var->blue.offset = 0;
1093         var->red.length = var->green.length = var->blue.length = 8;
1094         var->bits_per_pixel = 8;
1095         nom = den = 1;
1096         break;
1097     case 9 ... 15:
1098         var->green.length = 5;
1099         fallthrough;
1100     case 16:
1101         var->bits_per_pixel = 16;
1102         /* The Riva128 supports RGB555 only */
1103         if (par->riva.Architecture == NV_ARCH_03)
1104             var->green.length = 5;
1105         if (var->green.length == 5) {
1106             /* 0rrrrrgg gggbbbbb */
1107             var->red.offset = 10;
1108             var->green.offset = 5;
1109             var->blue.offset = 0;
1110             var->red.length = 5;
1111             var->green.length = 5;
1112             var->blue.length = 5;
1113         } else {
1114             /* rrrrrggg gggbbbbb */
1115             var->red.offset = 11;
1116             var->green.offset = 5;
1117             var->blue.offset = 0;
1118             var->red.length = 5;
1119             var->green.length = 6;
1120             var->blue.length = 5;
1121         }
1122         nom = 2;
1123         den = 1;
1124         break;
1125     case 17 ... 32:
1126         var->red.length = var->green.length = var->blue.length = 8;
1127         var->bits_per_pixel = 32;
1128         var->red.offset = 16;
1129         var->green.offset = 8;
1130         var->blue.offset = 0;
1131         nom = 4;
1132         den = 1;
1133         break;
1134     default:
1135         printk(KERN_ERR PFX
1136                "mode %dx%dx%d rejected...color depth not supported.\n",
1137                var->xres, var->yres, var->bits_per_pixel);
1138         NVTRACE("EXIT, returning -EINVAL\n");
1139         return -EINVAL;
1140     }
1141 
1142     if (!strictmode) {
1143         if (!info->monspecs.vfmax || !info->monspecs.hfmax ||
1144             !info->monspecs.dclkmax || !fb_validate_mode(var, info))
1145             mode_valid = 1;
1146     }
1147 
1148     /* calculate modeline if supported by monitor */
1149     if (!mode_valid && info->monspecs.gtf) {
1150         if (!fb_get_mode(FB_MAXTIMINGS, 0, var, info))
1151             mode_valid = 1;
1152     }
1153 
1154     if (!mode_valid) {
1155         mode = fb_find_best_mode(var, &info->modelist);
1156         if (mode) {
1157             riva_update_var(var, mode);
1158             mode_valid = 1;
1159         }
1160     }
1161 
1162     if (!mode_valid && info->monspecs.modedb_len)
1163         return -EINVAL;
1164 
1165     if (var->xres_virtual < var->xres)
1166         var->xres_virtual = var->xres;
1167     if (var->yres_virtual <= var->yres)
1168         var->yres_virtual = -1;
1169     if (rivafb_do_maximize(info, var, nom, den) < 0)
1170         return -EINVAL;
1171 
1172     /* truncate xoffset and yoffset to maximum if too high */
1173     if (var->xoffset > var->xres_virtual - var->xres)
1174         var->xoffset = var->xres_virtual - var->xres - 1;
1175 
1176     if (var->yoffset > var->yres_virtual - var->yres)
1177         var->yoffset = var->yres_virtual - var->yres - 1;
1178 
1179     var->red.msb_right = 
1180         var->green.msb_right =
1181         var->blue.msb_right =
1182         var->transp.offset = var->transp.length = var->transp.msb_right = 0;
1183     NVTRACE_LEAVE();
1184     return 0;
1185 }
1186 
1187 static int rivafb_set_par(struct fb_info *info)
1188 {
1189     struct riva_par *par = info->par;
1190     int rc = 0;
1191 
1192     NVTRACE_ENTER();
1193     /* vgaHWunlock() + riva unlock (0x7F) */
1194     CRTCout(par, 0x11, 0xFF);
1195     par->riva.LockUnlock(&par->riva, 0);
1196     rc = riva_load_video_mode(info);
1197     if (rc)
1198         goto out;
1199     if(!(info->flags & FBINFO_HWACCEL_DISABLED))
1200         riva_setup_accel(info);
1201     
1202     par->cursor_reset = 1;
1203     info->fix.line_length = (info->var.xres_virtual * (info->var.bits_per_pixel >> 3));
1204     info->fix.visual = (info->var.bits_per_pixel == 8) ?
1205                 FB_VISUAL_PSEUDOCOLOR : FB_VISUAL_DIRECTCOLOR;
1206 
1207     if (info->flags & FBINFO_HWACCEL_DISABLED)
1208         info->pixmap.scan_align = 1;
1209     else
1210         info->pixmap.scan_align = 4;
1211 
1212 out:
1213     NVTRACE_LEAVE();
1214     return rc;
1215 }
1216 
1217 /**
1218  * rivafb_pan_display
1219  * @var: standard kernel fb changeable data
1220  * @info: pointer to fb_info object containing info for current riva board
1221  *
1222  * DESCRIPTION:
1223  * Pan (or wrap, depending on the `vmode' field) the display using the
1224  * `xoffset' and `yoffset' fields of the `var' structure.
1225  * If the values don't fit, return -EINVAL.
1226  *
1227  * This call looks only at xoffset, yoffset and the FB_VMODE_YWRAP flag
1228  */
1229 static int rivafb_pan_display(struct fb_var_screeninfo *var,
1230                   struct fb_info *info)
1231 {
1232     struct riva_par *par = info->par;
1233     unsigned int base;
1234 
1235     NVTRACE_ENTER();
1236     base = var->yoffset * info->fix.line_length + var->xoffset;
1237     par->riva.SetStartAddress(&par->riva, base);
1238     NVTRACE_LEAVE();
1239     return 0;
1240 }
1241 
1242 static int rivafb_blank(int blank, struct fb_info *info)
1243 {
1244     struct riva_par *par= info->par;
1245     unsigned char tmp, vesa;
1246 
1247     tmp = SEQin(par, 0x01) & ~0x20; /* screen on/off */
1248     vesa = CRTCin(par, 0x1a) & ~0xc0;   /* sync on/off */
1249 
1250     NVTRACE_ENTER();
1251 
1252     if (blank)
1253         tmp |= 0x20;
1254 
1255     switch (blank) {
1256     case FB_BLANK_UNBLANK:
1257     case FB_BLANK_NORMAL:
1258         break;
1259     case FB_BLANK_VSYNC_SUSPEND:
1260         vesa |= 0x80;
1261         break;
1262     case FB_BLANK_HSYNC_SUSPEND:
1263         vesa |= 0x40;
1264         break;
1265     case FB_BLANK_POWERDOWN:
1266         vesa |= 0xc0;
1267         break;
1268     }
1269 
1270     SEQout(par, 0x01, tmp);
1271     CRTCout(par, 0x1a, vesa);
1272 
1273     NVTRACE_LEAVE();
1274 
1275     return 0;
1276 }
1277 
1278 /**
1279  * rivafb_setcolreg
1280  * @regno: register index
1281  * @red: red component
1282  * @green: green component
1283  * @blue: blue component
1284  * @transp: transparency
1285  * @info: pointer to fb_info object containing info for current riva board
1286  *
1287  * DESCRIPTION:
1288  * Set a single color register. The values supplied have a 16 bit
1289  * magnitude.
1290  *
1291  * RETURNS:
1292  * Return != 0 for invalid regno.
1293  *
1294  * CALLED FROM:
1295  * fbcmap.c:fb_set_cmap()
1296  */
1297 static int rivafb_setcolreg(unsigned regno, unsigned red, unsigned green,
1298               unsigned blue, unsigned transp,
1299               struct fb_info *info)
1300 {
1301     struct riva_par *par = info->par;
1302     RIVA_HW_INST *chip = &par->riva;
1303     int i;
1304 
1305     if (regno >= riva_get_cmap_len(&info->var))
1306             return -EINVAL;
1307 
1308     if (info->var.grayscale) {
1309         /* gray = 0.30*R + 0.59*G + 0.11*B */
1310         red = green = blue =
1311             (red * 77 + green * 151 + blue * 28) >> 8;
1312     }
1313 
1314     if (regno < 16 && info->fix.visual == FB_VISUAL_DIRECTCOLOR) {
1315         ((u32 *) info->pseudo_palette)[regno] =
1316             (regno << info->var.red.offset) |
1317             (regno << info->var.green.offset) |
1318             (regno << info->var.blue.offset);
1319         /*
1320          * The Riva128 2D engine requires color information in
1321          * TrueColor format even if framebuffer is in DirectColor
1322          */
1323         if (par->riva.Architecture == NV_ARCH_03) {
1324             switch (info->var.bits_per_pixel) {
1325             case 16:
1326                 par->palette[regno] = ((red & 0xf800) >> 1) |
1327                     ((green & 0xf800) >> 6) |
1328                     ((blue & 0xf800) >> 11);
1329                 break;
1330             case 32:
1331                 par->palette[regno] = ((red & 0xff00) << 8) |
1332                     ((green & 0xff00)) |
1333                     ((blue & 0xff00) >> 8);
1334                 break;
1335             }
1336         }
1337     }
1338 
1339     switch (info->var.bits_per_pixel) {
1340     case 8:
1341         /* "transparent" stuff is completely ignored. */
1342         riva_wclut(chip, regno, red >> 8, green >> 8, blue >> 8);
1343         break;
1344     case 16:
1345         if (info->var.green.length == 5) {
1346             for (i = 0; i < 8; i++) {
1347                 riva_wclut(chip, regno*8+i, red >> 8,
1348                        green >> 8, blue >> 8);
1349             }
1350         } else {
1351             u8 r, g, b;
1352 
1353             if (regno < 32) {
1354                 for (i = 0; i < 8; i++) {
1355                     riva_wclut(chip, regno*8+i,
1356                            red >> 8, green >> 8,
1357                            blue >> 8);
1358                 }
1359             }
1360             riva_rclut(chip, regno*4, &r, &g, &b);
1361             for (i = 0; i < 4; i++)
1362                 riva_wclut(chip, regno*4+i, r,
1363                        green >> 8, b);
1364         }
1365         break;
1366     case 32:
1367         riva_wclut(chip, regno, red >> 8, green >> 8, blue >> 8);
1368         break;
1369     default:
1370         /* do nothing */
1371         break;
1372     }
1373     return 0;
1374 }
1375 
1376 /**
1377  * rivafb_fillrect - hardware accelerated color fill function
1378  * @info: pointer to fb_info structure
1379  * @rect: pointer to fb_fillrect structure
1380  *
1381  * DESCRIPTION:
1382  * This function fills up a region of framebuffer memory with a solid
1383  * color with a choice of two different ROP's, copy or invert.
1384  *
1385  * CALLED FROM:
1386  * framebuffer hook
1387  */
1388 static void rivafb_fillrect(struct fb_info *info, const struct fb_fillrect *rect)
1389 {
1390     struct riva_par *par = info->par;
1391     u_int color, rop = 0;
1392 
1393     if ((info->flags & FBINFO_HWACCEL_DISABLED)) {
1394         cfb_fillrect(info, rect);
1395         return;
1396     }
1397 
1398     if (info->var.bits_per_pixel == 8)
1399         color = rect->color;
1400     else {
1401         if (par->riva.Architecture != NV_ARCH_03)
1402             color = ((u32 *)info->pseudo_palette)[rect->color];
1403         else
1404             color = par->palette[rect->color];
1405     }
1406 
1407     switch (rect->rop) {
1408     case ROP_XOR:
1409         rop = 0x66;
1410         break;
1411     case ROP_COPY:
1412     default:
1413         rop = 0xCC;
1414         break;
1415     }
1416 
1417     riva_set_rop_solid(par, rop);
1418 
1419     RIVA_FIFO_FREE(par->riva, Bitmap, 1);
1420     NV_WR32(&par->riva.Bitmap->Color1A, 0, color);
1421 
1422     RIVA_FIFO_FREE(par->riva, Bitmap, 2);
1423     NV_WR32(&par->riva.Bitmap->UnclippedRectangle[0].TopLeft, 0,
1424         (rect->dx << 16) | rect->dy);
1425     mb();
1426     NV_WR32(&par->riva.Bitmap->UnclippedRectangle[0].WidthHeight, 0,
1427         (rect->width << 16) | rect->height);
1428     mb();
1429     riva_set_rop_solid(par, 0xcc);
1430 
1431 }
1432 
1433 /**
1434  * rivafb_copyarea - hardware accelerated blit function
1435  * @info: pointer to fb_info structure
1436  * @region: pointer to fb_copyarea structure
1437  *
1438  * DESCRIPTION:
1439  * This copies an area of pixels from one location to another
1440  *
1441  * CALLED FROM:
1442  * framebuffer hook
1443  */
1444 static void rivafb_copyarea(struct fb_info *info, const struct fb_copyarea *region)
1445 {
1446     struct riva_par *par = info->par;
1447 
1448     if ((info->flags & FBINFO_HWACCEL_DISABLED)) {
1449         cfb_copyarea(info, region);
1450         return;
1451     }
1452 
1453     RIVA_FIFO_FREE(par->riva, Blt, 3);
1454     NV_WR32(&par->riva.Blt->TopLeftSrc, 0,
1455         (region->sy << 16) | region->sx);
1456     NV_WR32(&par->riva.Blt->TopLeftDst, 0,
1457         (region->dy << 16) | region->dx);
1458     mb();
1459     NV_WR32(&par->riva.Blt->WidthHeight, 0,
1460         (region->height << 16) | region->width);
1461     mb();
1462 }
1463 
1464 static inline void convert_bgcolor_16(u32 *col)
1465 {
1466     *col = ((*col & 0x0000F800) << 8)
1467         | ((*col & 0x00007E0) << 5)
1468         | ((*col & 0x0000001F) << 3)
1469         |      0xFF000000;
1470     mb();
1471 }
1472 
1473 /**
1474  * rivafb_imageblit: hardware accelerated color expand function
1475  * @info: pointer to fb_info structure
1476  * @image: pointer to fb_image structure
1477  *
1478  * DESCRIPTION:
1479  * If the source is a monochrome bitmap, the function fills up a a region
1480  * of framebuffer memory with pixels whose color is determined by the bit
1481  * setting of the bitmap, 1 - foreground, 0 - background.
1482  *
1483  * If the source is not a monochrome bitmap, color expansion is not done.
1484  * In this case, it is channeled to a software function.
1485  *
1486  * CALLED FROM:
1487  * framebuffer hook
1488  */
1489 static void rivafb_imageblit(struct fb_info *info, 
1490                  const struct fb_image *image)
1491 {
1492     struct riva_par *par = info->par;
1493     u32 fgx = 0, bgx = 0, width, tmp;
1494     u8 *cdat = (u8 *) image->data;
1495     volatile u32 __iomem *d;
1496     int i, size;
1497 
1498     if ((info->flags & FBINFO_HWACCEL_DISABLED) || image->depth != 1) {
1499         cfb_imageblit(info, image);
1500         return;
1501     }
1502 
1503     switch (info->var.bits_per_pixel) {
1504     case 8:
1505         fgx = image->fg_color;
1506         bgx = image->bg_color;
1507         break;
1508     case 16:
1509     case 32:
1510         if (par->riva.Architecture != NV_ARCH_03) {
1511             fgx = ((u32 *)info->pseudo_palette)[image->fg_color];
1512             bgx = ((u32 *)info->pseudo_palette)[image->bg_color];
1513         } else {
1514             fgx = par->palette[image->fg_color];
1515             bgx = par->palette[image->bg_color];
1516         }
1517         if (info->var.green.length == 6)
1518             convert_bgcolor_16(&bgx);   
1519         break;
1520     }
1521 
1522     RIVA_FIFO_FREE(par->riva, Bitmap, 7);
1523     NV_WR32(&par->riva.Bitmap->ClipE.TopLeft, 0,
1524         (image->dy << 16) | (image->dx & 0xFFFF));
1525     NV_WR32(&par->riva.Bitmap->ClipE.BottomRight, 0,
1526         (((image->dy + image->height) << 16) |
1527          ((image->dx + image->width) & 0xffff)));
1528     NV_WR32(&par->riva.Bitmap->Color0E, 0, bgx);
1529     NV_WR32(&par->riva.Bitmap->Color1E, 0, fgx);
1530     NV_WR32(&par->riva.Bitmap->WidthHeightInE, 0,
1531         (image->height << 16) | ((image->width + 31) & ~31));
1532     NV_WR32(&par->riva.Bitmap->WidthHeightOutE, 0,
1533         (image->height << 16) | ((image->width + 31) & ~31));
1534     NV_WR32(&par->riva.Bitmap->PointE, 0,
1535         (image->dy << 16) | (image->dx & 0xFFFF));
1536 
1537     d = &par->riva.Bitmap->MonochromeData01E;
1538 
1539     width = (image->width + 31)/32;
1540     size = width * image->height;
1541     while (size >= 16) {
1542         RIVA_FIFO_FREE(par->riva, Bitmap, 16);
1543         for (i = 0; i < 16; i++) {
1544             tmp = *((u32 *)cdat);
1545             cdat = (u8 *)((u32 *)cdat + 1);
1546             reverse_order(&tmp);
1547             NV_WR32(d, i*4, tmp);
1548         }
1549         size -= 16;
1550     }
1551     if (size) {
1552         RIVA_FIFO_FREE(par->riva, Bitmap, size);
1553         for (i = 0; i < size; i++) {
1554             tmp = *((u32 *) cdat);
1555             cdat = (u8 *)((u32 *)cdat + 1);
1556             reverse_order(&tmp);
1557             NV_WR32(d, i*4, tmp);
1558         }
1559     }
1560 }
1561 
1562 /**
1563  * rivafb_cursor - hardware cursor function
1564  * @info: pointer to info structure
1565  * @cursor: pointer to fbcursor structure
1566  *
1567  * DESCRIPTION:
1568  * A cursor function that supports displaying a cursor image via hardware.
1569  * Within the kernel, copy and invert rops are supported.  If exported
1570  * to user space, only the copy rop will be supported.
1571  *
1572  * CALLED FROM
1573  * framebuffer hook
1574  */
1575 static int rivafb_cursor(struct fb_info *info, struct fb_cursor *cursor)
1576 {
1577     struct riva_par *par = info->par;
1578     u8 data[MAX_CURS * MAX_CURS/8];
1579     int i, set = cursor->set;
1580     u16 fg, bg;
1581 
1582     if (cursor->image.width > MAX_CURS || cursor->image.height > MAX_CURS)
1583         return -ENXIO;
1584 
1585     par->riva.ShowHideCursor(&par->riva, 0);
1586 
1587     if (par->cursor_reset) {
1588         set = FB_CUR_SETALL;
1589         par->cursor_reset = 0;
1590     }
1591 
1592     if (set & FB_CUR_SETSIZE)
1593         memset_io(par->riva.CURSOR, 0, MAX_CURS * MAX_CURS * 2);
1594 
1595     if (set & FB_CUR_SETPOS) {
1596         u32 xx, yy, temp;
1597 
1598         yy = cursor->image.dy - info->var.yoffset;
1599         xx = cursor->image.dx - info->var.xoffset;
1600         temp = xx & 0xFFFF;
1601         temp |= yy << 16;
1602 
1603         NV_WR32(par->riva.PRAMDAC, 0x0000300, temp);
1604     }
1605 
1606 
1607     if (set & (FB_CUR_SETSHAPE | FB_CUR_SETCMAP | FB_CUR_SETIMAGE)) {
1608         u32 bg_idx = cursor->image.bg_color;
1609         u32 fg_idx = cursor->image.fg_color;
1610         u32 s_pitch = (cursor->image.width+7) >> 3;
1611         u32 d_pitch = MAX_CURS/8;
1612         u8 *dat = (u8 *) cursor->image.data;
1613         u8 *msk = (u8 *) cursor->mask;
1614         u8 *src;
1615         
1616         src = kmalloc_array(s_pitch, cursor->image.height, GFP_ATOMIC);
1617 
1618         if (src) {
1619             switch (cursor->rop) {
1620             case ROP_XOR:
1621                 for (i = 0; i < s_pitch * cursor->image.height; i++)
1622                     src[i] = dat[i] ^ msk[i];
1623                 break;
1624             case ROP_COPY:
1625             default:
1626                 for (i = 0; i < s_pitch * cursor->image.height; i++)
1627                     src[i] = dat[i] & msk[i];
1628                 break;
1629             }
1630 
1631             fb_pad_aligned_buffer(data, d_pitch, src, s_pitch,
1632                         cursor->image.height);
1633 
1634             bg = ((info->cmap.red[bg_idx] & 0xf8) << 7) |
1635                 ((info->cmap.green[bg_idx] & 0xf8) << 2) |
1636                 ((info->cmap.blue[bg_idx] & 0xf8) >> 3) |
1637                 1 << 15;
1638 
1639             fg = ((info->cmap.red[fg_idx] & 0xf8) << 7) |
1640                 ((info->cmap.green[fg_idx] & 0xf8) << 2) |
1641                 ((info->cmap.blue[fg_idx] & 0xf8) >> 3) |
1642                 1 << 15;
1643 
1644             par->riva.LockUnlock(&par->riva, 0);
1645 
1646             rivafb_load_cursor_image(par, data, bg, fg,
1647                          cursor->image.width,
1648                          cursor->image.height);
1649             kfree(src);
1650         }
1651     }
1652 
1653     if (cursor->enable)
1654         par->riva.ShowHideCursor(&par->riva, 1);
1655 
1656     return 0;
1657 }
1658 
1659 static int rivafb_sync(struct fb_info *info)
1660 {
1661     struct riva_par *par = info->par;
1662 
1663     wait_for_idle(par);
1664     return 0;
1665 }
1666 
1667 /* ------------------------------------------------------------------------- *
1668  *
1669  * initialization helper functions
1670  *
1671  * ------------------------------------------------------------------------- */
1672 
1673 /* kernel interface */
1674 static const struct fb_ops riva_fb_ops = {
1675     .owner      = THIS_MODULE,
1676     .fb_open    = rivafb_open,
1677     .fb_release = rivafb_release,
1678     .fb_check_var   = rivafb_check_var,
1679     .fb_set_par     = rivafb_set_par,
1680     .fb_setcolreg   = rivafb_setcolreg,
1681     .fb_pan_display = rivafb_pan_display,
1682     .fb_blank   = rivafb_blank,
1683     .fb_fillrect    = rivafb_fillrect,
1684     .fb_copyarea    = rivafb_copyarea,
1685     .fb_imageblit   = rivafb_imageblit,
1686     .fb_cursor  = rivafb_cursor,    
1687     .fb_sync    = rivafb_sync,
1688 };
1689 
1690 static int riva_set_fbinfo(struct fb_info *info)
1691 {
1692     unsigned int cmap_len;
1693     struct riva_par *par = info->par;
1694 
1695     NVTRACE_ENTER();
1696     info->flags = FBINFO_DEFAULT
1697             | FBINFO_HWACCEL_XPAN
1698             | FBINFO_HWACCEL_YPAN
1699             | FBINFO_HWACCEL_COPYAREA
1700             | FBINFO_HWACCEL_FILLRECT
1701                 | FBINFO_HWACCEL_IMAGEBLIT;
1702 
1703     /* Accel seems to not work properly on NV30 yet...*/
1704     if ((par->riva.Architecture == NV_ARCH_30) || noaccel) {
1705             printk(KERN_DEBUG PFX "disabling acceleration\n");
1706         info->flags |= FBINFO_HWACCEL_DISABLED;
1707     }
1708 
1709     info->var = rivafb_default_var;
1710     info->fix.visual = (info->var.bits_per_pixel == 8) ?
1711                 FB_VISUAL_PSEUDOCOLOR : FB_VISUAL_DIRECTCOLOR;
1712 
1713     info->pseudo_palette = par->pseudo_palette;
1714 
1715     cmap_len = riva_get_cmap_len(&info->var);
1716     fb_alloc_cmap(&info->cmap, cmap_len, 0);    
1717 
1718     info->pixmap.size = 8 * 1024;
1719     info->pixmap.buf_align = 4;
1720     info->pixmap.access_align = 32;
1721     info->pixmap.flags = FB_PIXMAP_SYSTEM;
1722     info->var.yres_virtual = -1;
1723     NVTRACE_LEAVE();
1724     return (rivafb_check_var(&info->var, info));
1725 }
1726 
1727 static int riva_get_EDID_OF(struct fb_info *info, struct pci_dev *pd)
1728 {
1729     struct riva_par *par = info->par;
1730     struct device_node *dp;
1731     const unsigned char *pedid = NULL;
1732     const unsigned char *disptype = NULL;
1733     static char *propnames[] = {
1734         "DFP,EDID", "LCD,EDID", "EDID", "EDID1", "EDID,B", "EDID,A", NULL };
1735     int i;
1736 
1737     NVTRACE_ENTER();
1738     dp = pci_device_to_OF_node(pd);
1739     for (; dp != NULL; dp = dp->child) {
1740         disptype = of_get_property(dp, "display-type", NULL);
1741         if (disptype == NULL)
1742             continue;
1743         if (strncmp(disptype, "LCD", 3) != 0)
1744             continue;
1745         for (i = 0; propnames[i] != NULL; ++i) {
1746             pedid = of_get_property(dp, propnames[i], NULL);
1747             if (pedid != NULL) {
1748                 par->EDID = (unsigned char *)pedid;
1749                 NVTRACE("LCD found.\n");
1750                 return 1;
1751             }
1752         }
1753     }
1754     NVTRACE_LEAVE();
1755     return 0;
1756 }
1757 
1758 #if defined(CONFIG_FB_RIVA_I2C)
1759 static int riva_get_EDID_i2c(struct fb_info *info)
1760 {
1761     struct riva_par *par = info->par;
1762     struct fb_var_screeninfo var;
1763     int i;
1764 
1765     NVTRACE_ENTER();
1766     par->riva.LockUnlock(&par->riva, 0);
1767     riva_create_i2c_busses(par);
1768     for (i = 0; i < 3; i++) {
1769         if (!par->chan[i].par)
1770             continue;
1771         riva_probe_i2c_connector(par, i, &par->EDID);
1772         if (par->EDID && !fb_parse_edid(par->EDID, &var)) {
1773             printk(PFX "Found EDID Block from BUS %i\n", i);
1774             break;
1775         }
1776     }
1777 
1778     NVTRACE_LEAVE();
1779     return (par->EDID) ? 1 : 0;
1780 }
1781 #endif /* CONFIG_FB_RIVA_I2C */
1782 
1783 static void riva_update_default_var(struct fb_var_screeninfo *var,
1784                     struct fb_info *info)
1785 {
1786     struct fb_monspecs *specs = &info->monspecs;
1787     struct fb_videomode modedb;
1788 
1789     NVTRACE_ENTER();
1790     /* respect mode options */
1791     if (mode_option) {
1792         fb_find_mode(var, info, mode_option,
1793                  specs->modedb, specs->modedb_len,
1794                  NULL, 8);
1795     } else if (specs->modedb != NULL) {
1796         /* get first mode in database as fallback */
1797         modedb = specs->modedb[0];
1798         /* get preferred timing */
1799         if (info->monspecs.misc & FB_MISC_1ST_DETAIL) {
1800             int i;
1801 
1802             for (i = 0; i < specs->modedb_len; i++) {
1803                 if (specs->modedb[i].flag & FB_MODE_IS_FIRST) {
1804                     modedb = specs->modedb[i];
1805                     break;
1806                 }
1807             }
1808         }
1809         var->bits_per_pixel = 8;
1810         riva_update_var(var, &modedb);
1811     }
1812     NVTRACE_LEAVE();
1813 }
1814 
1815 
1816 static void riva_get_EDID(struct fb_info *info, struct pci_dev *pdev)
1817 {
1818     NVTRACE_ENTER();
1819     if (riva_get_EDID_OF(info, pdev)) {
1820         NVTRACE_LEAVE();
1821         return;
1822     }
1823     if (IS_ENABLED(CONFIG_OF))
1824         printk(PFX "could not retrieve EDID from OF\n");
1825 #if defined(CONFIG_FB_RIVA_I2C)
1826     if (!riva_get_EDID_i2c(info))
1827         printk(PFX "could not retrieve EDID from DDC/I2C\n");
1828 #endif
1829     NVTRACE_LEAVE();
1830 }
1831 
1832 
1833 static void riva_get_edidinfo(struct fb_info *info)
1834 {
1835     struct fb_var_screeninfo *var = &rivafb_default_var;
1836     struct riva_par *par = info->par;
1837 
1838     fb_edid_to_monspecs(par->EDID, &info->monspecs);
1839     fb_videomode_to_modelist(info->monspecs.modedb, info->monspecs.modedb_len,
1840                  &info->modelist);
1841     riva_update_default_var(var, info);
1842 
1843     /* if user specified flatpanel, we respect that */
1844     if (info->monspecs.input & FB_DISP_DDI)
1845         par->FlatPanel = 1;
1846 }
1847 
1848 /* ------------------------------------------------------------------------- *
1849  *
1850  * PCI bus
1851  *
1852  * ------------------------------------------------------------------------- */
1853 
1854 static u32 riva_get_arch(struct pci_dev *pd)
1855 {
1856         u32 arch = 0;
1857 
1858     switch (pd->device & 0x0ff0) {
1859         case 0x0100:   /* GeForce 256 */
1860         case 0x0110:   /* GeForce2 MX */
1861         case 0x0150:   /* GeForce2 */
1862         case 0x0170:   /* GeForce4 MX */
1863         case 0x0180:   /* GeForce4 MX (8x AGP) */
1864         case 0x01A0:   /* nForce */
1865         case 0x01F0:   /* nForce2 */
1866              arch =  NV_ARCH_10;
1867              break;
1868         case 0x0200:   /* GeForce3 */
1869         case 0x0250:   /* GeForce4 Ti */
1870         case 0x0280:   /* GeForce4 Ti (8x AGP) */
1871              arch =  NV_ARCH_20;
1872              break;
1873         case 0x0300:   /* GeForceFX 5800 */
1874         case 0x0310:   /* GeForceFX 5600 */
1875         case 0x0320:   /* GeForceFX 5200 */
1876         case 0x0330:   /* GeForceFX 5900 */
1877         case 0x0340:   /* GeForceFX 5700 */
1878              arch =  NV_ARCH_30;
1879              break;
1880         case 0x0020:   /* TNT, TNT2 */
1881              arch =  NV_ARCH_04;
1882              break;
1883         case 0x0010:   /* Riva128 */
1884              arch =  NV_ARCH_03;
1885              break;
1886         default:   /* unknown architecture */
1887              break;
1888     }
1889     return arch;
1890 }
1891 
1892 static int rivafb_probe(struct pci_dev *pd, const struct pci_device_id *ent)
1893 {
1894     struct riva_par *default_par;
1895     struct fb_info *info;
1896     int ret;
1897 
1898     NVTRACE_ENTER();
1899     assert(pd != NULL);
1900 
1901     info = framebuffer_alloc(sizeof(struct riva_par), &pd->dev);
1902     if (!info) {
1903         ret = -ENOMEM;
1904         goto err_ret;
1905     }
1906     default_par = info->par;
1907     default_par->pdev = pd;
1908 
1909     info->pixmap.addr = kzalloc(8 * 1024, GFP_KERNEL);
1910     if (info->pixmap.addr == NULL) {
1911             ret = -ENOMEM;
1912         goto err_framebuffer_release;
1913     }
1914 
1915     ret = pci_enable_device(pd);
1916     if (ret < 0) {
1917         printk(KERN_ERR PFX "cannot enable PCI device\n");
1918         goto err_free_pixmap;
1919     }
1920 
1921     ret = pci_request_regions(pd, "rivafb");
1922     if (ret < 0) {
1923         printk(KERN_ERR PFX "cannot request PCI regions\n");
1924         goto err_disable_device;
1925     }
1926 
1927     mutex_init(&default_par->open_lock);
1928     default_par->riva.Architecture = riva_get_arch(pd);
1929 
1930     default_par->Chipset = (pd->vendor << 16) | pd->device;
1931     printk(KERN_INFO PFX "nVidia device/chipset %X\n",default_par->Chipset);
1932     
1933     if(default_par->riva.Architecture == 0) {
1934         printk(KERN_ERR PFX "unknown NV_ARCH\n");
1935         ret=-ENODEV;
1936         goto err_release_region;
1937     }
1938     if(default_par->riva.Architecture == NV_ARCH_10 ||
1939        default_par->riva.Architecture == NV_ARCH_20 ||
1940        default_par->riva.Architecture == NV_ARCH_30) {
1941         sprintf(rivafb_fix.id, "NV%x", (pd->device & 0x0ff0) >> 4);
1942     } else {
1943         sprintf(rivafb_fix.id, "NV%x", default_par->riva.Architecture);
1944     }
1945 
1946     default_par->FlatPanel = flatpanel;
1947     if (flatpanel == 1)
1948         printk(KERN_INFO PFX "flatpanel support enabled\n");
1949     default_par->forceCRTC = forceCRTC;
1950     
1951     rivafb_fix.mmio_len = pci_resource_len(pd, 0);
1952     rivafb_fix.smem_len = pci_resource_len(pd, 1);
1953 
1954     {
1955         /* enable IO and mem if not already done */
1956         unsigned short cmd;
1957 
1958         pci_read_config_word(pd, PCI_COMMAND, &cmd);
1959         cmd |= (PCI_COMMAND_IO | PCI_COMMAND_MEMORY);
1960         pci_write_config_word(pd, PCI_COMMAND, cmd);
1961     }
1962     
1963     rivafb_fix.mmio_start = pci_resource_start(pd, 0);
1964     rivafb_fix.smem_start = pci_resource_start(pd, 1);
1965 
1966     default_par->ctrl_base = ioremap(rivafb_fix.mmio_start,
1967                      rivafb_fix.mmio_len);
1968     if (!default_par->ctrl_base) {
1969         printk(KERN_ERR PFX "cannot ioremap MMIO base\n");
1970         ret = -EIO;
1971         goto err_release_region;
1972     }
1973 
1974     switch (default_par->riva.Architecture) {
1975     case NV_ARCH_03:
1976         /* Riva128's PRAMIN is in the "framebuffer" space
1977          * Since these cards were never made with more than 8 megabytes
1978          * we can safely allocate this separately.
1979          */
1980         default_par->riva.PRAMIN = ioremap(rivafb_fix.smem_start + 0x00C00000, 0x00008000);
1981         if (!default_par->riva.PRAMIN) {
1982             printk(KERN_ERR PFX "cannot ioremap PRAMIN region\n");
1983             ret = -EIO;
1984             goto err_iounmap_ctrl_base;
1985         }
1986         break;
1987     case NV_ARCH_04:
1988     case NV_ARCH_10:
1989     case NV_ARCH_20:
1990     case NV_ARCH_30:
1991         default_par->riva.PCRTC0 =
1992             (u32 __iomem *)(default_par->ctrl_base + 0x00600000);
1993         default_par->riva.PRAMIN =
1994             (u32 __iomem *)(default_par->ctrl_base + 0x00710000);
1995         break;
1996     }
1997     riva_common_setup(default_par);
1998 
1999     if (default_par->riva.Architecture == NV_ARCH_03) {
2000         default_par->riva.PCRTC = default_par->riva.PCRTC0
2001                                 = default_par->riva.PGRAPH;
2002     }
2003 
2004     rivafb_fix.smem_len = riva_get_memlen(default_par) * 1024;
2005     default_par->dclk_max = riva_get_maxdclk(default_par) * 1000;
2006     info->screen_base = ioremap_wc(rivafb_fix.smem_start,
2007                        rivafb_fix.smem_len);
2008     if (!info->screen_base) {
2009         printk(KERN_ERR PFX "cannot ioremap FB base\n");
2010         ret = -EIO;
2011         goto err_iounmap_pramin;
2012     }
2013 
2014     if (!nomtrr)
2015         default_par->wc_cookie =
2016             arch_phys_wc_add(rivafb_fix.smem_start,
2017                      rivafb_fix.smem_len);
2018 
2019     info->fbops = &riva_fb_ops;
2020     info->fix = rivafb_fix;
2021     riva_get_EDID(info, pd);
2022     riva_get_edidinfo(info);
2023 
2024     ret=riva_set_fbinfo(info);
2025     if (ret < 0) {
2026         printk(KERN_ERR PFX "error setting initial video mode\n");
2027         goto err_iounmap_screen_base;
2028     }
2029 
2030     fb_destroy_modedb(info->monspecs.modedb);
2031     info->monspecs.modedb = NULL;
2032 
2033     pci_set_drvdata(pd, info);
2034 
2035     if (backlight)
2036         riva_bl_init(info->par);
2037 
2038     ret = register_framebuffer(info);
2039     if (ret < 0) {
2040         printk(KERN_ERR PFX
2041             "error registering riva framebuffer\n");
2042         goto err_iounmap_screen_base;
2043     }
2044 
2045     printk(KERN_INFO PFX
2046         "PCI nVidia %s framebuffer ver %s (%dMB @ 0x%lX)\n",
2047         info->fix.id,
2048         RIVAFB_VERSION,
2049         info->fix.smem_len / (1024 * 1024),
2050         info->fix.smem_start);
2051 
2052     NVTRACE_LEAVE();
2053     return 0;
2054 
2055 err_iounmap_screen_base:
2056 #ifdef CONFIG_FB_RIVA_I2C
2057     riva_delete_i2c_busses(info->par);
2058 #endif
2059     iounmap(info->screen_base);
2060 err_iounmap_pramin:
2061     if (default_par->riva.Architecture == NV_ARCH_03) 
2062         iounmap(default_par->riva.PRAMIN);
2063 err_iounmap_ctrl_base:
2064     iounmap(default_par->ctrl_base);
2065 err_release_region:
2066     pci_release_regions(pd);
2067 err_disable_device:
2068 err_free_pixmap:
2069     kfree(info->pixmap.addr);
2070 err_framebuffer_release:
2071     framebuffer_release(info);
2072 err_ret:
2073     return ret;
2074 }
2075 
2076 static void rivafb_remove(struct pci_dev *pd)
2077 {
2078     struct fb_info *info = pci_get_drvdata(pd);
2079     struct riva_par *par = info->par;
2080     
2081     NVTRACE_ENTER();
2082 
2083 #ifdef CONFIG_FB_RIVA_I2C
2084     riva_delete_i2c_busses(par);
2085     kfree(par->EDID);
2086 #endif
2087 
2088     unregister_framebuffer(info);
2089 
2090     riva_bl_exit(info);
2091     arch_phys_wc_del(par->wc_cookie);
2092     iounmap(par->ctrl_base);
2093     iounmap(info->screen_base);
2094     if (par->riva.Architecture == NV_ARCH_03)
2095         iounmap(par->riva.PRAMIN);
2096     pci_release_regions(pd);
2097     kfree(info->pixmap.addr);
2098     framebuffer_release(info);
2099     NVTRACE_LEAVE();
2100 }
2101 
2102 /* ------------------------------------------------------------------------- *
2103  *
2104  * initialization
2105  *
2106  * ------------------------------------------------------------------------- */
2107 
2108 #ifndef MODULE
2109 static int rivafb_setup(char *options)
2110 {
2111     char *this_opt;
2112 
2113     NVTRACE_ENTER();
2114     if (!options || !*options)
2115         return 0;
2116 
2117     while ((this_opt = strsep(&options, ",")) != NULL) {
2118         if (!strncmp(this_opt, "forceCRTC", 9)) {
2119             char *p;
2120             
2121             p = this_opt + 9;
2122             if (!*p || !*(++p)) continue; 
2123             forceCRTC = *p - '0';
2124             if (forceCRTC < 0 || forceCRTC > 1) 
2125                 forceCRTC = -1;
2126         } else if (!strncmp(this_opt, "flatpanel", 9)) {
2127             flatpanel = 1;
2128         } else if (!strncmp(this_opt, "backlight:", 10)) {
2129             backlight = simple_strtoul(this_opt+10, NULL, 0);
2130         } else if (!strncmp(this_opt, "nomtrr", 6)) {
2131             nomtrr = 1;
2132         } else if (!strncmp(this_opt, "strictmode", 10)) {
2133             strictmode = 1;
2134         } else if (!strncmp(this_opt, "noaccel", 7)) {
2135             noaccel = 1;
2136         } else
2137             mode_option = this_opt;
2138     }
2139     NVTRACE_LEAVE();
2140     return 0;
2141 }
2142 #endif /* !MODULE */
2143 
2144 static struct pci_driver rivafb_driver = {
2145     .name       = "rivafb",
2146     .id_table   = rivafb_pci_tbl,
2147     .probe      = rivafb_probe,
2148     .remove     = rivafb_remove,
2149 };
2150 
2151 
2152 
2153 /* ------------------------------------------------------------------------- *
2154  *
2155  * modularization
2156  *
2157  * ------------------------------------------------------------------------- */
2158 
2159 static int rivafb_init(void)
2160 {
2161 #ifndef MODULE
2162     char *option = NULL;
2163 
2164     if (fb_get_options("rivafb", &option))
2165         return -ENODEV;
2166     rivafb_setup(option);
2167 #endif
2168     return pci_register_driver(&rivafb_driver);
2169 }
2170 
2171 
2172 module_init(rivafb_init);
2173 
2174 static void __exit rivafb_exit(void)
2175 {
2176     pci_unregister_driver(&rivafb_driver);
2177 }
2178 
2179 module_exit(rivafb_exit);
2180 
2181 module_param(noaccel, bool, 0);
2182 MODULE_PARM_DESC(noaccel, "bool: disable acceleration");
2183 module_param(flatpanel, int, 0);
2184 MODULE_PARM_DESC(flatpanel, "Enables experimental flat panel support for some chipsets. (0 or 1=enabled) (default=0)");
2185 module_param(forceCRTC, int, 0);
2186 MODULE_PARM_DESC(forceCRTC, "Forces usage of a particular CRTC in case autodetection fails. (0 or 1) (default=autodetect)");
2187 module_param(nomtrr, bool, 0);
2188 MODULE_PARM_DESC(nomtrr, "Disables MTRR support (0 or 1=disabled) (default=0)");
2189 module_param(strictmode, bool, 0);
2190 MODULE_PARM_DESC(strictmode, "Only use video modes from EDID");
2191 
2192 MODULE_AUTHOR("Ani Joshi, maintainer");
2193 MODULE_DESCRIPTION("Framebuffer driver for nVidia Riva 128, TNT, TNT2, and the GeForce series");
2194 MODULE_LICENSE("GPL");