diff options
Diffstat (limited to 'utils/hwstub/lib')
-rw-r--r-- | utils/hwstub/lib/hwstub.cpp | 46 | ||||
-rw-r--r-- | utils/hwstub/lib/hwstub_net.cpp | 12 | ||||
-rw-r--r-- | utils/hwstub/lib/hwstub_usb.cpp | 52 | ||||
-rw-r--r-- | utils/hwstub/lib/hwstub_virtual.cpp | 12 |
4 files changed, 122 insertions, 0 deletions
diff --git a/utils/hwstub/lib/hwstub.cpp b/utils/hwstub/lib/hwstub.cpp index 9dd2915903..5e708c3bb8 100644 --- a/utils/hwstub/lib/hwstub.cpp +++ b/utils/hwstub/lib/hwstub.cpp | |||
@@ -45,6 +45,8 @@ std::string error_string(error err) | |||
45 | case error::PROTOCOL_ERROR: return "network protocol error"; | 45 | case error::PROTOCOL_ERROR: return "network protocol error"; |
46 | case error::TIMEOUT: return "timeout"; | 46 | case error::TIMEOUT: return "timeout"; |
47 | case error::OVERFLW: return "overflow"; | 47 | case error::OVERFLW: return "overflow"; |
48 | case error::UNIMPLEMENTED: return "operation is not implemented"; | ||
49 | case error::UNSUPPORTED: return "operation unsupported"; | ||
48 | default: return "unknown error"; | 50 | default: return "unknown error"; |
49 | } | 51 | } |
50 | } | 52 | } |
@@ -457,6 +459,38 @@ error handle::write(uint32_t addr, const void *buf, size_t& sz, bool atomic) | |||
457 | return error::SUCCESS; | 459 | return error::SUCCESS; |
458 | } | 460 | } |
459 | 461 | ||
462 | error handle::cop_op(uint8_t op, uint8_t args[HWSTUB_COP_ARGS], const void *out_data, | ||
463 | size_t out_size, void *in_data, size_t *in_size) | ||
464 | { | ||
465 | std::unique_lock<std::recursive_mutex> lock(m_mutex); | ||
466 | /* get a pointer so that it's not destroyed during the runtime of the function, | ||
467 | * the pointer will be released at the end of the function */ | ||
468 | std::shared_ptr<context> ctx = m_dev->get_context(); | ||
469 | if(!ctx) | ||
470 | return error::NO_CONTEXT; | ||
471 | /* ensure valid status */ | ||
472 | error err = status(); | ||
473 | if(err != error::SUCCESS) | ||
474 | return err; | ||
475 | return cop_dev(op, args, out_data, out_size, in_data, in_size); | ||
476 | } | ||
477 | |||
478 | error handle::read32_cop(uint8_t args[HWSTUB_COP_ARGS], uint32_t& value) | ||
479 | { | ||
480 | size_t sz = sizeof(value); | ||
481 | error err = cop_op(HWSTUB_COP_READ, args, nullptr, 0, &value, &sz); | ||
482 | if(err != error::SUCCESS) | ||
483 | return err; | ||
484 | if(sz != sizeof(value)) | ||
485 | return error::ERROR; | ||
486 | return error::SUCCESS; | ||
487 | } | ||
488 | |||
489 | error handle::write32_cop(uint8_t args[HWSTUB_COP_ARGS], uint32_t value) | ||
490 | { | ||
491 | return cop_op(HWSTUB_COP_WRITE, args, &value, sizeof(value), nullptr, nullptr); | ||
492 | } | ||
493 | |||
460 | error handle::status() const | 494 | error handle::status() const |
461 | { | 495 | { |
462 | /* check context */ | 496 | /* check context */ |
@@ -616,6 +650,18 @@ error dummy_handle::exec_dev(uint32_t addr, uint16_t flags) | |||
616 | return error::DUMMY; | 650 | return error::DUMMY; |
617 | } | 651 | } |
618 | 652 | ||
653 | error dummy_handle::cop_dev(uint8_t op, uint8_t args[HWSTUB_COP_ARGS], | ||
654 | const void *out_data, size_t out_size, void *in_data, size_t *in_size) | ||
655 | { | ||
656 | (void) op; | ||
657 | (void) args; | ||
658 | (void) out_data; | ||
659 | (void) out_size; | ||
660 | (void) in_data; | ||
661 | (void) in_size; | ||
662 | return error::DUMMY; | ||
663 | } | ||
664 | |||
619 | error dummy_handle::status() const | 665 | error dummy_handle::status() const |
620 | { | 666 | { |
621 | error err = handle::status(); | 667 | error err = handle::status(); |
diff --git a/utils/hwstub/lib/hwstub_net.cpp b/utils/hwstub/lib/hwstub_net.cpp index ddafea6351..c9d201a761 100644 --- a/utils/hwstub/lib/hwstub_net.cpp +++ b/utils/hwstub/lib/hwstub_net.cpp | |||
@@ -735,6 +735,18 @@ error handle::exec_dev(uint32_t addr, uint16_t flags) | |||
735 | return error::SUCCESS; | 735 | return error::SUCCESS; |
736 | } | 736 | } |
737 | 737 | ||
738 | error handle::cop_dev(uint8_t op, uint8_t args[HWSTUB_COP_ARGS], | ||
739 | const void *out_data, size_t out_size, void *in_data, size_t *in_size) | ||
740 | { | ||
741 | (void) op; | ||
742 | (void) args; | ||
743 | (void) out_data; | ||
744 | (void) out_size; | ||
745 | (void) in_data; | ||
746 | (void) in_size; | ||
747 | return error::UNIMPLEMENTED; | ||
748 | } | ||
749 | |||
738 | error handle::status() const | 750 | error handle::status() const |
739 | { | 751 | { |
740 | return hwstub::handle::status(); | 752 | return hwstub::handle::status(); |
diff --git a/utils/hwstub/lib/hwstub_usb.cpp b/utils/hwstub/lib/hwstub_usb.cpp index 6bb1cfa049..37249f5812 100644 --- a/utils/hwstub/lib/hwstub_usb.cpp +++ b/utils/hwstub/lib/hwstub_usb.cpp | |||
@@ -399,6 +399,46 @@ error rb_handle::write_dev(uint32_t addr, const void *buf, size_t& sz, bool atom | |||
399 | return ret; | 399 | return ret; |
400 | } | 400 | } |
401 | 401 | ||
402 | error rb_handle::cop_dev(uint8_t op, uint8_t args[HWSTUB_COP_ARGS], | ||
403 | const void *out_data, size_t out_size, void *in_data, size_t *in_size) | ||
404 | { | ||
405 | (void) op; | ||
406 | (void) args; | ||
407 | (void) out_data; | ||
408 | (void) out_size; | ||
409 | (void) in_data; | ||
410 | (void) in_size; | ||
411 | std::shared_ptr<hwstub::context> hctx = get_device()->get_context(); | ||
412 | if(!hctx) | ||
413 | return error::NO_CONTEXT; | ||
414 | |||
415 | /* construct out request: header followed by (optional) data */ | ||
416 | size_t hdr_sz = sizeof(struct hwstub_cop_req_t); | ||
417 | uint8_t *tmp_buf = new uint8_t[out_size + hdr_sz]; | ||
418 | struct hwstub_cop_req_t *req = reinterpret_cast<struct hwstub_cop_req_t *>(tmp_buf); | ||
419 | req->bOp = op; | ||
420 | for(int i = 0; i < HWSTUB_COP_ARGS; i++) | ||
421 | req->bArgs[i] = args[i]; | ||
422 | if(out_size > 0) | ||
423 | memcpy(tmp_buf + hdr_sz, out_data, out_size); | ||
424 | error ret = interpret_libusb_error(libusb_control_transfer(m_handle, | ||
425 | LIBUSB_REQUEST_TYPE_CLASS | LIBUSB_RECIPIENT_INTERFACE | LIBUSB_ENDPOINT_OUT, | ||
426 | HWSTUB_COPROCESSOR_OP, m_transac_id++, m_intf, | ||
427 | (unsigned char *)req, out_size + hdr_sz, m_timeout), out_size + hdr_sz); | ||
428 | delete[] tmp_buf; | ||
429 | /* return errors if any */ | ||
430 | if(ret != error::SUCCESS) | ||
431 | return ret; | ||
432 | /* return now if there is no read stage */ | ||
433 | if(in_data == nullptr) | ||
434 | return error::SUCCESS; | ||
435 | /* perform read stage (use the same transaction ID) */ | ||
436 | return interpret_libusb_size(libusb_control_transfer(m_handle, | ||
437 | LIBUSB_REQUEST_TYPE_CLASS | LIBUSB_RECIPIENT_INTERFACE | LIBUSB_ENDPOINT_IN, | ||
438 | HWSTUB_READ2, m_transac_id - 1, m_intf, | ||
439 | (unsigned char *)in_data, *in_size, m_timeout), *in_size); | ||
440 | } | ||
441 | |||
402 | bool rb_handle::find_intf(struct libusb_device_descriptor *dev, | 442 | bool rb_handle::find_intf(struct libusb_device_descriptor *dev, |
403 | struct libusb_config_descriptor *config, int& intf_idx) | 443 | struct libusb_config_descriptor *config, int& intf_idx) |
404 | { | 444 | { |
@@ -674,6 +714,18 @@ error jz_handle::write_dev(uint32_t addr, const void *buf, size_t& sz, bool atom | |||
674 | return ret; | 714 | return ret; |
675 | } | 715 | } |
676 | 716 | ||
717 | error jz_handle::cop_dev(uint8_t op, uint8_t args[HWSTUB_COP_ARGS], | ||
718 | const void *out_data, size_t out_size, void *in_data, size_t *in_size) | ||
719 | { | ||
720 | (void) op; | ||
721 | (void) args; | ||
722 | (void) out_data; | ||
723 | (void) out_size; | ||
724 | (void) in_data; | ||
725 | (void) in_size; | ||
726 | return error::UNSUPPORTED; | ||
727 | } | ||
728 | |||
677 | bool jz_handle::is_boot_dev(struct libusb_device_descriptor *dev, | 729 | bool jz_handle::is_boot_dev(struct libusb_device_descriptor *dev, |
678 | struct libusb_config_descriptor *config) | 730 | struct libusb_config_descriptor *config) |
679 | { | 731 | { |
diff --git a/utils/hwstub/lib/hwstub_virtual.cpp b/utils/hwstub/lib/hwstub_virtual.cpp index fada56fb83..5c9e79e5a1 100644 --- a/utils/hwstub/lib/hwstub_virtual.cpp +++ b/utils/hwstub/lib/hwstub_virtual.cpp | |||
@@ -221,6 +221,18 @@ error handle::exec_dev(uint32_t addr, uint16_t flags) | |||
221 | return p ? p->exec_dev(addr, flags) : error::DISCONNECTED; | 221 | return p ? p->exec_dev(addr, flags) : error::DISCONNECTED; |
222 | } | 222 | } |
223 | 223 | ||
224 | error handle::cop_dev(uint8_t op, uint8_t args[HWSTUB_COP_ARGS], | ||
225 | const void *out_data, size_t out_size, void *in_data, size_t *in_size) | ||
226 | { | ||
227 | (void) op; | ||
228 | (void) args; | ||
229 | (void) out_data; | ||
230 | (void) out_size; | ||
231 | (void) in_data; | ||
232 | (void) in_size; | ||
233 | return error::UNSUPPORTED; | ||
234 | } | ||
235 | |||
224 | error handle::status() const | 236 | error handle::status() const |
225 | { | 237 | { |
226 | return hwstub::handle::status(); | 238 | return hwstub::handle::status(); |