usbconfig.c (9c79794016d679440487dea61b3b986397c9ecbb) usbconfig.c (cf109686d0a89f698ba59a65d3199bdfc151f88a)
1/* $FreeBSD$ */
2/*-
1/* $FreeBSD$ */
2/*-
3 * Copyright (c) 2008 Hans Petter Selasky. All rights reserved.
3 * Copyright (c) 2008-2009 Hans Petter Selasky. All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the

--- 64 unchanged lines hidden (view full) ---

76 uint8_t got_dump_quirk_names:1;
77 uint8_t got_dump_device_desc:1;
78 uint8_t got_dump_curr_config:1;
79 uint8_t got_dump_all_config:1;
80 uint8_t got_dump_info:1;
81 uint8_t got_show_iface_driver:1;
82 uint8_t got_remove_device_quirk:1;
83 uint8_t got_add_device_quirk:1;
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * 1. Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * 2. Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in the

--- 64 unchanged lines hidden (view full) ---

76 uint8_t got_dump_quirk_names:1;
77 uint8_t got_dump_device_desc:1;
78 uint8_t got_dump_curr_config:1;
79 uint8_t got_dump_all_config:1;
80 uint8_t got_dump_info:1;
81 uint8_t got_show_iface_driver:1;
82 uint8_t got_remove_device_quirk:1;
83 uint8_t got_add_device_quirk:1;
84 uint8_t got_remove_quirk:1;
85 uint8_t got_add_quirk:1;
84 uint8_t got_dump_string:1;
85 uint8_t got_do_request:1;
86};
87
88struct token {
89 const char *name;
90 uint8_t value;
91 uint8_t narg;
92};
93
94enum {
95 T_UNIT,
96 T_ADDR,
86 uint8_t got_dump_string:1;
87 uint8_t got_do_request:1;
88};
89
90struct token {
91 const char *name;
92 uint8_t value;
93 uint8_t narg;
94};
95
96enum {
97 T_UNIT,
98 T_ADDR,
99 T_UGEN,
97 T_IFACE,
98 T_SET_CONFIG,
99 T_SET_ALT,
100 T_SET_TEMPLATE,
101 T_GET_TEMPLATE,
102 T_ADD_DEVICE_QUIRK,
103 T_REMOVE_DEVICE_QUIRK,
100 T_IFACE,
101 T_SET_CONFIG,
102 T_SET_ALT,
103 T_SET_TEMPLATE,
104 T_GET_TEMPLATE,
105 T_ADD_DEVICE_QUIRK,
106 T_REMOVE_DEVICE_QUIRK,
107 T_ADD_QUIRK,
108 T_REMOVE_QUIRK,
104 T_SHOW_IFACE_DRIVER,
105 T_DUMP_QUIRK_NAMES,
106 T_DUMP_DEVICE_QUIRKS,
107 T_DUMP_DEVICE_DESC,
108 T_DUMP_CURR_CONFIG_DESC,
109 T_DUMP_ALL_CONFIG_DESC,
110 T_DUMP_STRING,
111 T_DUMP_INFO,

--- 7 unchanged lines hidden (view full) ---

119 T_DO_REQUEST,
120};
121
122static struct options options;
123
124static const struct token token[] = {
125 {"-u", T_UNIT, 1},
126 {"-a", T_ADDR, 1},
109 T_SHOW_IFACE_DRIVER,
110 T_DUMP_QUIRK_NAMES,
111 T_DUMP_DEVICE_QUIRKS,
112 T_DUMP_DEVICE_DESC,
113 T_DUMP_CURR_CONFIG_DESC,
114 T_DUMP_ALL_CONFIG_DESC,
115 T_DUMP_STRING,
116 T_DUMP_INFO,

--- 7 unchanged lines hidden (view full) ---

124 T_DO_REQUEST,
125};
126
127static struct options options;
128
129static const struct token token[] = {
130 {"-u", T_UNIT, 1},
131 {"-a", T_ADDR, 1},
132 {"-d", T_UGEN, 1},
127 {"-i", T_IFACE, 1},
128 {"set_config", T_SET_CONFIG, 1},
129 {"set_alt", T_SET_ALT, 1},
130 {"set_template", T_SET_TEMPLATE, 1},
131 {"get_template", T_GET_TEMPLATE, 0},
132 {"add_dev_quirk_vplh", T_ADD_DEVICE_QUIRK, 5},
133 {"remove_dev_quirk_vplh", T_REMOVE_DEVICE_QUIRK, 5},
133 {"-i", T_IFACE, 1},
134 {"set_config", T_SET_CONFIG, 1},
135 {"set_alt", T_SET_ALT, 1},
136 {"set_template", T_SET_TEMPLATE, 1},
137 {"get_template", T_GET_TEMPLATE, 0},
138 {"add_dev_quirk_vplh", T_ADD_DEVICE_QUIRK, 5},
139 {"remove_dev_quirk_vplh", T_REMOVE_DEVICE_QUIRK, 5},
140 {"add_quirk", T_ADD_QUIRK, 1},
141 {"remove_quirk", T_REMOVE_QUIRK, 1},
134 {"dump_quirk_names", T_DUMP_QUIRK_NAMES, 0},
135 {"dump_device_quirks", T_DUMP_DEVICE_QUIRKS, 0},
136 {"dump_device_desc", T_DUMP_DEVICE_DESC, 0},
137 {"dump_curr_config_desc", T_DUMP_CURR_CONFIG_DESC, 0},
138 {"dump_all_config_desc", T_DUMP_ALL_CONFIG_DESC, 0},
139 {"dump_string", T_DUMP_STRING, 1},
140 {"dump_info", T_DUMP_INFO, 0},
141 {"show_ifdrv", T_SHOW_IFACE_DRIVER, 0},

--- 100 unchanged lines hidden (view full) ---

242 }
243 if (*ep != '\0') {
244 errx(1, "illegal number: %s", s);
245 }
246 return val;
247}
248
249static void
142 {"dump_quirk_names", T_DUMP_QUIRK_NAMES, 0},
143 {"dump_device_quirks", T_DUMP_DEVICE_QUIRKS, 0},
144 {"dump_device_desc", T_DUMP_DEVICE_DESC, 0},
145 {"dump_curr_config_desc", T_DUMP_CURR_CONFIG_DESC, 0},
146 {"dump_all_config_desc", T_DUMP_ALL_CONFIG_DESC, 0},
147 {"dump_string", T_DUMP_STRING, 1},
148 {"dump_info", T_DUMP_INFO, 0},
149 {"show_ifdrv", T_SHOW_IFACE_DRIVER, 0},

--- 100 unchanged lines hidden (view full) ---

250 }
251 if (*ep != '\0') {
252 errx(1, "illegal number: %s", s);
253 }
254 return val;
255}
256
257static void
258duplicate_option(const char *ptr)
259{
260 printf("Syntax error: "
261 "Duplicate option: '%s'\n", ptr);
262 exit(1);
263}
264
265static void
250usage(void)
251{
252 printf(""
253 "usbconfig - configure the USB subsystem" "\n"
254 "usage: usbconfig -u <busnum> -a <devaddr> -i <ifaceindex> [cmds...]" "\n"
266usage(void)
267{
268 printf(""
269 "usbconfig - configure the USB subsystem" "\n"
270 "usage: usbconfig -u <busnum> -a <devaddr> -i <ifaceindex> [cmds...]" "\n"
271 "usage: usbconfig -d [ugen]<busnum>.<devaddr> -i <ifaceindex> [cmds...]" "\n"
255 "commands:" "\n"
256 " set_config <cfg_index>" "\n"
257 " set_alt <alt_index>" "\n"
258 " set_template <template>" "\n"
259 " get_template" "\n"
260 " add_dev_quirk_vplh <vid> <pid> <lo_rev> <hi_rev> <quirk>" "\n"
261 " remove_dev_quirk_vplh <vid> <pid> <lo_rev> <hi_rev> <quirk>" "\n"
272 "commands:" "\n"
273 " set_config <cfg_index>" "\n"
274 " set_alt <alt_index>" "\n"
275 " set_template <template>" "\n"
276 " get_template" "\n"
277 " add_dev_quirk_vplh <vid> <pid> <lo_rev> <hi_rev> <quirk>" "\n"
278 " remove_dev_quirk_vplh <vid> <pid> <lo_rev> <hi_rev> <quirk>" "\n"
279 " add_quirk <quirk>" "\n"
280 " remove_quirk <quirk>" "\n"
262 " dump_quirk_names" "\n"
263 " dump_device_quirks" "\n"
264 " dump_device_desc" "\n"
265 " dump_curr_config_desc" "\n"
266 " dump_all_config_desc" "\n"
267 " dump_string <index>" "\n"
268 " dump_info" "\n"
269 " show_ifdrv" "\n"

--- 85 unchanged lines hidden (view full) ---

355 continue;
356 }
357 if (opt->got_addr &&
358 (libusb20_dev_get_address(pdev) != opt->addr)) {
359 continue;
360 }
361 matches++;
362
281 " dump_quirk_names" "\n"
282 " dump_device_quirks" "\n"
283 " dump_device_desc" "\n"
284 " dump_curr_config_desc" "\n"
285 " dump_all_config_desc" "\n"
286 " dump_string <index>" "\n"
287 " dump_info" "\n"
288 " show_ifdrv" "\n"

--- 85 unchanged lines hidden (view full) ---

374 continue;
375 }
376 if (opt->got_addr &&
377 (libusb20_dev_get_address(pdev) != opt->addr)) {
378 continue;
379 }
380 matches++;
381
382 if (opt->got_remove_quirk) {
383 struct LIBUSB20_DEVICE_DESC_DECODED *ddesc;
384
385 ddesc = libusb20_dev_get_device_desc(pdev);
386
387 be_dev_remove_quirk(pbe,
388 ddesc->idVendor, ddesc->idProduct,
389 ddesc->bcdDevice, ddesc->bcdDevice,
390 opt->quirkname);
391 }
392
393 if (opt->got_add_quirk) {
394 struct LIBUSB20_DEVICE_DESC_DECODED *ddesc;
395
396 ddesc = libusb20_dev_get_device_desc(pdev);
397
398 be_dev_add_quirk(pbe,
399 ddesc->idVendor, ddesc->idProduct,
400 ddesc->bcdDevice, ddesc->bcdDevice,
401 opt->quirkname);
402 }
403
363 if (libusb20_dev_open(pdev, 0)) {
364 err(1, "could not open device");
365 }
366 if (opt->got_dump_string) {
404 if (libusb20_dev_open(pdev, 0)) {
405 err(1, "could not open device");
406 }
407 if (opt->got_dump_string) {
367 char *pbuf;
368
369 pbuf = malloc(256);
370 if (pbuf == NULL) {
371 err(1, "out of memory");
372 }
373 if (libusb20_dev_req_string_simple_sync(pdev,
374 opt->string_index, pbuf, 256)) {
375 printf("STRING_0x%02x = <read error>\n",
376 opt->string_index);
377 } else {
378 printf("STRING_0x%02x = <%s>\n",
379 opt->string_index, pbuf);
380 }
381 free(pbuf);
408 dump_string_by_index(pdev, opt->string_index);
382 }
383 if (opt->got_do_request) {
384 uint16_t actlen;
385 uint16_t t;
386
387 if (libusb20_dev_request_sync(pdev, &opt->setup,
388 opt->buffer, &actlen, 5000 /* 5 seconds */ , 0)) {
389 printf("REQUEST = <ERROR>\n");

--- 106 unchanged lines hidden (view full) ---

496 return;
497}
498
499int
500main(int argc, char **argv)
501{
502 struct libusb20_backend *pbe;
503 struct options *opt = &options;
409 }
410 if (opt->got_do_request) {
411 uint16_t actlen;
412 uint16_t t;
413
414 if (libusb20_dev_request_sync(pdev, &opt->setup,
415 opt->buffer, &actlen, 5000 /* 5 seconds */ , 0)) {
416 printf("REQUEST = <ERROR>\n");

--- 106 unchanged lines hidden (view full) ---

523 return;
524}
525
526int
527main(int argc, char **argv)
528{
529 struct libusb20_backend *pbe;
530 struct options *opt = &options;
531 const char *ptr;
532 int unit;
533 int addr;
504 int n;
505 int t;
506
507 if (argc < 1) {
508 usage();
509 }
510 pbe = libusb20_be_alloc_default();
511 if (pbe == NULL)
512 err(1, "could not access USB backend\n");
513
514 for (n = 1; n != argc; n++) {
515
516 /* get number of additional options */
517 t = (argc - n - 1);
518 if (t > 255)
519 t = 255;
520 switch (get_token(argv[n], t)) {
534 int n;
535 int t;
536
537 if (argc < 1) {
538 usage();
539 }
540 pbe = libusb20_be_alloc_default();
541 if (pbe == NULL)
542 err(1, "could not access USB backend\n");
543
544 for (n = 1; n != argc; n++) {
545
546 /* get number of additional options */
547 t = (argc - n - 1);
548 if (t > 255)
549 t = 255;
550 switch (get_token(argv[n], t)) {
551 case T_ADD_QUIRK:
552 if (opt->got_add_quirk) {
553 flush_command(pbe, opt);
554 }
555 opt->quirkname = argv[n + 1];
556 n++;
557
558 opt->got_add_quirk = 1;
559 opt->got_any++;
560 break;
561
562 case T_REMOVE_QUIRK:
563 if (opt->got_remove_quirk) {
564 flush_command(pbe, opt);
565 }
566 opt->quirkname = argv[n + 1];
567 n++;
568
569 opt->got_remove_quirk = 1;
570 opt->got_any++;
571 break;
572
521 case T_ADD_DEVICE_QUIRK:
522 if (opt->got_add_device_quirk) {
523 flush_command(pbe, opt);
524 }
525 opt->vid = num_id(argv[n + 1], "Vendor ID");
526 opt->pid = num_id(argv[n + 2], "Product ID");
527 opt->lo_rev = num_id(argv[n + 3], "Low Revision");
528 opt->hi_rev = num_id(argv[n + 4], "High Revision");

--- 14 unchanged lines hidden (view full) ---

543 opt->hi_rev = num_id(argv[n + 4], "High Revision");
544 opt->quirkname = argv[n + 5];
545 n += 5;
546 opt->got_remove_device_quirk = 1;
547 opt->got_any++;
548 break;
549
550 case T_DUMP_QUIRK_NAMES:
573 case T_ADD_DEVICE_QUIRK:
574 if (opt->got_add_device_quirk) {
575 flush_command(pbe, opt);
576 }
577 opt->vid = num_id(argv[n + 1], "Vendor ID");
578 opt->pid = num_id(argv[n + 2], "Product ID");
579 opt->lo_rev = num_id(argv[n + 3], "Low Revision");
580 opt->hi_rev = num_id(argv[n + 4], "High Revision");

--- 14 unchanged lines hidden (view full) ---

595 opt->hi_rev = num_id(argv[n + 4], "High Revision");
596 opt->quirkname = argv[n + 5];
597 n += 5;
598 opt->got_remove_device_quirk = 1;
599 opt->got_any++;
600 break;
601
602 case T_DUMP_QUIRK_NAMES:
603 if (opt->got_dump_quirk_names)
604 duplicate_option(argv[n]);
551 opt->got_dump_quirk_names = 1;
552 opt->got_any++;
553 break;
554
555 case T_DUMP_DEVICE_QUIRKS:
605 opt->got_dump_quirk_names = 1;
606 opt->got_any++;
607 break;
608
609 case T_DUMP_DEVICE_QUIRKS:
610 if (opt->got_dump_device_quirks)
611 duplicate_option(argv[n]);
556 opt->got_dump_device_quirks = 1;
557 opt->got_any++;
558 break;
559
560 case T_SHOW_IFACE_DRIVER:
561 opt->got_show_iface_driver = 1;
562 break;
563
612 opt->got_dump_device_quirks = 1;
613 opt->got_any++;
614 break;
615
616 case T_SHOW_IFACE_DRIVER:
617 opt->got_show_iface_driver = 1;
618 break;
619
620 case T_UGEN:
621 if (opt->got_any) {
622 /* allow multiple commands on the same line */
623 flush_command(pbe, opt);
624 }
625 ptr = argv[n + 1];
626
627 if ((ptr[0] == 'u') &&
628 (ptr[1] == 'g') &&
629 (ptr[2] == 'e') &&
630 (ptr[3] == 'n'))
631 ptr += 4;
632
633 if ((sscanf(ptr, "%d.%d",
634 &unit, &addr) != 2) ||
635 (unit < 0) || (unit > 65535) ||
636 (addr < 0) || (addr > 65535)) {
637 errx(1, "cannot "
638 "parse '%s'", argv[n + 1]);
639 }
640 opt->bus = unit;
641 opt->addr = addr;
642 opt->got_bus = 1;
643; opt->got_addr = 1;
644 n++;
645 break;
646
564 case T_UNIT:
565 if (opt->got_any) {
566 /* allow multiple commands on the same line */
567 flush_command(pbe, opt);
568 }
569 opt->bus = num_id(argv[n + 1], "busnum");
570 opt->got_bus = 1;
571 n++;

--- 4 unchanged lines hidden (view full) ---

576 n++;
577 break;
578 case T_IFACE:
579 opt->iface = num_id(argv[n + 1], "iface");
580 opt->got_iface = 1;
581 n++;
582 break;
583 case T_SET_CONFIG:
647 case T_UNIT:
648 if (opt->got_any) {
649 /* allow multiple commands on the same line */
650 flush_command(pbe, opt);
651 }
652 opt->bus = num_id(argv[n + 1], "busnum");
653 opt->got_bus = 1;
654 n++;

--- 4 unchanged lines hidden (view full) ---

659 n++;
660 break;
661 case T_IFACE:
662 opt->iface = num_id(argv[n + 1], "iface");
663 opt->got_iface = 1;
664 n++;
665 break;
666 case T_SET_CONFIG:
667 if (opt->got_set_config)
668 duplicate_option(argv[n]);
584 opt->config_index = num_id(argv[n + 1], "cfg_index");
585 opt->got_set_config = 1;
586 opt->got_any++;
587 n++;
588 break;
589 case T_SET_ALT:
669 opt->config_index = num_id(argv[n + 1], "cfg_index");
670 opt->got_set_config = 1;
671 opt->got_any++;
672 n++;
673 break;
674 case T_SET_ALT:
675 if (opt->got_set_alt)
676 duplicate_option(argv[n]);
590 opt->alt_index = num_id(argv[n + 1], "cfg_index");
591 opt->got_set_alt = 1;
592 opt->got_any++;
593 n++;
594 break;
595 case T_SET_TEMPLATE:
677 opt->alt_index = num_id(argv[n + 1], "cfg_index");
678 opt->got_set_alt = 1;
679 opt->got_any++;
680 n++;
681 break;
682 case T_SET_TEMPLATE:
683 if (opt->got_set_template)
684 duplicate_option(argv[n]);
596 opt->template = get_int(argv[n + 1]);
597 opt->got_set_template = 1;
598 opt->got_any++;
599 n++;
600 break;
601 case T_GET_TEMPLATE:
685 opt->template = get_int(argv[n + 1]);
686 opt->got_set_template = 1;
687 opt->got_any++;
688 n++;
689 break;
690 case T_GET_TEMPLATE:
691 if (opt->got_get_template)
692 duplicate_option(argv[n]);
602 opt->got_get_template = 1;
603 opt->got_any++;
604 break;
605 case T_DUMP_DEVICE_DESC:
693 opt->got_get_template = 1;
694 opt->got_any++;
695 break;
696 case T_DUMP_DEVICE_DESC:
697 if (opt->got_dump_device_desc)
698 duplicate_option(argv[n]);
606 opt->got_dump_device_desc = 1;
607 opt->got_any++;
608 break;
609 case T_DUMP_CURR_CONFIG_DESC:
699 opt->got_dump_device_desc = 1;
700 opt->got_any++;
701 break;
702 case T_DUMP_CURR_CONFIG_DESC:
703 if (opt->got_dump_curr_config)
704 duplicate_option(argv[n]);
610 opt->got_dump_curr_config = 1;
611 opt->got_any++;
612 break;
613 case T_DUMP_ALL_CONFIG_DESC:
705 opt->got_dump_curr_config = 1;
706 opt->got_any++;
707 break;
708 case T_DUMP_ALL_CONFIG_DESC:
709 if (opt->got_dump_all_config)
710 duplicate_option(argv[n]);
614 opt->got_dump_all_config = 1;
615 opt->got_any++;
616 break;
617 case T_DUMP_INFO:
711 opt->got_dump_all_config = 1;
712 opt->got_any++;
713 break;
714 case T_DUMP_INFO:
715 if (opt->got_dump_info)
716 duplicate_option(argv[n]);
618 opt->got_dump_info = 1;
619 opt->got_any++;
620 break;
621 case T_DUMP_STRING:
717 opt->got_dump_info = 1;
718 opt->got_any++;
719 break;
720 case T_DUMP_STRING:
622 if (opt->got_dump_string) {
623 flush_command(pbe, opt);
624 }
721 if (opt->got_dump_string)
722 duplicate_option(argv[n]);
625 opt->string_index = num_id(argv[n + 1], "str_index");
626 opt->got_dump_string = 1;
627 opt->got_any++;
628 n++;
629 break;
630 case T_SUSPEND:
723 opt->string_index = num_id(argv[n + 1], "str_index");
724 opt->got_dump_string = 1;
725 opt->got_any++;
726 n++;
727 break;
728 case T_SUSPEND:
729 if (opt->got_suspend)
730 duplicate_option(argv[n]);
631 opt->got_suspend = 1;
632 opt->got_any++;
633 break;
634 case T_RESUME:
731 opt->got_suspend = 1;
732 opt->got_any++;
733 break;
734 case T_RESUME:
735 if (opt->got_resume)
736 duplicate_option(argv[n]);
635 opt->got_resume = 1;
636 opt->got_any++;
637 break;
638 case T_POWER_OFF:
737 opt->got_resume = 1;
738 opt->got_any++;
739 break;
740 case T_POWER_OFF:
741 if (opt->got_power_off)
742 duplicate_option(argv[n]);
639 opt->got_power_off = 1;
640 opt->got_any++;
641 break;
642 case T_POWER_SAVE:
743 opt->got_power_off = 1;
744 opt->got_any++;
745 break;
746 case T_POWER_SAVE:
747 if (opt->got_power_save)
748 duplicate_option(argv[n]);
643 opt->got_power_save = 1;
644 opt->got_any++;
645 break;
646 case T_POWER_ON:
749 opt->got_power_save = 1;
750 opt->got_any++;
751 break;
752 case T_POWER_ON:
753 if (opt->got_power_on)
754 duplicate_option(argv[n]);
647 opt->got_power_on = 1;
648 opt->got_any++;
649 break;
650 case T_RESET:
755 opt->got_power_on = 1;
756 opt->got_any++;
757 break;
758 case T_RESET:
759 if (opt->got_reset)
760 duplicate_option(argv[n]);
651 opt->got_reset = 1;
652 opt->got_any++;
653 break;
654 case T_LIST:
761 opt->got_reset = 1;
762 opt->got_any++;
763 break;
764 case T_LIST:
765 if (opt->got_list)
766 duplicate_option(argv[n]);
655 opt->got_list = 1;
656 opt->got_any++;
657 break;
658 case T_DO_REQUEST:
767 opt->got_list = 1;
768 opt->got_any++;
769 break;
770 case T_DO_REQUEST:
659 if (opt->got_do_request) {
660 flush_command(pbe, opt);
661 }
771 if (opt->got_do_request)
772 duplicate_option(argv[n]);
662 LIBUSB20_INIT(LIBUSB20_CONTROL_SETUP, &opt->setup);
663 opt->setup.bmRequestType = num_id(argv[n + 1], "bmReqTyp");
664 opt->setup.bRequest = num_id(argv[n + 2], "bReq");
665 opt->setup.wValue = num_id(argv[n + 3], "wVal");
666 opt->setup.wIndex = num_id(argv[n + 4], "wIndex");
667 opt->setup.wLength = num_id(argv[n + 5], "wLen");
668 if (opt->setup.wLength != 0) {
669 opt->buffer = malloc(opt->setup.wLength);

--- 42 unchanged lines hidden ---
773 LIBUSB20_INIT(LIBUSB20_CONTROL_SETUP, &opt->setup);
774 opt->setup.bmRequestType = num_id(argv[n + 1], "bmReqTyp");
775 opt->setup.bRequest = num_id(argv[n + 2], "bReq");
776 opt->setup.wValue = num_id(argv[n + 3], "wVal");
777 opt->setup.wIndex = num_id(argv[n + 4], "wIndex");
778 opt->setup.wLength = num_id(argv[n + 5], "wLen");
779 if (opt->setup.wLength != 0) {
780 opt->buffer = malloc(opt->setup.wLength);

--- 42 unchanged lines hidden ---