1ff811b0aSSascha Wildner /* $FreeBSD: head/sys/dev/usb/quirk/usb_quirk.c 276239 2014-12-26 10:53:22Z hselasky $ */ 212bd3c8bSSascha Wildner /*- 312bd3c8bSSascha Wildner * Copyright (c) 1998 The NetBSD Foundation, Inc. All rights reserved. 412bd3c8bSSascha Wildner * Copyright (c) 1998 Lennart Augustsson. All rights reserved. 512bd3c8bSSascha Wildner * Copyright (c) 2008 Hans Petter Selasky. All rights reserved. 612bd3c8bSSascha Wildner * 712bd3c8bSSascha Wildner * Redistribution and use in source and binary forms, with or without 812bd3c8bSSascha Wildner * modification, are permitted provided that the following conditions 912bd3c8bSSascha Wildner * are met: 1012bd3c8bSSascha Wildner * 1. Redistributions of source code must retain the above copyright 1112bd3c8bSSascha Wildner * notice, this list of conditions and the following disclaimer. 1212bd3c8bSSascha Wildner * 2. Redistributions in binary form must reproduce the above copyright 1312bd3c8bSSascha Wildner * notice, this list of conditions and the following disclaimer in the 1412bd3c8bSSascha Wildner * documentation and/or other materials provided with the distribution. 1512bd3c8bSSascha Wildner * 1612bd3c8bSSascha Wildner * THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 1712bd3c8bSSascha Wildner * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1812bd3c8bSSascha Wildner * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 1912bd3c8bSSascha Wildner * ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 2012bd3c8bSSascha Wildner * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2112bd3c8bSSascha Wildner * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2212bd3c8bSSascha Wildner * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2312bd3c8bSSascha Wildner * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2412bd3c8bSSascha Wildner * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2512bd3c8bSSascha Wildner * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2612bd3c8bSSascha Wildner * SUCH DAMAGE. 2712bd3c8bSSascha Wildner */ 2812bd3c8bSSascha Wildner 2912bd3c8bSSascha Wildner #include <sys/stdint.h> 3012bd3c8bSSascha Wildner #include <sys/param.h> 3112bd3c8bSSascha Wildner #include <sys/queue.h> 3212bd3c8bSSascha Wildner #include <sys/types.h> 3312bd3c8bSSascha Wildner #include <sys/systm.h> 3412bd3c8bSSascha Wildner #include <sys/kernel.h> 3512bd3c8bSSascha Wildner #include <sys/bus.h> 3612bd3c8bSSascha Wildner #include <sys/module.h> 3712bd3c8bSSascha Wildner #include <sys/lock.h> 3812bd3c8bSSascha Wildner #include <sys/condvar.h> 3912bd3c8bSSascha Wildner #include <sys/sysctl.h> 4012bd3c8bSSascha Wildner #include <sys/unistd.h> 4112bd3c8bSSascha Wildner #include <sys/callout.h> 4212bd3c8bSSascha Wildner #include <sys/malloc.h> 4312bd3c8bSSascha Wildner #include <sys/priv.h> 44ac499a8fSSascha Wildner #include <sys/thread2.h> 4512bd3c8bSSascha Wildner 46ac499a8fSSascha Wildner #include <bus/u4b/usb.h> 47ac499a8fSSascha Wildner #include <bus/u4b/usb_ioctl.h> 48ac499a8fSSascha Wildner #include <bus/u4b/usbdi.h> 49ef4aa9ffSSascha Wildner #include "usbdevs.h" 5012bd3c8bSSascha Wildner 5112bd3c8bSSascha Wildner #define USB_DEBUG_VAR usb_debug 52ac499a8fSSascha Wildner #include <bus/u4b/usb_debug.h> 53ac499a8fSSascha Wildner #include <bus/u4b/usb_dynamic.h> 5412bd3c8bSSascha Wildner 55ac499a8fSSascha Wildner #include <bus/u4b/quirk/usb_quirk.h> 5612bd3c8bSSascha Wildner 5712bd3c8bSSascha Wildner MODULE_DEPEND(usb_quirk, usb, 1, 1, 1); 5812bd3c8bSSascha Wildner MODULE_VERSION(usb_quirk, 1); 5912bd3c8bSSascha Wildner 60ff811b0aSSascha Wildner #define USB_DEV_QUIRKS_MAX 384 6112bd3c8bSSascha Wildner #define USB_SUB_QUIRKS_MAX 8 6212bd3c8bSSascha Wildner 6312bd3c8bSSascha Wildner struct usb_quirk_entry { 6412bd3c8bSSascha Wildner uint16_t vid; 6512bd3c8bSSascha Wildner uint16_t pid; 6612bd3c8bSSascha Wildner uint16_t lo_rev; 6712bd3c8bSSascha Wildner uint16_t hi_rev; 6812bd3c8bSSascha Wildner uint16_t quirks[USB_SUB_QUIRKS_MAX]; 6912bd3c8bSSascha Wildner }; 7012bd3c8bSSascha Wildner 71ac499a8fSSascha Wildner static struct lock usb_quirk_lock; 7212bd3c8bSSascha Wildner 7312bd3c8bSSascha Wildner #define USB_QUIRK_VP(v,p,l,h,...) \ 7412bd3c8bSSascha Wildner { .vid = (v), .pid = (p), .lo_rev = (l), .hi_rev = (h), \ 7512bd3c8bSSascha Wildner .quirks = { __VA_ARGS__ } } 7612bd3c8bSSascha Wildner #define USB_QUIRK(v,p,l,h,...) \ 7712bd3c8bSSascha Wildner USB_QUIRK_VP(USB_VENDOR_##v, USB_PRODUCT_##v##_##p, l, h, __VA_ARGS__) 7812bd3c8bSSascha Wildner 7912bd3c8bSSascha Wildner static struct usb_quirk_entry usb_quirks[USB_DEV_QUIRKS_MAX] = { 8012bd3c8bSSascha Wildner USB_QUIRK(ASUS, LCM, 0x0000, 0xffff, UQ_HID_IGNORE), 8112bd3c8bSSascha Wildner USB_QUIRK(INSIDEOUT, EDGEPORT4, 0x094, 0x094, UQ_SWAP_UNICODE), 8212bd3c8bSSascha Wildner USB_QUIRK(DALLAS, J6502, 0x0a2, 0x0a2, UQ_BAD_ADC), 8312bd3c8bSSascha Wildner USB_QUIRK(DALLAS, J6502, 0x0a2, 0x0a2, UQ_AU_NO_XU), 8412bd3c8bSSascha Wildner USB_QUIRK(ALTEC, ADA70, 0x103, 0x103, UQ_BAD_ADC), 8512bd3c8bSSascha Wildner USB_QUIRK(ALTEC, ASC495, 0x000, 0x000, UQ_BAD_AUDIO), 8612bd3c8bSSascha Wildner USB_QUIRK(QTRONIX, 980N, 0x110, 0x110, UQ_SPUR_BUT_UP), 8712bd3c8bSSascha Wildner USB_QUIRK(ALCOR2, KBD_HUB, 0x001, 0x001, UQ_SPUR_BUT_UP), 8812bd3c8bSSascha Wildner USB_QUIRK(MCT, HUB0100, 0x102, 0x102, UQ_BUS_POWERED), 8912bd3c8bSSascha Wildner USB_QUIRK(MCT, USB232, 0x102, 0x102, UQ_BUS_POWERED), 9012bd3c8bSSascha Wildner USB_QUIRK(TI, UTUSB41, 0x110, 0x110, UQ_POWER_CLAIM), 9112bd3c8bSSascha Wildner USB_QUIRK(TELEX, MIC1, 0x009, 0x009, UQ_AU_NO_FRAC), 9212bd3c8bSSascha Wildner USB_QUIRK(SILICONPORTALS, YAPPHONE, 0x100, 0x100, UQ_AU_INP_ASYNC), 9312bd3c8bSSascha Wildner USB_QUIRK(LOGITECH, UN53B, 0x0000, 0xffff, UQ_NO_STRINGS), 94ff811b0aSSascha Wildner USB_QUIRK(REALTEK, RTL8196EU, 0x0000, 0xffff, UQ_CFG_INDEX_1), 9512bd3c8bSSascha Wildner USB_QUIRK(ELSA, MODEM1, 0x0000, 0xffff, UQ_CFG_INDEX_1), 9657bed822SMarkus Pfeiffer USB_QUIRK(PLANEX2, MZKUE150N, 0x0000, 0xffff, UQ_CFG_INDEX_1), 9712bd3c8bSSascha Wildner /* Quirks for printer devices */ 9812bd3c8bSSascha Wildner USB_QUIRK(HP, 895C, 0x0000, 0xffff, UQ_BROKEN_BIDIR), 9912bd3c8bSSascha Wildner USB_QUIRK(HP, 880C, 0x0000, 0xffff, UQ_BROKEN_BIDIR), 10012bd3c8bSSascha Wildner USB_QUIRK(HP, 815C, 0x0000, 0xffff, UQ_BROKEN_BIDIR), 10112bd3c8bSSascha Wildner USB_QUIRK(HP, 810C, 0x0000, 0xffff, UQ_BROKEN_BIDIR), 10212bd3c8bSSascha Wildner USB_QUIRK(HP, 830C, 0x0000, 0xffff, UQ_BROKEN_BIDIR), 10312bd3c8bSSascha Wildner USB_QUIRK(HP, 1220C, 0x0000, 0xffff, UQ_BROKEN_BIDIR), 10412bd3c8bSSascha Wildner USB_QUIRK(XEROX, WCM15, 0x0000, 0xffff, UQ_BROKEN_BIDIR), 10512bd3c8bSSascha Wildner /* Devices which should be ignored by uhid */ 10612bd3c8bSSascha Wildner USB_QUIRK(APC, UPS, 0x0000, 0xffff, UQ_HID_IGNORE), 10712bd3c8bSSascha Wildner USB_QUIRK(BELKIN, F6C550AVR, 0x0000, 0xffff, UQ_HID_IGNORE), 10812bd3c8bSSascha Wildner USB_QUIRK(CYBERPOWER, 1500CAVRLCD, 0x0000, 0xffff, UQ_HID_IGNORE), 10912bd3c8bSSascha Wildner USB_QUIRK(CYPRESS, SILVERSHIELD, 0x0000, 0xffff, UQ_HID_IGNORE), 11012bd3c8bSSascha Wildner USB_QUIRK(DELORME, EARTHMATE, 0x0000, 0xffff, UQ_HID_IGNORE), 111ff811b0aSSascha Wildner USB_QUIRK(DREAMLINK, DL100B, 0x0000, 0xffff, UQ_HID_IGNORE), 11212bd3c8bSSascha Wildner USB_QUIRK(ITUNERNET, USBLCD2X20, 0x0000, 0xffff, UQ_HID_IGNORE), 11312bd3c8bSSascha Wildner USB_QUIRK(ITUNERNET, USBLCD4X20, 0x0000, 0xffff, UQ_HID_IGNORE), 11412bd3c8bSSascha Wildner USB_QUIRK(LIEBERT, POWERSURE_PXT, 0x0000, 0xffff, UQ_HID_IGNORE), 11557bed822SMarkus Pfeiffer USB_QUIRK(LIEBERT2, PSI1000, 0x0000, 0xffff, UQ_HID_IGNORE), 11612bd3c8bSSascha Wildner USB_QUIRK(MGE, UPS1, 0x0000, 0xffff, UQ_HID_IGNORE), 11712bd3c8bSSascha Wildner USB_QUIRK(MGE, UPS2, 0x0000, 0xffff, UQ_HID_IGNORE), 11812bd3c8bSSascha Wildner USB_QUIRK(APPLE, IPHONE, 0x0000, 0xffff, UQ_HID_IGNORE), 11912bd3c8bSSascha Wildner USB_QUIRK(APPLE, IPHONE_3G, 0x0000, 0xffff, UQ_HID_IGNORE), 12012bd3c8bSSascha Wildner USB_QUIRK(MEGATEC, UPS, 0x0000, 0xffff, UQ_HID_IGNORE), 12112bd3c8bSSascha Wildner /* Devices which should be ignored by both ukbd and uhid */ 12212bd3c8bSSascha Wildner USB_QUIRK(CYPRESS, WISPY1A, 0x0000, 0xffff, UQ_KBD_IGNORE, UQ_HID_IGNORE), 12312bd3c8bSSascha Wildner USB_QUIRK(METAGEEK, WISPY1B, 0x0000, 0xffff, UQ_KBD_IGNORE, UQ_HID_IGNORE), 12412bd3c8bSSascha Wildner USB_QUIRK(METAGEEK, WISPY24X, 0x0000, 0xffff, UQ_KBD_IGNORE, UQ_HID_IGNORE), 12512bd3c8bSSascha Wildner USB_QUIRK(METAGEEK2, WISPYDBX, 0x0000, 0xffff, UQ_KBD_IGNORE, UQ_HID_IGNORE), 12612bd3c8bSSascha Wildner USB_QUIRK(TENX, UAUDIO0, 0x0101, 0x0101, UQ_AUDIO_SWAP_LR), 12712bd3c8bSSascha Wildner /* MS keyboards do weird things */ 12857bed822SMarkus Pfeiffer USB_QUIRK(MICROSOFT, NATURAL4000, 0x0000, 0xFFFF, UQ_KBD_BOOTPROTO), 12912bd3c8bSSascha Wildner USB_QUIRK(MICROSOFT, WLINTELLIMOUSE, 0x0000, 0xffff, UQ_MS_LEADING_BYTE), 13057bed822SMarkus Pfeiffer /* Quirk for Corsair Vengeance K60 keyboard */ 13157bed822SMarkus Pfeiffer USB_QUIRK(CORSAIR, K60, 0x0000, 0xffff, UQ_KBD_BOOTPROTO), 132ff811b0aSSascha Wildner /* Quirk for Corsair Vengeance K70 keyboard */ 133ff811b0aSSascha Wildner USB_QUIRK(CORSAIR, K70, 0x0000, 0xffff, UQ_KBD_BOOTPROTO), 134*57587a56SSascha Wildner /* Quirk for Corsair STRAFE Gaming keyboard */ 135*57587a56SSascha Wildner USB_QUIRK(CORSAIR, STRAFE, 0x0000, 0xffff, UQ_KBD_BOOTPROTO), 13612bd3c8bSSascha Wildner /* umodem(4) device quirks */ 13712bd3c8bSSascha Wildner USB_QUIRK(METRICOM, RICOCHET_GS, 0x100, 0x100, UQ_ASSUME_CM_OVER_DATA), 13812bd3c8bSSascha Wildner USB_QUIRK(SANYO, SCP4900, 0x000, 0x000, UQ_ASSUME_CM_OVER_DATA), 13912bd3c8bSSascha Wildner USB_QUIRK(MOTOROLA2, T720C, 0x001, 0x001, UQ_ASSUME_CM_OVER_DATA), 14012bd3c8bSSascha Wildner USB_QUIRK(EICON, DIVA852, 0x100, 0x100, UQ_ASSUME_CM_OVER_DATA), 14112bd3c8bSSascha Wildner USB_QUIRK(SIEMENS2, ES75, 0x000, 0x000, UQ_ASSUME_CM_OVER_DATA), 14212bd3c8bSSascha Wildner USB_QUIRK(QUALCOMM, CDMA_MSM, 0x0000, 0xffff, UQ_ASSUME_CM_OVER_DATA), 14312bd3c8bSSascha Wildner USB_QUIRK(QUALCOMM2, CDMA_MSM, 0x0000, 0xffff, UQ_ASSUME_CM_OVER_DATA), 14412bd3c8bSSascha Wildner USB_QUIRK(CURITEL, UM150, 0x0000, 0xffff, UQ_ASSUME_CM_OVER_DATA), 14512bd3c8bSSascha Wildner USB_QUIRK(CURITEL, UM175, 0x0000, 0xffff, UQ_ASSUME_CM_OVER_DATA), 14612bd3c8bSSascha Wildner USB_QUIRK(VERTEX, VW110L, 0x0000, 0xffff, UQ_ASSUME_CM_OVER_DATA), 14712bd3c8bSSascha Wildner 14812bd3c8bSSascha Wildner /* USB Mass Storage Class Quirks */ 14912bd3c8bSSascha Wildner USB_QUIRK_VP(USB_VENDOR_ASAHIOPTICAL, 0, UQ_MSC_NO_RS_CLEAR_UA, 15012bd3c8bSSascha Wildner UQ_MATCH_VENDOR_ONLY), 15112bd3c8bSSascha Wildner USB_QUIRK(ADDON, ATTACHE, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 15212bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 15312bd3c8bSSascha Wildner USB_QUIRK(ADDON, A256MB, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 15412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 15512bd3c8bSSascha Wildner USB_QUIRK(ADDON, DISKPRO512, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 15612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 15712bd3c8bSSascha Wildner USB_QUIRK(ADDONICS2, CABLE_205, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 15812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 15912bd3c8bSSascha Wildner USB_QUIRK(AIPTEK, POCKETCAM3M, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 16012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 16112bd3c8bSSascha Wildner USB_QUIRK(ALCOR, UMCR_9361, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 16212bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN), 16312bd3c8bSSascha Wildner USB_QUIRK(ALCOR, TRANSCEND, 0x0000, 0xffff, UQ_MSC_NO_GETMAXLUN, 16412bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE, UQ_MSC_NO_TEST_UNIT_READY), 16512bd3c8bSSascha Wildner USB_QUIRK(APACER, HT202, 0x0000, 0xffff, UQ_MSC_NO_TEST_UNIT_READY, 16612bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 16712bd3c8bSSascha Wildner USB_QUIRK(ASAHIOPTICAL, OPTIO230, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 16812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 16912bd3c8bSSascha Wildner USB_QUIRK(ASAHIOPTICAL, OPTIO330, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 17012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 171ff811b0aSSascha Wildner USB_QUIRK(ATP, EUSB, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 17212bd3c8bSSascha Wildner USB_QUIRK(BELKIN, USB2SCSI, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 17312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 17412bd3c8bSSascha Wildner USB_QUIRK(CASIO, QV_DIGICAM, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 17512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 17612bd3c8bSSascha Wildner USB_QUIRK(CCYU, ED1064, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 17712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 17812bd3c8bSSascha Wildner USB_QUIRK(CENTURY, EX35QUAT, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 17912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 18012bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_IGNORE_RESIDUE), 18112bd3c8bSSascha Wildner USB_QUIRK(CYPRESS, XX6830XX, 0x0000, 0xffff, UQ_MSC_NO_GETMAXLUN, 18212bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 18312bd3c8bSSascha Wildner USB_QUIRK(DESKNOTE, UCR_61S2B, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 18412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 18512bd3c8bSSascha Wildner USB_QUIRK(DMI, CFSM_RW, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI, 18612bd3c8bSSascha Wildner UQ_MSC_NO_GETMAXLUN), 18757bed822SMarkus Pfeiffer USB_QUIRK(EMTEC, RUF2PS, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 18812bd3c8bSSascha Wildner USB_QUIRK(EPSON, STYLUS_875DC, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 18912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 19012bd3c8bSSascha Wildner USB_QUIRK(EPSON, STYLUS_895, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 19112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN), 19212bd3c8bSSascha Wildner USB_QUIRK(FEIYA, 5IN1, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 19312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 19457bed822SMarkus Pfeiffer USB_QUIRK(FEIYA, ELANGO, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 19512bd3c8bSSascha Wildner USB_QUIRK(FREECOM, DVD, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 19612bd3c8bSSascha Wildner USB_QUIRK(FUJIPHOTO, MASS0100, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI_I, 19712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_RS_CLEAR_UA, UQ_MSC_NO_SYNC_CACHE), 19812bd3c8bSSascha Wildner USB_QUIRK(GENESYS, GL641USB2IDE, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 19912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 20012bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_IGNORE_RESIDUE, UQ_MSC_NO_SYNC_CACHE), 20112bd3c8bSSascha Wildner USB_QUIRK(GENESYS, GL641USB2IDE_2, 0x0000, 0xffff, 20212bd3c8bSSascha Wildner UQ_MSC_FORCE_WIRE_BBB, UQ_MSC_FORCE_PROTO_ATAPI, 20312bd3c8bSSascha Wildner UQ_MSC_FORCE_SHORT_INQ, UQ_MSC_NO_START_STOP, 20412bd3c8bSSascha Wildner UQ_MSC_IGNORE_RESIDUE), 20512bd3c8bSSascha Wildner USB_QUIRK(GENESYS, GL641USB, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 20612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 20712bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_IGNORE_RESIDUE), 20812bd3c8bSSascha Wildner USB_QUIRK(GENESYS, GL641USB_2, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 20912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_WRONG_CSWSIG), 21012bd3c8bSSascha Wildner USB_QUIRK(HAGIWARA, FG, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 21112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 21212bd3c8bSSascha Wildner USB_QUIRK(HAGIWARA, FGSM, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 21312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 21412bd3c8bSSascha Wildner USB_QUIRK(HITACHI, DVDCAM_DZ_MV100A, 0x0000, 0xffff, 21512bd3c8bSSascha Wildner UQ_MSC_FORCE_WIRE_CBI, UQ_MSC_FORCE_PROTO_SCSI, 21612bd3c8bSSascha Wildner UQ_MSC_NO_GETMAXLUN), 21712bd3c8bSSascha Wildner USB_QUIRK(HITACHI, DVDCAM_USB, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI_I, 21812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_INQUIRY), 21912bd3c8bSSascha Wildner USB_QUIRK(HP, CDW4E, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_ATAPI), 22012bd3c8bSSascha Wildner USB_QUIRK(HP, CDW8200, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI_I, 22112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_TEST_UNIT_READY, 22212bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP), 22312bd3c8bSSascha Wildner USB_QUIRK(IMAGINATION, DBX1, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 22412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_WRONG_CSWSIG), 22512bd3c8bSSascha Wildner USB_QUIRK(INSYSTEM, USBCABLE, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 22612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_TEST_UNIT_READY, 22712bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_ALT_IFACE_1), 22812bd3c8bSSascha Wildner USB_QUIRK(INSYSTEM, ATAPI, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 22912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC), 23012bd3c8bSSascha Wildner USB_QUIRK(INSYSTEM, STORAGE_V2, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 23112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC), 23212bd3c8bSSascha Wildner USB_QUIRK(IODATA, IU_CD2, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 23312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 23412bd3c8bSSascha Wildner USB_QUIRK(IODATA, DVR_UEH8, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 23512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 23612bd3c8bSSascha Wildner USB_QUIRK(IOMEGA, ZIP100, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 23712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, 23812bd3c8bSSascha Wildner UQ_MSC_NO_TEST_UNIT_READY), /* XXX ZIP drives can also use ATAPI */ 23912bd3c8bSSascha Wildner USB_QUIRK(JMICRON, JM20337, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 24012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, 24112bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 242ff811b0aSSascha Wildner USB_QUIRK(KINGSTON, HYPERX3_0, 0x0000, 0xffff, UQ_MSC_NO_INQUIRY), 24312bd3c8bSSascha Wildner USB_QUIRK(KYOCERA, FINECAM_L3, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 24412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 24512bd3c8bSSascha Wildner USB_QUIRK(KYOCERA, FINECAM_S3X, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 24612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_INQUIRY), 24712bd3c8bSSascha Wildner USB_QUIRK(KYOCERA, FINECAM_S4, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 24812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_INQUIRY), 24912bd3c8bSSascha Wildner USB_QUIRK(KYOCERA, FINECAM_S5, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 25012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 25112bd3c8bSSascha Wildner USB_QUIRK(LACIE, HD, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 25212bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC), 25312bd3c8bSSascha Wildner USB_QUIRK(LEXAR, CF_READER, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 25412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 25512bd3c8bSSascha Wildner USB_QUIRK(LEXAR, JUMPSHOT, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 256ff811b0aSSascha Wildner USB_QUIRK(LEXAR, JUMPDRIVE, 0x0000, 0xffff, UQ_MSC_NO_INQUIRY), 25712bd3c8bSSascha Wildner USB_QUIRK(LOGITEC, LDR_H443SU2, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 25812bd3c8bSSascha Wildner USB_QUIRK(LOGITEC, LDR_H443U2, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 25912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI,), 26012bd3c8bSSascha Wildner USB_QUIRK(MELCO, DUBPXXG, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 26112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 26212bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_IGNORE_RESIDUE), 26312bd3c8bSSascha Wildner USB_QUIRK(MICROTECH, DPCM, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 26412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_TEST_UNIT_READY, 26512bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP), 26612bd3c8bSSascha Wildner USB_QUIRK(MICRON, REALSSD, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 26712bd3c8bSSascha Wildner USB_QUIRK(MICROTECH, SCSIDB25, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 26812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 26912bd3c8bSSascha Wildner USB_QUIRK(MICROTECH, SCSIHD50, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 27012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 27112bd3c8bSSascha Wildner USB_QUIRK(MINOLTA, E223, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 27212bd3c8bSSascha Wildner USB_QUIRK(MINOLTA, F300, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 27312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 27412bd3c8bSSascha Wildner USB_QUIRK(MITSUMI, CDRRW, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI | 27512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI), 27612bd3c8bSSascha Wildner USB_QUIRK(MOTOROLA2, E398, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 27712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 27812bd3c8bSSascha Wildner UQ_MSC_NO_INQUIRY_EVPD, UQ_MSC_NO_GETMAXLUN), 27912bd3c8bSSascha Wildner USB_QUIRK_VP(USB_VENDOR_MPMAN, 0, UQ_MSC_NO_SYNC_CACHE, 28012bd3c8bSSascha Wildner UQ_MATCH_VENDOR_ONLY), 28112bd3c8bSSascha Wildner USB_QUIRK(MSYSTEMS, DISKONKEY, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 28212bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE, UQ_MSC_NO_GETMAXLUN, 28312bd3c8bSSascha Wildner UQ_MSC_NO_RS_CLEAR_UA), 28412bd3c8bSSascha Wildner USB_QUIRK(MSYSTEMS, DISKONKEY2, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 28512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI), 28612bd3c8bSSascha Wildner USB_QUIRK(MYSON, HEDEN, 0x0000, 0xffff, UQ_MSC_IGNORE_RESIDUE, 28712bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 28812bd3c8bSSascha Wildner USB_QUIRK(NEODIO, ND3260, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 28912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ), 29012bd3c8bSSascha Wildner USB_QUIRK(NETAC, CF_CARD, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 29112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 29212bd3c8bSSascha Wildner USB_QUIRK(NETAC, ONLYDISK, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 29312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 29412bd3c8bSSascha Wildner USB_QUIRK(NETCHIP, CLIK_40, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_ATAPI, 29512bd3c8bSSascha Wildner UQ_MSC_NO_INQUIRY), 296ff811b0aSSascha Wildner USB_QUIRK(NETCHIP, POCKETBOOK, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 29712bd3c8bSSascha Wildner USB_QUIRK(NIKON, D300, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 29812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 29912bd3c8bSSascha Wildner USB_QUIRK(OLYMPUS, C1, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 30012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_WRONG_CSWSIG), 30112bd3c8bSSascha Wildner USB_QUIRK(OLYMPUS, C700, 0x0000, 0xffff, UQ_MSC_NO_GETMAXLUN), 30212bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, SDS_HOTFIND_D, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 30312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN, UQ_MSC_NO_SYNC_CACHE), 30412bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, CFMS_RW, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 30512bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, CFSM_COMBO, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 30612bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, CFSM_READER, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 30712bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, CFSM_READER2, 0x0000, 0xffff, 30812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 30912bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, MDCFE_B_CF_READER, 0x0000, 0xffff, 31012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 31112bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, MDSM_B_READER, 0x0000, 0xffff, 31212bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 31312bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, READER, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 31412bd3c8bSSascha Wildner USB_QUIRK(ONSPEC, UCF100, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 31557bed822SMarkus Pfeiffer UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_INQUIRY, UQ_MSC_NO_GETMAXLUN), 31612bd3c8bSSascha Wildner USB_QUIRK(ONSPEC2, IMAGEMATE_SDDR55, 0x0000, 0xffff, 31712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN), 31812bd3c8bSSascha Wildner USB_QUIRK(PANASONIC, KXL840AN, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 31912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_GETMAXLUN), 32012bd3c8bSSascha Wildner USB_QUIRK(PANASONIC, KXLCB20AN, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 32112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 32212bd3c8bSSascha Wildner USB_QUIRK(PANASONIC, KXLCB35AN, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 32312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 32412bd3c8bSSascha Wildner USB_QUIRK(PANASONIC, LS120CAM, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_UFI), 32512bd3c8bSSascha Wildner USB_QUIRK(PLEXTOR, 40_12_40U, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 32612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_TEST_UNIT_READY), 32712bd3c8bSSascha Wildner USB_QUIRK(PNY, ATTACHE2, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 32812bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE, 32912bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP), 33012bd3c8bSSascha Wildner USB_QUIRK(PROLIFIC, PL2506, 0x0000, 0xffff, 33112bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 33212bd3c8bSSascha Wildner USB_QUIRK_VP(USB_VENDOR_SAMSUNG_TECHWIN, 33312bd3c8bSSascha Wildner USB_PRODUCT_SAMSUNG_TECHWIN_DIGIMAX_410, UQ_MSC_FORCE_WIRE_BBB, 33412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 33512bd3c8bSSascha Wildner USB_QUIRK(SANDISK, SDDR05A, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 33612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_READ_CAP_OFFBY1, 33712bd3c8bSSascha Wildner UQ_MSC_NO_GETMAXLUN), 33812bd3c8bSSascha Wildner USB_QUIRK(SANDISK, SDDR09, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI, 33912bd3c8bSSascha Wildner UQ_MSC_READ_CAP_OFFBY1, UQ_MSC_NO_GETMAXLUN), 34012bd3c8bSSascha Wildner USB_QUIRK(SANDISK, SDDR12, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 34112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_READ_CAP_OFFBY1, 34212bd3c8bSSascha Wildner UQ_MSC_NO_GETMAXLUN), 343ff811b0aSSascha Wildner USB_QUIRK(SANDISK, SDCZ2_128, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 344ff811b0aSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE, 345ff811b0aSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 34612bd3c8bSSascha Wildner USB_QUIRK(SANDISK, SDCZ2_256, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 34712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 34812bd3c8bSSascha Wildner USB_QUIRK(SANDISK, SDCZ4_128, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 34912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 35012bd3c8bSSascha Wildner USB_QUIRK(SANDISK, SDCZ4_256, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 35112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 35212bd3c8bSSascha Wildner USB_QUIRK(SANDISK, SDDR31, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 35312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_READ_CAP_OFFBY1), 35457bed822SMarkus Pfeiffer USB_QUIRK(SANDISK, IMAGEMATE_SDDR289, 0x0000, 0xffff, 35557bed822SMarkus Pfeiffer UQ_MSC_NO_SYNC_CACHE, UQ_MSC_NO_GETMAXLUN), 35612bd3c8bSSascha Wildner USB_QUIRK(SCANLOGIC, SL11R, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 35712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_INQUIRY), 35812bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, EUSB, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI_I, 35912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_NO_TEST_UNIT_READY, 36012bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_SHUTTLE_INIT), 36112bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, CDRW, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 36212bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI), 36312bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, CF, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 36412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI), 36512bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, EUSBATAPI, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 36612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI), 36712bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, EUSBCFSM, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 36812bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, EUSCSI, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 36912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 37012bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, HIFD, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 37112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN), 37212bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, SDDR09, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI, 37312bd3c8bSSascha Wildner UQ_MSC_NO_GETMAXLUN), 37412bd3c8bSSascha Wildner USB_QUIRK(SHUTTLE, ZIOMMC, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 37512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN), 37612bd3c8bSSascha Wildner USB_QUIRK(SIGMATEL, I_BEAD100, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 37712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_SHUTTLE_INIT), 37812bd3c8bSSascha Wildner USB_QUIRK(SIIG, WINTERREADER, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 37912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_IGNORE_RESIDUE), 38012bd3c8bSSascha Wildner USB_QUIRK(SKANHEX, MD_7425, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 38112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 38212bd3c8bSSascha Wildner USB_QUIRK(SKANHEX, SX_520Z, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 38312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 38412bd3c8bSSascha Wildner USB_QUIRK(SONY, HANDYCAM, 0x0500, 0x0500, UQ_MSC_FORCE_WIRE_CBI, 38512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC, UQ_MSC_RBC_PAD_TO_12), 38612bd3c8bSSascha Wildner USB_QUIRK(SONY, CLIE_40_MS, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 38712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 38812bd3c8bSSascha Wildner USB_QUIRK(SONY, DSC, 0x0500, 0x0500, UQ_MSC_FORCE_WIRE_CBI, 38912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC, UQ_MSC_RBC_PAD_TO_12), 39012bd3c8bSSascha Wildner USB_QUIRK(SONY, DSC, 0x0600, 0x0600, UQ_MSC_FORCE_WIRE_CBI, 39112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC, UQ_MSC_RBC_PAD_TO_12), 39212bd3c8bSSascha Wildner USB_QUIRK(SONY, DSC, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 39312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC), 39412bd3c8bSSascha Wildner USB_QUIRK(SONY, HANDYCAM, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 39512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC), 39612bd3c8bSSascha Wildner USB_QUIRK(SONY, MSC, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 39712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_RBC), 39812bd3c8bSSascha Wildner USB_QUIRK(SONY, MS_MSC_U03, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 39912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_UFI, UQ_MSC_NO_GETMAXLUN), 40012bd3c8bSSascha Wildner USB_QUIRK(SONY, MS_NW_MS7, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 40112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN), 40212bd3c8bSSascha Wildner USB_QUIRK(SONY, MS_PEG_N760C, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 40312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 40412bd3c8bSSascha Wildner USB_QUIRK(SONY, MSACUS1, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 40512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_GETMAXLUN), 40612bd3c8bSSascha Wildner USB_QUIRK(SONY, PORTABLE_HDD_V2, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 40712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 40857bed822SMarkus Pfeiffer USB_QUIRK(STMICRO, ST72682, 0x0000, 0xffff, UQ_MSC_NO_PREVENT_ALLOW), 40912bd3c8bSSascha Wildner USB_QUIRK(SUPERTOP, IDE, 0x0000, 0xffff, UQ_MSC_IGNORE_RESIDUE, 41012bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 41157bed822SMarkus Pfeiffer USB_QUIRK(SUPERTOP, FLASHDRIVE, 0x0000, 0xffff, UQ_MSC_NO_TEST_UNIT_READY, 41257bed822SMarkus Pfeiffer UQ_MSC_NO_SYNC_CACHE), 41312bd3c8bSSascha Wildner USB_QUIRK(TAUGA, CAMERAMATE, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 41412bd3c8bSSascha Wildner USB_QUIRK(TEAC, FD05PUB, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 41512bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_UFI), 41612bd3c8bSSascha Wildner USB_QUIRK(TECLAST, TLC300, 0x0000, 0xffff, UQ_MSC_NO_TEST_UNIT_READY, 41712bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 41812bd3c8bSSascha Wildner USB_QUIRK(TREK, MEMKEY, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 41912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 42012bd3c8bSSascha Wildner USB_QUIRK(TREK, THUMBDRIVE_8MB, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 42112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_IGNORE_RESIDUE), 42212bd3c8bSSascha Wildner USB_QUIRK(TRUMPION, C3310, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 42312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_UFI), 42412bd3c8bSSascha Wildner USB_QUIRK(TRUMPION, MP3, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_RBC), 42512bd3c8bSSascha Wildner USB_QUIRK(TRUMPION, T33520, 0x0000, 0xffff, UQ_MSC_FORCE_PROTO_SCSI), 42612bd3c8bSSascha Wildner USB_QUIRK(TWINMOS, MDIV, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 42712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI), 42812bd3c8bSSascha Wildner USB_QUIRK(VIA, USB2IDEBRIDGE, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 42912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_SYNC_CACHE), 43012bd3c8bSSascha Wildner USB_QUIRK(VIVITAR, 35XX, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 43112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 43212bd3c8bSSascha Wildner USB_QUIRK(WESTERN, COMBO, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 43312bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 43412bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_IGNORE_RESIDUE), 43512bd3c8bSSascha Wildner USB_QUIRK(WESTERN, EXTHDD, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 43612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 43712bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_IGNORE_RESIDUE), 43812bd3c8bSSascha Wildner USB_QUIRK(WESTERN, MYBOOK, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 43912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY_EVPD, 44012bd3c8bSSascha Wildner UQ_MSC_NO_SYNC_CACHE), 441ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_00, 0x0000, 0xffff, UQ_MSC_FORCE_SHORT_INQ), 442ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_01, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 443ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_02, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 444ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_03, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 445ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_04, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 446ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_05, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 447ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_06, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 448ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_07, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 449ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_08, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 450ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_09, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 451ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_10, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 452ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORT_11, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 453ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_00, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 454ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_01, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 455ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_02, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 456ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_03, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 457ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_04, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 458ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_05, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 459ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_06, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 460ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_07, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 461ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_08, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 462ff811b0aSSascha Wildner USB_QUIRK(WESTERN, MYPASSPORTES_09, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 46312bd3c8bSSascha Wildner USB_QUIRK(WINMAXGROUP, FLASH64MC, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 46412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY), 46512bd3c8bSSascha Wildner USB_QUIRK(YANO, FW800HD, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 46612bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_FORCE_SHORT_INQ, 46712bd3c8bSSascha Wildner UQ_MSC_NO_START_STOP, UQ_MSC_IGNORE_RESIDUE), 46812bd3c8bSSascha Wildner USB_QUIRK(YANO, U640MO, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI_I, 46912bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI, UQ_MSC_FORCE_SHORT_INQ), 47012bd3c8bSSascha Wildner USB_QUIRK(YEDATA, FLASHBUSTERU, 0x0000, 0x007F, UQ_MSC_FORCE_WIRE_CBI, 47112bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_UFI, UQ_MSC_NO_RS_CLEAR_UA, UQ_MSC_FLOPPY_SPEED, 47212bd3c8bSSascha Wildner UQ_MSC_NO_TEST_UNIT_READY, UQ_MSC_NO_GETMAXLUN), 47312bd3c8bSSascha Wildner USB_QUIRK(YEDATA, FLASHBUSTERU, 0x0080, 0x0080, UQ_MSC_FORCE_WIRE_CBI_I, 47412bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_UFI, UQ_MSC_NO_RS_CLEAR_UA, UQ_MSC_FLOPPY_SPEED, 47512bd3c8bSSascha Wildner UQ_MSC_NO_TEST_UNIT_READY, UQ_MSC_NO_GETMAXLUN), 47612bd3c8bSSascha Wildner USB_QUIRK(YEDATA, FLASHBUSTERU, 0x0081, 0xFFFF, UQ_MSC_FORCE_WIRE_CBI_I, 47712bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_UFI, UQ_MSC_NO_RS_CLEAR_UA, UQ_MSC_FLOPPY_SPEED, 47812bd3c8bSSascha Wildner UQ_MSC_NO_GETMAXLUN), 47912bd3c8bSSascha Wildner USB_QUIRK(ZORAN, EX20DSC, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_CBI, 48012bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_ATAPI), 48112bd3c8bSSascha Wildner USB_QUIRK(MEIZU, M6_SL, 0x0000, 0xffff, UQ_MSC_FORCE_WIRE_BBB, 48212bd3c8bSSascha Wildner UQ_MSC_FORCE_PROTO_SCSI, UQ_MSC_NO_INQUIRY, UQ_MSC_NO_SYNC_CACHE), 483ff811b0aSSascha Wildner USB_QUIRK(TOSHIBA, TRANSMEMORY, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE, 484ff811b0aSSascha Wildner UQ_MSC_NO_PREVENT_ALLOW), 48557bed822SMarkus Pfeiffer USB_QUIRK(VIALABS, USB30SATABRIDGE, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE), 486dd681da6SMatthew Dillon USB_QUIRK(QUALCOMMINC, ZTE_MF730M, 0x0000, 0xffff, UQ_MSC_NO_GETMAXLUN, 487dd681da6SMatthew Dillon UQ_MSC_NO_INQUIRY, UQ_CFG_INDEX_0), 48857bed822SMarkus Pfeiffer 48912bd3c8bSSascha Wildner /* Non-standard USB MIDI devices */ 49012bd3c8bSSascha Wildner USB_QUIRK(ROLAND, UM1, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49112bd3c8bSSascha Wildner USB_QUIRK(ROLAND, SC8850, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49212bd3c8bSSascha Wildner USB_QUIRK(ROLAND, SD90, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49312bd3c8bSSascha Wildner USB_QUIRK(ROLAND, UM880N, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49412bd3c8bSSascha Wildner USB_QUIRK(ROLAND, UA100, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49512bd3c8bSSascha Wildner USB_QUIRK(ROLAND, UM4, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49612bd3c8bSSascha Wildner USB_QUIRK(ROLAND, U8, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49712bd3c8bSSascha Wildner USB_QUIRK(ROLAND, UM2, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49812bd3c8bSSascha Wildner USB_QUIRK(ROLAND, SC8820, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 49912bd3c8bSSascha Wildner USB_QUIRK(ROLAND, PC300, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 50012bd3c8bSSascha Wildner USB_QUIRK(ROLAND, SK500, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 50112bd3c8bSSascha Wildner USB_QUIRK(ROLAND, SCD70, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 50212bd3c8bSSascha Wildner USB_QUIRK(ROLAND, UM550, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 50312bd3c8bSSascha Wildner USB_QUIRK(ROLAND, SD20, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 50412bd3c8bSSascha Wildner USB_QUIRK(ROLAND, SD80, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 50512bd3c8bSSascha Wildner USB_QUIRK(ROLAND, UA700, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 50657bed822SMarkus Pfeiffer USB_QUIRK(EGO, M4U, 0x0000, 0xffff, UQ_SINGLE_CMD_MIDI), 50757bed822SMarkus Pfeiffer USB_QUIRK(LOGILINK, U2M, 0x0000, 0xffff, UQ_SINGLE_CMD_MIDI), 50812bd3c8bSSascha Wildner USB_QUIRK(MEDELI, DD305, 0x0000, 0xffff, UQ_SINGLE_CMD_MIDI, UQ_MATCH_VENDOR_ONLY), 50957bed822SMarkus Pfeiffer USB_QUIRK(REDOCTANE, GHMIDI, 0x0000, 0xffff, UQ_SINGLE_CMD_MIDI), 51057bed822SMarkus Pfeiffer USB_QUIRK(TEXTECH, U2M_1, 0x0000, 0xffff, UQ_SINGLE_CMD_MIDI), 51157bed822SMarkus Pfeiffer USB_QUIRK(TEXTECH, U2M_2, 0x0000, 0xffff, UQ_SINGLE_CMD_MIDI), 51257bed822SMarkus Pfeiffer USB_QUIRK(WCH2, U2M, 0x0000, 0xffff, UQ_SINGLE_CMD_MIDI), 51357bed822SMarkus Pfeiffer 51457bed822SMarkus Pfeiffer /* Non-standard USB AUDIO devices */ 51557bed822SMarkus Pfeiffer USB_QUIRK(MAUDIO, FASTTRACKULTRA, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 51657bed822SMarkus Pfeiffer USB_QUIRK(MAUDIO, FASTTRACKULTRA8R, 0x0000, 0xffff, UQ_AU_VENDOR_CLASS), 51712bd3c8bSSascha Wildner 51812bd3c8bSSascha Wildner /* 51912bd3c8bSSascha Wildner * Quirks for manufacturers which USB devices does not respond 52012bd3c8bSSascha Wildner * after issuing non-supported commands: 52112bd3c8bSSascha Wildner */ 52212bd3c8bSSascha Wildner USB_QUIRK(ALCOR, DUMMY, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE, UQ_MSC_NO_TEST_UNIT_READY, UQ_MATCH_VENDOR_ONLY), 52357bed822SMarkus Pfeiffer USB_QUIRK(APPLE, DUMMY, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE, UQ_MATCH_VENDOR_ONLY), 52412bd3c8bSSascha Wildner USB_QUIRK(FEIYA, DUMMY, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE, UQ_MATCH_VENDOR_ONLY), 52512bd3c8bSSascha Wildner USB_QUIRK(REALTEK, DUMMY, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE, UQ_MATCH_VENDOR_ONLY), 52612bd3c8bSSascha Wildner USB_QUIRK(INITIO, DUMMY, 0x0000, 0xffff, UQ_MSC_NO_SYNC_CACHE, UQ_MATCH_VENDOR_ONLY), 52712bd3c8bSSascha Wildner }; 52812bd3c8bSSascha Wildner #undef USB_QUIRK_VP 52912bd3c8bSSascha Wildner #undef USB_QUIRK 53012bd3c8bSSascha Wildner 53112bd3c8bSSascha Wildner static const char *usb_quirk_str[USB_QUIRK_MAX] = { 53212bd3c8bSSascha Wildner [UQ_NONE] = "UQ_NONE", 53312bd3c8bSSascha Wildner [UQ_MATCH_VENDOR_ONLY] = "UQ_MATCH_VENDOR_ONLY", 53412bd3c8bSSascha Wildner [UQ_AUDIO_SWAP_LR] = "UQ_AUDIO_SWAP_LR", 53512bd3c8bSSascha Wildner [UQ_AU_INP_ASYNC] = "UQ_AU_INP_ASYNC", 53612bd3c8bSSascha Wildner [UQ_AU_NO_FRAC] = "UQ_AU_NO_FRAC", 53712bd3c8bSSascha Wildner [UQ_AU_NO_XU] = "UQ_AU_NO_XU", 53812bd3c8bSSascha Wildner [UQ_BAD_ADC] = "UQ_BAD_ADC", 53912bd3c8bSSascha Wildner [UQ_BAD_AUDIO] = "UQ_BAD_AUDIO", 54012bd3c8bSSascha Wildner [UQ_BROKEN_BIDIR] = "UQ_BROKEN_BIDIR", 54112bd3c8bSSascha Wildner [UQ_BUS_POWERED] = "UQ_BUS_POWERED", 54212bd3c8bSSascha Wildner [UQ_HID_IGNORE] = "UQ_HID_IGNORE", 54312bd3c8bSSascha Wildner [UQ_KBD_IGNORE] = "UQ_KBD_IGNORE", 54412bd3c8bSSascha Wildner [UQ_KBD_BOOTPROTO] = "UQ_KBD_BOOTPROTO", 54557bed822SMarkus Pfeiffer [UQ_UMS_IGNORE] = "UQ_UMS_IGNORE", 54612bd3c8bSSascha Wildner [UQ_MS_BAD_CLASS] = "UQ_MS_BAD_CLASS", 54712bd3c8bSSascha Wildner [UQ_MS_LEADING_BYTE] = "UQ_MS_LEADING_BYTE", 54812bd3c8bSSascha Wildner [UQ_MS_REVZ] = "UQ_MS_REVZ", 54912bd3c8bSSascha Wildner [UQ_NO_STRINGS] = "UQ_NO_STRINGS", 55012bd3c8bSSascha Wildner [UQ_POWER_CLAIM] = "UQ_POWER_CLAIM", 55112bd3c8bSSascha Wildner [UQ_SPUR_BUT_UP] = "UQ_SPUR_BUT_UP", 55212bd3c8bSSascha Wildner [UQ_SWAP_UNICODE] = "UQ_SWAP_UNICODE", 55312bd3c8bSSascha Wildner [UQ_CFG_INDEX_1] = "UQ_CFG_INDEX_1", 55412bd3c8bSSascha Wildner [UQ_CFG_INDEX_2] = "UQ_CFG_INDEX_2", 55512bd3c8bSSascha Wildner [UQ_CFG_INDEX_3] = "UQ_CFG_INDEX_3", 55612bd3c8bSSascha Wildner [UQ_CFG_INDEX_4] = "UQ_CFG_INDEX_4", 55712bd3c8bSSascha Wildner [UQ_CFG_INDEX_0] = "UQ_CFG_INDEX_0", 55812bd3c8bSSascha Wildner [UQ_ASSUME_CM_OVER_DATA] = "UQ_ASSUME_CM_OVER_DATA", 55912bd3c8bSSascha Wildner [UQ_MSC_NO_TEST_UNIT_READY] = "UQ_MSC_NO_TEST_UNIT_READY", 56012bd3c8bSSascha Wildner [UQ_MSC_NO_RS_CLEAR_UA] = "UQ_MSC_NO_RS_CLEAR_UA", 56112bd3c8bSSascha Wildner [UQ_MSC_NO_START_STOP] = "UQ_MSC_NO_START_STOP", 56212bd3c8bSSascha Wildner [UQ_MSC_NO_GETMAXLUN] = "UQ_MSC_NO_GETMAXLUN", 56312bd3c8bSSascha Wildner [UQ_MSC_NO_INQUIRY] = "UQ_MSC_NO_INQUIRY", 56412bd3c8bSSascha Wildner [UQ_MSC_NO_INQUIRY_EVPD] = "UQ_MSC_NO_INQUIRY_EVPD", 56557bed822SMarkus Pfeiffer [UQ_MSC_NO_PREVENT_ALLOW] = "UQ_MSC_NO_PREVENT_ALLOW", 56612bd3c8bSSascha Wildner [UQ_MSC_NO_SYNC_CACHE] = "UQ_MSC_NO_SYNC_CACHE", 56712bd3c8bSSascha Wildner [UQ_MSC_SHUTTLE_INIT] = "UQ_MSC_SHUTTLE_INIT", 56812bd3c8bSSascha Wildner [UQ_MSC_ALT_IFACE_1] = "UQ_MSC_ALT_IFACE_1", 56912bd3c8bSSascha Wildner [UQ_MSC_FLOPPY_SPEED] = "UQ_MSC_FLOPPY_SPEED", 57012bd3c8bSSascha Wildner [UQ_MSC_IGNORE_RESIDUE] = "UQ_MSC_IGNORE_RESIDUE", 57112bd3c8bSSascha Wildner [UQ_MSC_WRONG_CSWSIG] = "UQ_MSC_WRONG_CSWSIG", 57212bd3c8bSSascha Wildner [UQ_MSC_RBC_PAD_TO_12] = "UQ_MSC_RBC_PAD_TO_12", 57312bd3c8bSSascha Wildner [UQ_MSC_READ_CAP_OFFBY1] = "UQ_MSC_READ_CAP_OFFBY1", 57412bd3c8bSSascha Wildner [UQ_MSC_FORCE_SHORT_INQ] = "UQ_MSC_FORCE_SHORT_INQ", 57512bd3c8bSSascha Wildner [UQ_MSC_FORCE_WIRE_BBB] = "UQ_MSC_FORCE_WIRE_BBB", 57612bd3c8bSSascha Wildner [UQ_MSC_FORCE_WIRE_CBI] = "UQ_MSC_FORCE_WIRE_CBI", 57712bd3c8bSSascha Wildner [UQ_MSC_FORCE_WIRE_CBI_I] = "UQ_MSC_FORCE_WIRE_CBI_I", 57812bd3c8bSSascha Wildner [UQ_MSC_FORCE_PROTO_SCSI] = "UQ_MSC_FORCE_PROTO_SCSI", 57912bd3c8bSSascha Wildner [UQ_MSC_FORCE_PROTO_ATAPI] = "UQ_MSC_FORCE_PROTO_ATAPI", 58012bd3c8bSSascha Wildner [UQ_MSC_FORCE_PROTO_UFI] = "UQ_MSC_FORCE_PROTO_UFI", 58112bd3c8bSSascha Wildner [UQ_MSC_FORCE_PROTO_RBC] = "UQ_MSC_FORCE_PROTO_RBC", 58212bd3c8bSSascha Wildner [UQ_MSC_EJECT_HUAWEI] = "UQ_MSC_EJECT_HUAWEI", 58312bd3c8bSSascha Wildner [UQ_MSC_EJECT_SIERRA] = "UQ_MSC_EJECT_SIERRA", 58412bd3c8bSSascha Wildner [UQ_MSC_EJECT_SCSIEJECT] = "UQ_MSC_EJECT_SCSIEJECT", 58512bd3c8bSSascha Wildner [UQ_MSC_EJECT_REZERO] = "UQ_MSC_EJECT_REZERO", 58612bd3c8bSSascha Wildner [UQ_MSC_EJECT_ZTESTOR] = "UQ_MSC_EJECT_ZTESTOR", 58712bd3c8bSSascha Wildner [UQ_MSC_EJECT_CMOTECH] = "UQ_MSC_EJECT_CMOTECH", 58812bd3c8bSSascha Wildner [UQ_MSC_EJECT_WAIT] = "UQ_MSC_EJECT_WAIT", 58912bd3c8bSSascha Wildner [UQ_MSC_EJECT_SAEL_M460] = "UQ_MSC_EJECT_SAEL_M460", 59012bd3c8bSSascha Wildner [UQ_MSC_EJECT_HUAWEISCSI] = "UQ_MSC_EJECT_HUAWEISCSI", 591ff811b0aSSascha Wildner [UQ_MSC_EJECT_HUAWEISCSI2] = "UQ_MSC_EJECT_HUAWEISCSI2", 59212bd3c8bSSascha Wildner [UQ_MSC_EJECT_TCT] = "UQ_MSC_EJECT_TCT", 59312bd3c8bSSascha Wildner [UQ_BAD_MIDI] = "UQ_BAD_MIDI", 59412bd3c8bSSascha Wildner [UQ_AU_VENDOR_CLASS] = "UQ_AU_VENDOR_CLASS", 59512bd3c8bSSascha Wildner [UQ_SINGLE_CMD_MIDI] = "UQ_SINGLE_CMD_MIDI", 59612bd3c8bSSascha Wildner }; 59712bd3c8bSSascha Wildner 59812bd3c8bSSascha Wildner /*------------------------------------------------------------------------* 59912bd3c8bSSascha Wildner * usb_quirkstr 60012bd3c8bSSascha Wildner * 60112bd3c8bSSascha Wildner * This function converts an USB quirk code into a string. 60212bd3c8bSSascha Wildner *------------------------------------------------------------------------*/ 60312bd3c8bSSascha Wildner static const char * 60412bd3c8bSSascha Wildner usb_quirkstr(uint16_t quirk) 60512bd3c8bSSascha Wildner { 60612bd3c8bSSascha Wildner return ((quirk < USB_QUIRK_MAX) ? 60712bd3c8bSSascha Wildner usb_quirk_str[quirk] : "USB_QUIRK_UNKNOWN"); 60812bd3c8bSSascha Wildner } 60912bd3c8bSSascha Wildner 61012bd3c8bSSascha Wildner /*------------------------------------------------------------------------* 61112bd3c8bSSascha Wildner * usb_test_quirk_by_info 61212bd3c8bSSascha Wildner * 61312bd3c8bSSascha Wildner * Returns: 61412bd3c8bSSascha Wildner * 0: Quirk not found 61512bd3c8bSSascha Wildner * Else: Quirk found 61612bd3c8bSSascha Wildner *------------------------------------------------------------------------*/ 61712bd3c8bSSascha Wildner static uint8_t 61812bd3c8bSSascha Wildner usb_test_quirk_by_info(const struct usbd_lookup_info *info, uint16_t quirk) 61912bd3c8bSSascha Wildner { 62012bd3c8bSSascha Wildner uint16_t x; 62112bd3c8bSSascha Wildner uint16_t y; 62212bd3c8bSSascha Wildner 62312bd3c8bSSascha Wildner if (quirk == UQ_NONE) 62412bd3c8bSSascha Wildner goto done; 62512bd3c8bSSascha Wildner 626ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_EXCLUSIVE); 62712bd3c8bSSascha Wildner 62812bd3c8bSSascha Wildner for (x = 0; x != USB_DEV_QUIRKS_MAX; x++) { 62912bd3c8bSSascha Wildner /* see if quirk information does not match */ 63012bd3c8bSSascha Wildner if ((usb_quirks[x].vid != info->idVendor) || 63112bd3c8bSSascha Wildner (usb_quirks[x].lo_rev > info->bcdDevice) || 63212bd3c8bSSascha Wildner (usb_quirks[x].hi_rev < info->bcdDevice)) { 63312bd3c8bSSascha Wildner continue; 63412bd3c8bSSascha Wildner } 63512bd3c8bSSascha Wildner /* see if quirk only should match vendor ID */ 63612bd3c8bSSascha Wildner if (usb_quirks[x].pid != info->idProduct) { 63712bd3c8bSSascha Wildner if (usb_quirks[x].pid != 0) 63812bd3c8bSSascha Wildner continue; 63912bd3c8bSSascha Wildner 64012bd3c8bSSascha Wildner for (y = 0; y != USB_SUB_QUIRKS_MAX; y++) { 64112bd3c8bSSascha Wildner if (usb_quirks[x].quirks[y] == UQ_MATCH_VENDOR_ONLY) 64212bd3c8bSSascha Wildner break; 64312bd3c8bSSascha Wildner } 64412bd3c8bSSascha Wildner if (y == USB_SUB_QUIRKS_MAX) 64512bd3c8bSSascha Wildner continue; 64612bd3c8bSSascha Wildner } 64712bd3c8bSSascha Wildner /* lookup quirk */ 64812bd3c8bSSascha Wildner for (y = 0; y != USB_SUB_QUIRKS_MAX; y++) { 64912bd3c8bSSascha Wildner if (usb_quirks[x].quirks[y] == quirk) { 650ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 65112bd3c8bSSascha Wildner DPRINTF("Found quirk '%s'.\n", usb_quirkstr(quirk)); 65212bd3c8bSSascha Wildner return (1); 65312bd3c8bSSascha Wildner } 65412bd3c8bSSascha Wildner } 65512bd3c8bSSascha Wildner /* no quirk found */ 65612bd3c8bSSascha Wildner break; 65712bd3c8bSSascha Wildner } 658ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 65912bd3c8bSSascha Wildner done: 66012bd3c8bSSascha Wildner return (0); /* no quirk match */ 66112bd3c8bSSascha Wildner } 66212bd3c8bSSascha Wildner 66312bd3c8bSSascha Wildner static struct usb_quirk_entry * 66412bd3c8bSSascha Wildner usb_quirk_get_entry(uint16_t vid, uint16_t pid, 66512bd3c8bSSascha Wildner uint16_t lo_rev, uint16_t hi_rev, uint8_t do_alloc) 66612bd3c8bSSascha Wildner { 66712bd3c8bSSascha Wildner uint16_t x; 66812bd3c8bSSascha Wildner 669ac499a8fSSascha Wildner KKASSERT(lockowned(&usb_quirk_lock)); 67012bd3c8bSSascha Wildner 67112bd3c8bSSascha Wildner if ((vid | pid | lo_rev | hi_rev) == 0) { 67212bd3c8bSSascha Wildner /* all zero - special case */ 67312bd3c8bSSascha Wildner return (usb_quirks + USB_DEV_QUIRKS_MAX - 1); 67412bd3c8bSSascha Wildner } 67512bd3c8bSSascha Wildner /* search for an existing entry */ 67612bd3c8bSSascha Wildner for (x = 0; x != USB_DEV_QUIRKS_MAX; x++) { 67712bd3c8bSSascha Wildner /* see if quirk information does not match */ 67812bd3c8bSSascha Wildner if ((usb_quirks[x].vid != vid) || 67912bd3c8bSSascha Wildner (usb_quirks[x].pid != pid) || 68012bd3c8bSSascha Wildner (usb_quirks[x].lo_rev != lo_rev) || 68112bd3c8bSSascha Wildner (usb_quirks[x].hi_rev != hi_rev)) { 68212bd3c8bSSascha Wildner continue; 68312bd3c8bSSascha Wildner } 68412bd3c8bSSascha Wildner return (usb_quirks + x); 68512bd3c8bSSascha Wildner } 68612bd3c8bSSascha Wildner 68712bd3c8bSSascha Wildner if (do_alloc == 0) { 68812bd3c8bSSascha Wildner /* no match */ 68912bd3c8bSSascha Wildner return (NULL); 69012bd3c8bSSascha Wildner } 69112bd3c8bSSascha Wildner /* search for a free entry */ 69212bd3c8bSSascha Wildner for (x = 0; x != USB_DEV_QUIRKS_MAX; x++) { 69312bd3c8bSSascha Wildner /* see if quirk information does not match */ 69412bd3c8bSSascha Wildner if ((usb_quirks[x].vid | 69512bd3c8bSSascha Wildner usb_quirks[x].pid | 69612bd3c8bSSascha Wildner usb_quirks[x].lo_rev | 69712bd3c8bSSascha Wildner usb_quirks[x].hi_rev) != 0) { 69812bd3c8bSSascha Wildner continue; 69912bd3c8bSSascha Wildner } 70012bd3c8bSSascha Wildner usb_quirks[x].vid = vid; 70112bd3c8bSSascha Wildner usb_quirks[x].pid = pid; 70212bd3c8bSSascha Wildner usb_quirks[x].lo_rev = lo_rev; 70312bd3c8bSSascha Wildner usb_quirks[x].hi_rev = hi_rev; 70412bd3c8bSSascha Wildner 70512bd3c8bSSascha Wildner return (usb_quirks + x); 70612bd3c8bSSascha Wildner } 70712bd3c8bSSascha Wildner 70812bd3c8bSSascha Wildner /* no entry found */ 70912bd3c8bSSascha Wildner return (NULL); 71012bd3c8bSSascha Wildner } 71112bd3c8bSSascha Wildner 71212bd3c8bSSascha Wildner /*------------------------------------------------------------------------* 71312bd3c8bSSascha Wildner * usb_quirk_ioctl - handle quirk IOCTLs 71412bd3c8bSSascha Wildner * 71512bd3c8bSSascha Wildner * Returns: 71612bd3c8bSSascha Wildner * 0: Success 71712bd3c8bSSascha Wildner * Else: Failure 71812bd3c8bSSascha Wildner *------------------------------------------------------------------------*/ 71912bd3c8bSSascha Wildner static int 72012bd3c8bSSascha Wildner usb_quirk_ioctl(unsigned long cmd, caddr_t data, 72112bd3c8bSSascha Wildner int fflag, struct thread *td) 72212bd3c8bSSascha Wildner { 72312bd3c8bSSascha Wildner struct usb_gen_quirk *pgq; 72412bd3c8bSSascha Wildner struct usb_quirk_entry *pqe; 72512bd3c8bSSascha Wildner uint32_t x; 72612bd3c8bSSascha Wildner uint32_t y; 72712bd3c8bSSascha Wildner int err; 72812bd3c8bSSascha Wildner 72912bd3c8bSSascha Wildner switch (cmd) { 73012bd3c8bSSascha Wildner case USB_DEV_QUIRK_GET: 73112bd3c8bSSascha Wildner pgq = (void *)data; 73212bd3c8bSSascha Wildner x = pgq->index % USB_SUB_QUIRKS_MAX; 73312bd3c8bSSascha Wildner y = pgq->index / USB_SUB_QUIRKS_MAX; 73412bd3c8bSSascha Wildner if (y >= USB_DEV_QUIRKS_MAX) { 73512bd3c8bSSascha Wildner return (EINVAL); 73612bd3c8bSSascha Wildner } 737ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_EXCLUSIVE); 73812bd3c8bSSascha Wildner /* copy out data */ 73912bd3c8bSSascha Wildner pgq->vid = usb_quirks[y].vid; 74012bd3c8bSSascha Wildner pgq->pid = usb_quirks[y].pid; 74112bd3c8bSSascha Wildner pgq->bcdDeviceLow = usb_quirks[y].lo_rev; 74212bd3c8bSSascha Wildner pgq->bcdDeviceHigh = usb_quirks[y].hi_rev; 74312bd3c8bSSascha Wildner strlcpy(pgq->quirkname, 74412bd3c8bSSascha Wildner usb_quirkstr(usb_quirks[y].quirks[x]), 74512bd3c8bSSascha Wildner sizeof(pgq->quirkname)); 746ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 74712bd3c8bSSascha Wildner return (0); /* success */ 74812bd3c8bSSascha Wildner 74912bd3c8bSSascha Wildner case USB_QUIRK_NAME_GET: 75012bd3c8bSSascha Wildner pgq = (void *)data; 75112bd3c8bSSascha Wildner x = pgq->index; 75212bd3c8bSSascha Wildner if (x >= USB_QUIRK_MAX) { 75312bd3c8bSSascha Wildner return (EINVAL); 75412bd3c8bSSascha Wildner } 75512bd3c8bSSascha Wildner strlcpy(pgq->quirkname, 75612bd3c8bSSascha Wildner usb_quirkstr(x), sizeof(pgq->quirkname)); 75712bd3c8bSSascha Wildner return (0); /* success */ 75812bd3c8bSSascha Wildner 75912bd3c8bSSascha Wildner case USB_DEV_QUIRK_ADD: 76012bd3c8bSSascha Wildner pgq = (void *)data; 76112bd3c8bSSascha Wildner 76212bd3c8bSSascha Wildner /* check privileges */ 76312bd3c8bSSascha Wildner err = priv_check(curthread, PRIV_DRIVER); 76412bd3c8bSSascha Wildner if (err) { 76512bd3c8bSSascha Wildner return (err); 76612bd3c8bSSascha Wildner } 76712bd3c8bSSascha Wildner /* convert quirk string into numerical */ 76812bd3c8bSSascha Wildner for (y = 0; y != USB_DEV_QUIRKS_MAX; y++) { 76912bd3c8bSSascha Wildner if (strcmp(pgq->quirkname, usb_quirkstr(y)) == 0) { 77012bd3c8bSSascha Wildner break; 77112bd3c8bSSascha Wildner } 77212bd3c8bSSascha Wildner } 77312bd3c8bSSascha Wildner if (y == USB_DEV_QUIRKS_MAX) { 77412bd3c8bSSascha Wildner return (EINVAL); 77512bd3c8bSSascha Wildner } 77612bd3c8bSSascha Wildner if (y == UQ_NONE) { 77712bd3c8bSSascha Wildner return (EINVAL); 77812bd3c8bSSascha Wildner } 779ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_EXCLUSIVE); 78012bd3c8bSSascha Wildner pqe = usb_quirk_get_entry(pgq->vid, pgq->pid, 78112bd3c8bSSascha Wildner pgq->bcdDeviceLow, pgq->bcdDeviceHigh, 1); 78212bd3c8bSSascha Wildner if (pqe == NULL) { 783ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 78412bd3c8bSSascha Wildner return (EINVAL); 78512bd3c8bSSascha Wildner } 78612bd3c8bSSascha Wildner for (x = 0; x != USB_SUB_QUIRKS_MAX; x++) { 78712bd3c8bSSascha Wildner if (pqe->quirks[x] == UQ_NONE) { 78812bd3c8bSSascha Wildner pqe->quirks[x] = y; 78912bd3c8bSSascha Wildner break; 79012bd3c8bSSascha Wildner } 79112bd3c8bSSascha Wildner } 792ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 79312bd3c8bSSascha Wildner if (x == USB_SUB_QUIRKS_MAX) { 79412bd3c8bSSascha Wildner return (ENOMEM); 79512bd3c8bSSascha Wildner } 79612bd3c8bSSascha Wildner return (0); /* success */ 79712bd3c8bSSascha Wildner 79812bd3c8bSSascha Wildner case USB_DEV_QUIRK_REMOVE: 79912bd3c8bSSascha Wildner pgq = (void *)data; 80012bd3c8bSSascha Wildner /* check privileges */ 80112bd3c8bSSascha Wildner err = priv_check(curthread, PRIV_DRIVER); 80212bd3c8bSSascha Wildner if (err) { 80312bd3c8bSSascha Wildner return (err); 80412bd3c8bSSascha Wildner } 80512bd3c8bSSascha Wildner /* convert quirk string into numerical */ 80612bd3c8bSSascha Wildner for (y = 0; y != USB_DEV_QUIRKS_MAX; y++) { 80712bd3c8bSSascha Wildner if (strcmp(pgq->quirkname, usb_quirkstr(y)) == 0) { 80812bd3c8bSSascha Wildner break; 80912bd3c8bSSascha Wildner } 81012bd3c8bSSascha Wildner } 81112bd3c8bSSascha Wildner if (y == USB_DEV_QUIRKS_MAX) { 81212bd3c8bSSascha Wildner return (EINVAL); 81312bd3c8bSSascha Wildner } 81412bd3c8bSSascha Wildner if (y == UQ_NONE) { 81512bd3c8bSSascha Wildner return (EINVAL); 81612bd3c8bSSascha Wildner } 817ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_EXCLUSIVE); 81812bd3c8bSSascha Wildner pqe = usb_quirk_get_entry(pgq->vid, pgq->pid, 81912bd3c8bSSascha Wildner pgq->bcdDeviceLow, pgq->bcdDeviceHigh, 0); 82012bd3c8bSSascha Wildner if (pqe == NULL) { 821ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 82212bd3c8bSSascha Wildner return (EINVAL); 82312bd3c8bSSascha Wildner } 82412bd3c8bSSascha Wildner for (x = 0; x != USB_SUB_QUIRKS_MAX; x++) { 82512bd3c8bSSascha Wildner if (pqe->quirks[x] == y) { 82612bd3c8bSSascha Wildner pqe->quirks[x] = UQ_NONE; 82712bd3c8bSSascha Wildner break; 82812bd3c8bSSascha Wildner } 82912bd3c8bSSascha Wildner } 83012bd3c8bSSascha Wildner if (x == USB_SUB_QUIRKS_MAX) { 831ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 83212bd3c8bSSascha Wildner return (ENOMEM); 83312bd3c8bSSascha Wildner } 83412bd3c8bSSascha Wildner for (x = 0; x != USB_SUB_QUIRKS_MAX; x++) { 83512bd3c8bSSascha Wildner if (pqe->quirks[x] != UQ_NONE) { 83612bd3c8bSSascha Wildner break; 83712bd3c8bSSascha Wildner } 83812bd3c8bSSascha Wildner } 83912bd3c8bSSascha Wildner if (x == USB_SUB_QUIRKS_MAX) { 84012bd3c8bSSascha Wildner /* all quirk entries are unused - release */ 841cc194c56SSascha Wildner memset(pqe, 0, sizeof(*pqe)); 84212bd3c8bSSascha Wildner } 843ac499a8fSSascha Wildner lockmgr(&usb_quirk_lock, LK_RELEASE); 84412bd3c8bSSascha Wildner return (0); /* success */ 84512bd3c8bSSascha Wildner 84612bd3c8bSSascha Wildner default: 84712bd3c8bSSascha Wildner break; 84812bd3c8bSSascha Wildner } 84912bd3c8bSSascha Wildner return (ENOIOCTL); 85012bd3c8bSSascha Wildner } 85112bd3c8bSSascha Wildner 85212bd3c8bSSascha Wildner static void 85312bd3c8bSSascha Wildner usb_quirk_init(void *arg) 85412bd3c8bSSascha Wildner { 85512bd3c8bSSascha Wildner /* initialize mutex */ 856ac499a8fSSascha Wildner lockinit(&usb_quirk_lock, "USB quirk", 0, 0); 85712bd3c8bSSascha Wildner 85812bd3c8bSSascha Wildner /* register our function */ 85912bd3c8bSSascha Wildner usb_test_quirk_p = &usb_test_quirk_by_info; 86012bd3c8bSSascha Wildner usb_quirk_ioctl_p = &usb_quirk_ioctl; 86112bd3c8bSSascha Wildner } 86212bd3c8bSSascha Wildner 86312bd3c8bSSascha Wildner static void 86412bd3c8bSSascha Wildner usb_quirk_uninit(void *arg) 86512bd3c8bSSascha Wildner { 86612bd3c8bSSascha Wildner usb_quirk_unload(arg); 86712bd3c8bSSascha Wildner 86812bd3c8bSSascha Wildner /* destroy mutex */ 869ac499a8fSSascha Wildner lockuninit(&usb_quirk_lock); 87012bd3c8bSSascha Wildner } 87112bd3c8bSSascha Wildner 872ac499a8fSSascha Wildner SYSINIT(usb_quirk_init, SI_SUB_DRIVERS, SI_ORDER_FIRST, usb_quirk_init, NULL); 873ac499a8fSSascha Wildner SYSUNINIT(usb_quirk_uninit, SI_SUB_DRIVERS, SI_ORDER_ANY, usb_quirk_uninit, NULL); 874