2 * udlfb.c -- Framebuffer driver for DisplayLink USB controller
4 * Copyright (C) 2009 Roberto De Ioris <roberto@unbit.it>
5 * Copyright (C) 2009 Jaya Kumar <jayakumar.lkml@gmail.com>
7 * This file is subject to the terms and conditions of the GNU General Public
8 * License v2. See the file COPYING in the main directory of this archive for
11 * Layout is based on skeletonfb by James Simmons and Geert Uytterhoeven,
12 * usb-skeleton by GregKH.
14 * Device-specific portions based on information from Displaylink, with work
15 * from Florian Echtler, Henrik Bjerregaard Pedersen, and others.
18 #include <linux/module.h>
19 #include <linux/kernel.h>
20 #include <linux/init.h>
21 #include <linux/usb.h>
22 #include <linux/uaccess.h>
25 #include <linux/mutex.h>
26 #include <linux/vmalloc.h>
30 #define DRIVER_VERSION "DisplayLink Framebuffer Driver 0.4.1"
32 static struct fb_fix_screeninfo dlfb_fix
= {
33 .id
= "displaylinkfb",
34 .type
= FB_TYPE_PACKED_PIXELS
,
35 .visual
= FB_VISUAL_TRUECOLOR
,
39 .accel
= FB_ACCEL_NONE
,
42 #define NR_USB_REQUEST_I2C_SUB_IO 0x02
43 #define NR_USB_REQUEST_CHANNEL 0x12
46 * Inserts a specific DisplayLink controller command into the provided
49 static char *insert_command(char *buf
, u8 reg
, u8 val
)
58 static char *insert_vidreg_lock(char *buf
)
60 return insert_command(buf
, 0xFF, 0x00);
63 static char *insert_vidreg_unlock(char *buf
)
65 return insert_command(buf
, 0xFF, 0xFF);
69 * Once you send this command, the DisplayLink framebuffer gets driven to the
72 static char *insert_enable_hvsync(char *buf
)
74 return insert_command(buf
, 0x1F, 0x00);
77 static char *insert_set_color_depth(char *buf
, u8 selection
)
79 return insert_command(buf
, 0x00, selection
);
82 static char *insert_set_base16bpp(char *wrptr
, u32 base
)
84 /* the base pointer is 16 bits wide, 0x20 is hi byte. */
85 wrptr
= insert_command(wrptr
, 0x20, base
>> 16);
86 wrptr
= insert_command(wrptr
, 0x21, base
>> 8);
87 return insert_command(wrptr
, 0x22, base
);
90 static char *insert_set_base8bpp(char *wrptr
, u32 base
)
92 wrptr
= insert_command(wrptr
, 0x26, base
>> 16);
93 wrptr
= insert_command(wrptr
, 0x27, base
>> 8);
94 return insert_command(wrptr
, 0x28, base
);
97 static char *insert_command_16(char *wrptr
, u8 reg
, u16 value
)
99 wrptr
= insert_command(wrptr
, reg
, value
>> 8);
100 return insert_command(wrptr
, reg
+1, value
);
104 * This is kind of weird because the controller takes some
105 * register values in a different byte order than other registers.
107 static char *insert_command_16be(char *wrptr
, u8 reg
, u16 value
)
109 wrptr
= insert_command(wrptr
, reg
, value
);
110 return insert_command(wrptr
, reg
+1, value
>> 8);
114 * LFSR is linear feedback shift register. The reason we have this is
115 * because the display controller needs to minimize the clock depth of
116 * various counters used in the display path. So this code reverses the
117 * provided value into the lfsr16 value by counting backwards to get
118 * the value that needs to be set in the hardware comparator to get the
119 * same actual count. This makes sense once you read above a couple of
120 * times and think about it from a hardware perspective.
122 static u16
lfsr16(u16 actual_count
)
124 u32 lv
= 0xFFFF; /* This is the lfsr value that the hw starts with */
126 while (actual_count
--) {
128 (((lv
>> 15) ^ (lv
>> 4) ^ (lv
>> 2) ^ (lv
>> 1)) & 1))
136 * This does LFSR conversion on the value that is to be written.
137 * See LFSR explanation above for more detail.
139 static char *insert_command_lfsr16(char *wrptr
, u8 reg
, u16 value
)
141 return insert_command_16(wrptr
, reg
, lfsr16(value
));
145 * This takes a standard fbdev screeninfo struct and all of its monitor mode
146 * details and converts them into the DisplayLink equivalent register commands.
148 static char *insert_set_vid_cmds(char *wrptr
, struct fb_var_screeninfo
*var
)
155 /* x display start */
156 xds
= var
->left_margin
+ var
->hsync_len
;
157 wrptr
= insert_command_lfsr16(wrptr
, 0x01, xds
);
159 xde
= xds
+ var
->xres
;
160 wrptr
= insert_command_lfsr16(wrptr
, 0x03, xde
);
162 /* y display start */
163 yds
= var
->upper_margin
+ var
->vsync_len
;
164 wrptr
= insert_command_lfsr16(wrptr
, 0x05, yds
);
166 yde
= yds
+ var
->yres
;
167 wrptr
= insert_command_lfsr16(wrptr
, 0x07, yde
);
169 /* x end count is active + blanking - 1 */
170 wrptr
= insert_command_lfsr16(wrptr
, 0x09, xde
+ var
->right_margin
- 1);
172 /* libdlo hardcodes hsync start to 1 */
173 wrptr
= insert_command_lfsr16(wrptr
, 0x0B, 1);
175 /* hsync end is width of sync pulse + 1 */
176 wrptr
= insert_command_lfsr16(wrptr
, 0x0D, var
->hsync_len
+ 1);
178 /* hpixels is active pixels */
179 wrptr
= insert_command_16(wrptr
, 0x0F, var
->xres
);
181 /* yendcount is vertical active + vertical blanking */
182 yec
= var
->yres
+ var
->upper_margin
+ var
->lower_margin
+
184 wrptr
= insert_command_lfsr16(wrptr
, 0x11, yec
);
186 /* libdlo hardcodes vsync start to 0 */
187 wrptr
= insert_command_lfsr16(wrptr
, 0x13, 0);
189 /* vsync end is width of vsync pulse */
190 wrptr
= insert_command_lfsr16(wrptr
, 0x15, var
->vsync_len
);
192 /* vpixels is active pixels */
193 wrptr
= insert_command_16(wrptr
, 0x17, var
->yres
);
195 /* convert picoseconds to 5kHz multiple for pclk5k = x * 1E12/5k */
196 wrptr
= insert_command_16be(wrptr
, 0x1B, 200*1000*1000/var
->pixclock
);
202 * This takes a standard fbdev screeninfo struct that was fetched or prepared
203 * and then generates the appropriate command sequence that then drives the
204 * display controller.
206 static int dlfb_set_video_mode(struct dlfb_data
*dev
,
207 struct fb_var_screeninfo
*var
)
217 * This first section has to do with setting the base address on the
218 * controller * associated with the display. There are 2 base
219 * pointers, currently, we only * use the 16 bpp segment.
221 wrptr
= insert_vidreg_lock(buf
);
222 wrptr
= insert_set_color_depth(wrptr
, 0x00);
223 /* set base for 16bpp segment to 0 */
224 wrptr
= insert_set_base16bpp(wrptr
, 0);
225 /* set base for 8bpp segment to end of fb */
226 wrptr
= insert_set_base8bpp(wrptr
, dev
->info
->fix
.smem_len
);
228 wrptr
= insert_set_vid_cmds(wrptr
, var
);
229 wrptr
= insert_enable_hvsync(wrptr
);
230 wrptr
= insert_vidreg_unlock(wrptr
);
232 writesize
= wrptr
- buf
;
234 mutex_lock(&dev
->bulk_mutex
);
235 if (!dev
->interface
) { /* disconnect() was called */
236 mutex_unlock(&dev
->bulk_mutex
);
241 retval
= dlfb_bulk_msg(dev
, writesize
);
242 mutex_unlock(&dev
->bulk_mutex
);
244 dev_err(&dev
->udev
->dev
, "Problem %d with submit write bulk.\n",
256 * This is necessary before we can communicate with the display controller.
258 static int dlfb_select_std_channel(struct dlfb_data
*dev
)
261 u8 set_def_chn
[] = { 0x57, 0xCD, 0xDC, 0xA7,
262 0x1C, 0x88, 0x5E, 0x15,
263 0x60, 0xFE, 0xC6, 0x97,
264 0x16, 0x3D, 0x47, 0xF2 };
266 ret
= usb_control_msg(dev
->udev
, usb_sndctrlpipe(dev
->udev
, 0),
267 NR_USB_REQUEST_CHANNEL
,
268 (USB_DIR_OUT
| USB_TYPE_VENDOR
), 0, 0,
269 set_def_chn
, sizeof(set_def_chn
), USB_CTRL_SET_TIMEOUT
);
275 * Query EDID from the handware, then hand it off to fbdev's edid parse
276 * routine which should give us back a filled in screeninfo structure.
278 static int dlfb_get_var_from_edid(struct dlfb_data
*dev
,
279 struct fb_var_screeninfo
*var
)
284 ret
= fb_parse_edid(dev
->edid
, var
);
289 static int dlfb_mmap(struct fb_info
*info
, struct vm_area_struct
*vma
)
291 unsigned long start
= vma
->vm_start
;
292 unsigned long size
= vma
->vm_end
- vma
->vm_start
;
293 unsigned long offset
= vma
->vm_pgoff
<< PAGE_SHIFT
;
294 unsigned long page
, pos
;
296 printk("MMAP: %lu %u\n", offset
+ size
, info
->fix
.smem_len
);
298 if (offset
+ size
> info
->fix
.smem_len
)
301 pos
= (unsigned long)info
->fix
.smem_start
+ offset
;
304 page
= vmalloc_to_pfn((void *)pos
);
305 if (remap_pfn_range(vma
, start
, page
, PAGE_SIZE
, PAGE_SHARED
))
310 if (size
> PAGE_SIZE
)
316 vma
->vm_flags
|= VM_RESERVED
; /* avoid to swap out this VMA */
321 /* ioctl structure */
329 * There are many DisplayLink-based products, all with unique PIDs. We are able
330 * to support all volume ones (circa 2009) with a single driver, so we match
331 * globally on VID. TODO: Probe() needs to detect when we might be running
332 * "future" chips, and bail on those, so a compatible driver can match.
334 static struct usb_device_id id_table
[] = {
335 {.idVendor
= 0x17e9, .match_flags
= USB_DEVICE_ID_MATCH_VENDOR
,},
338 MODULE_DEVICE_TABLE(usb
, id_table
);
340 static struct usb_driver dlfb_driver
;
342 /* thanks to Henrik Bjerregaard Pedersen for this function */
343 static char *rle_compress16(uint16_t * src
, char *dst
, int rem
)
348 char *end_if_raw
= dst
+ 6 + 2 * rem
;
350 dst
+= 6; /* header will be filled in if RLE is worth it */
352 while (rem
&& dst
< end_if_raw
) {
353 char *start
= (char *)src
;
358 while (rem
&& *src
== pix0
)
369 Thanks to Henrik Bjerregaard Pedersen for rle implementation
370 and code refactoring. Next step is huffman compression.
374 image_blit(struct dlfb_data
*dev_info
, int x
, int y
, int width
, int height
,
382 int firstdiff
, thistime
;
386 if (x
+ width
> dev_info
->info
->var
.xres
)
389 if (y
+ height
> dev_info
->info
->var
.yres
)
392 mutex_lock(&dev_info
->bulk_mutex
);
395 dev_info
->base16
+ ((dev_info
->info
->var
.xres
* 2 * y
) + (x
* 2));
397 data
+= (dev_info
->info
->var
.xres
* 2 * y
) + (x
* 2);
399 /* printk("IMAGE_BLIT\n"); */
401 bufptr
= dev_info
->buf
;
403 for (i
= y
; i
< y
+ height
; i
++) {
405 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
406 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
407 bufptr
= dev_info
->buf
;
412 /* printk("WRITING LINE %d\n", i); */
416 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
418 dlfb_bulk_msg(dev_info
,
419 bufptr
- dev_info
->buf
);
420 bufptr
= dev_info
->buf
;
422 /* number of pixels to consider this time */
427 if (dev_info
->backing_buffer
) {
428 /* find first pixel that has changed */
430 for (j
= 0; j
< thistime
* 2; j
++) {
431 if (dev_info
->backing_buffer
432 [base
- dev_info
->base16
+ j
]
444 if (firstdiff
>= 0) {
448 rle_compress16((uint16_t *) (data
+
451 thistime
- firstdiff
);
454 bufptr
+ 6 + 2 * (thistime
- firstdiff
)) {
460 firstdiff
* 2) >> 16);
462 (char)((base
+ firstdiff
* 2) >> 8);
464 (char)(base
+ firstdiff
* 2);
465 bufptr
[5] = thistime
- firstdiff
;
470 /* fallback to raw (or other?) */
476 firstdiff
* 2) >> 16);
478 (char)((base
+ firstdiff
* 2) >> 8);
480 (char)(base
+ firstdiff
* 2);
481 *bufptr
++ = thistime
- firstdiff
;
482 for (j
= firstdiff
* 2;
483 j
< thistime
* 2; j
+= 2) {
484 *bufptr
++ = data
[j
+ 1];
490 base
+= thistime
* 2;
491 data
+= thistime
* 2;
495 if (dev_info
->backing_buffer
)
496 memcpy(dev_info
->backing_buffer
+
497 (base
- dev_info
->base16
) -
498 (width
* 2), data
- (width
* 2), width
* 2);
500 base
+= (dev_info
->info
->var
.xres
* 2) - (width
* 2);
501 data
+= (dev_info
->info
->var
.xres
* 2) - (width
* 2);
505 if (bufptr
> dev_info
->buf
) {
506 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
509 mutex_unlock(&dev_info
->bulk_mutex
);
516 draw_rect(struct dlfb_data
*dev_info
, int x
, int y
, int width
, int height
,
517 unsigned char red
, unsigned char green
, unsigned char blue
)
523 (((((red
) & 0xF8) | ((green
) >> 5)) & 0xFF) << 8) +
524 (((((green
) & 0x1C) << 3) | ((blue
) >> 3)) & 0xFF);
529 if (x
+ width
> dev_info
->info
->var
.xres
)
532 if (y
+ height
> dev_info
->info
->var
.yres
)
535 mutex_lock(&dev_info
->bulk_mutex
);
537 base
= dev_info
->base16
+ (dev_info
->info
->var
.xres
* 2 * y
) + (x
* 2);
539 bufptr
= dev_info
->buf
;
541 for (i
= y
; i
< y
+ height
; i
++) {
543 if (dev_info
->backing_buffer
) {
544 for (j
= 0; j
< width
* 2; j
+= 2) {
545 dev_info
->backing_buffer
546 [base
- dev_info
->base16
+ j
] =
548 dev_info
->backing_buffer
549 [base
- dev_info
->base16
+ j
+ 1] =
554 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
555 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
556 bufptr
= dev_info
->buf
;
563 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
565 dlfb_bulk_msg(dev_info
,
566 bufptr
- dev_info
->buf
);
567 bufptr
= dev_info
->buf
;
573 *bufptr
++ = (char)(base
>> 16);
574 *bufptr
++ = (char)(base
>> 8);
575 *bufptr
++ = (char)(base
);
589 *bufptr
++ = (char)(col
>> 8);
590 *bufptr
++ = (char)(col
);
594 base
+= (dev_info
->info
->var
.xres
* 2) - (width
* 2);
598 if (bufptr
> dev_info
->buf
)
599 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
601 mutex_unlock(&dev_info
->bulk_mutex
);
606 static void swapfb(struct dlfb_data
*dev_info
)
612 mutex_lock(&dev_info
->bulk_mutex
);
614 tmpbase
= dev_info
->base16
;
616 dev_info
->base16
= dev_info
->base16d
;
617 dev_info
->base16d
= tmpbase
;
619 bufptr
= dev_info
->buf
;
621 bufptr
= dlfb_set_register(bufptr
, 0xFF, 0x00);
625 dlfb_set_register(bufptr
, 0x20, (char)(dev_info
->base16
>> 16));
626 bufptr
= dlfb_set_register(bufptr
, 0x21, (char)(dev_info
->base16
>> 8));
627 bufptr
= dlfb_set_register(bufptr
, 0x22, (char)(dev_info
->base16
));
629 bufptr
= dlfb_set_register(bufptr
, 0xFF, 0x00);
631 dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
633 mutex_unlock(&dev_info
->bulk_mutex
);
636 static int copyfb(struct dlfb_data
*dev_info
)
645 base
= dev_info
->base16d
;
647 mutex_lock(&dev_info
->bulk_mutex
);
649 source
= dev_info
->base16
;
651 bufptr
= dev_info
->buf
;
653 for (i
= 0; i
< dev_info
->info
->var
.yres
; i
++) {
655 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
656 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
657 bufptr
= dev_info
->buf
;
660 rem
= dev_info
->info
->var
.xres
;
664 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
666 dlfb_bulk_msg(dev_info
,
667 bufptr
- dev_info
->buf
);
668 bufptr
= dev_info
->buf
;
675 *bufptr
++ = (char)(base
>> 16);
676 *bufptr
++ = (char)(base
>> 8);
677 *bufptr
++ = (char)(base
);
681 *bufptr
++ = (char)(source
>> 16);
682 *bufptr
++ = (char)(source
>> 8);
683 *bufptr
++ = (char)(source
);
691 *bufptr
++ = (char)(source
>> 16);
692 *bufptr
++ = (char)(source
>> 8);
693 *bufptr
++ = (char)(source
);
702 if (bufptr
> dev_info
->buf
)
703 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
705 mutex_unlock(&dev_info
->bulk_mutex
);
712 copyarea(struct dlfb_data
*dev_info
, int dx
, int dy
, int sx
, int sy
,
713 int width
, int height
)
722 if (dx
+ width
> dev_info
->info
->var
.xres
)
725 if (dy
+ height
> dev_info
->info
->var
.yres
)
728 mutex_lock(&dev_info
->bulk_mutex
);
731 dev_info
->base16
+ (dev_info
->info
->var
.xres
* 2 * dy
) + (dx
* 2);
732 source
= (dev_info
->info
->var
.xres
* 2 * sy
) + (sx
* 2);
734 bufptr
= dev_info
->buf
;
736 for (i
= sy
; i
< sy
+ height
; i
++) {
738 memcpy(dev_info
->backing_buffer
+ base
- dev_info
->base16
,
739 dev_info
->backing_buffer
+ source
, width
* 2);
741 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
742 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
743 bufptr
= dev_info
->buf
;
750 if (dev_info
->bufend
- bufptr
< BUF_HIGH_WATER_MARK
) {
752 dlfb_bulk_msg(dev_info
,
753 bufptr
- dev_info
->buf
);
754 bufptr
= dev_info
->buf
;
760 *bufptr
++ = (char)(base
>> 16);
761 *bufptr
++ = (char)(base
>> 8);
762 *bufptr
++ = (char)(base
);
766 *bufptr
++ = (char)(source
>> 16);
767 *bufptr
++ = (char)(source
>> 8);
768 *bufptr
++ = (char)(source
);
776 *bufptr
++ = (char)(source
>> 16);
777 *bufptr
++ = (char)(source
>> 8);
778 *bufptr
++ = (char)(source
);
786 base
+= (dev_info
->info
->var
.xres
* 2) - (width
* 2);
787 source
+= (dev_info
->info
->var
.xres
* 2) - (width
* 2);
790 if (bufptr
> dev_info
->buf
)
791 ret
= dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
793 mutex_unlock(&dev_info
->bulk_mutex
);
798 static void dlfb_copyarea(struct fb_info
*info
, const struct fb_copyarea
*area
)
801 struct dlfb_data
*dev
= info
->par
;
803 copyarea(dev
, area
->dx
, area
->dy
, area
->sx
, area
->sy
, area
->width
,
807 static void dlfb_imageblit(struct fb_info
*info
, const struct fb_image
*image
)
811 struct dlfb_data
*dev
= info
->par
;
812 cfb_imageblit(info
, image
);
814 image_blit(dev
, image
->dx
, image
->dy
, image
->width
, image
->height
,
818 static void dlfb_fillrect(struct fb_info
*info
,
819 const struct fb_fillrect
*region
)
822 unsigned char red
, green
, blue
;
823 struct dlfb_data
*dev
= info
->par
;
825 memcpy(&red
, ®ion
->color
, 1);
826 memcpy(&green
, ®ion
->color
+ 1, 1);
827 memcpy(&blue
, ®ion
->color
+ 2, 1);
828 draw_rect(dev
, region
->dx
, region
->dy
, region
->width
, region
->height
,
830 /* printk("FILL RECT %d %d !!!\n", region->dx, region->dy); */
834 static int dlfb_ioctl(struct fb_info
*info
, unsigned int cmd
, unsigned long arg
)
837 struct dlfb_data
*dev_info
= info
->par
;
838 struct dloarea
*area
= NULL
;
841 char *edid
= (char *)arg
;
843 if (copy_to_user(edid
, dev_info
->edid
, 128)) {
849 if (cmd
== 0xAA || cmd
== 0xAB || cmd
== 0xAC) {
851 area
= (struct dloarea
*)arg
;
856 if (area
->x
> info
->var
.xres
)
857 area
->x
= info
->var
.xres
;
862 if (area
->y
> info
->var
.yres
)
863 area
->y
= info
->var
.yres
;
867 image_blit(dev_info
, area
->x
, area
->y
, area
->w
, area
->h
,
872 image_blit(dev_info
, area
->x
, area
->y
, area
->w
, area
->h
,
875 } else if (cmd
== 0xAB) {
884 area
->x2
, area
->y2
, area
->x
, area
->y
, area
->w
,
890 /* taken from vesafb */
893 dlfb_setcolreg(unsigned regno
, unsigned red
, unsigned green
,
894 unsigned blue
, unsigned transp
, struct fb_info
*info
)
898 if (regno
>= info
->cmap
.len
)
902 if (info
->var
.red
.offset
== 10) {
904 ((u32
*) (info
->pseudo_palette
))[regno
] =
905 ((red
& 0xf800) >> 1) |
906 ((green
& 0xf800) >> 6) | ((blue
& 0xf800) >> 11);
909 ((u32
*) (info
->pseudo_palette
))[regno
] =
911 ((green
& 0xfc00) >> 5) | ((blue
& 0xf800) >> 11);
918 static int dlfb_release(struct fb_info
*info
, int user
)
920 struct dlfb_data
*dev_info
= info
->par
;
921 image_blit(dev_info
, 0, 0, info
->var
.xres
, info
->var
.yres
,
926 static int dlfb_blank(int blank_mode
, struct fb_info
*info
)
928 struct dlfb_data
*dev_info
= info
->par
;
929 char *bufptr
= dev_info
->buf
;
931 bufptr
= dlfb_set_register(bufptr
, 0xFF, 0x00);
932 if (blank_mode
!= FB_BLANK_UNBLANK
) {
933 bufptr
= dlfb_set_register(bufptr
, 0x1F, 0x01);
935 bufptr
= dlfb_set_register(bufptr
, 0x1F, 0x00);
937 bufptr
= dlfb_set_register(bufptr
, 0xFF, 0xFF);
939 dlfb_bulk_msg(dev_info
, bufptr
- dev_info
->buf
);
944 static struct fb_ops dlfb_ops
= {
945 .fb_setcolreg
= dlfb_setcolreg
,
946 .fb_fillrect
= dlfb_fillrect
,
947 .fb_copyarea
= dlfb_copyarea
,
948 .fb_imageblit
= dlfb_imageblit
,
949 .fb_mmap
= dlfb_mmap
,
950 .fb_ioctl
= dlfb_ioctl
,
951 .fb_release
= dlfb_release
,
952 .fb_blank
= dlfb_blank
,
955 static int dlfb_probe(struct usb_interface
*interface
,
956 const struct usb_device_id
*id
)
958 struct device
*mydev
;
959 struct usb_device
*usbdev
;
960 struct dlfb_data
*dev
;
961 struct fb_info
*info
;
963 unsigned char *videomemory
;
964 int retval
= -ENOMEM
;
965 struct fb_var_screeninfo
*var
;
966 struct fb_bitfield red
= { 11, 5, 0 };
967 struct fb_bitfield green
= { 5, 6, 0 };
968 struct fb_bitfield blue
= { 0, 5, 0 };
970 usbdev
= usb_get_dev(interface_to_usbdev(interface
));
971 mydev
= &usbdev
->dev
;
973 dev
= kzalloc(sizeof(*dev
), GFP_KERNEL
);
975 dev_err(mydev
, "failed alloc of dev struct\n");
979 mutex_init(&dev
->bulk_mutex
);
981 dev
->interface
= interface
;
982 usb_set_intfdata(interface
, dev
);
984 dev_info(mydev
, "dlfb_probe: setting up DisplayLink device\n");
987 * TODO: replace single 64K buffer with buffer list
990 dev
->buf
= kmalloc(BUF_SIZE
, GFP_KERNEL
);
991 if (dev
->buf
== NULL
) {
992 dev_err(mydev
, "unable to allocate memory for dlfb commands\n");
995 dev
->bufend
= dev
->buf
+ BUF_SIZE
;
997 dev
->tx_urb
= usb_alloc_urb(0, GFP_KERNEL
);
998 usb_fill_bulk_urb(dev
->tx_urb
, dev
->udev
,
999 usb_sndbulkpipe(dev
->udev
, 1), dev
->buf
, 0,
1000 dlfb_bulk_callback
, dev
);
1002 /* allocates framebuffer driver structure, not framebuffer memory */
1003 info
= framebuffer_alloc(0, mydev
);
1009 info
->pseudo_palette
= dev
->pseudo_palette
;
1012 retval
= dlfb_get_var_from_edid(dev
, var
);
1014 /* had a problem getting edid. so fallback to 640x480 */
1015 dev_err(mydev
, "Problem %d with EDID.\n", retval
);
1021 * ok, now that we've got the size info, we can alloc our framebuffer.
1022 * We are using 16bpp.
1024 info
->var
.bits_per_pixel
= 16;
1025 info
->fix
= dlfb_fix
;
1026 info
->fix
.line_length
= var
->xres
* (var
->bits_per_pixel
/ 8);
1027 videomemorysize
= info
->fix
.line_length
* var
->yres
;
1030 * The big chunk of system memory we use as a virtual framebuffer.
1031 * Pages don't need to be set RESERVED (non-swap) immediately on 2.6
1032 * remap_pfn_page() syscall in our mmap and/or defio will handle.
1034 videomemory
= vmalloc(videomemorysize
);
1037 memset(videomemory
, 0, videomemorysize
);
1039 info
->screen_base
= videomemory
;
1040 info
->fix
.smem_len
= PAGE_ALIGN(videomemorysize
);
1041 info
->fix
.smem_start
= (unsigned long) videomemory
;
1043 FBINFO_DEFAULT
| FBINFO_READS_FAST
| FBINFO_HWACCEL_IMAGEBLIT
|
1044 FBINFO_HWACCEL_COPYAREA
| FBINFO_HWACCEL_FILLRECT
;
1047 * Second framebuffer copy, mirroring the state of the framebuffer
1048 * on the physical USB device. We can function without this.
1049 * But with imperfect damage info we may end up sending pixels over USB
1050 * that were, in fact, unchanged -- wasting limited USB bandwidth
1052 dev
->backing_buffer
= vmalloc(dev
->screen_size
);
1053 if (!dev
->backing_buffer
)
1054 dev_info(mydev
, "No backing buffer allocated!\n");
1056 info
->fbops
= &dlfb_ops
;
1058 var
->vmode
= FB_VMODE_NONINTERLACED
;
1064 * TODO: Enable FB_CONFIG_DEFIO support
1066 info->fbdefio = &dlfb_defio;
1067 fb_deferred_io_init(info);
1071 retval
= fb_alloc_cmap(&info
->cmap
, 256, 0);
1073 dev_err(mydev
, "Failed to allocate colormap\n");
1077 dlfb_select_std_channel(dev
);
1078 dlfb_set_video_mode(dev
, var
);
1079 /* TODO: dlfb_dpy_update(dev); */
1081 retval
= register_framebuffer(info
);
1085 /* paint "successful" green screen */
1086 draw_rect(dev
, 0, 0, dev
->info
->var
.xres
,
1087 dev
->info
->var
.yres
, 0x30, 0xff, 0x30);
1089 dev_info(mydev
, "DisplayLink USB device %d now attached, "
1090 "using %dK of memory\n", info
->node
,
1091 ((dev
->backing_buffer
) ?
1092 videomemorysize
* 2 : videomemorysize
) >> 10);
1096 fb_dealloc_cmap(&info
->cmap
);
1098 /* TODO: fb_deferred_io_cleanup(info); */
1101 framebuffer_release(info
);
1105 usb_set_intfdata(interface
, NULL
);
1106 usb_put_dev(dev
->udev
);
1112 static void dlfb_disconnect(struct usb_interface
*interface
)
1114 struct dlfb_data
*dev
;
1115 struct fb_info
*info
;
1117 dev
= usb_get_intfdata(interface
);
1118 usb_set_intfdata(interface
, NULL
);
1119 usb_put_dev(dev
->udev
);
1122 * TODO: since, upon usb disconnect(), usb will cancel in-flight urbs
1123 * and error out any new ones, look at eliminating need for mutex
1125 mutex_lock(&dev
->bulk_mutex
);
1126 dev
->interface
= NULL
;
1128 mutex_unlock(&dev
->bulk_mutex
);
1131 dev_info(&interface
->dev
, "Detaching DisplayLink device %d.\n",
1133 unregister_framebuffer(info
);
1134 fb_dealloc_cmap(&info
->cmap
);
1135 /* TODO: fb_deferred_io_cleanup(info); */
1136 fb_dealloc_cmap(&info
->cmap
);
1137 vfree((void __force
*)info
->screen_base
);
1138 framebuffer_release(info
);
1141 if (dev
->backing_buffer
)
1142 vfree(dev
->backing_buffer
);
1147 static struct usb_driver dlfb_driver
= {
1149 .probe
= dlfb_probe
,
1150 .disconnect
= dlfb_disconnect
,
1151 .id_table
= id_table
,
1154 static int __init
dlfb_init(void)
1158 res
= usb_register(&dlfb_driver
);
1160 err("usb_register failed. Error number %d", res
);
1162 printk("VMODES initialized\n");
1167 static void __exit
dlfb_exit(void)
1169 usb_deregister(&dlfb_driver
);
1172 module_init(dlfb_init
);
1173 module_exit(dlfb_exit
);
1175 MODULE_AUTHOR("Roberto De Ioris <roberto@unbit.it>, "
1176 "Jaya Kumar <jayakumar.lkml@gmail.com>");
1177 MODULE_DESCRIPTION(DRIVER_VERSION
);
1178 MODULE_LICENSE("GPL");