Remove an outdated FIXME
[fw/stlink] / src / stlink-usb.c
1 #include <stdio.h>
2 #include <stdlib.h>
3 #include <string.h>
4 #include <stdint.h>
5 #include <time.h>
6 #include <sys/types.h>
7 #include <libusb.h>
8
9 #include "stlink-common.h"
10 #include "stlink-usb.h"
11 #include "uglylogging.h"
12
13 #define LOG_TAG __FILE__
14 #define DLOG(format, args...)         ugly_log(UDEBUG, LOG_TAG, format, ## args)
15 #define ILOG(format, args...)         ugly_log(UINFO, LOG_TAG, format, ## args)
16 #define WLOG(format, args...)         ugly_log(UWARN, LOG_TAG, format, ## args)
17 #define fatal(format, args...)        ugly_log(UFATAL, LOG_TAG, format, ## args)
18
19
20 enum SCSI_Generic_Direction {SG_DXFER_TO_DEV=0, SG_DXFER_FROM_DEV=0x80};
21
22 void _stlink_usb_close(stlink_t* sl) {
23     struct stlink_libusb * const handle = sl->backend_data;
24     // maybe we couldn't even get the usb device?
25     if (handle != NULL) {
26         if (handle->req_trans != NULL)
27             libusb_free_transfer(handle->req_trans);
28
29         if (handle->rep_trans != NULL)
30             libusb_free_transfer(handle->rep_trans);
31
32         if (handle->usb_handle != NULL) {
33             libusb_close(handle->usb_handle);
34         }
35
36         libusb_exit(handle->libusb_ctx);
37         free(handle);
38     }
39 }
40
41
42 struct trans_ctx {
43 #define TRANS_FLAGS_IS_DONE (1 << 0)
44 #define TRANS_FLAGS_HAS_ERROR (1 << 1)
45     volatile unsigned long flags;
46 };
47
48 static void on_trans_done(struct libusb_transfer * trans) {
49     struct trans_ctx * const ctx = trans->user_data;
50
51     if (trans->status != LIBUSB_TRANSFER_COMPLETED)
52         ctx->flags |= TRANS_FLAGS_HAS_ERROR;
53
54     ctx->flags |= TRANS_FLAGS_IS_DONE;
55 }
56
57 int submit_wait(struct stlink_libusb *slu, struct libusb_transfer * trans) {
58     struct timeval start;
59     struct timeval now;
60     struct timeval diff;
61     struct trans_ctx trans_ctx;
62     enum libusb_error error;
63
64     trans_ctx.flags = 0;
65
66     /* brief intrusion inside the libusb interface */
67     trans->callback = on_trans_done;
68     trans->user_data = &trans_ctx;
69
70     if ((error = libusb_submit_transfer(trans))) {
71         printf("libusb_submit_transfer(%d)\n", error);
72         return -1;
73     }
74
75     gettimeofday(&start, NULL);
76
77     while (trans_ctx.flags == 0) {
78         struct timeval timeout;
79         timeout.tv_sec = 3;
80         timeout.tv_usec = 0;
81         if (libusb_handle_events_timeout(slu->libusb_ctx, &timeout)) {
82             printf("libusb_handle_events()\n");
83             return -1;
84         }
85
86         gettimeofday(&now, NULL);
87         timersub(&now, &start, &diff);
88         if (diff.tv_sec >= 3) {
89             printf("libusb_handle_events() timeout\n");
90             return -1;
91         }
92     }
93
94     if (trans_ctx.flags & TRANS_FLAGS_HAS_ERROR) {
95         printf("libusb_handle_events() | has_error\n");
96         return -1;
97     }
98
99     return 0;
100 }
101
102 ssize_t send_recv(struct stlink_libusb* handle, int terminate,
103         unsigned char* txbuf, size_t txsize,
104         unsigned char* rxbuf, size_t rxsize) {
105     /* note: txbuf and rxbuf can point to the same area */
106     int res = 0;
107
108     libusb_fill_bulk_transfer(handle->req_trans, handle->usb_handle,
109             handle->ep_req,
110             txbuf, txsize,
111             NULL, NULL,
112             0
113             );
114
115     if (submit_wait(handle, handle->req_trans)) return -1;
116
117     /* send_only */
118     if (rxsize != 0) {
119
120         /* read the response */
121         
122         libusb_fill_bulk_transfer(handle->rep_trans, handle->usb_handle,
123                                   handle->ep_rep, rxbuf, rxsize, NULL, NULL, 0);
124         
125         if (submit_wait(handle, handle->rep_trans)) return -1;
126         res = handle->rep_trans->actual_length;
127     }
128     
129     if ((handle->protocoll == 1) && terminate) {
130         fprintf(stderr, "This is never used....\n");
131         exit(EXIT_FAILURE);
132         /* Read the SG reply */
133         unsigned char sg_buf[13];
134         libusb_fill_bulk_transfer
135             (handle->rep_trans, handle->usb_handle,
136              handle->ep_rep, sg_buf, 13, NULL, NULL, 0);
137         res = submit_wait(handle, handle->rep_trans);
138         /* The STLink doesn't seem to evaluate the sequence number */
139         handle->sg_transfer_idx++;
140         if (res ) return -1;
141     }
142
143     return handle->rep_trans->actual_length;
144 }
145
146 static inline int send_only
147 (struct stlink_libusb* handle, int terminate,
148  unsigned char* txbuf, size_t txsize) {
149     return send_recv(handle, terminate, txbuf, txsize, NULL, 0);
150 }
151
152
153 static int fill_command
154 (stlink_t * sl, enum SCSI_Generic_Direction dir, uint32_t len) {
155     struct stlink_libusb * const slu = sl->backend_data;
156     unsigned char* const cmd = sl->c_buf;
157     int i = 0;
158     memset(cmd, 0, sizeof (sl->c_buf));
159     if(slu->protocoll == 1) {
160         fprintf(stderr, "This is never used....\n");
161         cmd[i++] = 'U';
162         cmd[i++] = 'S';
163         cmd[i++] = 'B';
164         cmd[i++] = 'C';
165         write_uint32(&cmd[i], slu->sg_transfer_idx);
166         write_uint32(&cmd[i + 4], len);
167         i += 8;
168         cmd[i++] = (dir == SG_DXFER_FROM_DEV)?0x80:0;
169         cmd[i++] = 0; /* Logical unit */
170         cmd[i++] = 0xa; /* Command length */
171     }
172     return i;
173 }
174
175 void _stlink_usb_version(stlink_t *sl) {
176     struct stlink_libusb * const slu = sl->backend_data;
177     unsigned char* const data = sl->q_buf;
178     unsigned char* const cmd  = sl->c_buf;
179     ssize_t size;
180     uint32_t rep_len = 6;
181     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
182
183     cmd[i++] = STLINK_GET_VERSION;
184
185     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
186     if (size == -1) {
187         printf("[!] send_recv\n");
188         return;
189     }
190 }
191
192 uint32_t _stlink_usb_read_debug32(stlink_t *sl, uint32_t addr) {
193     struct stlink_libusb * const slu = sl->backend_data;
194     unsigned char* const rdata = sl->q_buf;
195     unsigned char* const cmd  = sl->c_buf;
196     ssize_t size;
197     const int rep_len = 8;
198  
199     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
200     cmd[i++] = STLINK_DEBUG_COMMAND;
201     cmd[i++] = STLINK_JTAG_READDEBUG_32BIT;
202     write_uint32(&cmd[i], addr);
203     size = send_recv(slu, 1, cmd, slu->cmd_len, rdata, rep_len);
204     if (size == -1) {
205         printf("[!] send_recv\n");
206         return 0;
207     }
208     return read_uint32(rdata, 4);
209 }
210
211 void _stlink_usb_write_debug32(stlink_t *sl, uint32_t addr, uint32_t data) {
212     struct stlink_libusb * const slu = sl->backend_data;
213     unsigned char* const rdata = sl->q_buf;
214     unsigned char* const cmd  = sl->c_buf;
215     ssize_t size;
216     const int rep_len = 2;
217  
218     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
219     cmd[i++] = STLINK_DEBUG_COMMAND;
220     cmd[i++] = STLINK_JTAG_WRITEDEBUG_32BIT;
221     write_uint32(&cmd[i], addr);
222     write_uint32(&cmd[i + 4], data);
223     size = send_recv(slu, 1, cmd, slu->cmd_len, rdata, rep_len);
224     if (size == -1) {
225         printf("[!] send_recv\n");
226         return;
227     }
228 }
229
230 void _stlink_usb_write_mem32(stlink_t *sl, uint32_t addr, uint16_t len) {
231     struct stlink_libusb * const slu = sl->backend_data;
232     unsigned char* const data = sl->q_buf;
233     unsigned char* const cmd  = sl->c_buf;
234
235     int i = fill_command(sl, SG_DXFER_TO_DEV, len);
236     cmd[i++] = STLINK_DEBUG_COMMAND;
237     cmd[i++] = STLINK_DEBUG_WRITEMEM_32BIT;
238     write_uint32(&cmd[i], addr);
239     write_uint16(&cmd[i + 4], len);
240     send_only(slu, 0, cmd, slu->cmd_len);
241
242     send_only(slu, 1, data, len);
243 }
244
245 void _stlink_usb_write_mem8(stlink_t *sl, uint32_t addr, uint16_t len) {
246     struct stlink_libusb * const slu = sl->backend_data;
247     unsigned char* const data = sl->q_buf;
248     unsigned char* const cmd  = sl->c_buf;
249
250     int i = fill_command(sl, SG_DXFER_TO_DEV, 0);
251     cmd[i++] = STLINK_DEBUG_COMMAND;
252     cmd[i++] = STLINK_DEBUG_WRITEMEM_8BIT;
253     write_uint32(&cmd[i], addr);
254     write_uint16(&cmd[i + 4], len);
255     send_only(slu, 0, cmd, slu->cmd_len);
256     send_only(slu, 1, data, len);
257 }
258
259
260 int _stlink_usb_current_mode(stlink_t * sl) {
261     struct stlink_libusb * const slu = sl->backend_data;
262     unsigned char* const cmd  = sl->c_buf;
263     unsigned char* const data = sl->q_buf;
264     ssize_t size;
265     int rep_len = 2;
266     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
267     
268     cmd[i++] = STLINK_GET_CURRENT_MODE;
269     size = send_recv(slu, 1, cmd,  slu->cmd_len, data, rep_len);
270     if (size == -1) {
271         printf("[!] send_recv\n");
272         return -1;
273     }
274     return sl->q_buf[0];
275 }
276
277 void _stlink_usb_core_id(stlink_t * sl) {
278     struct stlink_libusb * const slu = sl->backend_data;
279     unsigned char* const cmd  = sl->c_buf;
280     unsigned char* const data = sl->q_buf;
281     ssize_t size;
282     int rep_len = 4;
283     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
284
285     cmd[i++] = STLINK_DEBUG_COMMAND;
286     cmd[i++] = STLINK_DEBUG_READCOREID;
287
288     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
289     if (size == -1) {
290         printf("[!] send_recv\n");
291         return;
292     }
293
294     sl->core_id = read_uint32(data, 0);
295 }
296
297 void _stlink_usb_status(stlink_t * sl) {
298     struct stlink_libusb * const slu = sl->backend_data;
299     unsigned char* const data = sl->q_buf;
300     unsigned char* const cmd  = sl->c_buf;
301     ssize_t size;
302     int rep_len = 2;
303     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
304
305     cmd[i++] = STLINK_DEBUG_COMMAND;
306     cmd[i++] = STLINK_DEBUG_GETSTATUS;
307
308     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
309     if (size == -1) {
310         printf("[!] send_recv\n");
311         return;
312     }
313 }
314
315 void _stlink_usb_force_debug(stlink_t *sl) {
316     struct stlink_libusb *slu = sl->backend_data;
317     unsigned char* const data = sl->q_buf;
318     unsigned char* const cmd  = sl->c_buf;
319     ssize_t size;
320     int rep_len = 2;
321     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
322
323     cmd[i++] = STLINK_DEBUG_COMMAND;
324     cmd[i++] = STLINK_DEBUG_FORCEDEBUG;
325     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
326     if (size == -1) {
327         printf("[!] send_recv\n");
328         return;
329     }
330 }
331
332 void _stlink_usb_enter_swd_mode(stlink_t * sl) {
333     struct stlink_libusb * const slu = sl->backend_data;
334     unsigned char* const cmd  = sl->c_buf;
335     ssize_t size;
336     const int rep_len = 0;
337     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
338
339     cmd[i++] = STLINK_DEBUG_COMMAND;
340     cmd[i++] = STLINK_DEBUG_ENTER;
341     cmd[i++] = STLINK_DEBUG_ENTER_SWD;
342
343     size = send_only(slu, 1, cmd, slu->cmd_len);
344     if (size == -1) {
345         printf("[!] send_recv\n");
346         return;
347     }
348 }
349
350 void _stlink_usb_exit_dfu_mode(stlink_t* sl) {
351     struct stlink_libusb * const slu = sl->backend_data;
352     unsigned char* const cmd = sl->c_buf;
353     ssize_t size;
354     int i = fill_command(sl, SG_DXFER_FROM_DEV, 0);
355
356     cmd[i++] = STLINK_DFU_COMMAND;
357     cmd[i++] = STLINK_DFU_EXIT;
358
359     size = send_only(slu, 1, cmd, slu->cmd_len);
360     if (size == -1) {
361         printf("[!] send_recv\n");
362         return;
363     }
364 }
365
366 /**
367  * TODO - not convinced this does anything...
368  * @param sl
369  */
370 void _stlink_usb_reset(stlink_t * sl) {
371     struct stlink_libusb * const slu = sl->backend_data;
372     unsigned char* const data = sl->q_buf;
373     unsigned char* const cmd = sl->c_buf;
374     ssize_t size;
375     int rep_len = 2;
376     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
377
378     cmd[i++] = STLINK_DEBUG_COMMAND;
379     cmd[i++] = STLINK_DEBUG_RESETSYS;
380
381     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
382     if (size == -1) {
383         printf("[!] send_recv\n");
384         return;
385     }
386 }
387
388
389 void _stlink_usb_jtag_reset(stlink_t * sl, int value) {
390     struct stlink_libusb * const slu = sl->backend_data;
391     unsigned char* const data = sl->q_buf;
392     unsigned char* const cmd = sl->c_buf;
393     ssize_t size;
394     int rep_len = 2;
395     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
396
397     cmd[i++] = STLINK_DEBUG_COMMAND;
398     cmd[i++] = STLINK_JTAG_DRIVE_NRST;
399     cmd[i++] = (value)?0:1;
400
401     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
402     if (size == -1) {
403         printf("[!] send_recv\n");
404         return;
405     }
406 }
407
408
409 void _stlink_usb_step(stlink_t* sl) {
410     struct stlink_libusb * const slu = sl->backend_data;
411     unsigned char* const data = sl->q_buf;
412     unsigned char* const cmd = sl->c_buf;
413     ssize_t size;
414     int rep_len = 2;
415     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
416
417     cmd[i++] = STLINK_DEBUG_COMMAND;
418     cmd[i++] = STLINK_DEBUG_STEPCORE;
419
420     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
421     if (size == -1) {
422         printf("[!] send_recv\n");
423         return;
424     }
425 }
426
427 /**
428  * This seems to do a good job of restarting things from the beginning?
429  * @param sl
430  */
431 void _stlink_usb_run(stlink_t* sl) {
432     struct stlink_libusb * const slu = sl->backend_data;
433     unsigned char* const data = sl->q_buf;
434     unsigned char* const cmd = sl->c_buf;
435     ssize_t size;
436     int rep_len = 2;
437     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
438
439     cmd[i++] = STLINK_DEBUG_COMMAND;
440     cmd[i++] = STLINK_DEBUG_RUNCORE;
441
442     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
443     if (size == -1) {
444         printf("[!] send_recv\n");
445         return;
446     }
447 }
448
449 void _stlink_usb_exit_debug_mode(stlink_t *sl) {
450     struct stlink_libusb * const slu = sl->backend_data;
451     unsigned char* const cmd = sl->c_buf;
452     ssize_t size;
453     int i = fill_command(sl, SG_DXFER_FROM_DEV, 0);
454
455     cmd[i++] = STLINK_DEBUG_COMMAND;
456     cmd[i++] = STLINK_DEBUG_EXIT;
457
458     size = send_only(slu, 1, cmd, slu->cmd_len);
459     if (size == -1) {
460         printf("[!] send_only\n");
461         return;
462     }
463 }
464
465 void _stlink_usb_read_mem32(stlink_t *sl, uint32_t addr, uint16_t len) {
466     struct stlink_libusb * const slu = sl->backend_data;
467     unsigned char* const data = sl->q_buf;
468     unsigned char* const cmd = sl->c_buf;
469     ssize_t size;
470     int i = fill_command(sl, SG_DXFER_FROM_DEV, len);
471
472     cmd[i++] = STLINK_DEBUG_COMMAND;
473     cmd[i++] = STLINK_DEBUG_READMEM_32BIT;
474     write_uint32(&cmd[i], addr);
475     write_uint16(&cmd[i + 4], len);
476
477     size = send_recv(slu, 1, cmd, slu->cmd_len, data, len);
478     if (size == -1) {
479         printf("[!] send_recv\n");
480         return;
481     }
482
483     sl->q_len = (size_t) size;
484
485     stlink_print_data(sl);
486 }
487
488 void _stlink_usb_read_all_regs(stlink_t *sl, reg *regp) {
489     struct stlink_libusb * const slu = sl->backend_data;
490     unsigned char* const cmd = sl->c_buf;
491     unsigned char* const data = sl->q_buf;
492     ssize_t size;
493     uint32_t rep_len = 84;
494     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
495
496     cmd[i++] = STLINK_DEBUG_COMMAND;
497     cmd[i++] = STLINK_DEBUG_READALLREGS;
498     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
499     if (size == -1) {
500         printf("[!] send_recv\n");
501         return;
502     }
503     sl->q_len = (size_t) size;
504     stlink_print_data(sl);
505     for(i=0; i<16; i++)
506         regp->r[i]= read_uint32(sl->q_buf, i*4);
507     regp->xpsr       = read_uint32(sl->q_buf, 64);
508     regp->main_sp    = read_uint32(sl->q_buf, 68);
509     regp->process_sp = read_uint32(sl->q_buf, 72);
510     regp->rw         = read_uint32(sl->q_buf, 76);
511     regp->rw2        = read_uint32(sl->q_buf, 80);
512     if (sl->verbose < 2)
513         return;
514
515     DLOG("xpsr       = 0x%08x\n", read_uint32(sl->q_buf, 64));
516     DLOG("main_sp    = 0x%08x\n", read_uint32(sl->q_buf, 68));
517     DLOG("process_sp = 0x%08x\n", read_uint32(sl->q_buf, 72));
518     DLOG("rw         = 0x%08x\n", read_uint32(sl->q_buf, 76));
519     DLOG("rw2        = 0x%08x\n", read_uint32(sl->q_buf, 80));
520 }
521
522 void _stlink_usb_read_reg(stlink_t *sl, int r_idx, reg *regp) {
523     struct stlink_libusb * const slu = sl->backend_data;
524     unsigned char* const data = sl->q_buf;
525     unsigned char* const cmd  = sl->c_buf;
526     ssize_t size;
527     uint32_t r;
528     uint32_t rep_len = 4;
529     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
530
531     cmd[i++] = STLINK_DEBUG_COMMAND;
532     cmd[i++] = STLINK_DEBUG_READREG;
533     cmd[i++] = (uint8_t) r_idx;
534     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
535     if (size == -1) {
536         printf("[!] send_recv\n");
537         return;
538     }
539     sl->q_len = (size_t) size;
540     stlink_print_data(sl);
541     r = read_uint32(sl->q_buf, 0);
542     DLOG("r_idx (%2d) = 0x%08x\n", r_idx, r);
543     
544     switch (r_idx) {
545     case 16:
546         regp->xpsr = r;
547         break;
548     case 17:
549         regp->main_sp = r;
550         break;
551     case 18:
552         regp->process_sp = r;
553         break;
554     case 19:
555         regp->rw = r; /* XXX ?(primask, basemask etc.) */
556         break;
557     case 20:
558         regp->rw2 = r; /* XXX ?(primask, basemask etc.) */
559         break;
560     default:
561         regp->r[r_idx] = r;
562     }
563 }
564
565 void _stlink_usb_write_reg(stlink_t *sl, uint32_t reg, int idx) {
566     struct stlink_libusb * const slu = sl->backend_data;
567     unsigned char* const data = sl->q_buf;
568     unsigned char* const cmd  = sl->c_buf;
569     ssize_t size;
570     uint32_t rep_len = 2;
571     int i = fill_command(sl, SG_DXFER_FROM_DEV, rep_len);
572
573     cmd[i++] = STLINK_DEBUG_COMMAND;
574     cmd[i++] = STLINK_DEBUG_WRITEREG;
575     cmd[i++] = idx;
576     write_uint32(&cmd[i], reg);
577     size = send_recv(slu, 1, cmd, slu->cmd_len, data, rep_len);
578     if (size == -1) {
579         printf("[!] send_recv\n");
580         return;
581     }
582     sl->q_len = (size_t) size;
583     stlink_print_data(sl);
584 }
585
586 stlink_backend_t _stlink_usb_backend = {
587     _stlink_usb_close,
588     _stlink_usb_exit_debug_mode,
589     _stlink_usb_enter_swd_mode,
590     NULL,  // no enter_jtag_mode here...
591     _stlink_usb_exit_dfu_mode,
592     _stlink_usb_core_id,
593     _stlink_usb_reset,
594     _stlink_usb_jtag_reset,
595     _stlink_usb_run,
596     _stlink_usb_status,
597     _stlink_usb_version,
598     _stlink_usb_read_debug32,
599     _stlink_usb_read_mem32,
600     _stlink_usb_write_debug32,
601     _stlink_usb_write_mem32,
602     _stlink_usb_write_mem8,
603     _stlink_usb_read_all_regs,
604     _stlink_usb_read_reg,
605     _stlink_usb_write_reg,
606     _stlink_usb_step,
607     _stlink_usb_current_mode,
608     _stlink_usb_force_debug
609 };
610
611
612 stlink_t* stlink_open_usb(const int verbose) {
613     stlink_t* sl = NULL;
614     struct stlink_libusb* slu = NULL;
615     int error = -1;
616     libusb_device** devs = NULL;
617     int config;
618
619     sl = malloc(sizeof (stlink_t));
620     slu = malloc(sizeof (struct stlink_libusb));
621     if (sl == NULL) goto on_error;
622     if (slu == NULL) goto on_error;
623     memset(sl, 0, sizeof (stlink_t));
624     memset(slu, 0, sizeof (struct stlink_libusb));
625
626     ugly_init(verbose);
627     sl->backend = &_stlink_usb_backend;
628     sl->backend_data = slu;
629     
630     sl->core_stat = STLINK_CORE_STAT_UNKNOWN;
631
632     if (libusb_init(&(slu->libusb_ctx))) {
633         WLOG("failed to init libusb context, wrong version of libraries?\n");
634         goto on_error;
635     }
636     
637     slu->usb_handle = libusb_open_device_with_vid_pid(slu->libusb_ctx, USB_ST_VID, USB_STLINK_32L_PID);
638     if (slu->usb_handle == NULL) {
639                 WLOG("Couldn't find any ST-Link/V2 devices");
640         goto on_error;
641     }
642     
643     if (libusb_kernel_driver_active(slu->usb_handle, 0) == 1) {
644         int r;
645         
646         r = libusb_detach_kernel_driver(slu->usb_handle, 0);
647         if (r<0) {
648             WLOG("libusb_detach_kernel_driver(() error %s\n", strerror(-r));
649             goto on_libusb_error;
650         }
651     }
652
653     if (libusb_get_configuration(slu->usb_handle, &config)) {
654         /* this may fail for a previous configured device */
655         WLOG("libusb_get_configuration()\n");
656         goto on_libusb_error;
657     }
658
659     if (config != 1) {
660         printf("setting new configuration (%d -> 1)\n", config);
661         if (libusb_set_configuration(slu->usb_handle, 1)) {
662             /* this may fail for a previous configured device */
663             WLOG("libusb_set_configuration() failed\n");
664             goto on_libusb_error;
665         }
666     }
667
668     if (libusb_claim_interface(slu->usb_handle, 0)) {
669         WLOG("libusb_claim_interface() failed\n");
670         goto on_libusb_error;
671     }
672
673     slu->req_trans = libusb_alloc_transfer(0);
674     if (slu->req_trans == NULL) {
675         WLOG("libusb_alloc_transfer failed\n");
676         goto on_libusb_error;
677     }
678
679     slu->rep_trans = libusb_alloc_transfer(0);
680     if (slu->rep_trans == NULL) {
681         WLOG("libusb_alloc_transfer failed\n");
682         goto on_libusb_error;
683     }
684     // TODO - could use the scanning techniq from stm8 code here...
685     slu->ep_rep = 1 /* ep rep */ | LIBUSB_ENDPOINT_IN;
686     slu->ep_req = 2 /* ep req */ | LIBUSB_ENDPOINT_OUT;
687
688     slu->sg_transfer_idx = 0;
689     // TODO - never used at the moment, always CMD_SIZE
690     slu->cmd_len = (slu->protocoll == 1)? STLINK_SG_SIZE: STLINK_CMD_SIZE;
691
692     /* success */
693
694     if (stlink_current_mode(sl) == STLINK_DEV_DFU_MODE) {
695       ILOG("-- exit_dfu_mode\n");
696       stlink_exit_dfu_mode(sl);
697     }
698
699     if (stlink_current_mode(sl) != STLINK_DEV_DEBUG_MODE) {
700       stlink_enter_swd_mode(sl);
701     }
702
703     stlink_reset(sl);
704     stlink_load_device_params(sl);
705     stlink_version(sl);
706
707     error = 0;
708
709 on_libusb_error:
710     if (devs != NULL) {
711         libusb_free_device_list(devs, 1);
712     }
713
714     if (error == -1) {
715         stlink_close(sl);
716         return NULL;
717     }
718
719     /* success */
720     return sl;
721
722 on_error:
723     if( slu->libusb_ctx)
724         libusb_exit(slu->libusb_ctx);
725     if (sl != NULL) free(sl);
726     if (slu != NULL) free(slu);
727     return 0;
728 }
729