1 // SPDX-License-Identifier: GPL-2.0
3 * Common USB debugging functions
5 * Copyright (C) 2010-2011 Texas Instruments Incorporated - https://www.ti.com
11 #include <linux/kernel.h>
12 #include <linux/usb/ch9.h>
14 static void usb_decode_get_status(__u8 bRequestType, __u16 wIndex,
15 __u16 wLength, char *str, size_t size)
17 switch (bRequestType & USB_RECIP_MASK) {
18 case USB_RECIP_DEVICE:
19 snprintf(str, size, "Get Device Status(Length = %d)", wLength);
21 case USB_RECIP_INTERFACE:
23 "Get Interface Status(Intf = %d, Length = %d)",
26 case USB_RECIP_ENDPOINT:
27 snprintf(str, size, "Get Endpoint Status(ep%d%s)",
29 wIndex & USB_DIR_IN ? "in" : "out");
34 static const char *usb_decode_device_feature(u16 wValue)
37 case USB_DEVICE_SELF_POWERED:
38 return "Self Powered";
39 case USB_DEVICE_REMOTE_WAKEUP:
40 return "Remote Wakeup";
41 case USB_DEVICE_TEST_MODE:
43 case USB_DEVICE_U1_ENABLE:
45 case USB_DEVICE_U2_ENABLE:
47 case USB_DEVICE_LTM_ENABLE:
54 static const char *usb_decode_test_mode(u16 wIndex)
61 case USB_TEST_SE0_NAK:
62 return ": TEST_SE0_NAK";
64 return ": TEST_PACKET";
65 case USB_TEST_FORCE_ENABLE:
66 return ": TEST_FORCE_EN";
72 static void usb_decode_set_clear_feature(__u8 bRequestType,
73 __u8 bRequest, __u16 wValue,
74 __u16 wIndex, char *str, size_t size)
76 switch (bRequestType & USB_RECIP_MASK) {
77 case USB_RECIP_DEVICE:
78 snprintf(str, size, "%s Device Feature(%s%s)",
79 bRequest == USB_REQ_CLEAR_FEATURE ? "Clear" : "Set",
80 usb_decode_device_feature(wValue),
81 wValue == USB_DEVICE_TEST_MODE ?
82 usb_decode_test_mode(wIndex) : "");
84 case USB_RECIP_INTERFACE:
85 snprintf(str, size, "%s Interface Feature(%s)",
86 bRequest == USB_REQ_CLEAR_FEATURE ? "Clear" : "Set",
87 wValue == USB_INTRF_FUNC_SUSPEND ?
88 "Function Suspend" : "UNKNOWN");
90 case USB_RECIP_ENDPOINT:
91 snprintf(str, size, "%s Endpoint Feature(%s ep%d%s)",
92 bRequest == USB_REQ_CLEAR_FEATURE ? "Clear" : "Set",
93 wValue == USB_ENDPOINT_HALT ? "Halt" : "UNKNOWN",
95 wIndex & USB_DIR_IN ? "in" : "out");
100 static void usb_decode_set_address(__u16 wValue, char *str, size_t size)
102 snprintf(str, size, "Set Address(Addr = %02x)", wValue);
105 static void usb_decode_get_set_descriptor(__u8 bRequestType, __u8 bRequest,
106 __u16 wValue, __u16 wIndex,
107 __u16 wLength, char *str, size_t size)
111 switch (wValue >> 8) {
121 case USB_DT_INTERFACE:
124 case USB_DT_ENDPOINT:
127 case USB_DT_DEVICE_QUALIFIER:
128 s = "Device Qualifier";
130 case USB_DT_OTHER_SPEED_CONFIG:
131 s = "Other Speed Config";
133 case USB_DT_INTERFACE_POWER:
134 s = "Interface Power";
142 case USB_DT_INTERFACE_ASSOCIATION:
143 s = "Interface Association";
148 case USB_DT_DEVICE_CAPABILITY:
149 s = "Device Capability";
151 case USB_DT_PIPE_USAGE:
154 case USB_DT_SS_ENDPOINT_COMP:
155 s = "SS Endpoint Companion";
157 case USB_DT_SSP_ISOC_ENDPOINT_COMP:
158 s = "SSP Isochronous Endpoint Companion";
165 snprintf(str, size, "%s %s Descriptor(Index = %d, Length = %d)",
166 bRequest == USB_REQ_GET_DESCRIPTOR ? "Get" : "Set",
167 s, wValue & 0xff, wLength);
170 static void usb_decode_get_configuration(__u16 wLength, char *str, size_t size)
172 snprintf(str, size, "Get Configuration(Length = %d)", wLength);
175 static void usb_decode_set_configuration(__u8 wValue, char *str, size_t size)
177 snprintf(str, size, "Set Configuration(Config = %d)", wValue);
180 static void usb_decode_get_intf(__u16 wIndex, __u16 wLength, char *str,
183 snprintf(str, size, "Get Interface(Intf = %d, Length = %d)",
187 static void usb_decode_set_intf(__u8 wValue, __u16 wIndex, char *str,
190 snprintf(str, size, "Set Interface(Intf = %d, Alt.Setting = %d)",
194 static void usb_decode_synch_frame(__u16 wIndex, __u16 wLength,
195 char *str, size_t size)
197 snprintf(str, size, "Synch Frame(Endpoint = %d, Length = %d)",
201 static void usb_decode_set_sel(__u16 wLength, char *str, size_t size)
203 snprintf(str, size, "Set SEL(Length = %d)", wLength);
206 static void usb_decode_set_isoch_delay(__u8 wValue, char *str, size_t size)
208 snprintf(str, size, "Set Isochronous Delay(Delay = %d ns)", wValue);
211 static void usb_decode_ctrl_generic(char *str, size_t size, __u8 bRequestType,
212 __u8 bRequest, __u16 wValue, __u16 wIndex,
215 u8 recip = bRequestType & USB_RECIP_MASK;
216 u8 type = bRequestType & USB_TYPE_MASK;
219 "Type=%s Recipient=%s Dir=%s bRequest=%u wValue=%u wIndex=%u wLength=%u",
220 (type == USB_TYPE_STANDARD) ? "Standard" :
221 (type == USB_TYPE_VENDOR) ? "Vendor" :
222 (type == USB_TYPE_CLASS) ? "Class" : "Unknown",
223 (recip == USB_RECIP_DEVICE) ? "Device" :
224 (recip == USB_RECIP_INTERFACE) ? "Interface" :
225 (recip == USB_RECIP_ENDPOINT) ? "Endpoint" : "Unknown",
226 (bRequestType & USB_DIR_IN) ? "IN" : "OUT",
227 bRequest, wValue, wIndex, wLength);
230 static void usb_decode_ctrl_standard(char *str, size_t size, __u8 bRequestType,
231 __u8 bRequest, __u16 wValue, __u16 wIndex,
235 case USB_REQ_GET_STATUS:
236 usb_decode_get_status(bRequestType, wIndex, wLength, str, size);
238 case USB_REQ_CLEAR_FEATURE:
239 case USB_REQ_SET_FEATURE:
240 usb_decode_set_clear_feature(bRequestType, bRequest, wValue,
243 case USB_REQ_SET_ADDRESS:
244 usb_decode_set_address(wValue, str, size);
246 case USB_REQ_GET_DESCRIPTOR:
247 case USB_REQ_SET_DESCRIPTOR:
248 usb_decode_get_set_descriptor(bRequestType, bRequest, wValue,
249 wIndex, wLength, str, size);
251 case USB_REQ_GET_CONFIGURATION:
252 usb_decode_get_configuration(wLength, str, size);
254 case USB_REQ_SET_CONFIGURATION:
255 usb_decode_set_configuration(wValue, str, size);
257 case USB_REQ_GET_INTERFACE:
258 usb_decode_get_intf(wIndex, wLength, str, size);
260 case USB_REQ_SET_INTERFACE:
261 usb_decode_set_intf(wValue, wIndex, str, size);
263 case USB_REQ_SYNCH_FRAME:
264 usb_decode_synch_frame(wIndex, wLength, str, size);
266 case USB_REQ_SET_SEL:
267 usb_decode_set_sel(wLength, str, size);
269 case USB_REQ_SET_ISOCH_DELAY:
270 usb_decode_set_isoch_delay(wValue, str, size);
273 usb_decode_ctrl_generic(str, size, bRequestType, bRequest,
274 wValue, wIndex, wLength);
280 * usb_decode_ctrl - Returns human readable representation of control request.
281 * @str: buffer to return a human-readable representation of control request.
282 * This buffer should have about 200 bytes.
283 * @size: size of str buffer.
284 * @bRequestType: matches the USB bmRequestType field
285 * @bRequest: matches the USB bRequest field
286 * @wValue: matches the USB wValue field (CPU byte order)
287 * @wIndex: matches the USB wIndex field (CPU byte order)
288 * @wLength: matches the USB wLength field (CPU byte order)
290 * Function returns decoded, formatted and human-readable description of
291 * control request packet.
293 * The usage scenario for this is for tracepoints, so function as a return
294 * use the same value as in parameters. This approach allows to use this
295 * function in TP_printk
297 * Important: wValue, wIndex, wLength parameters before invoking this function
298 * should be processed by le16_to_cpu macro.
300 const char *usb_decode_ctrl(char *str, size_t size, __u8 bRequestType,
301 __u8 bRequest, __u16 wValue, __u16 wIndex,
304 switch (bRequestType & USB_TYPE_MASK) {
305 case USB_TYPE_STANDARD:
306 usb_decode_ctrl_standard(str, size, bRequestType, bRequest,
307 wValue, wIndex, wLength);
309 case USB_TYPE_VENDOR:
312 usb_decode_ctrl_generic(str, size, bRequestType, bRequest,
313 wValue, wIndex, wLength);
319 EXPORT_SYMBOL_GPL(usb_decode_ctrl);