FreeBSD/Linux Kernel Cross Reference
sys/dev/fb/fb.c
1 /*-
2 * Copyright (c) 1999 Kazutaka YOKOTA <yokota@zodiac.mech.utsunomiya-u.ac.jp>
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer as
10 * the first lines of this file unmodified.
11 * 2. Redistributions in binary form must reproduce the above copyright
12 * notice, this list of conditions and the following disclaimer in the
13 * documentation and/or other materials provided with the distribution.
14 * 3. The name of the author may not be used to endorse or promote products
15 * derived from this software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE AUTHORS ``AS IS'' AND ANY EXPRESS OR
18 * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
19 * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
20 * IN NO EVENT SHALL THE AUTHORS BE LIABLE FOR ANY DIRECT, INDIRECT,
21 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
22 * NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
26 * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
27 *
28 * $FreeBSD$
29 */
30
31 #include "opt_fb.h"
32
33 #include <sys/param.h>
34 #include <sys/systm.h>
35 #include <sys/conf.h>
36 #include <sys/bus.h>
37 #include <sys/kernel.h>
38 #include <sys/malloc.h>
39 #include <sys/uio.h>
40 #include <sys/fbio.h>
41
42 #include <vm/vm.h>
43 #include <vm/pmap.h>
44
45 #include <dev/fb/fbreg.h>
46
47 /* local arrays */
48
49 /*
50 * We need at least one entry each in order to initialize a video card
51 * for the kernel console. The arrays will be increased dynamically
52 * when necessary.
53 */
54
55 static int vid_malloc;
56 static int adapters = 1;
57 static video_adapter_t *adp_ini;
58 static video_adapter_t **adapter = &adp_ini;
59 static video_switch_t *vidsw_ini;
60 video_switch_t **vidsw = &vidsw_ini;
61
62 #ifdef FB_INSTALL_CDEV
63 static struct cdevsw *vidcdevsw_ini;
64 static struct cdevsw **vidcdevsw = &vidcdevsw_ini;
65 #endif
66
67 #define ARRAY_DELTA 4
68
69 static int
70 vid_realloc_array(void)
71 {
72 video_adapter_t **new_adp;
73 video_switch_t **new_vidsw;
74 #ifdef FB_INSTALL_CDEV
75 struct cdevsw **new_cdevsw;
76 #endif
77 int newsize;
78 int s;
79
80 if (!vid_malloc)
81 return ENOMEM;
82
83 s = spltty();
84 newsize = ((adapters + ARRAY_DELTA)/ARRAY_DELTA)*ARRAY_DELTA;
85 new_adp = malloc(sizeof(*new_adp)*newsize, M_DEVBUF, M_WAITOK);
86 new_vidsw = malloc(sizeof(*new_vidsw)*newsize, M_DEVBUF, M_WAITOK);
87 #ifdef FB_INSTALL_CDEV
88 new_cdevsw = malloc(sizeof(*new_cdevsw)*newsize, M_DEVBUF, M_WAITOK);
89 #endif
90 bzero(new_adp, sizeof(*new_adp)*newsize);
91 bzero(new_vidsw, sizeof(*new_vidsw)*newsize);
92 bcopy(adapter, new_adp, sizeof(*adapter)*adapters);
93 bcopy(vidsw, new_vidsw, sizeof(*vidsw)*adapters);
94 #ifdef FB_INSTALL_CDEV
95 bzero(new_cdevsw, sizeof(*new_cdevsw)*newsize);
96 bcopy(vidcdevsw, new_cdevsw, sizeof(*vidcdevsw)*adapters);
97 #endif
98 if (adapters > 1) {
99 free(adapter, M_DEVBUF);
100 free(vidsw, M_DEVBUF);
101 #ifdef FB_INSTALL_CDEV
102 free(vidcdevsw, M_DEVBUF);
103 #endif
104 }
105 adapter = new_adp;
106 vidsw = new_vidsw;
107 #ifdef FB_INSTALL_CDEV
108 vidcdevsw = new_cdevsw;
109 #endif
110 adapters = newsize;
111 splx(s);
112
113 if (bootverbose)
114 printf("fb: new array size %d\n", adapters);
115
116 return 0;
117 }
118
119 static void
120 vid_malloc_init(void *arg)
121 {
122 vid_malloc = TRUE;
123 }
124
125 SYSINIT(vid_mem, SI_SUB_KMEM, SI_ORDER_ANY, vid_malloc_init, NULL);
126
127 /*
128 * Low-level frame buffer driver functions
129 * frame buffer subdrivers, such as the VGA driver, call these functions
130 * to initialize the video_adapter structure and register it to the virtual
131 * frame buffer driver `fb'.
132 */
133
134 /* initialize the video_adapter_t structure */
135 void
136 vid_init_struct(video_adapter_t *adp, char *name, int type, int unit)
137 {
138 adp->va_flags = 0;
139 adp->va_name = name;
140 adp->va_type = type;
141 adp->va_unit = unit;
142 }
143
144 /* Register a video adapter */
145 int
146 vid_register(video_adapter_t *adp)
147 {
148 const video_driver_t **list;
149 const video_driver_t *p;
150 int index;
151
152 for (index = 0; index < adapters; ++index) {
153 if (adapter[index] == NULL)
154 break;
155 }
156 if (index >= adapters) {
157 if (vid_realloc_array())
158 return -1;
159 }
160
161 adp->va_index = index;
162 adp->va_token = NULL;
163 list = (const video_driver_t **)videodriver_set.ls_items;
164 while ((p = *list++) != NULL) {
165 if (strcmp(p->name, adp->va_name) == 0) {
166 adapter[index] = adp;
167 vidsw[index] = p->vidsw;
168 return index;
169 }
170 }
171
172 return -1;
173 }
174
175 int
176 vid_unregister(video_adapter_t *adp)
177 {
178 if ((adp->va_index < 0) || (adp->va_index >= adapters))
179 return ENOENT;
180 if (adapter[adp->va_index] != adp)
181 return ENOENT;
182
183 adapter[adp->va_index] = NULL;
184 vidsw[adp->va_index] = NULL;
185 return 0;
186 }
187
188 /* Get video I/O function table */
189 video_switch_t
190 *vid_get_switch(char *name)
191 {
192 const video_driver_t **list;
193 const video_driver_t *p;
194
195 list = (const video_driver_t **)videodriver_set.ls_items;
196 while ((p = *list++) != NULL) {
197 if (strcmp(p->name, name) == 0)
198 return p->vidsw;
199 }
200
201 return NULL;
202 }
203
204 /*
205 * Video card client functions
206 * Video card clients, such as the console driver `syscons' and the frame
207 * buffer cdev driver, use these functions to claim and release a card for
208 * exclusive use.
209 */
210
211 /* find the video card specified by a driver name and a unit number */
212 int
213 vid_find_adapter(char *driver, int unit)
214 {
215 int i;
216
217 for (i = 0; i < adapters; ++i) {
218 if (adapter[i] == NULL)
219 continue;
220 if (strcmp("*", driver) && strcmp(adapter[i]->va_name, driver))
221 continue;
222 if ((unit != -1) && (adapter[i]->va_unit != unit))
223 continue;
224 return i;
225 }
226 return -1;
227 }
228
229 /* allocate a video card */
230 int
231 vid_allocate(char *driver, int unit, void *id)
232 {
233 int index;
234 int s;
235
236 s = spltty();
237 index = vid_find_adapter(driver, unit);
238 if (index >= 0) {
239 if (adapter[index]->va_token) {
240 splx(s);
241 return -1;
242 }
243 adapter[index]->va_token = id;
244 }
245 splx(s);
246 return index;
247 }
248
249 int
250 vid_release(video_adapter_t *adp, void *id)
251 {
252 int error;
253 int s;
254
255 s = spltty();
256 if (adp->va_token == NULL) {
257 error = EINVAL;
258 } else if (adp->va_token != id) {
259 error = EPERM;
260 } else {
261 adp->va_token = NULL;
262 error = 0;
263 }
264 splx(s);
265 return error;
266 }
267
268 /* Get a video adapter structure */
269 video_adapter_t
270 *vid_get_adapter(int index)
271 {
272 if ((index < 0) || (index >= adapters))
273 return NULL;
274 return adapter[index];
275 }
276
277 /* Configure drivers: this is a backdoor for the console driver XXX */
278 int
279 vid_configure(int flags)
280 {
281 const video_driver_t **list;
282 const video_driver_t *p;
283
284 list = (const video_driver_t **)videodriver_set.ls_items;
285 while ((p = *list++) != NULL) {
286 if (p->configure != NULL)
287 (*p->configure)(flags);
288 }
289
290 return 0;
291 }
292
293 /*
294 * Virtual frame buffer cdev driver functions
295 * The virtual frame buffer driver dispatches driver functions to
296 * appropriate subdrivers.
297 */
298
299 #define FB_DRIVER_NAME "fb"
300
301 #ifdef FB_INSTALL_CDEV
302
303 #if experimental
304
305 static devclass_t fb_devclass;
306
307 static int fbprobe(device_t dev);
308 static int fbattach(device_t dev);
309
310 static device_method_t fb_methods[] = {
311 DEVMETHOD(device_probe, fbprobe),
312 DEVMETHOD(device_attach, fbattach),
313
314 DEVMETHOD(bus_print_child, bus_generic_print_child),
315 { 0, 0 }
316 };
317
318 static driver_t fb_driver = {
319 FB_DRIVER_NAME,
320 fb_methods,
321 0,
322 };
323
324 static int
325 fbprobe(device_t dev)
326 {
327 int unit;
328
329 unit = device_get_unit(dev);
330 if (unit >= adapters)
331 return ENXIO;
332 if (adapter[unit] == NULL)
333 return ENXIO;
334
335 device_set_desc(dev, "generic frame buffer");
336 return 0;
337 }
338
339 static int
340 fbattach(device_t dev)
341 {
342 printf("fbattach: about to attach children\n");
343 bus_generic_attach(dev);
344 return 0;
345 }
346
347 #endif /* experimental */
348
349 #define FB_UNIT(dev) minor(dev)
350 #define FB_MKMINOR(unit) (u)
351
352 static d_open_t fbopen;
353 static d_close_t fbclose;
354 static d_read_t fbread;
355 static d_write_t fbwrite;
356 static d_ioctl_t fbioctl;
357 static d_mmap_t fbmmap;
358
359 #define CDEV_MAJOR 123 /* XXX */
360
361 static struct cdevsw fb_cdevsw = {
362 /* open */ fbopen,
363 /* close */ fbclose,
364 /* read */ fbread,
365 /* write */ fbwrite,
366 /* ioctl */ fbioctl,
367 /* poll */ nopoll,
368 /* mmap */ fbmmap,
369 /* strategy */ nostrategy,
370 /* name */ FB_DRIVER_NAME,
371 /* maj */ CDEV_MAJOR,
372 /* dump */ nodump,
373 /* psize */ nopsize,
374 /* flags */ 0,
375 /* bmaj */ -1
376 };
377
378 static void
379 vfbattach(void *arg)
380 {
381 static int fb_devsw_installed = FALSE;
382
383 if (!fb_devsw_installed) {
384 cdevsw_add(&fb_cdevsw);
385 fb_devsw_installed = TRUE;
386 }
387 }
388
389 PSEUDO_SET(vfbattach, fb);
390
391 int
392 fb_attach(dev_t dev, video_adapter_t *adp, struct cdevsw *cdevsw)
393 {
394 int s;
395
396 if (adp->va_index >= adapters)
397 return EINVAL;
398 if (adapter[adp->va_index] != adp)
399 return EINVAL;
400
401 s = spltty();
402 adp->va_minor = minor(dev);
403 vidcdevsw[adp->va_index] = cdevsw;
404 splx(s);
405
406 printf("fb%d at %s%d\n", adp->va_index, adp->va_name, adp->va_unit);
407 return 0;
408 }
409
410 int
411 fb_detach(dev_t dev, video_adapter_t *adp, struct cdevsw *cdevsw)
412 {
413 int s;
414
415 if (adp->va_index >= adapters)
416 return EINVAL;
417 if (adapter[adp->va_index] != adp)
418 return EINVAL;
419 if (vidcdevsw[adp->va_index] != cdevsw)
420 return EINVAL;
421
422 s = spltty();
423 vidcdevsw[adp->va_index] = NULL;
424 splx(s);
425 return 0;
426 }
427
428 static int
429 fbopen(dev_t dev, int flag, int mode, struct proc *p)
430 {
431 int unit;
432
433 unit = FB_UNIT(dev);
434 if (unit >= adapters)
435 return ENXIO;
436 if (vidcdevsw[unit] == NULL)
437 return ENXIO;
438 return (*vidcdevsw[unit]->d_open)(makedev(0, adapter[unit]->va_minor),
439 flag, mode, p);
440 }
441
442 static int
443 fbclose(dev_t dev, int flag, int mode, struct proc *p)
444 {
445 int unit;
446
447 unit = FB_UNIT(dev);
448 if (vidcdevsw[unit] == NULL)
449 return ENXIO;
450 return (*vidcdevsw[unit]->d_close)(makedev(0, adapter[unit]->va_minor),
451 flag, mode, p);
452 }
453
454 static int
455 fbread(dev_t dev, struct uio *uio, int flag)
456 {
457 int unit;
458
459 unit = FB_UNIT(dev);
460 if (vidcdevsw[unit] == NULL)
461 return ENXIO;
462 return (*vidcdevsw[unit]->d_read)(makedev(0, adapter[unit]->va_minor),
463 uio, flag);
464 }
465
466 static int
467 fbwrite(dev_t dev, struct uio *uio, int flag)
468 {
469 int unit;
470
471 unit = FB_UNIT(dev);
472 if (vidcdevsw[unit] == NULL)
473 return ENXIO;
474 return (*vidcdevsw[unit]->d_write)(makedev(0, adapter[unit]->va_minor),
475 uio, flag);
476 }
477
478 static int
479 fbioctl(dev_t dev, u_long cmd, caddr_t arg, int flag, struct proc *p)
480 {
481 int unit;
482
483 unit = FB_UNIT(dev);
484 if (vidcdevsw[unit] == NULL)
485 return ENXIO;
486 return (*vidcdevsw[unit]->d_ioctl)(makedev(0, adapter[unit]->va_minor),
487 cmd, arg, flag, p);
488 }
489
490 static int
491 fbmmap(dev_t dev, vm_offset_t offset, int nprot)
492 {
493 int unit;
494
495 unit = FB_UNIT(dev);
496 if (vidcdevsw[unit] == NULL)
497 return ENXIO;
498 return (*vidcdevsw[unit]->d_mmap)(makedev(0, adapter[unit]->va_minor),
499 offset, nprot);
500 }
501
502 #if experimental
503 DEV_DRIVER_MODULE(fb, ???, fb_driver, fb_devclass, fb_cdevsw, 0, 0);
504 #endif
505
506 /*
507 * Generic frame buffer cdev driver functions
508 * Frame buffer subdrivers may call these functions to implement common
509 * driver functions.
510 */
511
512 int genfbopen(genfb_softc_t *sc, video_adapter_t *adp, int flag, int mode,
513 struct proc *p)
514 {
515 int s;
516
517 s = spltty();
518 if (!(sc->gfb_flags & FB_OPEN))
519 sc->gfb_flags |= FB_OPEN;
520 splx(s);
521 return 0;
522 }
523
524 int genfbclose(genfb_softc_t *sc, video_adapter_t *adp, int flag, int mode,
525 struct proc *p)
526 {
527 int s;
528
529 s = spltty();
530 sc->gfb_flags &= ~FB_OPEN;
531 splx(s);
532 return 0;
533 }
534
535 int genfbread(genfb_softc_t *sc, video_adapter_t *adp, struct uio *uio,
536 int flag)
537 {
538 int size;
539 int offset;
540 int error;
541 int len;
542
543 error = 0;
544 size = adp->va_buffer_size/adp->va_info.vi_planes;
545 while (uio->uio_resid > 0) {
546 if (uio->uio_offset >= size)
547 break;
548 offset = uio->uio_offset%adp->va_window_size;
549 len = imin(uio->uio_resid, size - uio->uio_offset);
550 len = imin(len, adp->va_window_size - offset);
551 if (len <= 0)
552 break;
553 (*vidsw[adp->va_index]->set_win_org)(adp, uio->uio_offset);
554 error = uiomove((caddr_t)(adp->va_window + offset), len, uio);
555 if (error)
556 break;
557 }
558 return error;
559 }
560
561 int genfbwrite(genfb_softc_t *sc, video_adapter_t *adp, struct uio *uio,
562 int flag)
563 {
564 return ENODEV;
565 }
566
567 int genfbioctl(genfb_softc_t *sc, video_adapter_t *adp, u_long cmd,
568 caddr_t arg, int flag, struct proc *p)
569 {
570 int error;
571
572 if (adp == NULL) /* XXX */
573 return ENXIO;
574 error = (*vidsw[adp->va_index]->ioctl)(adp, cmd, arg);
575 if (error == ENOIOCTL)
576 error = ENODEV;
577 return error;
578 }
579
580 int genfbmmap(genfb_softc_t *sc, video_adapter_t *adp, vm_offset_t offset,
581 int prot)
582 {
583 return (*vidsw[adp->va_index]->mmap)(adp, offset, prot);
584 }
585
586 #endif /* FB_INSTALL_CDEV */
587
588 static char
589 *adapter_name(int type)
590 {
591 static struct {
592 int type;
593 char *name;
594 } names[] = {
595 { KD_MONO, "MDA" },
596 { KD_HERCULES, "Hercules" },
597 { KD_CGA, "CGA" },
598 { KD_EGA, "EGA" },
599 { KD_VGA, "VGA" },
600 { KD_PC98, "PC-98x1" },
601 { KD_TGA, "TGA" },
602 { -1, "Unknown" },
603 };
604 int i;
605
606 for (i = 0; names[i].type != -1; ++i)
607 if (names[i].type == type)
608 break;
609 return names[i].name;
610 }
611
612 /*
613 * Generic low-level frame buffer functions
614 * The low-level functions in the frame buffer subdriver may use these
615 * functions.
616 */
617
618 void
619 fb_dump_adp_info(char *driver, video_adapter_t *adp, int level)
620 {
621 if (level <= 0)
622 return;
623
624 printf("%s%d: %s%d, %s, type:%s (%d), flags:0x%x\n",
625 FB_DRIVER_NAME, adp->va_index, driver, adp->va_unit, adp->va_name,
626 adapter_name(adp->va_type), adp->va_type, adp->va_flags);
627 printf("%s%d: port:0x%x-0x%x, crtc:0x%x, mem:0x%x 0x%x\n",
628 FB_DRIVER_NAME, adp->va_index,
629 adp->va_io_base, adp->va_io_base + adp->va_io_size - 1,
630 adp->va_crtc_addr, adp->va_mem_base, adp->va_mem_size);
631 printf("%s%d: init mode:%d, bios mode:%d, current mode:%d\n",
632 FB_DRIVER_NAME, adp->va_index,
633 adp->va_initial_mode, adp->va_initial_bios_mode, adp->va_mode);
634 printf("%s%d: window:%p size:%dk gran:%dk, buf:%p size:%dk\n",
635 FB_DRIVER_NAME, adp->va_index,
636 (void *)adp->va_window, (int)adp->va_window_size/1024,
637 (int)adp->va_window_gran/1024, (void *)adp->va_buffer,
638 (int)adp->va_buffer_size/1024);
639 }
640
641 void
642 fb_dump_mode_info(char *driver, video_adapter_t *adp, video_info_t *info,
643 int level)
644 {
645 if (level <= 0)
646 return;
647
648 printf("%s%d: %s, mode:%d, flags:0x%x ",
649 driver, adp->va_unit, adp->va_name, info->vi_mode, info->vi_flags);
650 if (info->vi_flags & V_INFO_GRAPHICS)
651 printf("G %dx%dx%d, %d plane(s), font:%dx%d, ",
652 info->vi_width, info->vi_height,
653 info->vi_depth, info->vi_planes,
654 info->vi_cwidth, info->vi_cheight);
655 else
656 printf("T %dx%d, font:%dx%d, ",
657 info->vi_width, info->vi_height,
658 info->vi_cwidth, info->vi_cheight);
659 printf("win:0x%x\n", info->vi_window);
660 }
661
662 int
663 fb_type(int adp_type)
664 {
665 static struct {
666 int fb_type;
667 int va_type;
668 } types[] = {
669 { FBTYPE_MDA, KD_MONO },
670 { FBTYPE_HERCULES, KD_HERCULES },
671 { FBTYPE_CGA, KD_CGA },
672 { FBTYPE_EGA, KD_EGA },
673 { FBTYPE_VGA, KD_VGA },
674 { FBTYPE_PC98, KD_PC98 },
675 { FBTYPE_TGA, KD_TGA },
676 };
677 int i;
678
679 for (i = 0; i < sizeof(types)/sizeof(types[0]); ++i) {
680 if (types[i].va_type == adp_type)
681 return types[i].fb_type;
682 }
683 return -1;
684 }
685
686 int
687 fb_commonioctl(video_adapter_t *adp, u_long cmd, caddr_t arg)
688 {
689 int error;
690 int s;
691
692 /* assert(adp != NULL) */
693
694 error = 0;
695 s = spltty();
696
697 switch (cmd) {
698
699 case FBIO_ADAPTER: /* get video adapter index */
700 *(int *)arg = adp->va_index;
701 break;
702
703 case FBIO_ADPTYPE: /* get video adapter type */
704 *(int *)arg = adp->va_type;
705 break;
706
707 case FBIO_ADPINFO: /* get video adapter info */
708 ((video_adapter_info_t *)arg)->va_index = adp->va_index;
709 ((video_adapter_info_t *)arg)->va_type = adp->va_type;
710 bcopy(adp->va_name, ((video_adapter_info_t *)arg)->va_name,
711 imin(strlen(adp->va_name) + 1,
712 sizeof(((video_adapter_info_t *)arg)->va_name)));
713 ((video_adapter_info_t *)arg)->va_unit = adp->va_unit;
714 ((video_adapter_info_t *)arg)->va_flags = adp->va_flags;
715 ((video_adapter_info_t *)arg)->va_io_base = adp->va_io_base;
716 ((video_adapter_info_t *)arg)->va_io_size = adp->va_io_size;
717 ((video_adapter_info_t *)arg)->va_crtc_addr = adp->va_crtc_addr;
718 ((video_adapter_info_t *)arg)->va_mem_base = adp->va_mem_base;
719 ((video_adapter_info_t *)arg)->va_mem_size = adp->va_mem_size;
720 ((video_adapter_info_t *)arg)->va_window
721 #ifdef __i386__
722 = vtophys(adp->va_window);
723 #else
724 = adp->va_window;
725 #endif
726 ((video_adapter_info_t *)arg)->va_window_size
727 = adp->va_window_size;
728 ((video_adapter_info_t *)arg)->va_window_gran
729 = adp->va_window_gran;
730 ((video_adapter_info_t *)arg)->va_window_orig
731 = adp->va_window_orig;
732 ((video_adapter_info_t *)arg)->va_unused0
733 #ifdef __i386__
734 = (adp->va_buffer) ? vtophys(adp->va_buffer) : 0;
735 #else
736 = adp->va_buffer;
737 #endif
738 ((video_adapter_info_t *)arg)->va_buffer_size
739 = adp->va_buffer_size;
740 ((video_adapter_info_t *)arg)->va_mode = adp->va_mode;
741 ((video_adapter_info_t *)arg)->va_initial_mode
742 = adp->va_initial_mode;
743 ((video_adapter_info_t *)arg)->va_initial_bios_mode
744 = adp->va_initial_bios_mode;
745 ((video_adapter_info_t *)arg)->va_line_width
746 = adp->va_line_width;
747 ((video_adapter_info_t *)arg)->va_disp_start.x
748 = adp->va_disp_start.x;
749 ((video_adapter_info_t *)arg)->va_disp_start.y
750 = adp->va_disp_start.y;
751 break;
752
753 case FBIO_MODEINFO: /* get mode information */
754 error = (*vidsw[adp->va_index]->get_info)(adp,
755 ((video_info_t *)arg)->vi_mode,
756 (video_info_t *)arg);
757 if (error)
758 error = ENODEV;
759 break;
760
761 case FBIO_FINDMODE: /* find a matching video mode */
762 error = (*vidsw[adp->va_index]->query_mode)(adp,
763 (video_info_t *)arg);
764 break;
765
766 case FBIO_GETMODE: /* get video mode */
767 *(int *)arg = adp->va_mode;
768 break;
769
770 case FBIO_SETMODE: /* set video mode */
771 error = (*vidsw[adp->va_index]->set_mode)(adp, *(int *)arg);
772 if (error)
773 error = ENODEV; /* EINVAL? */
774 break;
775
776 case FBIO_GETWINORG: /* get frame buffer window origin */
777 *(u_int *)arg = adp->va_window_orig;
778 break;
779
780 case FBIO_GETDISPSTART: /* get display start address */
781 ((video_display_start_t *)arg)->x = adp->va_disp_start.x;
782 ((video_display_start_t *)arg)->y = adp->va_disp_start.y;
783 break;
784
785 case FBIO_GETLINEWIDTH: /* get scan line width in bytes */
786 *(u_int *)arg = adp->va_line_width;
787 break;
788
789 case FBIO_GETPALETTE: /* get color palette */
790 case FBIO_SETPALETTE: /* set color palette */
791 /* XXX */
792
793 case FBIOPUTCMAP:
794 case FBIOGETCMAP:
795 /* XXX */
796
797 case FBIO_SETWINORG: /* set frame buffer window origin */
798 case FBIO_SETDISPSTART: /* set display start address */
799 case FBIO_SETLINEWIDTH: /* set scan line width in pixel */
800
801 case FBIOGTYPE:
802 case FBIOGATTR:
803 case FBIOSVIDEO:
804 case FBIOGVIDEO:
805 case FBIOSCURSOR:
806 case FBIOGCURSOR:
807 case FBIOSCURPOS:
808 case FBIOGCURPOS:
809 case FBIOGCURMAX:
810
811 default:
812 error = ENODEV;
813 break;
814 }
815
816 splx(s);
817 return error;
818 }
Cache object: 0faf4bb1b9ef001482fba9b7ea783925
|