]>
Commit | Line | Data |
---|---|---|
5320918b DA |
1 | /* |
2 | * Copyright (C) 2012 Red Hat | |
3 | * | |
4 | * This file is subject to the terms and conditions of the GNU General Public | |
5 | * License v2. See the file COPYING in the main directory of this archive for | |
6 | * more details. | |
7 | */ | |
8 | ||
9 | #include <linux/module.h> | |
d4f68a75 | 10 | #include <drm/drmP.h> |
760285e7 | 11 | #include <drm/drm_crtc_helper.h> |
5320918b DA |
12 | #include "udl_drv.h" |
13 | ||
915b4d11 DH |
14 | static int udl_driver_set_busid(struct drm_device *d, struct drm_master *m) |
15 | { | |
16 | return 0; | |
17 | } | |
18 | ||
78b68556 | 19 | static const struct vm_operations_struct udl_gem_vm_ops = { |
5320918b DA |
20 | .fault = udl_gem_fault, |
21 | .open = drm_gem_vm_open, | |
22 | .close = drm_gem_vm_close, | |
23 | }; | |
24 | ||
25 | static const struct file_operations udl_driver_fops = { | |
26 | .owner = THIS_MODULE, | |
27 | .open = drm_open, | |
fa9e8550 | 28 | .mmap = udl_drm_gem_mmap, |
5320918b DA |
29 | .poll = drm_poll, |
30 | .read = drm_read, | |
31 | .unlocked_ioctl = drm_ioctl, | |
32 | .release = drm_release, | |
804d74ab KP |
33 | #ifdef CONFIG_COMPAT |
34 | .compat_ioctl = drm_compat_ioctl, | |
35 | #endif | |
5320918b DA |
36 | .llseek = noop_llseek, |
37 | }; | |
38 | ||
39 | static struct drm_driver driver = { | |
96503f59 | 40 | .driver_features = DRIVER_MODESET | DRIVER_GEM | DRIVER_PRIME, |
5320918b DA |
41 | .load = udl_driver_load, |
42 | .unload = udl_driver_unload, | |
915b4d11 | 43 | .set_busid = udl_driver_set_busid, |
5320918b DA |
44 | |
45 | /* gem hooks */ | |
5320918b DA |
46 | .gem_free_object = udl_gem_free_object, |
47 | .gem_vm_ops = &udl_gem_vm_ops, | |
48 | ||
49 | .dumb_create = udl_dumb_create, | |
50 | .dumb_map_offset = udl_gem_mmap, | |
43387b37 | 51 | .dumb_destroy = drm_gem_dumb_destroy, |
5320918b | 52 | .fops = &udl_driver_fops, |
96503f59 | 53 | |
ebfdd6d5 | 54 | .prime_handle_to_fd = drm_gem_prime_handle_to_fd, |
96503f59 | 55 | .prime_fd_to_handle = drm_gem_prime_fd_to_handle, |
ebfdd6d5 | 56 | .gem_prime_export = udl_gem_prime_export, |
96503f59 DA |
57 | .gem_prime_import = udl_gem_prime_import, |
58 | ||
5320918b DA |
59 | .name = DRIVER_NAME, |
60 | .desc = DRIVER_DESC, | |
61 | .date = DRIVER_DATE, | |
62 | .major = DRIVER_MAJOR, | |
63 | .minor = DRIVER_MINOR, | |
64 | .patchlevel = DRIVER_PATCHLEVEL, | |
65 | }; | |
66 | ||
d4f68a75 DH |
67 | static int udl_usb_probe(struct usb_interface *interface, |
68 | const struct usb_device_id *id) | |
69 | { | |
70 | struct usb_device *udev = interface_to_usbdev(interface); | |
71 | struct drm_device *dev; | |
72 | int r; | |
73 | ||
74 | dev = drm_dev_alloc(&driver, &interface->dev); | |
75 | if (!dev) | |
76 | return -ENOMEM; | |
77 | ||
78 | r = drm_dev_register(dev, (unsigned long)udev); | |
79 | if (r) | |
80 | goto err_free; | |
81 | ||
82 | usb_set_intfdata(interface, dev); | |
83 | DRM_INFO("Initialized udl on minor %d\n", dev->primary->index); | |
84 | ||
85 | return 0; | |
86 | ||
87 | err_free: | |
88 | drm_dev_unref(dev); | |
89 | return r; | |
90 | } | |
91 | ||
92 | static void udl_usb_disconnect(struct usb_interface *interface) | |
93 | { | |
94 | struct drm_device *dev = usb_get_intfdata(interface); | |
95 | ||
96 | drm_kms_helper_poll_disable(dev); | |
6c87e5c3 | 97 | drm_connector_unregister_all(dev); |
d4f68a75 DH |
98 | udl_fbdev_unplug(dev); |
99 | udl_drop_usb(dev); | |
100 | drm_unplug_dev(dev); | |
101 | } | |
102 | ||
103 | /* | |
104 | * There are many DisplayLink-based graphics products, all with unique PIDs. | |
105 | * So we match on DisplayLink's VID + Vendor-Defined Interface Class (0xff) | |
106 | * We also require a match on SubClass (0x00) and Protocol (0x00), | |
107 | * which is compatible with all known USB 2.0 era graphics chips and firmware, | |
108 | * but allows DisplayLink to increment those for any future incompatible chips | |
109 | */ | |
110 | static struct usb_device_id id_table[] = { | |
111 | {.idVendor = 0x17e9, .bInterfaceClass = 0xff, | |
112 | .bInterfaceSubClass = 0x00, | |
113 | .bInterfaceProtocol = 0x00, | |
114 | .match_flags = USB_DEVICE_ID_MATCH_VENDOR | | |
115 | USB_DEVICE_ID_MATCH_INT_CLASS | | |
116 | USB_DEVICE_ID_MATCH_INT_SUBCLASS | | |
117 | USB_DEVICE_ID_MATCH_INT_PROTOCOL,}, | |
118 | {}, | |
119 | }; | |
120 | MODULE_DEVICE_TABLE(usb, id_table); | |
121 | ||
5320918b DA |
122 | static struct usb_driver udl_driver = { |
123 | .name = "udl", | |
124 | .probe = udl_usb_probe, | |
125 | .disconnect = udl_usb_disconnect, | |
126 | .id_table = id_table, | |
127 | }; | |
a6ddd2f1 | 128 | module_usb_driver(udl_driver); |
d4f68a75 | 129 | MODULE_LICENSE("GPL"); |