aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorMichal Januszewski <spock@gentoo.org>2007-10-16 04:28:26 -0400
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2007-10-16 12:43:13 -0400
commit8bdb3a2d7df48b861972c4bfb58490853a228f51 (patch)
treefebc4fbe0fd90e4677fe7703350ce349ddbfc342 /drivers
parentcc54f46e39dff9891dd334ef158a238ff5a9ffd2 (diff)
uvesafb: the driver core
uvesafb is an enhanced version of vesafb. It uses a userspace helper (v86d) to execute calls to the x86 Video BIOS functions. The driver is not limited to any specific arch and whether it works on a given arch or not depends on that arch being supported by the userspace daemon. It has been tested on x86_32 and x86_64. A single BIOS call is represented by an instance of the uvesafb_ktask structure. This structure contains a buffer, a completion struct and a uvesafb_task substructure, containing the values of the x86 registers, a flags field and a field indicating the length of the buffer. Whenever a BIOS call is made in the driver, uvesafb_exec() builds a message using the uvesafb_task substructure and the contents of the buffer. This message is then assigned a random ack number and sent to the userspace daemon using the connector interface. The message's sequence number is used as an index for the uvfb_tasks array, which provides a mapping from the messages coming from userspace to the in-kernel uvesafb_ktask structs. The userspace daemon performs the requested operation and sends a reply in the form of a uvesafb_task struct and, optionally, a buffer. The seq and ack numbers in the reply should be exactly the same as those in the request. Each message from userspace is processed by uvesafb_cn_callback() and after passing a few sanity checks leads to the completion of a BIOS call request. Signed-off-by: Michal Januszewski <spock@gentoo.org> Signed-off-by: Antonino Daplas <adaplas@gmail.com> Cc: Paul Mundt <lethal@linux-sh.org> Cc: Paulo Marques <pmarques@grupopie.com> Cc: "H. Peter Anvin" <hpa@zytor.com> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/video/Kconfig18
-rw-r--r--drivers/video/Makefile1
-rw-r--r--drivers/video/uvesafb.c2066
3 files changed, 2085 insertions, 0 deletions
diff --git a/drivers/video/Kconfig b/drivers/video/Kconfig
index 5216c11d4dec..f1cc8996456f 100644
--- a/drivers/video/Kconfig
+++ b/drivers/video/Kconfig
@@ -592,6 +592,24 @@ config FB_TGA
592 592
593 Say Y if you have one of those. 593 Say Y if you have one of those.
594 594
595config FB_UVESA
596 tristate "Userspace VESA VGA graphics support"
597 depends on FB && CONNECTOR
598 select FB_CFB_FILLRECT
599 select FB_CFB_COPYAREA
600 select FB_CFB_IMAGEBLIT
601 select FB_MODE_HELPERS
602 help
603 This is the frame buffer driver for generic VBE 2.0 compliant
604 graphic cards. It can also take advantage of VBE 3.0 features,
605 such as refresh rate adjustment.
606
607 This driver generally provides more features than vesafb but
608 requires a userspace helper application called 'v86d'. See
609 <file:Documentation/fb/uvesafb.txt> for more information.
610
611 If unsure, say N.
612
595config FB_VESA 613config FB_VESA
596 bool "VESA VGA graphics support" 614 bool "VESA VGA graphics support"
597 depends on (FB = y) && X86 615 depends on (FB = y) && X86
diff --git a/drivers/video/Makefile b/drivers/video/Makefile
index 06eec7b182b7..67dc278e5573 100644
--- a/drivers/video/Makefile
+++ b/drivers/video/Makefile
@@ -115,6 +115,7 @@ obj-$(CONFIG_FB_XILINX) += xilinxfb.o
115obj-$(CONFIG_FB_OMAP) += omap/ 115obj-$(CONFIG_FB_OMAP) += omap/
116 116
117# Platform or fallback drivers go here 117# Platform or fallback drivers go here
118obj-$(CONFIG_FB_UVESA) += uvesafb.o
118obj-$(CONFIG_FB_VESA) += vesafb.o 119obj-$(CONFIG_FB_VESA) += vesafb.o
119obj-$(CONFIG_FB_IMAC) += imacfb.o 120obj-$(CONFIG_FB_IMAC) += imacfb.o
120obj-$(CONFIG_FB_VGA16) += vga16fb.o 121obj-$(CONFIG_FB_VGA16) += vga16fb.o
diff --git a/drivers/video/uvesafb.c b/drivers/video/uvesafb.c
new file mode 100644
index 000000000000..b983d262ab78
--- /dev/null
+++ b/drivers/video/uvesafb.c
@@ -0,0 +1,2066 @@
1/*
2 * A framebuffer driver for VBE 2.0+ compliant video cards
3 *
4 * (c) 2007 Michal Januszewski <spock@gentoo.org>
5 * Loosely based upon the vesafb driver.
6 *
7 */
8#include <linux/init.h>
9#include <linux/module.h>
10#include <linux/moduleparam.h>
11#include <linux/skbuff.h>
12#include <linux/timer.h>
13#include <linux/completion.h>
14#include <linux/connector.h>
15#include <linux/random.h>
16#include <linux/platform_device.h>
17#include <linux/limits.h>
18#include <linux/fb.h>
19#include <linux/io.h>
20#include <linux/mutex.h>
21#include <video/edid.h>
22#include <video/uvesafb.h>
23#ifdef CONFIG_X86
24#include <video/vga.h>
25#endif
26#ifdef CONFIG_MTRR
27#include <asm/mtrr.h>
28#endif
29#include "edid.h"
30
31static struct cb_id uvesafb_cn_id = {
32 .idx = CN_IDX_V86D,
33 .val = CN_VAL_V86D_UVESAFB
34};
35static char v86d_path[PATH_MAX] = "/sbin/v86d";
36static char v86d_started; /* has v86d been started by uvesafb? */
37
38static struct fb_fix_screeninfo uvesafb_fix __devinitdata = {
39 .id = "VESA VGA",
40 .type = FB_TYPE_PACKED_PIXELS,
41 .accel = FB_ACCEL_NONE,
42 .visual = FB_VISUAL_TRUECOLOR,
43};
44
45static int mtrr __devinitdata = 3; /* enable mtrr by default */
46static int blank __devinitdata = 1; /* enable blanking by default */
47static int ypan __devinitdata = 1; /* 0: scroll, 1: ypan, 2: ywrap */
48static int pmi_setpal __devinitdata = 1; /* use PMI for palette changes */
49static int nocrtc __devinitdata; /* ignore CRTC settings */
50static int noedid __devinitdata; /* don't try DDC transfers */
51static int vram_remap __devinitdata; /* set amt. of memory to be used */
52static int vram_total __devinitdata; /* set total amount of memory */
53static u16 maxclk __devinitdata; /* maximum pixel clock */
54static u16 maxvf __devinitdata; /* maximum vertical frequency */
55static u16 maxhf __devinitdata; /* maximum horizontal frequency */
56static u16 vbemode __devinitdata; /* force use of a specific VBE mode */
57static char *mode_option __devinitdata;
58
59static struct uvesafb_ktask *uvfb_tasks[UVESAFB_TASKS_MAX];
60static DEFINE_MUTEX(uvfb_lock);
61
62/*
63 * A handler for replies from userspace.
64 *
65 * Make sure each message passes consistency checks and if it does,
66 * find the kernel part of the task struct, copy the registers and
67 * the buffer contents and then complete the task.
68 */
69static void uvesafb_cn_callback(void *data)
70{
71 struct cn_msg *msg = data;
72 struct uvesafb_task *utask;
73 struct uvesafb_ktask *task;
74
75 if (msg->seq >= UVESAFB_TASKS_MAX)
76 return;
77
78 mutex_lock(&uvfb_lock);
79 task = uvfb_tasks[msg->seq];
80
81 if (!task || msg->ack != task->ack) {
82 mutex_unlock(&uvfb_lock);
83 return;
84 }
85
86 utask = (struct uvesafb_task *)msg->data;
87
88 /* Sanity checks for the buffer length. */
89 if (task->t.buf_len < utask->buf_len ||
90 utask->buf_len > msg->len - sizeof(*utask)) {
91 mutex_unlock(&uvfb_lock);
92 return;
93 }
94
95 uvfb_tasks[msg->seq] = NULL;
96 mutex_unlock(&uvfb_lock);
97
98 memcpy(&task->t, utask, sizeof(*utask));
99
100 if (task->t.buf_len && task->buf)
101 memcpy(task->buf, utask + 1, task->t.buf_len);
102
103 complete(task->done);
104 return;
105}
106
107static int uvesafb_helper_start(void)
108{
109 char *envp[] = {
110 "HOME=/",
111 "PATH=/sbin:/bin",
112 NULL,
113 };
114
115 char *argv[] = {
116 v86d_path,
117 NULL,
118 };
119
120 return call_usermodehelper(v86d_path, argv, envp, 1);
121}
122
123/*
124 * Execute a uvesafb task.
125 *
126 * Returns 0 if the task is executed successfully.
127 *
128 * A message sent to the userspace consists of the uvesafb_task
129 * struct and (optionally) a buffer. The uvesafb_task struct is
130 * a simplified version of uvesafb_ktask (its kernel counterpart)
131 * containing only the register values, flags and the length of
132 * the buffer.
133 *
134 * Each message is assigned a sequence number (increased linearly)
135 * and a random ack number. The sequence number is used as a key
136 * for the uvfb_tasks array which holds pointers to uvesafb_ktask
137 * structs for all requests.
138 */
139static int uvesafb_exec(struct uvesafb_ktask *task)
140{
141 static int seq;
142 struct cn_msg *m;
143 int err;
144 int len = sizeof(task->t) + task->t.buf_len;
145
146 /*
147 * Check whether the message isn't longer than the maximum
148 * allowed by connector.
149 */
150 if (sizeof(*m) + len > CONNECTOR_MAX_MSG_SIZE) {
151 printk(KERN_WARNING "uvesafb: message too long (%d), "
152 "can't execute task\n", (int)(sizeof(*m) + len));
153 return -E2BIG;
154 }
155
156 m = kzalloc(sizeof(*m) + len, GFP_KERNEL);
157 if (!m)
158 return -ENOMEM;
159
160 init_completion(task->done);
161
162 memcpy(&m->id, &uvesafb_cn_id, sizeof(m->id));
163 m->seq = seq;
164 m->len = len;
165 m->ack = random32();
166
167 /* uvesafb_task structure */
168 memcpy(m + 1, &task->t, sizeof(task->t));
169
170 /* Buffer */
171 memcpy((u8 *)(m + 1) + sizeof(task->t), task->buf, task->t.buf_len);
172
173 /*
174 * Save the message ack number so that we can find the kernel
175 * part of this task when a reply is received from userspace.
176 */
177 task->ack = m->ack;
178
179 mutex_lock(&uvfb_lock);
180
181 /* If all slots are taken -- bail out. */
182 if (uvfb_tasks[seq]) {
183 mutex_unlock(&uvfb_lock);
184 return -EBUSY;
185 }
186
187 /* Save a pointer to the kernel part of the task struct. */
188 uvfb_tasks[seq] = task;
189 mutex_unlock(&uvfb_lock);
190
191 err = cn_netlink_send(m, 0, gfp_any());
192 if (err == -ESRCH) {
193 /*
194 * Try to start the userspace helper if sending
195 * the request failed the first time.
196 */
197 err = uvesafb_helper_start();
198 if (err) {
199 printk(KERN_ERR "uvesafb: failed to execute %s\n",
200 v86d_path);
201 printk(KERN_ERR "uvesafb: make sure that the v86d "
202 "helper is installed and executable\n");
203 } else {
204 v86d_started = 1;
205 err = cn_netlink_send(m, 0, gfp_any());
206 }
207 }
208 kfree(m);
209
210 if (!err && !(task->t.flags & TF_EXIT))
211 err = !wait_for_completion_timeout(task->done,
212 msecs_to_jiffies(UVESAFB_TIMEOUT));
213
214 mutex_lock(&uvfb_lock);
215 uvfb_tasks[seq] = NULL;
216 mutex_unlock(&uvfb_lock);
217
218 seq++;
219 if (seq >= UVESAFB_TASKS_MAX)
220 seq = 0;
221
222 return err;
223}
224
225/*
226 * Free a uvesafb_ktask struct.
227 */
228static void uvesafb_free(struct uvesafb_ktask *task)
229{
230 if (task) {
231 if (task->done)
232 kfree(task->done);
233 kfree(task);
234 }
235}
236
237/*
238 * Prepare a uvesafb_ktask struct to be used again.
239 */
240static void uvesafb_reset(struct uvesafb_ktask *task)
241{
242 struct completion *cpl = task->done;
243
244 memset(task, 0, sizeof(*task));
245 task->done = cpl;
246}
247
248/*
249 * Allocate and prepare a uvesafb_ktask struct.
250 */
251static struct uvesafb_ktask *uvesafb_prep(void)
252{
253 struct uvesafb_ktask *task;
254
255 task = kzalloc(sizeof(*task), GFP_KERNEL);
256 if (task) {
257 task->done = kzalloc(sizeof(*task->done), GFP_KERNEL);
258 if (!task->done) {
259 kfree(task);
260 task = NULL;
261 }
262 }
263 return task;
264}
265
266static void uvesafb_setup_var(struct fb_var_screeninfo *var,
267 struct fb_info *info, struct vbe_mode_ib *mode)
268{
269 struct uvesafb_par *par = info->par;
270
271 var->vmode = FB_VMODE_NONINTERLACED;
272 var->sync = FB_SYNC_VERT_HIGH_ACT;
273
274 var->xres = mode->x_res;
275 var->yres = mode->y_res;
276 var->xres_virtual = mode->x_res;
277 var->yres_virtual = (par->ypan) ?
278 info->fix.smem_len / mode->bytes_per_scan_line :
279 mode->y_res;
280 var->xoffset = 0;
281 var->yoffset = 0;
282 var->bits_per_pixel = mode->bits_per_pixel;
283
284 if (var->bits_per_pixel == 15)
285 var->bits_per_pixel = 16;
286
287 if (var->bits_per_pixel > 8) {
288 var->red.offset = mode->red_off;
289 var->red.length = mode->red_len;
290 var->green.offset = mode->green_off;
291 var->green.length = mode->green_len;
292 var->blue.offset = mode->blue_off;
293 var->blue.length = mode->blue_len;
294 var->transp.offset = mode->rsvd_off;
295 var->transp.length = mode->rsvd_len;
296 } else {
297 var->red.offset = 0;
298 var->green.offset = 0;
299 var->blue.offset = 0;
300 var->transp.offset = 0;
301
302 /*
303 * We're assuming that we can switch the DAC to 8 bits. If
304 * this proves to be incorrect, we'll update the fields
305 * later in set_par().
306 */
307 if (par->vbe_ib.capabilities & VBE_CAP_CAN_SWITCH_DAC) {
308 var->red.length = 8;
309 var->green.length = 8;
310 var->blue.length = 8;
311 var->transp.length = 0;
312 } else {
313 var->red.length = 6;
314 var->green.length = 6;
315 var->blue.length = 6;
316 var->transp.length = 0;
317 }
318 }
319}
320
321static int uvesafb_vbe_find_mode(struct uvesafb_par *par,
322 int xres, int yres, int depth, unsigned char flags)
323{
324 int i, match = -1, h = 0, d = 0x7fffffff;
325
326 for (i = 0; i < par->vbe_modes_cnt; i++) {
327 h = abs(par->vbe_modes[i].x_res - xres) +
328 abs(par->vbe_modes[i].y_res - yres) +
329 abs(depth - par->vbe_modes[i].depth);
330
331 /*
332 * We have an exact match in terms of resolution
333 * and depth.
334 */
335 if (h == 0)
336 return i;
337
338 if (h < d || (h == d && par->vbe_modes[i].depth > depth)) {
339 d = h;
340 match = i;
341 }
342 }
343 i = 1;
344
345 if (flags & UVESAFB_EXACT_DEPTH &&
346 par->vbe_modes[match].depth != depth)
347 i = 0;
348
349 if (flags & UVESAFB_EXACT_RES && d > 24)
350 i = 0;
351
352 if (i != 0)
353 return match;
354 else
355 return -1;
356}
357
358static u8 *uvesafb_vbe_state_save(struct uvesafb_par *par)
359{
360 struct uvesafb_ktask *task;
361 u8 *state;
362 int err;
363
364 if (!par->vbe_state_size)
365 return NULL;
366
367 state = kmalloc(par->vbe_state_size, GFP_KERNEL);
368 if (!state)
369 return NULL;
370
371 task = uvesafb_prep();
372 if (!task) {
373 kfree(state);
374 return NULL;
375 }
376
377 task->t.regs.eax = 0x4f04;
378 task->t.regs.ecx = 0x000f;
379 task->t.regs.edx = 0x0001;
380 task->t.flags = TF_BUF_RET | TF_BUF_ESBX;
381 task->t.buf_len = par->vbe_state_size;
382 task->buf = state;
383 err = uvesafb_exec(task);
384
385 if (err || (task->t.regs.eax & 0xffff) != 0x004f) {
386 printk(KERN_WARNING "uvesafb: VBE get state call "
387 "failed (eax=0x%x, err=%d)\n",
388 task->t.regs.eax, err);
389 kfree(state);
390 state = NULL;
391 }
392
393 uvesafb_free(task);
394 return state;
395}
396
397static void uvesafb_vbe_state_restore(struct uvesafb_par *par, u8 *state_buf)
398{
399 struct uvesafb_ktask *task;
400 int err;
401
402 if (!state_buf)
403 return;
404
405 task = uvesafb_prep();
406 if (!task)
407 return;
408
409 task->t.regs.eax = 0x4f04;
410 task->t.regs.ecx = 0x000f;
411 task->t.regs.edx = 0x0002;
412 task->t.buf_len = par->vbe_state_size;
413 task->t.flags = TF_BUF_ESBX;
414 task->buf = state_buf;
415
416 err = uvesafb_exec(task);
417 if (err || (task->t.regs.eax & 0xffff) != 0x004f)
418 printk(KERN_WARNING "uvesafb: VBE state restore call "
419 "failed (eax=0x%x, err=%d)\n",
420 task->t.regs.eax, err);
421
422 uvesafb_free(task);
423}
424
425static int __devinit uvesafb_vbe_getinfo(struct uvesafb_ktask *task,
426 struct uvesafb_par *par)
427{
428 int err;
429
430 task->t.regs.eax = 0x4f00;
431 task->t.flags = TF_VBEIB;
432 task->t.buf_len = sizeof(struct vbe_ib);
433 task->buf = &par->vbe_ib;
434 strncpy(par->vbe_ib.vbe_signature, "VBE2", 4);
435
436 err = uvesafb_exec(task);
437 if (err || (task->t.regs.eax & 0xffff) != 0x004f) {
438 printk(KERN_ERR "uvesafb: Getting VBE info block failed "
439 "(eax=0x%x, err=%d)\n", (u32)task->t.regs.eax,
440 err);
441 return -EINVAL;
442 }
443
444 if (par->vbe_ib.vbe_version < 0x0200) {
445 printk(KERN_ERR "uvesafb: Sorry, pre-VBE 2.0 cards are "
446 "not supported.\n");
447 return -EINVAL;
448 }
449
450 if (!par->vbe_ib.mode_list_ptr) {
451 printk(KERN_ERR "uvesafb: Missing mode list!\n");
452 return -EINVAL;
453 }
454
455 printk(KERN_INFO "uvesafb: ");
456
457 /*
458 * Convert string pointers and the mode list pointer into
459 * usable addresses. Print informational messages about the
460 * video adapter and its vendor.
461 */
462 if (par->vbe_ib.oem_vendor_name_ptr)
463 printk("%s, ",
464 ((char *)task->buf) + par->vbe_ib.oem_vendor_name_ptr);
465
466 if (par->vbe_ib.oem_product_name_ptr)
467 printk("%s, ",
468 ((char *)task->buf) + par->vbe_ib.oem_product_name_ptr);
469
470 if (par->vbe_ib.oem_product_rev_ptr)
471 printk("%s, ",
472 ((char *)task->buf) + par->vbe_ib.oem_product_rev_ptr);
473
474 if (par->vbe_ib.oem_string_ptr)
475 printk("OEM: %s, ",
476 ((char *)task->buf) + par->vbe_ib.oem_string_ptr);
477
478 printk("VBE v%d.%d\n", ((par->vbe_ib.vbe_version & 0xff00) >> 8),
479 par->vbe_ib.vbe_version & 0xff);
480
481 return 0;
482}
483
484static int __devinit uvesafb_vbe_getmodes(struct uvesafb_ktask *task,
485 struct uvesafb_par *par)
486{
487 int off = 0, err;
488 u16 *mode;
489
490 par->vbe_modes_cnt = 0;
491
492 /* Count available modes. */
493 mode = (u16 *) (((u8 *)&par->vbe_ib) + par->vbe_ib.mode_list_ptr);
494 while (*mode != 0xffff) {
495 par->vbe_modes_cnt++;
496 mode++;
497 }
498
499 par->vbe_modes = kzalloc(sizeof(struct vbe_mode_ib) *
500 par->vbe_modes_cnt, GFP_KERNEL);
501 if (!par->vbe_modes)
502 return -ENOMEM;
503
504 /* Get info about all available modes. */
505 mode = (u16 *) (((u8 *)&par->vbe_ib) + par->vbe_ib.mode_list_ptr);
506 while (*mode != 0xffff) {
507 struct vbe_mode_ib *mib;
508
509 uvesafb_reset(task);
510 task->t.regs.eax = 0x4f01;
511 task->t.regs.ecx = (u32) *mode;
512 task->t.flags = TF_BUF_RET | TF_BUF_ESDI;
513 task->t.buf_len = sizeof(struct vbe_mode_ib);
514 task->buf = par->vbe_modes + off;
515
516 err = uvesafb_exec(task);
517 if (err || (task->t.regs.eax & 0xffff) != 0x004f) {
518 printk(KERN_ERR "uvesafb: Getting mode info block "
519 "for mode 0x%x failed (eax=0x%x, err=%d)\n",
520 *mode, (u32)task->t.regs.eax, err);
521 return -EINVAL;
522 }
523
524 mib = task->buf;
525 mib->mode_id = *mode;
526
527 /*
528 * We only want modes that are supported with the current
529 * hardware configuration, color, graphics and that have
530 * support for the LFB.
531 */
532 if ((mib->mode_attr & VBE_MODE_MASK) == VBE_MODE_MASK &&
533 mib->bits_per_pixel >= 8)
534 off++;
535 else
536 par->vbe_modes_cnt--;
537
538 mode++;
539 mib->depth = mib->red_len + mib->green_len + mib->blue_len;
540
541 /*
542 * Handle 8bpp modes and modes with broken color component
543 * lengths.
544 */
545 if (mib->depth == 0 || (mib->depth == 24 &&
546 mib->bits_per_pixel == 32))
547 mib->depth = mib->bits_per_pixel;
548 }
549
550 return 0;
551}
552
553/*
554 * The Protected Mode Interface is 32-bit x86 code, so we only run it on
555 * x86 and not x86_64.
556 */
557#ifdef CONFIG_X86_32
558static int __devinit uvesafb_vbe_getpmi(struct uvesafb_ktask *task,
559 struct uvesafb_par *par)
560{
561 int i, err;
562
563 uvesafb_reset(task);
564 task->t.regs.eax = 0x4f0a;
565 task->t.regs.ebx = 0x0;
566 err = uvesafb_exec(task);
567
568 if ((task->t.regs.eax & 0xffff) != 0x4f || task->t.regs.es < 0xc000) {
569 par->pmi_setpal = par->ypan = 0;
570 } else {
571 par->pmi_base = (u16 *)phys_to_virt(((u32)task->t.regs.es << 4)
572 + task->t.regs.edi);
573 par->pmi_start = (u8 *)par->pmi_base + par->pmi_base[1];
574 par->pmi_pal = (u8 *)par->pmi_base + par->pmi_base[2];
575 printk(KERN_INFO "uvesafb: protected mode interface info at "
576 "%04x:%04x\n",
577 (u16)task->t.regs.es, (u16)task->t.regs.edi);
578 printk(KERN_INFO "uvesafb: pmi: set display start = %p, "
579 "set palette = %p\n", par->pmi_start,
580 par->pmi_pal);
581
582 if (par->pmi_base[3]) {
583 printk(KERN_INFO "uvesafb: pmi: ports = ");
584 for (i = par->pmi_base[3]/2;
585 par->pmi_base[i] != 0xffff; i++)
586 printk("%x ", par->pmi_base[i]);
587 printk("\n");
588
589 if (par->pmi_base[i] != 0xffff) {
590 printk(KERN_INFO "uvesafb: can't handle memory"
591 " requests, pmi disabled\n");
592 par->ypan = par->pmi_setpal = 0;
593 }
594 }
595 }
596 return 0;
597}
598#endif /* CONFIG_X86_32 */
599
600/*
601 * Check whether a video mode is supported by the Video BIOS and is
602 * compatible with the monitor limits.
603 */
604static int __devinit uvesafb_is_valid_mode(struct fb_videomode *mode,
605 struct fb_info *info)
606{
607 if (info->monspecs.gtf) {
608 fb_videomode_to_var(&info->var, mode);
609 if (fb_validate_mode(&info->var, info))
610 return 0;
611 }
612
613 if (uvesafb_vbe_find_mode(info->par, mode->xres, mode->yres, 8,
614 UVESAFB_EXACT_RES) == -1)
615 return 0;
616
617 return 1;
618}
619
620static int __devinit uvesafb_vbe_getedid(struct uvesafb_ktask *task,
621 struct fb_info *info)
622{
623 struct uvesafb_par *par = info->par;
624 int err = 0;
625
626 if (noedid || par->vbe_ib.vbe_version < 0x0300)
627 return -EINVAL;
628
629 task->t.regs.eax = 0x4f15;
630 task->t.regs.ebx = 0;
631 task->t.regs.ecx = 0;
632 task->t.buf_len = 0;
633 task->t.flags = 0;
634
635 err = uvesafb_exec(task);
636
637 if ((task->t.regs.eax & 0xffff) != 0x004f || err)
638 return -EINVAL;
639
640 if ((task->t.regs.ebx & 0x3) == 3) {
641 printk(KERN_INFO "uvesafb: VBIOS/hardware supports both "
642 "DDC1 and DDC2 transfers\n");
643 } else if ((task->t.regs.ebx & 0x3) == 2) {
644 printk(KERN_INFO "uvesafb: VBIOS/hardware supports DDC2 "
645 "transfers\n");
646 } else if ((task->t.regs.ebx & 0x3) == 1) {
647 printk(KERN_INFO "uvesafb: VBIOS/hardware supports DDC1 "
648 "transfers\n");
649 } else {
650 printk(KERN_INFO "uvesafb: VBIOS/hardware doesn't support "
651 "DDC transfers\n");
652 return -EINVAL;
653 }
654
655 task->t.regs.eax = 0x4f15;
656 task->t.regs.ebx = 1;
657 task->t.regs.ecx = task->t.regs.edx = 0;
658 task->t.flags = TF_BUF_RET | TF_BUF_ESDI;
659 task->t.buf_len = EDID_LENGTH;
660 task->buf = kzalloc(EDID_LENGTH, GFP_KERNEL);
661
662 err = uvesafb_exec(task);
663
664 if ((task->t.regs.eax & 0xffff) == 0x004f && !err) {
665 fb_edid_to_monspecs(task->buf, &info->monspecs);
666
667 if (info->monspecs.vfmax && info->monspecs.hfmax) {
668 /*
669 * If the maximum pixel clock wasn't specified in
670 * the EDID block, set it to 300 MHz.
671 */
672 if (info->monspecs.dclkmax == 0)
673 info->monspecs.dclkmax = 300 * 1000000;
674 info->monspecs.gtf = 1;
675 }
676 } else {
677 err = -EINVAL;
678 }
679
680 kfree(task->buf);
681 return err;
682}
683
684static void __devinit uvesafb_vbe_getmonspecs(struct uvesafb_ktask *task,
685 struct fb_info *info)
686{
687 struct uvesafb_par *par = info->par;
688 int i;
689
690 memset(&info->monspecs, 0, sizeof(info->monspecs));
691
692 /*
693 * If we don't get all necessary data from the EDID block,
694 * mark it as incompatible with the GTF and set nocrtc so
695 * that we always use the default BIOS refresh rate.
696 */
697 if (uvesafb_vbe_getedid(task, info)) {
698 info->monspecs.gtf = 0;
699 par->nocrtc = 1;
700 }
701
702 /* Kernel command line overrides. */
703 if (maxclk)
704 info->monspecs.dclkmax = maxclk * 1000000;
705 if (maxvf)
706 info->monspecs.vfmax = maxvf;
707 if (maxhf)
708 info->monspecs.hfmax = maxhf * 1000;
709
710 /*
711 * In case DDC transfers are not supported, the user can provide
712 * monitor limits manually. Lower limits are set to "safe" values.
713 */
714 if (info->monspecs.gtf == 0 && maxclk && maxvf && maxhf) {
715 info->monspecs.dclkmin = 0;
716 info->monspecs.vfmin = 60;
717 info->monspecs.hfmin = 29000;
718 info->monspecs.gtf = 1;
719 par->nocrtc = 0;
720 }
721
722 if (info->monspecs.gtf)
723 printk(KERN_INFO
724 "uvesafb: monitor limits: vf = %d Hz, hf = %d kHz, "
725 "clk = %d MHz\n", info->monspecs.vfmax,
726 (int)(info->monspecs.hfmax / 1000),
727 (int)(info->monspecs.dclkmax / 1000000));
728 else
729 printk(KERN_INFO "uvesafb: no monitor limits have been set, "
730 "default refresh rate will be used\n");
731
732 /* Add VBE modes to the modelist. */
733 for (i = 0; i < par->vbe_modes_cnt; i++) {
734 struct fb_var_screeninfo var;
735 struct vbe_mode_ib *mode;
736 struct fb_videomode vmode;
737
738 mode = &par->vbe_modes[i];
739 memset(&var, 0, sizeof(var));
740
741 var.xres = mode->x_res;
742 var.yres = mode->y_res;
743
744 fb_get_mode(FB_VSYNCTIMINGS | FB_IGNOREMON, 60, &var, info);
745 fb_var_to_videomode(&vmode, &var);
746 fb_add_videomode(&vmode, &info->modelist);
747 }
748
749 /* Add valid VESA modes to our modelist. */
750 for (i = 0; i < VESA_MODEDB_SIZE; i++) {
751 if (uvesafb_is_valid_mode((struct fb_videomode *)
752 &vesa_modes[i], info))
753 fb_add_videomode(&vesa_modes[i], &info->modelist);
754 }
755
756 for (i = 0; i < info->monspecs.modedb_len; i++) {
757 if (uvesafb_is_valid_mode(&info->monspecs.modedb[i], info))
758 fb_add_videomode(&info->monspecs.modedb[i],
759 &info->modelist);
760 }
761
762 return;
763}
764
765static void __devinit uvesafb_vbe_getstatesize(struct uvesafb_ktask *task,
766 struct uvesafb_par *par)
767{
768 int err;
769
770 uvesafb_reset(task);
771
772 /*
773 * Get the VBE state buffer size. We want all available
774 * hardware state data (CL = 0x0f).
775 */
776 task->t.regs.eax = 0x4f04;
777 task->t.regs.ecx = 0x000f;
778 task->t.regs.edx = 0x0000;
779 task->t.flags = 0;
780
781 err = uvesafb_exec(task);
782
783 if (err || (task->t.regs.eax & 0xffff) != 0x004f) {
784 printk(KERN_WARNING "uvesafb: VBE state buffer size "
785 "cannot be determined (eax=0x%x, err=%d)\n",
786 task->t.regs.eax, err);
787 par->vbe_state_size = 0;
788 return;
789 }
790
791 par->vbe_state_size = 64 * (task->t.regs.ebx & 0xffff);
792}
793
794static int __devinit uvesafb_vbe_init(struct fb_info *info)
795{
796 struct uvesafb_ktask *task = NULL;
797 struct uvesafb_par *par = info->par;
798 int err;
799
800 task = uvesafb_prep();
801 if (!task)
802 return -ENOMEM;
803
804 err = uvesafb_vbe_getinfo(task, par);
805 if (err)
806 goto out;
807
808 err = uvesafb_vbe_getmodes(task, par);
809 if (err)
810 goto out;
811
812 par->nocrtc = nocrtc;
813#ifdef CONFIG_X86_32
814 par->pmi_setpal = pmi_setpal;
815 par->ypan = ypan;
816
817 if (par->pmi_setpal || par->ypan)
818 uvesafb_vbe_getpmi(task, par);
819#else
820 /* The protected mode interface is not available on non-x86. */
821 par->pmi_setpal = par->ypan = 0;
822#endif
823
824 INIT_LIST_HEAD(&info->modelist);
825 uvesafb_vbe_getmonspecs(task, info);
826 uvesafb_vbe_getstatesize(task, par);
827
828out: uvesafb_free(task);
829 return err;
830}
831
832static int __devinit uvesafb_vbe_init_mode(struct fb_info *info)
833{
834 struct list_head *pos;
835 struct fb_modelist *modelist;
836 struct fb_videomode *mode;
837 struct uvesafb_par *par = info->par;
838 int i, modeid;
839
840 /* Has the user requested a specific VESA mode? */
841 if (vbemode) {
842 for (i = 0; i < par->vbe_modes_cnt; i++) {
843 if (par->vbe_modes[i].mode_id == vbemode) {
844 fb_get_mode(FB_VSYNCTIMINGS | FB_IGNOREMON, 60,
845 &info->var, info);
846 /*
847 * With pixclock set to 0, the default BIOS
848 * timings will be used in set_par().
849 */
850 info->var.pixclock = 0;
851 modeid = i;
852 goto gotmode;
853 }
854 }
855 printk(KERN_INFO "uvesafb: requested VBE mode 0x%x is "
856 "unavailable\n", vbemode);
857 vbemode = 0;
858 }
859
860 /* Count the modes in the modelist */
861 i = 0;
862 list_for_each(pos, &info->modelist)
863 i++;
864
865 /*
866 * Convert the modelist into a modedb so that we can use it with
867 * fb_find_mode().
868 */
869 mode = kzalloc(i * sizeof(*mode), GFP_KERNEL);
870 if (mode) {
871 i = 0;
872 list_for_each(pos, &info->modelist) {
873 modelist = list_entry(pos, struct fb_modelist, list);
874 mode[i] = modelist->mode;
875 i++;
876 }
877
878 if (!mode_option)
879 mode_option = UVESAFB_DEFAULT_MODE;
880
881 i = fb_find_mode(&info->var, info, mode_option, mode, i,
882 NULL, 8);
883
884 kfree(mode);
885 }
886
887 /* fb_find_mode() failed */
888 if (i == 0 || i >= 3) {
889 info->var.xres = 640;
890 info->var.yres = 480;
891 mode = (struct fb_videomode *)
892 fb_find_best_mode(&info->var, &info->modelist);
893
894 if (mode) {
895 fb_videomode_to_var(&info->var, mode);
896 } else {
897 modeid = par->vbe_modes[0].mode_id;
898 fb_get_mode(FB_VSYNCTIMINGS | FB_IGNOREMON, 60,
899 &info->var, info);
900 goto gotmode;
901 }
902 }
903
904 /* Look for a matching VBE mode. */
905 modeid = uvesafb_vbe_find_mode(par, info->var.xres, info->var.yres,
906 info->var.bits_per_pixel, UVESAFB_EXACT_RES);
907
908 if (modeid == -1)
909 return -EINVAL;
910
911gotmode:
912 uvesafb_setup_var(&info->var, info, &par->vbe_modes[modeid]);
913
914 /*
915 * If we are not VBE3.0+ compliant, we're done -- the BIOS will
916 * ignore our timings anyway.
917 */
918 if (par->vbe_ib.vbe_version < 0x0300 || par->nocrtc)
919 fb_get_mode(FB_VSYNCTIMINGS | FB_IGNOREMON, 60,
920 &info->var, info);
921
922 return modeid;
923}
924
925static int uvesafb_setpalette(struct uvesafb_pal_entry *entries, int count,
926 int start, struct fb_info *info)
927{
928 struct uvesafb_ktask *task;
929 struct uvesafb_par *par = info->par;
930 int i = par->mode_idx;
931 int err = 0;
932
933 /*
934 * We support palette modifications for 8 bpp modes only, so
935 * there can never be more than 256 entries.
936 */
937 if (start + count > 256)
938 return -EINVAL;
939
940#ifdef CONFIG_X86
941 /* Use VGA registers if mode is VGA-compatible. */
942 if (i >= 0 && i < par->vbe_modes_cnt &&
943 par->vbe_modes[i].mode_attr & VBE_MODE_VGACOMPAT) {
944 for (i = 0; i < count; i++) {
945 outb_p(start + i, dac_reg);
946 outb_p(entries[i].red, dac_val);
947 outb_p(entries[i].green, dac_val);
948 outb_p(entries[i].blue, dac_val);
949 }
950 }
951#ifdef CONFIG_X86_32
952 else if (par->pmi_setpal) {
953 __asm__ __volatile__(
954 "call *(%%esi)"
955 : /* no return value */
956 : "a" (0x4f09), /* EAX */
957 "b" (0), /* EBX */
958 "c" (count), /* ECX */
959 "d" (start), /* EDX */
960 "D" (entries), /* EDI */
961 "S" (&par->pmi_pal)); /* ESI */
962 }
963#endif /* CONFIG_X86_32 */
964 else
965#endif /* CONFIG_X86 */
966 {
967 task = uvesafb_prep();
968 if (!task)
969 return -ENOMEM;
970
971 task->t.regs.eax = 0x4f09;
972 task->t.regs.ebx = 0x0;
973 task->t.regs.ecx = count;
974 task->t.regs.edx = start;
975 task->t.flags = TF_BUF_ESDI;
976 task->t.buf_len = sizeof(struct uvesafb_pal_entry) * count;
977 task->buf = entries;
978
979 err = uvesafb_exec(task);
980 if ((task->t.regs.eax & 0xffff) != 0x004f)
981 err = 1;
982
983 uvesafb_free(task);
984 }
985 return err;
986}
987
988static int uvesafb_setcolreg(unsigned regno, unsigned red, unsigned green,
989 unsigned blue, unsigned transp,
990 struct fb_info *info)
991{
992 struct uvesafb_pal_entry entry;
993 int shift = 16 - info->var.green.length;
994 int err = 0;
995
996 if (regno >= info->cmap.len)
997 return -EINVAL;
998
999 if (info->var.bits_per_pixel == 8) {
1000 entry.red = red >> shift;
1001 entry.green = green >> shift;
1002 entry.blue = blue >> shift;
1003 entry.pad = 0;
1004
1005 err = uvesafb_setpalette(&entry, 1, regno, info);
1006 } else if (regno < 16) {
1007 switch (info->var.bits_per_pixel) {
1008 case 16:
1009 if (info->var.red.offset == 10) {
1010 /* 1:5:5:5 */
1011 ((u32 *) (info->pseudo_palette))[regno] =
1012 ((red & 0xf800) >> 1) |
1013 ((green & 0xf800) >> 6) |
1014 ((blue & 0xf800) >> 11);
1015 } else {
1016 /* 0:5:6:5 */
1017 ((u32 *) (info->pseudo_palette))[regno] =
1018 ((red & 0xf800) ) |
1019 ((green & 0xfc00) >> 5) |
1020 ((blue & 0xf800) >> 11);
1021 }
1022 break;
1023
1024 case 24:
1025 case 32:
1026 red >>= 8;
1027 green >>= 8;
1028 blue >>= 8;
1029 ((u32 *)(info->pseudo_palette))[regno] =
1030 (red << info->var.red.offset) |
1031 (green << info->var.green.offset) |
1032 (blue << info->var.blue.offset);
1033 break;
1034 }
1035 }
1036 return err;
1037}
1038
1039static int uvesafb_setcmap(struct fb_cmap *cmap, struct fb_info *info)
1040{
1041 struct uvesafb_pal_entry *entries;
1042 int shift = 16 - info->var.green.length;
1043 int i, err = 0;
1044
1045 if (info->var.bits_per_pixel == 8) {
1046 if (cmap->start + cmap->len > info->cmap.start +
1047 info->cmap.len || cmap->start < info->cmap.start)
1048 return -EINVAL;
1049
1050 entries = kmalloc(sizeof(*entries) * cmap->len, GFP_KERNEL);
1051 if (!entries)
1052 return -ENOMEM;
1053
1054 for (i = 0; i < cmap->len; i++) {
1055 entries[i].red = cmap->red[i] >> shift;
1056 entries[i].green = cmap->green[i] >> shift;
1057 entries[i].blue = cmap->blue[i] >> shift;
1058 entries[i].pad = 0;
1059 }
1060 err = uvesafb_setpalette(entries, cmap->len, cmap->start, info);
1061 kfree(entries);
1062 } else {
1063 /*
1064 * For modes with bpp > 8, we only set the pseudo palette in
1065 * the fb_info struct. We rely on uvesafb_setcolreg to do all
1066 * sanity checking.
1067 */
1068 for (i = 0; i < cmap->len; i++) {
1069 err |= uvesafb_setcolreg(cmap->start + i, cmap->red[i],
1070 cmap->green[i], cmap->blue[i],
1071 0, info);
1072 }
1073 }
1074 return err;
1075}
1076
1077static int uvesafb_pan_display(struct fb_var_screeninfo *var,
1078 struct fb_info *info)
1079{
1080#ifdef CONFIG_X86_32
1081 int offset;
1082 struct uvesafb_par *par = info->par;
1083
1084 offset = (var->yoffset * info->fix.line_length + var->xoffset) / 4;
1085
1086 /*
1087 * It turns out it's not the best idea to do panning via vm86,
1088 * so we only allow it if we have a PMI.
1089 */
1090 if (par->pmi_start) {
1091 __asm__ __volatile__(
1092 "call *(%%edi)"
1093 : /* no return value */
1094 : "a" (0x4f07), /* EAX */
1095 "b" (0), /* EBX */
1096 "c" (offset), /* ECX */
1097 "d" (offset >> 16), /* EDX */
1098 "D" (&par->pmi_start)); /* EDI */
1099 }
1100#endif
1101 return 0;
1102}
1103
1104static int uvesafb_blank(int blank, struct fb_info *info)
1105{
1106 struct uvesafb_par *par = info->par;
1107 struct uvesafb_ktask *task;
1108 int err = 1;
1109
1110#ifdef CONFIG_X86
1111 if (par->vbe_ib.capabilities & VBE_CAP_VGACOMPAT) {
1112 int loop = 10000;
1113 u8 seq = 0, crtc17 = 0;
1114
1115 if (blank == FB_BLANK_POWERDOWN) {
1116 seq = 0x20;
1117 crtc17 = 0x00;
1118 err = 0;
1119 } else {
1120 seq = 0x00;
1121 crtc17 = 0x80;
1122 err = (blank == FB_BLANK_UNBLANK) ? 0 : -EINVAL;
1123 }
1124
1125 vga_wseq(NULL, 0x00, 0x01);
1126 seq |= vga_rseq(NULL, 0x01) & ~0x20;
1127 vga_wseq(NULL, 0x00, seq);
1128
1129 crtc17 |= vga_rcrt(NULL, 0x17) & ~0x80;
1130 while (loop--);
1131 vga_wcrt(NULL, 0x17, crtc17);
1132 vga_wseq(NULL, 0x00, 0x03);
1133 } else
1134#endif /* CONFIG_X86 */
1135 {
1136 task = uvesafb_prep();
1137 if (!task)
1138 return -ENOMEM;
1139
1140 task->t.regs.eax = 0x4f10;
1141 switch (blank) {
1142 case FB_BLANK_UNBLANK:
1143 task->t.regs.ebx = 0x0001;
1144 break;
1145 case FB_BLANK_NORMAL:
1146 task->t.regs.ebx = 0x0101; /* standby */
1147 break;
1148 case FB_BLANK_POWERDOWN:
1149 task->t.regs.ebx = 0x0401; /* powerdown */
1150 break;
1151 default:
1152 goto out;
1153 }
1154
1155 err = uvesafb_exec(task);
1156 if (err || (task->t.regs.eax & 0xffff) != 0x004f)
1157 err = 1;
1158out: uvesafb_free(task);
1159 }
1160 return err;
1161}
1162
1163static int uvesafb_open(struct fb_info *info, int user)
1164{
1165 struct uvesafb_par *par = info->par;
1166 int cnt = atomic_read(&par->ref_count);
1167
1168 if (!cnt && par->vbe_state_size)
1169 par->vbe_state_orig = uvesafb_vbe_state_save(par);
1170
1171 atomic_inc(&par->ref_count);
1172 return 0;
1173}
1174
1175static int uvesafb_release(struct fb_info *info, int user)
1176{
1177 struct uvesafb_ktask *task = NULL;
1178 struct uvesafb_par *par = info->par;
1179 int cnt = atomic_read(&par->ref_count);
1180
1181 if (!cnt)
1182 return -EINVAL;
1183
1184 if (cnt != 1)
1185 goto out;
1186
1187 task = uvesafb_prep();
1188 if (!task)
1189 goto out;
1190
1191 /* First, try to set the standard 80x25 text mode. */
1192 task->t.regs.eax = 0x0003;
1193 uvesafb_exec(task);
1194
1195 /*
1196 * Now try to restore whatever hardware state we might have
1197 * saved when the fb device was first opened.
1198 */
1199 uvesafb_vbe_state_restore(par, par->vbe_state_orig);
1200out:
1201 atomic_dec(&par->ref_count);
1202 if (task)
1203 uvesafb_free(task);
1204 return 0;
1205}
1206
1207static int uvesafb_set_par(struct fb_info *info)
1208{
1209 struct uvesafb_par *par = info->par;
1210 struct uvesafb_ktask *task = NULL;
1211 struct vbe_crtc_ib *crtc = NULL;
1212 struct vbe_mode_ib *mode = NULL;
1213 int i, err = 0, depth = info->var.bits_per_pixel;
1214
1215 if (depth > 8 && depth != 32)
1216 depth = info->var.red.length + info->var.green.length +
1217 info->var.blue.length;
1218
1219 i = uvesafb_vbe_find_mode(par, info->var.xres, info->var.yres, depth,
1220 UVESAFB_EXACT_RES | UVESAFB_EXACT_DEPTH);
1221 if (i >= 0)
1222 mode = &par->vbe_modes[i];
1223 else
1224 return -EINVAL;
1225
1226 task = uvesafb_prep();
1227 if (!task)
1228 return -ENOMEM;
1229setmode:
1230 task->t.regs.eax = 0x4f02;
1231 task->t.regs.ebx = mode->mode_id | 0x4000; /* use LFB */
1232
1233 if (par->vbe_ib.vbe_version >= 0x0300 && !par->nocrtc &&
1234 info->var.pixclock != 0) {
1235 task->t.regs.ebx |= 0x0800; /* use CRTC data */
1236 task->t.flags = TF_BUF_ESDI;
1237 crtc = kzalloc(sizeof(struct vbe_crtc_ib), GFP_KERNEL);
1238 if (!crtc) {
1239 err = -ENOMEM;
1240 goto out;
1241 }
1242 crtc->horiz_start = info->var.xres + info->var.right_margin;
1243 crtc->horiz_end = crtc->horiz_start + info->var.hsync_len;
1244 crtc->horiz_total = crtc->horiz_end + info->var.left_margin;
1245
1246 crtc->vert_start = info->var.yres + info->var.lower_margin;
1247 crtc->vert_end = crtc->vert_start + info->var.vsync_len;
1248 crtc->vert_total = crtc->vert_end + info->var.upper_margin;
1249
1250 crtc->pixel_clock = PICOS2KHZ(info->var.pixclock) * 1000;
1251 crtc->refresh_rate = (u16)(100 * (crtc->pixel_clock /
1252 (crtc->vert_total * crtc->horiz_total)));
1253
1254 if (info->var.vmode & FB_VMODE_DOUBLE)
1255 crtc->flags |= 0x1;
1256 if (info->var.vmode & FB_VMODE_INTERLACED)
1257 crtc->flags |= 0x2;
1258 if (!(info->var.sync & FB_SYNC_HOR_HIGH_ACT))
1259 crtc->flags |= 0x4;
1260 if (!(info->var.sync & FB_SYNC_VERT_HIGH_ACT))
1261 crtc->flags |= 0x8;
1262 memcpy(&par->crtc, crtc, sizeof(*crtc));
1263 } else {
1264 memset(&par->crtc, 0, sizeof(*crtc));
1265 }
1266
1267 task->t.buf_len = sizeof(struct vbe_crtc_ib);
1268 task->buf = &par->crtc;
1269
1270 err = uvesafb_exec(task);
1271 if (err || (task->t.regs.eax & 0xffff) != 0x004f) {
1272 /*
1273 * The mode switch might have failed because we tried to
1274 * use our own timings. Try again with the default timings.
1275 */
1276 if (crtc != NULL) {
1277 printk(KERN_WARNING "uvesafb: mode switch failed "
1278 "(eax=0x%x, err=%d). Trying again with "
1279 "default timings.\n", task->t.regs.eax, err);
1280 uvesafb_reset(task);
1281 kfree(crtc);
1282 crtc = NULL;
1283 info->var.pixclock = 0;
1284 goto setmode;
1285 } else {
1286 printk(KERN_ERR "uvesafb: mode switch failed (eax="
1287 "0x%x, err=%d)\n", task->t.regs.eax, err);
1288 err = -EINVAL;
1289 goto out;
1290 }
1291 }
1292 par->mode_idx = i;
1293
1294 /* For 8bpp modes, always try to set the DAC to 8 bits. */
1295 if (par->vbe_ib.capabilities & VBE_CAP_CAN_SWITCH_DAC &&
1296 mode->bits_per_pixel <= 8) {
1297 uvesafb_reset(task);
1298 task->t.regs.eax = 0x4f08;
1299 task->t.regs.ebx = 0x0800;
1300
1301 err = uvesafb_exec(task);
1302 if (err || (task->t.regs.eax & 0xffff) != 0x004f ||
1303 ((task->t.regs.ebx & 0xff00) >> 8) != 8) {
1304 /*
1305 * We've failed to set the DAC palette format -
1306 * time to correct var.
1307 */
1308 info->var.red.length = 6;
1309 info->var.green.length = 6;
1310 info->var.blue.length = 6;
1311 }
1312 }
1313
1314 info->fix.visual = (info->var.bits_per_pixel == 8) ?
1315 FB_VISUAL_PSEUDOCOLOR : FB_VISUAL_TRUECOLOR;
1316 info->fix.line_length = mode->bytes_per_scan_line;
1317
1318out: if (crtc != NULL)
1319 kfree(crtc);
1320 uvesafb_free(task);
1321
1322 return err;
1323}
1324
1325static void uvesafb_check_limits(struct fb_var_screeninfo *var,
1326 struct fb_info *info)
1327{
1328 const struct fb_videomode *mode;
1329 struct uvesafb_par *par = info->par;
1330
1331 /*
1332 * If pixclock is set to 0, then we're using default BIOS timings
1333 * and thus don't have to perform any checks here.
1334 */
1335 if (!var->pixclock)
1336 return;
1337
1338 if (par->vbe_ib.vbe_version < 0x0300) {
1339 fb_get_mode(FB_VSYNCTIMINGS | FB_IGNOREMON, 60, var, info);
1340 return;
1341 }
1342
1343 if (!fb_validate_mode(var, info))
1344 return;
1345
1346 mode = fb_find_best_mode(var, &info->modelist);
1347 if (mode) {
1348 if (mode->xres == var->xres && mode->yres == var->yres &&
1349 !(mode->vmode & (FB_VMODE_INTERLACED | FB_VMODE_DOUBLE))) {
1350 fb_videomode_to_var(var, mode);
1351 return;
1352 }
1353 }
1354
1355 if (info->monspecs.gtf && !fb_get_mode(FB_MAXTIMINGS, 0, var, info))
1356 return;
1357 /* Use default refresh rate */
1358 var->pixclock = 0;
1359}
1360
1361static int uvesafb_check_var(struct fb_var_screeninfo *var,
1362 struct fb_info *info)
1363{
1364 struct uvesafb_par *par = info->par;
1365 struct vbe_mode_ib *mode = NULL;
1366 int match = -1;
1367 int depth = var->red.length + var->green.length + var->blue.length;
1368
1369 /*
1370 * Various apps will use bits_per_pixel to set the color depth,
1371 * which is theoretically incorrect, but which we'll try to handle
1372 * here.
1373 */
1374 if (depth == 0 || abs(depth - var->bits_per_pixel) >= 8)
1375 depth = var->bits_per_pixel;
1376
1377 match = uvesafb_vbe_find_mode(par, var->xres, var->yres, depth,
1378 UVESAFB_EXACT_RES);
1379 if (match == -1)
1380 return -EINVAL;
1381
1382 mode = &par->vbe_modes[match];
1383 uvesafb_setup_var(var, info, mode);
1384
1385 /*
1386 * Check whether we have remapped enough memory for this mode.
1387 * We might be called at an early stage, when we haven't remapped
1388 * any memory yet, in which case we simply skip the check.
1389 */
1390 if (var->yres * mode->bytes_per_scan_line > info->fix.smem_len
1391 && info->fix.smem_len)
1392 return -EINVAL;
1393
1394 if ((var->vmode & FB_VMODE_DOUBLE) &&
1395 !(par->vbe_modes[match].mode_attr & 0x100))
1396 var->vmode &= ~FB_VMODE_DOUBLE;
1397
1398 if ((var->vmode & FB_VMODE_INTERLACED) &&
1399 !(par->vbe_modes[match].mode_attr & 0x200))
1400 var->vmode &= ~FB_VMODE_INTERLACED;
1401
1402 uvesafb_check_limits(var, info);
1403
1404 var->xres_virtual = var->xres;
1405 var->yres_virtual = (par->ypan) ?
1406 info->fix.smem_len / mode->bytes_per_scan_line :
1407 var->yres;
1408 return 0;
1409}
1410
1411static void uvesafb_save_state(struct fb_info *info)
1412{
1413 struct uvesafb_par *par = info->par;
1414
1415 if (par->vbe_state_saved)
1416 kfree(par->vbe_state_saved);
1417
1418 par->vbe_state_saved = uvesafb_vbe_state_save(par);
1419}
1420
1421static void uvesafb_restore_state(struct fb_info *info)
1422{
1423 struct uvesafb_par *par = info->par;
1424
1425 uvesafb_vbe_state_restore(par, par->vbe_state_saved);
1426}
1427
1428static struct fb_ops uvesafb_ops = {
1429 .owner = THIS_MODULE,
1430 .fb_open = uvesafb_open,
1431 .fb_release = uvesafb_release,
1432 .fb_setcolreg = uvesafb_setcolreg,
1433 .fb_setcmap = uvesafb_setcmap,
1434 .fb_pan_display = uvesafb_pan_display,
1435 .fb_blank = uvesafb_blank,
1436 .fb_fillrect = cfb_fillrect,
1437 .fb_copyarea = cfb_copyarea,
1438 .fb_imageblit = cfb_imageblit,
1439 .fb_check_var = uvesafb_check_var,
1440 .fb_set_par = uvesafb_set_par,
1441 .fb_save_state = uvesafb_save_state,
1442 .fb_restore_state = uvesafb_restore_state,
1443};
1444
1445static void __devinit uvesafb_init_info(struct fb_info *info,
1446 struct vbe_mode_ib *mode)
1447{
1448 unsigned int size_vmode;
1449 unsigned int size_remap;
1450 unsigned int size_total;
1451 struct uvesafb_par *par = info->par;
1452 int i, h;
1453
1454 info->pseudo_palette = ((u8 *)info->par + sizeof(struct uvesafb_par));
1455 info->fix = uvesafb_fix;
1456 info->fix.ypanstep = par->ypan ? 1 : 0;
1457 info->fix.ywrapstep = (par->ypan > 1) ? 1 : 0;
1458
1459 /*
1460 * If we were unable to get the state buffer size, disable
1461 * functions for saving and restoring the hardware state.
1462 */
1463 if (par->vbe_state_size == 0) {
1464 info->fbops->fb_save_state = NULL;
1465 info->fbops->fb_restore_state = NULL;
1466 }
1467
1468 /* Disable blanking if the user requested so. */
1469 if (!blank)
1470 info->fbops->fb_blank = NULL;
1471
1472 /*
1473 * Find out how much IO memory is required for the mode with
1474 * the highest resolution.
1475 */
1476 size_remap = 0;
1477 for (i = 0; i < par->vbe_modes_cnt; i++) {
1478 h = par->vbe_modes[i].bytes_per_scan_line *
1479 par->vbe_modes[i].y_res;
1480 if (h > size_remap)
1481 size_remap = h;
1482 }
1483 size_remap *= 2;
1484
1485 /*
1486 * size_vmode -- that is the amount of memory needed for the
1487 * used video mode, i.e. the minimum amount of
1488 * memory we need.
1489 */
1490 if (mode != NULL) {
1491 size_vmode = info->var.yres * mode->bytes_per_scan_line;
1492 } else {
1493 size_vmode = info->var.yres * info->var.xres *
1494 ((info->var.bits_per_pixel + 7) >> 3);
1495 }
1496
1497 /*
1498 * size_total -- all video memory we have. Used for mtrr
1499 * entries, resource allocation and bounds
1500 * checking.
1501 */
1502 size_total = par->vbe_ib.total_memory * 65536;
1503 if (vram_total)
1504 size_total = vram_total * 1024 * 1024;
1505 if (size_total < size_vmode)
1506 size_total = size_vmode;
1507
1508 /*
1509 * size_remap -- the amount of video memory we are going to
1510 * use for vesafb. With modern cards it is no
1511 * option to simply use size_total as th
1512 * wastes plenty of kernel address space.
1513 */
1514 if (vram_remap)
1515 size_remap = vram_remap * 1024 * 1024;
1516 if (size_remap < size_vmode)
1517 size_remap = size_vmode;
1518 if (size_remap > size_total)
1519 size_remap = size_total;
1520
1521 info->fix.smem_len = size_remap;
1522 info->fix.smem_start = mode->phys_base_ptr;
1523
1524 /*
1525 * We have to set yres_virtual here because when setup_var() was
1526 * called, smem_len wasn't defined yet.
1527 */
1528 info->var.yres_virtual = info->fix.smem_len /
1529 mode->bytes_per_scan_line;
1530
1531 if (par->ypan && info->var.yres_virtual > info->var.yres) {
1532 printk(KERN_INFO "uvesafb: scrolling: %s "
1533 "using protected mode interface, "
1534 "yres_virtual=%d\n",
1535 (par->ypan > 1) ? "ywrap" : "ypan",
1536 info->var.yres_virtual);
1537 } else {
1538 printk(KERN_INFO "uvesafb: scrolling: redraw\n");
1539 info->var.yres_virtual = info->var.yres;
1540 par->ypan = 0;
1541 }
1542
1543 info->flags = FBINFO_FLAG_DEFAULT |
1544 (par->ypan) ? FBINFO_HWACCEL_YPAN : 0;
1545
1546 if (!par->ypan)
1547 info->fbops->fb_pan_display = NULL;
1548}
1549
1550static void uvesafb_init_mtrr(struct fb_info *info)
1551{
1552#ifdef CONFIG_MTRR
1553 if (mtrr && !(info->fix.smem_start & (PAGE_SIZE - 1))) {
1554 int temp_size = info->fix.smem_len;
1555 unsigned int type = 0;
1556
1557 switch (mtrr) {
1558 case 1:
1559 type = MTRR_TYPE_UNCACHABLE;
1560 break;
1561 case 2:
1562 type = MTRR_TYPE_WRBACK;
1563 break;
1564 case 3:
1565 type = MTRR_TYPE_WRCOMB;
1566 break;
1567 case 4:
1568 type = MTRR_TYPE_WRTHROUGH;
1569 break;
1570 default:
1571 type = 0;
1572 break;
1573 }
1574
1575 if (type) {
1576 int rc;
1577
1578 /* Find the largest power-of-two */
1579 while (temp_size & (temp_size - 1))
1580 temp_size &= (temp_size - 1);
1581
1582 /* Try and find a power of two to add */
1583 do {
1584 rc = mtrr_add(info->fix.smem_start,
1585 temp_size, type, 1);
1586 temp_size >>= 1;
1587 } while (temp_size >= PAGE_SIZE && rc == -EINVAL);
1588 }
1589 }
1590#endif /* CONFIG_MTRR */
1591}
1592
1593
1594static ssize_t uvesafb_show_vbe_ver(struct device *dev,
1595 struct device_attribute *attr, char *buf)
1596{
1597 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1598 struct uvesafb_par *par = info->par;
1599
1600 return snprintf(buf, PAGE_SIZE, "%.4x\n", par->vbe_ib.vbe_version);
1601}
1602
1603static DEVICE_ATTR(vbe_version, S_IRUGO, uvesafb_show_vbe_ver, NULL);
1604
1605static ssize_t uvesafb_show_vbe_modes(struct device *dev,
1606 struct device_attribute *attr, char *buf)
1607{
1608 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1609 struct uvesafb_par *par = info->par;
1610 int ret = 0, i;
1611
1612 for (i = 0; i < par->vbe_modes_cnt && ret < PAGE_SIZE; i++) {
1613 ret += snprintf(buf + ret, PAGE_SIZE - ret,
1614 "%dx%d-%d, 0x%.4x\n",
1615 par->vbe_modes[i].x_res, par->vbe_modes[i].y_res,
1616 par->vbe_modes[i].depth, par->vbe_modes[i].mode_id);
1617 }
1618
1619 return ret;
1620}
1621
1622static DEVICE_ATTR(vbe_modes, S_IRUGO, uvesafb_show_vbe_modes, NULL);
1623
1624static ssize_t uvesafb_show_vendor(struct device *dev,
1625 struct device_attribute *attr, char *buf)
1626{
1627 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1628 struct uvesafb_par *par = info->par;
1629
1630 if (par->vbe_ib.oem_vendor_name_ptr)
1631 return snprintf(buf, PAGE_SIZE, "%s\n", (char *)
1632 (&par->vbe_ib) + par->vbe_ib.oem_vendor_name_ptr);
1633 else
1634 return 0;
1635}
1636
1637static DEVICE_ATTR(oem_vendor, S_IRUGO, uvesafb_show_vendor, NULL);
1638
1639static ssize_t uvesafb_show_product_name(struct device *dev,
1640 struct device_attribute *attr, char *buf)
1641{
1642 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1643 struct uvesafb_par *par = info->par;
1644
1645 if (par->vbe_ib.oem_product_name_ptr)
1646 return snprintf(buf, PAGE_SIZE, "%s\n", (char *)
1647 (&par->vbe_ib) + par->vbe_ib.oem_product_name_ptr);
1648 else
1649 return 0;
1650}
1651
1652static DEVICE_ATTR(oem_product_name, S_IRUGO, uvesafb_show_product_name, NULL);
1653
1654static ssize_t uvesafb_show_product_rev(struct device *dev,
1655 struct device_attribute *attr, char *buf)
1656{
1657 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1658 struct uvesafb_par *par = info->par;
1659
1660 if (par->vbe_ib.oem_product_rev_ptr)
1661 return snprintf(buf, PAGE_SIZE, "%s\n", (char *)
1662 (&par->vbe_ib) + par->vbe_ib.oem_product_rev_ptr);
1663 else
1664 return 0;
1665}
1666
1667static DEVICE_ATTR(oem_product_rev, S_IRUGO, uvesafb_show_product_rev, NULL);
1668
1669static ssize_t uvesafb_show_oem_string(struct device *dev,
1670 struct device_attribute *attr, char *buf)
1671{
1672 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1673 struct uvesafb_par *par = info->par;
1674
1675 if (par->vbe_ib.oem_string_ptr)
1676 return snprintf(buf, PAGE_SIZE, "%s\n",
1677 (char *)(&par->vbe_ib) + par->vbe_ib.oem_string_ptr);
1678 else
1679 return 0;
1680}
1681
1682static DEVICE_ATTR(oem_string, S_IRUGO, uvesafb_show_oem_string, NULL);
1683
1684static ssize_t uvesafb_show_nocrtc(struct device *dev,
1685 struct device_attribute *attr, char *buf)
1686{
1687 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1688 struct uvesafb_par *par = info->par;
1689
1690 return snprintf(buf, PAGE_SIZE, "%d\n", par->nocrtc);
1691}
1692
1693static ssize_t uvesafb_store_nocrtc(struct device *dev,
1694 struct device_attribute *attr, const char *buf, size_t count)
1695{
1696 struct fb_info *info = platform_get_drvdata(to_platform_device(dev));
1697 struct uvesafb_par *par = info->par;
1698
1699 if (count > 0) {
1700 if (buf[0] == '0')
1701 par->nocrtc = 0;
1702 else
1703 par->nocrtc = 1;
1704 }
1705 return count;
1706}
1707
1708static DEVICE_ATTR(nocrtc, S_IRUGO | S_IWUSR, uvesafb_show_nocrtc,
1709 uvesafb_store_nocrtc);
1710
1711static struct attribute *uvesafb_dev_attrs[] = {
1712 &dev_attr_vbe_version.attr,
1713 &dev_attr_vbe_modes.attr,
1714 &dev_attr_oem_vendor.attr,
1715 &dev_attr_oem_product_name.attr,
1716 &dev_attr_oem_product_rev.attr,
1717 &dev_attr_oem_string.attr,
1718 &dev_attr_nocrtc.attr,
1719 NULL,
1720};
1721
1722static struct attribute_group uvesafb_dev_attgrp = {
1723 .name = NULL,
1724 .attrs = uvesafb_dev_attrs,
1725};
1726
1727static int __devinit uvesafb_probe(struct platform_device *dev)
1728{
1729 struct fb_info *info;
1730 struct vbe_mode_ib *mode = NULL;
1731 struct uvesafb_par *par;
1732 int err = 0, i;
1733
1734 info = framebuffer_alloc(sizeof(*par) + sizeof(u32) * 256, &dev->dev);
1735 if (!info)
1736 return -ENOMEM;
1737
1738 par = info->par;
1739
1740 err = uvesafb_vbe_init(info);
1741 if (err) {
1742 printk(KERN_ERR "uvesafb: vbe_init() failed with %d\n", err);
1743 goto out;
1744 }
1745
1746 info->fbops = &uvesafb_ops;
1747
1748 i = uvesafb_vbe_init_mode(info);
1749 if (i < 0) {
1750 err = -EINVAL;
1751 goto out;
1752 } else {
1753 mode = &par->vbe_modes[i];
1754 }
1755
1756 if (fb_alloc_cmap(&info->cmap, 256, 0) < 0) {
1757 err = -ENXIO;
1758 goto out;
1759 }
1760
1761 uvesafb_init_info(info, mode);
1762
1763 if (!request_mem_region(info->fix.smem_start, info->fix.smem_len,
1764 "uvesafb")) {
1765 printk(KERN_ERR "uvesafb: cannot reserve video memory at "
1766 "0x%lx\n", info->fix.smem_start);
1767 err = -EIO;
1768 goto out_mode;
1769 }
1770
1771 info->screen_base = ioremap(info->fix.smem_start, info->fix.smem_len);
1772
1773 if (!info->screen_base) {
1774 printk(KERN_ERR
1775 "uvesafb: abort, cannot ioremap 0x%x bytes of video "
1776 "memory at 0x%lx\n",
1777 info->fix.smem_len, info->fix.smem_start);
1778 err = -EIO;
1779 goto out_mem;
1780 }
1781
1782 if (!request_region(0x3c0, 32, "uvesafb")) {
1783 printk(KERN_ERR "uvesafb: request region 0x3c0-0x3e0 failed\n");
1784 err = -EIO;
1785 goto out_unmap;
1786 }
1787
1788 uvesafb_init_mtrr(info);
1789 platform_set_drvdata(dev, info);
1790
1791 if (register_framebuffer(info) < 0) {
1792 printk(KERN_ERR
1793 "uvesafb: failed to register framebuffer device\n");
1794 err = -EINVAL;
1795 goto out_reg;
1796 }
1797
1798 printk(KERN_INFO "uvesafb: framebuffer at 0x%lx, mapped to 0x%p, "
1799 "using %dk, total %dk\n", info->fix.smem_start,
1800 info->screen_base, info->fix.smem_len/1024,
1801 par->vbe_ib.total_memory * 64);
1802 printk(KERN_INFO "fb%d: %s frame buffer device\n", info->node,
1803 info->fix.id);
1804
1805 err = sysfs_create_group(&dev->dev.kobj, &uvesafb_dev_attgrp);
1806 if (err != 0)
1807 printk(KERN_WARNING "fb%d: failed to register attributes\n",
1808 info->node);
1809
1810 return 0;
1811
1812out_reg:
1813 release_region(0x3c0, 32);
1814out_unmap:
1815 iounmap(info->screen_base);
1816out_mem:
1817 release_mem_region(info->fix.smem_start, info->fix.smem_len);
1818out_mode:
1819 if (!list_empty(&info->modelist))
1820 fb_destroy_modelist(&info->modelist);
1821 fb_destroy_modedb(info->monspecs.modedb);
1822 fb_dealloc_cmap(&info->cmap);
1823out:
1824 if (par->vbe_modes)
1825 kfree(par->vbe_modes);
1826
1827 framebuffer_release(info);
1828 return err;
1829}
1830
1831static int uvesafb_remove(struct platform_device *dev)
1832{
1833 struct fb_info *info = platform_get_drvdata(dev);
1834
1835 if (info) {
1836 struct uvesafb_par *par = info->par;
1837
1838 sysfs_remove_group(&dev->dev.kobj, &uvesafb_dev_attgrp);
1839 unregister_framebuffer(info);
1840 release_region(0x3c0, 32);
1841 iounmap(info->screen_base);
1842 release_mem_region(info->fix.smem_start, info->fix.smem_len);
1843 fb_destroy_modedb(info->monspecs.modedb);
1844 fb_dealloc_cmap(&info->cmap);
1845
1846 if (par) {
1847 if (par->vbe_modes)
1848 kfree(par->vbe_modes);
1849 if (par->vbe_state_orig)
1850 kfree(par->vbe_state_orig);
1851 if (par->vbe_state_saved)
1852 kfree(par->vbe_state_saved);
1853 }
1854
1855 framebuffer_release(info);
1856 }
1857 return 0;
1858}
1859
1860static struct platform_driver uvesafb_driver = {
1861 .probe = uvesafb_probe,
1862 .remove = uvesafb_remove,
1863 .driver = {
1864 .name = "uvesafb",
1865 },
1866};
1867
1868static struct platform_device *uvesafb_device;
1869
1870#ifndef MODULE
1871static int __devinit uvesafb_setup(char *options)
1872{
1873 char *this_opt;
1874
1875 if (!options || !*options)
1876 return 0;
1877
1878 while ((this_opt = strsep(&options, ",")) != NULL) {
1879 if (!*this_opt) continue;
1880
1881 if (!strcmp(this_opt, "redraw"))
1882 ypan = 0;
1883 else if (!strcmp(this_opt, "ypan"))
1884 ypan = 1;
1885 else if (!strcmp(this_opt, "ywrap"))
1886 ypan = 2;
1887 else if (!strcmp(this_opt, "vgapal"))
1888 pmi_setpal = 0;
1889 else if (!strcmp(this_opt, "pmipal"))
1890 pmi_setpal = 1;
1891 else if (!strncmp(this_opt, "mtrr:", 5))
1892 mtrr = simple_strtoul(this_opt+5, NULL, 0);
1893 else if (!strcmp(this_opt, "nomtrr"))
1894 mtrr = 0;
1895 else if (!strcmp(this_opt, "nocrtc"))
1896 nocrtc = 1;
1897 else if (!strcmp(this_opt, "noedid"))
1898 noedid = 1;
1899 else if (!strcmp(this_opt, "noblank"))
1900 blank = 0;
1901 else if (!strncmp(this_opt, "vtotal:", 7))
1902 vram_total = simple_strtoul(this_opt + 7, NULL, 0);
1903 else if (!strncmp(this_opt, "vremap:", 7))
1904 vram_remap = simple_strtoul(this_opt + 7, NULL, 0);
1905 else if (!strncmp(this_opt, "maxhf:", 6))
1906 maxhf = simple_strtoul(this_opt + 6, NULL, 0);
1907 else if (!strncmp(this_opt, "maxvf:", 6))
1908 maxvf = simple_strtoul(this_opt + 6, NULL, 0);
1909 else if (!strncmp(this_opt, "maxclk:", 7))
1910 maxclk = simple_strtoul(this_opt + 7, NULL, 0);
1911 else if (!strncmp(this_opt, "vbemode:", 8))
1912 vbemode = simple_strtoul(this_opt + 8, NULL, 0);
1913 else if (this_opt[0] >= '0' && this_opt[0] <= '9') {
1914 mode_option = this_opt;
1915 } else {
1916 printk(KERN_WARNING
1917 "uvesafb: unrecognized option %s\n", this_opt);
1918 }
1919 }
1920
1921 return 0;
1922}
1923#endif /* !MODULE */
1924
1925static ssize_t show_v86d(struct device_driver *dev, char *buf)
1926{
1927 return snprintf(buf, PAGE_SIZE, "%s\n", v86d_path);
1928}
1929
1930static ssize_t store_v86d(struct device_driver *dev, const char *buf,
1931 size_t count)
1932{
1933 strncpy(v86d_path, buf, PATH_MAX);
1934 return count;
1935}
1936
1937static DRIVER_ATTR(v86d, S_IRUGO | S_IWUSR, show_v86d, store_v86d);
1938
1939static int __devinit uvesafb_init(void)
1940{
1941 int err;
1942
1943#ifndef MODULE
1944 char *option = NULL;
1945
1946 if (fb_get_options("uvesafb", &option))
1947 return -ENODEV;
1948 uvesafb_setup(option);
1949#endif
1950 err = cn_add_callback(&uvesafb_cn_id, "uvesafb", uvesafb_cn_callback);
1951 if (err)
1952 return err;
1953
1954 err = platform_driver_register(&uvesafb_driver);
1955
1956 if (!err) {
1957 uvesafb_device = platform_device_alloc("uvesafb", 0);
1958 if (uvesafb_device)
1959 err = platform_device_add(uvesafb_device);
1960 else
1961 err = -ENOMEM;
1962
1963 if (err) {
1964 platform_device_put(uvesafb_device);
1965 platform_driver_unregister(&uvesafb_driver);
1966 cn_del_callback(&uvesafb_cn_id);
1967 return err;
1968 }
1969
1970 err = driver_create_file(&uvesafb_driver.driver,
1971 &driver_attr_v86d);
1972 if (err) {
1973 printk(KERN_WARNING "uvesafb: failed to register "
1974 "attributes\n");
1975 err = 0;
1976 }
1977 }
1978 return err;
1979}
1980
1981module_init(uvesafb_init);
1982
1983static void __devexit uvesafb_exit(void)
1984{
1985 struct uvesafb_ktask *task;
1986
1987 if (v86d_started) {
1988 task = uvesafb_prep();
1989 if (task) {
1990 task->t.flags = TF_EXIT;
1991 uvesafb_exec(task);
1992 uvesafb_free(task);
1993 }
1994 }
1995
1996 cn_del_callback(&uvesafb_cn_id);
1997 driver_remove_file(&uvesafb_driver.driver, &driver_attr_v86d);
1998 platform_device_unregister(uvesafb_device);
1999 platform_driver_unregister(&uvesafb_driver);
2000}
2001
2002module_exit(uvesafb_exit);
2003
2004static inline int param_get_scroll(char *buffer, struct kernel_param *kp)
2005{
2006 return 0;
2007}
2008
2009static inline int param_set_scroll(const char *val, struct kernel_param *kp)
2010{
2011 ypan = 0;
2012
2013 if (!strcmp(val, "redraw"))
2014 ypan = 0;
2015 else if (!strcmp(val, "ypan"))
2016 ypan = 1;
2017 else if (!strcmp(val, "ywrap"))
2018 ypan = 2;
2019
2020 return 0;
2021}
2022
2023#define param_check_scroll(name, p) __param_check(name, p, void);
2024
2025module_param_named(scroll, ypan, scroll, 0);
2026MODULE_PARM_DESC(scroll,
2027 "Scrolling mode, set to 'redraw', ''ypan' or 'ywrap'");
2028module_param_named(vgapal, pmi_setpal, invbool, 0);
2029MODULE_PARM_DESC(vgapal, "Set palette using VGA registers");
2030module_param_named(pmipal, pmi_setpal, bool, 0);
2031MODULE_PARM_DESC(pmipal, "Set palette using PMI calls");
2032module_param(mtrr, uint, 0);
2033MODULE_PARM_DESC(mtrr,
2034 "Memory Type Range Registers setting. Use 0 to disable.");
2035module_param(blank, bool, 0);
2036MODULE_PARM_DESC(blank, "Enable hardware blanking");
2037module_param(nocrtc, bool, 0);
2038MODULE_PARM_DESC(nocrtc, "Ignore CRTC timings when setting modes");
2039module_param(noedid, bool, 0);
2040MODULE_PARM_DESC(noedid,
2041 "Ignore EDID-provided monitor limits when setting modes");
2042module_param(vram_remap, uint, 0);
2043MODULE_PARM_DESC(vram_remap, "Set amount of video memory to be used [MiB]");
2044module_param(vram_total, uint, 0);
2045MODULE_PARM_DESC(vram_total, "Set total amount of video memoery [MiB]");
2046module_param(maxclk, ushort, 0);
2047MODULE_PARM_DESC(maxclk, "Maximum pixelclock [MHz], overrides EDID data");
2048module_param(maxhf, ushort, 0);
2049MODULE_PARM_DESC(maxhf,
2050 "Maximum horizontal frequency [kHz], overrides EDID data");
2051module_param(maxvf, ushort, 0);
2052MODULE_PARM_DESC(maxvf,
2053 "Maximum vertical frequency [Hz], overrides EDID data");
2054module_param_named(mode, mode_option, charp, 0);
2055MODULE_PARM_DESC(mode,
2056 "Specify initial video mode as \"<xres>x<yres>[-<bpp>][@<refresh>]\"");
2057module_param(vbemode, ushort, 0);
2058MODULE_PARM_DESC(vbemode,
2059 "VBE mode number to set, overrides the 'mode' option");
2060module_param_string(v86d, v86d_path, PATH_MAX, 0660);
2061MODULE_PARM_DESC(v86d, "Path to the v86d userspace helper.");
2062
2063MODULE_LICENSE("GPL");
2064MODULE_AUTHOR("Michal Januszewski <spock@gentoo.org>");
2065MODULE_DESCRIPTION("Framebuffer driver for VBE2.0+ compliant graphics boards");
2066