aboutsummaryrefslogtreecommitdiff
path: root/src/libusb-glue.c
diff options
context:
space:
mode:
authorJerry Zhang <zhangjerry@google.com>2017-06-15 12:42:13 -0700
committerJerry Zhang <zhangjerry@google.com>2017-06-15 14:40:03 -0700
commit6c016415c6bd986413088a330595786d7d3d358c (patch)
tree5451c867ef898d36760d56a1a8f2d48822ceea5a /src/libusb-glue.c
parentc58b24651a56989fdf39b42202c77e72749e8bab (diff)
downloadlibmtp-6c016415c6bd986413088a330595786d7d3d358c.tar.gz
ptp_usb_senddata will store file size in a uint64_t, but ptp_write_func casts this down to an unsigned long, which is 32 bits on i386. To fix, break up transfers into pieces less than ULONG_MAX rounded down by packet size.
Diffstat (limited to 'src/libusb-glue.c')
-rw-r--r--src/libusb-glue.c8
1 files changed, 7 insertions, 1 deletions
diff --git a/src/libusb-glue.c b/src/libusb-glue.c
index 722a591..0079b08 100644
--- a/src/libusb-glue.c
+++ b/src/libusb-glue.c
@@ -1202,6 +1202,10 @@ ptp_usb_senddata (PTPParams* params, PTPContainer* ptp,
PTPUSBBulkContainer usbdata;
uint64_t bytes_left_to_transfer;
PTPDataHandler memhandler;
+ unsigned long packet_size;
+ PTP_USB *ptp_usb = (PTP_USB *) params->data;
+
+ packet_size = ptp_usb->inep_maxpacket;
LIBMTP_USB_DEBUG("SEND DATA PHASE\n");
@@ -1242,7 +1246,9 @@ ptp_usb_senddata (PTPParams* params, PTPContainer* ptp,
bytes_left_to_transfer = size-datawlen;
ret = PTP_RC_OK;
while(bytes_left_to_transfer > 0) {
- ret = ptp_write_func (bytes_left_to_transfer, handler, params->data, &written);
+ int max_long_transfer = ULONG_MAX + 1 - packet_size;
+ ret = ptp_write_func (bytes_left_to_transfer > max_long_transfer ? max_long_transfer : bytes_left_to_transfer,
+ handler, params->data, &written);
if (ret != PTP_RC_OK)
break;
if (written == 0) {