diff options
Diffstat (limited to 'drivers/video/via/viafbdev.c')
-rw-r--r-- | drivers/video/via/viafbdev.c | 76 |
1 files changed, 39 insertions, 37 deletions
diff --git a/drivers/video/via/viafbdev.c b/drivers/video/via/viafbdev.c index f555b891cc72..a542bed086e2 100644 --- a/drivers/video/via/viafbdev.c +++ b/drivers/video/via/viafbdev.c | |||
@@ -182,13 +182,24 @@ static int viafb_release(struct fb_info *info, int user) | |||
182 | return 0; | 182 | return 0; |
183 | } | 183 | } |
184 | 184 | ||
185 | static inline int get_var_refresh(struct fb_var_screeninfo *var) | ||
186 | { | ||
187 | u32 htotal, vtotal; | ||
188 | |||
189 | htotal = var->left_margin + var->xres + var->right_margin | ||
190 | + var->hsync_len; | ||
191 | vtotal = var->upper_margin + var->yres + var->lower_margin | ||
192 | + var->vsync_len; | ||
193 | return PICOS2KHZ(var->pixclock) * 1000 / (htotal * vtotal); | ||
194 | } | ||
195 | |||
185 | static int viafb_check_var(struct fb_var_screeninfo *var, | 196 | static int viafb_check_var(struct fb_var_screeninfo *var, |
186 | struct fb_info *info) | 197 | struct fb_info *info) |
187 | { | 198 | { |
188 | int htotal, vtotal, depth; | 199 | int depth, refresh; |
189 | struct VideoModeTable *vmode_entry; | 200 | struct VideoModeTable *vmode_entry; |
190 | struct viafb_par *ppar = info->par; | 201 | struct viafb_par *ppar = info->par; |
191 | u32 long_refresh, line; | 202 | u32 line; |
192 | 203 | ||
193 | DEBUG_MSG(KERN_INFO "viafb_check_var!\n"); | 204 | DEBUG_MSG(KERN_INFO "viafb_check_var!\n"); |
194 | /* Sanity check */ | 205 | /* Sanity check */ |
@@ -231,17 +242,11 @@ static int viafb_check_var(struct fb_var_screeninfo *var, | |||
231 | /* Based on var passed in to calculate the refresh, | 242 | /* Based on var passed in to calculate the refresh, |
232 | * because our driver use some modes special. | 243 | * because our driver use some modes special. |
233 | */ | 244 | */ |
234 | htotal = var->xres + var->left_margin + | 245 | refresh = viafb_get_refresh(var->xres, var->yres, |
235 | var->right_margin + var->hsync_len; | 246 | get_var_refresh(var)); |
236 | vtotal = var->yres + var->upper_margin + | ||
237 | var->lower_margin + var->vsync_len; | ||
238 | long_refresh = 1000000000UL / var->pixclock * 1000; | ||
239 | long_refresh /= (htotal * vtotal); | ||
240 | |||
241 | viafb_refresh = viafb_get_refresh(var->xres, var->yres, long_refresh); | ||
242 | 247 | ||
243 | /* Adjust var according to our driver's own table */ | 248 | /* Adjust var according to our driver's own table */ |
244 | viafb_fill_var_timing_info(var, viafb_refresh, vmode_entry); | 249 | viafb_fill_var_timing_info(var, refresh, vmode_entry); |
245 | if (var->accel_flags & FB_ACCELF_TEXT && | 250 | if (var->accel_flags & FB_ACCELF_TEXT && |
246 | !ppar->shared->vdev->engine_mmio) | 251 | !ppar->shared->vdev->engine_mmio) |
247 | var->accel_flags = 0; | 252 | var->accel_flags = 0; |
@@ -253,12 +258,13 @@ static int viafb_set_par(struct fb_info *info) | |||
253 | { | 258 | { |
254 | struct viafb_par *viapar = info->par; | 259 | struct viafb_par *viapar = info->par; |
255 | struct VideoModeTable *vmode_entry, *vmode_entry1 = NULL; | 260 | struct VideoModeTable *vmode_entry, *vmode_entry1 = NULL; |
261 | int refresh; | ||
256 | DEBUG_MSG(KERN_INFO "viafb_set_par!\n"); | 262 | DEBUG_MSG(KERN_INFO "viafb_set_par!\n"); |
257 | 263 | ||
258 | viafb_update_fix(info); | 264 | viafb_update_fix(info); |
259 | viapar->depth = fb_get_color_depth(&info->var, &info->fix); | 265 | viapar->depth = fb_get_color_depth(&info->var, &info->fix); |
260 | viafb_update_device_setting(viafbinfo->var.xres, viafbinfo->var.yres, | 266 | viafb_update_device_setting(viafbinfo->var.xres, viafbinfo->var.yres, |
261 | viafbinfo->var.bits_per_pixel, viafb_refresh, 0); | 267 | viafbinfo->var.bits_per_pixel, 0); |
262 | 268 | ||
263 | vmode_entry = viafb_get_mode(viafbinfo->var.xres, viafbinfo->var.yres); | 269 | vmode_entry = viafb_get_mode(viafbinfo->var.xres, viafbinfo->var.yres); |
264 | if (viafb_dual_fb) { | 270 | if (viafb_dual_fb) { |
@@ -266,7 +272,7 @@ static int viafb_set_par(struct fb_info *info) | |||
266 | viafbinfo1->var.yres); | 272 | viafbinfo1->var.yres); |
267 | viafb_update_device_setting(viafbinfo1->var.xres, | 273 | viafb_update_device_setting(viafbinfo1->var.xres, |
268 | viafbinfo1->var.yres, viafbinfo1->var.bits_per_pixel, | 274 | viafbinfo1->var.yres, viafbinfo1->var.bits_per_pixel, |
269 | viafb_refresh1, 1); | 275 | 1); |
270 | } else if (viafb_SAMM_ON == 1) { | 276 | } else if (viafb_SAMM_ON == 1) { |
271 | DEBUG_MSG(KERN_INFO | 277 | DEBUG_MSG(KERN_INFO |
272 | "viafb_second_xres = %d, viafb_second_yres = %d, bpp = %d\n", | 278 | "viafb_second_xres = %d, viafb_second_yres = %d, bpp = %d\n", |
@@ -275,14 +281,19 @@ static int viafb_set_par(struct fb_info *info) | |||
275 | viafb_second_yres); | 281 | viafb_second_yres); |
276 | 282 | ||
277 | viafb_update_device_setting(viafb_second_xres, | 283 | viafb_update_device_setting(viafb_second_xres, |
278 | viafb_second_yres, viafb_bpp1, viafb_refresh1, 1); | 284 | viafb_second_yres, viafb_bpp1, 1); |
279 | } | 285 | } |
280 | 286 | ||
287 | refresh = viafb_get_refresh(info->var.xres, info->var.yres, | ||
288 | get_var_refresh(&info->var)); | ||
281 | if (vmode_entry) { | 289 | if (vmode_entry) { |
282 | if (viafb_dual_fb && viapar->iga_path == IGA2) | 290 | if (viafb_dual_fb && viapar->iga_path == IGA2) { |
283 | viafb_bpp1 = info->var.bits_per_pixel; | 291 | viafb_bpp1 = info->var.bits_per_pixel; |
284 | else | 292 | viafb_refresh1 = refresh; |
293 | } else { | ||
285 | viafb_bpp = info->var.bits_per_pixel; | 294 | viafb_bpp = info->var.bits_per_pixel; |
295 | viafb_refresh = refresh; | ||
296 | } | ||
286 | 297 | ||
287 | if (info->var.accel_flags & FB_ACCELF_TEXT) | 298 | if (info->var.accel_flags & FB_ACCELF_TEXT) |
288 | info->flags &= ~FBINFO_HWACCEL_DISABLED; | 299 | info->flags &= ~FBINFO_HWACCEL_DISABLED; |
@@ -1795,14 +1806,9 @@ int __devinit via_fb_pci_probe(struct viafb_dev *vdev) | |||
1795 | default_var.xres_virtual = default_xres; | 1806 | default_var.xres_virtual = default_xres; |
1796 | default_var.yres_virtual = default_yres; | 1807 | default_var.yres_virtual = default_yres; |
1797 | default_var.bits_per_pixel = viafb_bpp; | 1808 | default_var.bits_per_pixel = viafb_bpp; |
1798 | default_var.pixclock = | 1809 | viafb_fill_var_timing_info(&default_var, viafb_get_refresh( |
1799 | viafb_get_pixclock(default_xres, default_yres, viafb_refresh); | 1810 | default_var.xres, default_var.yres, viafb_refresh), |
1800 | default_var.left_margin = (default_xres >> 3) & 0xf8; | 1811 | viafb_get_mode(default_var.xres, default_var.yres)); |
1801 | default_var.right_margin = 32; | ||
1802 | default_var.upper_margin = 16; | ||
1803 | default_var.lower_margin = 4; | ||
1804 | default_var.hsync_len = default_var.left_margin; | ||
1805 | default_var.vsync_len = 4; | ||
1806 | viafb_setup_fixinfo(&viafbinfo->fix, viaparinfo); | 1812 | viafb_setup_fixinfo(&viafbinfo->fix, viaparinfo); |
1807 | viafbinfo->var = default_var; | 1813 | viafbinfo->var = default_var; |
1808 | 1814 | ||
@@ -1841,15 +1847,9 @@ int __devinit via_fb_pci_probe(struct viafb_dev *vdev) | |||
1841 | default_var.xres_virtual = viafb_second_virtual_xres; | 1847 | default_var.xres_virtual = viafb_second_virtual_xres; |
1842 | default_var.yres_virtual = viafb_second_virtual_yres; | 1848 | default_var.yres_virtual = viafb_second_virtual_yres; |
1843 | default_var.bits_per_pixel = viafb_bpp1; | 1849 | default_var.bits_per_pixel = viafb_bpp1; |
1844 | default_var.pixclock = | 1850 | viafb_fill_var_timing_info(&default_var, viafb_get_refresh( |
1845 | viafb_get_pixclock(viafb_second_xres, viafb_second_yres, | 1851 | default_var.xres, default_var.yres, viafb_refresh1), |
1846 | viafb_refresh); | 1852 | viafb_get_mode(default_var.xres, default_var.yres)); |
1847 | default_var.left_margin = (viafb_second_xres >> 3) & 0xf8; | ||
1848 | default_var.right_margin = 32; | ||
1849 | default_var.upper_margin = 16; | ||
1850 | default_var.lower_margin = 4; | ||
1851 | default_var.hsync_len = default_var.left_margin; | ||
1852 | default_var.vsync_len = 4; | ||
1853 | 1853 | ||
1854 | viafb_setup_fixinfo(&viafbinfo1->fix, viaparinfo1); | 1854 | viafb_setup_fixinfo(&viafbinfo1->fix, viaparinfo1); |
1855 | viafb_check_var(&default_var, viafbinfo1); | 1855 | viafb_check_var(&default_var, viafbinfo1); |
@@ -2004,22 +2004,24 @@ static int __init viafb_setup(char *options) | |||
2004 | */ | 2004 | */ |
2005 | int __init viafb_init(void) | 2005 | int __init viafb_init(void) |
2006 | { | 2006 | { |
2007 | u32 dummy; | 2007 | u32 dummy_x, dummy_y; |
2008 | #ifndef MODULE | 2008 | #ifndef MODULE |
2009 | char *option = NULL; | 2009 | char *option = NULL; |
2010 | if (fb_get_options("viafb", &option)) | 2010 | if (fb_get_options("viafb", &option)) |
2011 | return -ENODEV; | 2011 | return -ENODEV; |
2012 | viafb_setup(option); | 2012 | viafb_setup(option); |
2013 | #endif | 2013 | #endif |
2014 | if (parse_mode(viafb_mode, &dummy, &dummy) | 2014 | if (parse_mode(viafb_mode, &dummy_x, &dummy_y) |
2015 | || parse_mode(viafb_mode1, &dummy, &dummy) | 2015 | || !viafb_get_mode(dummy_x, dummy_y) |
2016 | || parse_mode(viafb_mode1, &dummy_x, &dummy_y) | ||
2017 | || !viafb_get_mode(dummy_x, dummy_y) | ||
2016 | || viafb_bpp < 0 || viafb_bpp > 32 | 2018 | || viafb_bpp < 0 || viafb_bpp > 32 |
2017 | || viafb_bpp1 < 0 || viafb_bpp1 > 32 | 2019 | || viafb_bpp1 < 0 || viafb_bpp1 > 32 |
2018 | || parse_active_dev()) | 2020 | || parse_active_dev()) |
2019 | return -EINVAL; | 2021 | return -EINVAL; |
2020 | 2022 | ||
2021 | printk(KERN_INFO | 2023 | printk(KERN_INFO |
2022 | "VIA Graphics Intergration Chipset framebuffer %d.%d initializing\n", | 2024 | "VIA Graphics Integration Chipset framebuffer %d.%d initializing\n", |
2023 | VERSION_MAJOR, VERSION_MINOR); | 2025 | VERSION_MAJOR, VERSION_MINOR); |
2024 | return 0; | 2026 | return 0; |
2025 | } | 2027 | } |