7efea5166689d26339de7fcc377afaddddc2eda4
[fw/openocd] / src / jtag / drivers / cmsis_dap_usb_bulk.c
1 /***************************************************************************
2  *   Copyright (C) 2018 by MickaĆ«l Thomas                                  *
3  *   mickael9@gmail.com                                                    *
4  *                                                                         *
5  *   Copyright (C) 2016 by Maksym Hilliaka                                 *
6  *   oter@frozen-team.com                                                  *
7  *                                                                         *
8  *   Copyright (C) 2016 by Phillip Pearson                                 *
9  *   pp@myelin.co.nz                                                       *
10  *                                                                         *
11  *   Copyright (C) 2014 by Paul Fertser                                    *
12  *   fercerpav@gmail.com                                                   *
13  *                                                                         *
14  *   Copyright (C) 2013 by mike brown                                      *
15  *   mike@theshedworks.org.uk                                              *
16  *                                                                         *
17  *   Copyright (C) 2013 by Spencer Oliver                                  *
18  *   spen@spen-soft.co.uk                                                  *
19  *                                                                         *
20  *   This program is free software; you can redistribute it and/or modify  *
21  *   it under the terms of the GNU General Public License as published by  *
22  *   the Free Software Foundation; either version 2 of the License, or     *
23  *   (at your option) any later version.                                   *
24  *                                                                         *
25  *   This program is distributed in the hope that it will be useful,       *
26  *   but WITHOUT ANY WARRANTY; without even the implied warranty of        *
27  *   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the         *
28  *   GNU General Public License for more details.                          *
29  *                                                                         *
30  *   You should have received a copy of the GNU General Public License     *
31  *   along with this program.  If not, see <http://www.gnu.org/licenses/>. *
32  ***************************************************************************/
33
34 #ifdef HAVE_CONFIG_H
35 #include "config.h"
36 #endif
37
38 #include <libusb.h>
39 #include <helper/log.h>
40
41 #include "cmsis_dap.h"
42
43 struct cmsis_dap_backend_data {
44         libusb_context *usb_ctx;
45         libusb_device_handle *dev_handle;
46         unsigned int ep_out;
47         unsigned int ep_in;
48         int interface;
49 };
50
51 static int cmsis_dap_usb_interface = -1;
52
53 static void cmsis_dap_usb_close(struct cmsis_dap *dap);
54 static int cmsis_dap_usb_alloc(struct cmsis_dap *dap, unsigned int pkt_sz);
55
56 static int cmsis_dap_usb_open(struct cmsis_dap *dap, uint16_t vids[], uint16_t pids[], char *serial)
57 {
58         int err;
59         libusb_context *ctx;
60         libusb_device **device_list;
61
62         err = libusb_init(&ctx);
63         if (err) {
64                 LOG_ERROR("libusb initialization failed: %s", libusb_strerror(err));
65                 return ERROR_FAIL;
66         }
67
68         int num_devices = libusb_get_device_list(ctx, &device_list);
69         if (num_devices < 0) {
70                 LOG_ERROR("could not enumerate USB devices: %s", libusb_strerror(num_devices));
71                 libusb_exit(ctx);
72                 return ERROR_FAIL;
73         }
74
75         for (int i = 0; i < num_devices; i++) {
76                 libusb_device *dev = device_list[i];
77                 struct libusb_device_descriptor dev_desc;
78
79                 err = libusb_get_device_descriptor(dev, &dev_desc);
80                 if (err) {
81                         LOG_ERROR("could not get device descriptor for device %d: %s", i, libusb_strerror(err));
82                         continue;
83                 }
84
85                 /* Match VID/PID */
86
87                 bool id_match = false;
88                 bool id_filter = vids[0] || pids[0];
89                 for (int id = 0; vids[id] || pids[id]; id++) {
90                         id_match = !vids[id] || dev_desc.idVendor == vids[id];
91                         id_match &= !pids[id] || dev_desc.idProduct == pids[id];
92
93                         if (id_match)
94                                 break;
95                 }
96
97                 if (id_filter && !id_match)
98                         continue;
99
100                 /* Don't continue if we asked for a serial number and the device doesn't have one */
101                 if (dev_desc.iSerialNumber == 0 && serial && serial[0])
102                         continue;
103
104                 libusb_device_handle *dev_handle = NULL;
105                 err = libusb_open(dev, &dev_handle);
106                 if (err) {
107                         /* It's to be expected that most USB devices can't be opened
108                          * so only report an error if it was explicitly selected
109                          */
110                         if (id_filter) {
111                                 LOG_ERROR("could not open device 0x%04x:0x%04x: %s",
112                                                 dev_desc.idVendor, dev_desc.idProduct, libusb_strerror(err));
113                         } else {
114                                 LOG_DEBUG("could not open device 0x%04x:0x%04x: %s",
115                                                 dev_desc.idVendor, dev_desc.idProduct, libusb_strerror(err));
116                         }
117                         continue;
118                 }
119
120                 /* Match serial number */
121
122                 bool serial_match = false;
123                 char dev_serial[256] = {0};
124                 if (dev_desc.iSerialNumber > 0) {
125                         err = libusb_get_string_descriptor_ascii(
126                                         dev_handle, dev_desc.iSerialNumber,
127                                         (uint8_t *)dev_serial, sizeof(dev_serial));
128
129                         if (err < 0) {
130                                 const char *msg = "could not read serial number for device 0x%04x:0x%04x: %s";
131                                 if (serial)
132                                         LOG_WARNING(msg, dev_desc.idVendor, dev_desc.idProduct,
133                                                                 libusb_strerror(err));
134                                 else
135                                         LOG_DEBUG(msg, dev_desc.idVendor, dev_desc.idProduct,
136                                                                 libusb_strerror(err));
137                         } else if (serial && strncmp(dev_serial, serial, sizeof(dev_serial)) == 0) {
138                                 serial_match = true;
139                         }
140                 }
141
142                 if (serial && !serial_match) {
143                         libusb_close(dev_handle);
144                         continue;
145                 }
146
147                 /* Find the CMSIS-DAP string in product string */
148
149                 bool cmsis_dap_in_product_str = false;
150                 char product_string[256] = {0};
151                 if (dev_desc.iProduct > 0) {
152                         err = libusb_get_string_descriptor_ascii(
153                                         dev_handle, dev_desc.iProduct,
154                                         (uint8_t *)product_string, sizeof(product_string));
155                         if (err < 0) {
156                                 LOG_WARNING("could not read product string for device 0x%04x:0x%04x: %s",
157                                                 dev_desc.idVendor, dev_desc.idProduct, libusb_strerror(err));
158                         } else if (strstr(product_string, "CMSIS-DAP")) {
159                                 LOG_DEBUG("found product string of 0x%04x:0x%04x '%s'",
160                                                   dev_desc.idVendor, dev_desc.idProduct, product_string);
161                                 cmsis_dap_in_product_str = true;
162                         }
163                 }
164
165                 bool device_identified_reliably = cmsis_dap_in_product_str
166                                                                                         || serial_match || id_match;
167
168                 /* Find the CMSIS-DAP interface */
169
170                 for (int config = 0; config < dev_desc.bNumConfigurations; config++) {
171                         struct libusb_config_descriptor *config_desc;
172                         err = libusb_get_config_descriptor(dev, config, &config_desc);
173                         if (err) {
174                                 LOG_ERROR("could not get configuration descriptor %d for device 0x%04x:0x%04x: %s",
175                                                 config, dev_desc.idVendor, dev_desc.idProduct, libusb_strerror(err));
176                                 continue;
177                         }
178
179                         LOG_DEBUG("enumerating interfaces of 0x%04x:0x%04x",
180                                           dev_desc.idVendor, dev_desc.idProduct);
181                         int config_num = config_desc->bConfigurationValue;
182                         const struct libusb_interface_descriptor *intf_desc_candidate = NULL;
183                         const struct libusb_interface_descriptor *intf_desc_found = NULL;
184
185                         for (int interface = 0; interface < config_desc->bNumInterfaces; interface++) {
186                                 const struct libusb_interface_descriptor *intf_desc = &config_desc->interface[interface].altsetting[0];
187                                 int interface_num = intf_desc->bInterfaceNumber;
188
189                                 /* Skip this interface if another one was requested explicitly */
190                                 if (cmsis_dap_usb_interface != -1 && cmsis_dap_usb_interface != interface_num)
191                                         continue;
192
193                                 /* CMSIS-DAP v2 spec says:
194                                  *
195                                  * CMSIS-DAP with default V2 configuration uses WinUSB and is therefore faster.
196                                  * Optionally support for streaming SWO trace is provided via an additional USB endpoint.
197                                  *
198                                  * The WinUSB configuration requires custom class support with the interface setting
199                                  *     Class Code: 0xFF (Vendor specific)
200                                  *     Subclass: 0x00
201                                  *     Protocol code: 0x00
202                                  *
203                                  * Depending on the configuration it uses the following USB endpoints which should be configured
204                                  * in the interface descriptor in this order:
205                                  *  - Endpoint 1: Bulk Out ā€“ used for commands received from host PC.
206                                  *  - Endpoint 2: Bulk In ā€“ used for responses send to host PC.
207                                  *  - Endpoint 3: Bulk In (optional) ā€“ used for streaming SWO trace (if enabled with SWO_STREAM).
208                                  */
209
210                                 /* Search for "CMSIS-DAP" in the interface string */
211                                 bool cmsis_dap_in_interface_str = false;
212                                 if (intf_desc->iInterface != 0) {
213
214                                         char interface_str[256] = {0};
215
216                                         err = libusb_get_string_descriptor_ascii(
217                                                         dev_handle, intf_desc->iInterface,
218                                                         (uint8_t *)interface_str, sizeof(interface_str));
219                                         if (err < 0) {
220                                                 LOG_DEBUG("could not read interface string %d for device 0x%04x:0x%04x: %s",
221                                                                   intf_desc->iInterface,
222                                                                   dev_desc.idVendor, dev_desc.idProduct,
223                                                                   libusb_strerror(err));
224                                         } else if (strstr(interface_str, "CMSIS-DAP")) {
225                                                 cmsis_dap_in_interface_str = true;
226                                                 LOG_DEBUG("found interface %d string '%s'",
227                                                                   interface_num, interface_str);
228                                         }
229                                 }
230
231                                 /* Bypass the following check if this interface was explicitly requested. */
232                                 if (cmsis_dap_usb_interface == -1) {
233                                         if (!cmsis_dap_in_product_str && !cmsis_dap_in_interface_str)
234                                                 continue;
235                                 }
236
237                                 /* check endpoints */
238                                 if (intf_desc->bNumEndpoints < 2) {
239                                         LOG_DEBUG("skipping interface %d, has only %d endpoints",
240                                                           interface_num, intf_desc->bNumEndpoints);
241                                         continue;
242                                 }
243
244                                 if ((intf_desc->endpoint[0].bmAttributes & 3) != LIBUSB_TRANSFER_TYPE_BULK ||
245                                                 (intf_desc->endpoint[0].bEndpointAddress & 0x80) != LIBUSB_ENDPOINT_OUT) {
246                                         LOG_DEBUG("skipping interface %d, endpoint[0] is not bulk out",
247                                                           interface_num);
248                                         continue;
249                                 }
250
251                                 if ((intf_desc->endpoint[1].bmAttributes & 3) != LIBUSB_TRANSFER_TYPE_BULK ||
252                                                 (intf_desc->endpoint[1].bEndpointAddress & 0x80) != LIBUSB_ENDPOINT_IN) {
253                                         LOG_DEBUG("skipping interface %d, endpoint[1] is not bulk in",
254                                                           interface_num);
255                                         continue;
256                                 }
257
258                                 /* We can rely on the interface is really CMSIS-DAP if
259                                  * - we've seen CMSIS-DAP in the interface string
260                                  * - config asked explicitly for an interface number
261                                  * - the device has only one interface
262                                  * The later two cases should be honored only if we know
263                                  * we are on the rigt device */
264                                 bool intf_identified_reliably = cmsis_dap_in_interface_str
265                                                         || (device_identified_reliably &&
266                                                                         (cmsis_dap_usb_interface != -1
267                                                                          || config_desc->bNumInterfaces == 1));
268
269                                 if (intf_desc->bInterfaceClass != LIBUSB_CLASS_VENDOR_SPEC ||
270                                                 intf_desc->bInterfaceSubClass != 0 || intf_desc->bInterfaceProtocol != 0) {
271                                         /* If the interface is reliably identified
272                                          * then we need not insist on setting USB class, subclass and protocol
273                                          * exactly as the specification requires.
274                                          * At least KitProg3 uses class 0 contrary to the specification */
275                                         if (intf_identified_reliably) {
276                                                 LOG_WARNING("Using CMSIS-DAPv2 interface %d with wrong class %" PRId8
277                                                                   " subclass %" PRId8 " or protocol %" PRId8,
278                                                                   interface_num,
279                                                                   intf_desc->bInterfaceClass,
280                                                                   intf_desc->bInterfaceSubClass,
281                                                                   intf_desc->bInterfaceProtocol);
282                                         } else {
283                                                 LOG_DEBUG("skipping interface %d, class %" PRId8
284                                                                   " subclass %" PRId8 " protocol %" PRId8,
285                                                                   interface_num,
286                                                                   intf_desc->bInterfaceClass,
287                                                                   intf_desc->bInterfaceSubClass,
288                                                                   intf_desc->bInterfaceProtocol);
289                                                 continue;
290
291                                         }
292                                 }
293
294                                 if (intf_identified_reliably) {
295                                         /* That's the one! */
296                                         intf_desc_found = intf_desc;
297                                         break;
298                                 }
299
300                                 if (!intf_desc_candidate && device_identified_reliably) {
301                                         /* This interface looks suitable for CMSIS-DAP. Store the pointer to it
302                                          * and keep searching for another one with CMSIS-DAP in interface string */
303                                         intf_desc_candidate = intf_desc;
304                                 }
305                         }
306
307                         if (!intf_desc_found) {
308                                 /* We were not able to identify reliably which interface is CMSIS-DAP.
309                                  * Let's use the first suitable if we found one */
310                                 intf_desc_found = intf_desc_candidate;
311                         }
312
313                         if (!intf_desc_found) {
314                                 libusb_free_config_descriptor(config_desc);
315                                 continue;
316                         }
317
318                         /* We've chosen an interface, connect to it */
319                         int interface_num = intf_desc_found->bInterfaceNumber;
320                         int packet_size = intf_desc_found->endpoint[0].wMaxPacketSize;
321                         int ep_out = intf_desc_found->endpoint[0].bEndpointAddress;
322                         int ep_in = intf_desc_found->endpoint[1].bEndpointAddress;
323
324                         libusb_free_config_descriptor(config_desc);
325                         libusb_free_device_list(device_list, true);
326
327                         LOG_INFO("Using CMSIS-DAPv2 interface with VID:PID=0x%04x:0x%04x, serial=%s",
328                                         dev_desc.idVendor, dev_desc.idProduct, dev_serial);
329
330                         int current_config;
331                         err = libusb_get_configuration(dev_handle, &current_config);
332                         if (err) {
333                                 LOG_ERROR("could not find current configuration: %s", libusb_strerror(err));
334                                 libusb_close(dev_handle);
335                                 libusb_exit(ctx);
336                                 return ERROR_FAIL;
337                         }
338
339                         if (config_num != current_config) {
340                                 err = libusb_set_configuration(dev_handle, config_num);
341                                 if (err) {
342                                         LOG_ERROR("could not set configuration: %s", libusb_strerror(err));
343                                         libusb_close(dev_handle);
344                                         libusb_exit(ctx);
345                                         return ERROR_FAIL;
346                                 }
347                         }
348
349                         err = libusb_claim_interface(dev_handle, interface_num);
350                         if (err)
351                                 LOG_WARNING("could not claim interface: %s", libusb_strerror(err));
352
353                         dap->bdata = malloc(sizeof(struct cmsis_dap_backend_data));
354                         if (dap->bdata == NULL) {
355                                 LOG_ERROR("unable to allocate memory");
356                                 libusb_release_interface(dev_handle, interface_num);
357                                 libusb_close(dev_handle);
358                                 libusb_exit(ctx);
359                                 return ERROR_FAIL;
360                         }
361
362                         dap->packet_size = packet_size;
363                         dap->packet_buffer_size = packet_size + REPORT_ID_SIZE;
364                         dap->bdata->usb_ctx = ctx;
365                         dap->bdata->dev_handle = dev_handle;
366                         dap->bdata->ep_out = ep_out;
367                         dap->bdata->ep_in = ep_in;
368                         dap->bdata->interface = interface_num;
369
370                         dap->packet_buffer = malloc(dap->packet_buffer_size);
371                         if (dap->packet_buffer == NULL) {
372                                 LOG_ERROR("unable to allocate memory");
373                                 cmsis_dap_usb_close(dap);
374                                 return ERROR_FAIL;
375                         }
376
377                         return ERROR_OK;
378                 }
379
380                 libusb_close(dev_handle);
381         }
382
383         libusb_free_device_list(device_list, true);
384
385         libusb_exit(ctx);
386         return ERROR_FAIL;
387 }
388
389 static void cmsis_dap_usb_close(struct cmsis_dap *dap)
390 {
391         libusb_release_interface(dap->bdata->dev_handle, dap->bdata->interface);
392         libusb_close(dap->bdata->dev_handle);
393         libusb_exit(dap->bdata->usb_ctx);
394         free(dap->bdata);
395         dap->bdata = NULL;
396         free(dap->packet_buffer);
397         dap->packet_buffer = NULL;
398 }
399
400 static int cmsis_dap_usb_read(struct cmsis_dap *dap, int timeout_ms)
401 {
402         int transferred = 0;
403         int err;
404
405         err = libusb_bulk_transfer(dap->bdata->dev_handle, dap->bdata->ep_in,
406                                                         dap->packet_buffer, dap->packet_size, &transferred, timeout_ms);
407         if (err) {
408                 if (err == LIBUSB_ERROR_TIMEOUT) {
409                         return ERROR_TIMEOUT_REACHED;
410                 } else {
411                         LOG_ERROR("error reading data: %s", libusb_strerror(err));
412                         return ERROR_FAIL;
413                 }
414         }
415
416         memset(&dap->packet_buffer[transferred], 0, dap->packet_buffer_size - transferred);
417
418         return transferred;
419 }
420
421 static int cmsis_dap_usb_write(struct cmsis_dap *dap, int txlen, int timeout_ms)
422 {
423         int transferred = 0;
424         int err;
425
426         /* skip the first byte that is only used by the HID backend */
427         err = libusb_bulk_transfer(dap->bdata->dev_handle, dap->bdata->ep_out,
428                                                         dap->packet_buffer + REPORT_ID_SIZE, txlen - REPORT_ID_SIZE, &transferred, timeout_ms);
429         if (err) {
430                 if (err == LIBUSB_ERROR_TIMEOUT) {
431                         return ERROR_TIMEOUT_REACHED;
432                 } else {
433                         LOG_ERROR("error writing data: %s", libusb_strerror(err));
434                         return ERROR_FAIL;
435                 }
436         }
437
438         return transferred;
439 }
440
441 static int cmsis_dap_usb_alloc(struct cmsis_dap *dap, unsigned int pkt_sz)
442 {
443         unsigned int packet_buffer_size = pkt_sz + REPORT_ID_SIZE;
444         uint8_t *buf = malloc(packet_buffer_size);
445         if (buf == NULL) {
446                 LOG_ERROR("unable to allocate CMSIS-DAP packet buffer");
447                 return ERROR_FAIL;
448         }
449
450         dap->packet_buffer = buf;
451         dap->packet_size = pkt_sz;
452         dap->packet_buffer_size = packet_buffer_size;
453
454         return ERROR_OK;
455 }
456
457 COMMAND_HANDLER(cmsis_dap_handle_usb_interface_command)
458 {
459         if (CMD_ARGC == 1)
460                 cmsis_dap_usb_interface = strtoul(CMD_ARGV[0], NULL, 10);
461         else
462                 LOG_ERROR("expected exactly one argument to cmsis_dap_usb_interface <interface_number>");
463
464         return ERROR_OK;
465 }
466
467 const struct command_registration cmsis_dap_usb_subcommand_handlers[] = {
468         {
469                 .name = "interface",
470                 .handler = &cmsis_dap_handle_usb_interface_command,
471                 .mode = COMMAND_CONFIG,
472                 .help = "set the USB interface number to use (for USB bulk backend only)",
473                 .usage = "<interface_number>",
474         },
475         COMMAND_REGISTRATION_DONE
476 };
477
478 const struct cmsis_dap_backend cmsis_dap_usb_backend = {
479         .name = "usb_bulk",
480         .open = cmsis_dap_usb_open,
481         .close = cmsis_dap_usb_close,
482         .read = cmsis_dap_usb_read,
483         .write = cmsis_dap_usb_write,
484         .packet_buffer_alloc = cmsis_dap_usb_alloc,
485 };