GNOME Bugzilla – Bug 612536
Unable to copy folders from device to pc
Last modified: 2010-03-15 18:37:36 UTC
When trying to copy a folder from an afc capable device via nautilus or gvfs-copy to the local filesystem, the operation fails (pc -> device works), regardless of the folder being empty or not. Instead of a folder just a file is created. The problem seems to be that the folder is opened like a regular file, as the following debugging output reveals (comments=***) $ /usr/lib/gvfs/gvfsd-afc --debug host=`idevice_id -l` [... skipping irrelevant part ...] ***** gvfs-copy afc://xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx/Downloads . backend_dbus_handler org.gtk.vfs.Mount:Pull Remove Source: false Queued new job 0x9ec7410 (GVfsJobPull) send_reply(0x9ec7410), failed=1 (Vorgang wird vom Backend nicht unterstützt) ***** ^^ just saw this, maybe that is the reason? unsupported operation? ****** backend_dbus_handler org.gtk.vfs.Mount:QueryInfo Queued new job 0x9ec7460 (GVfsJobQueryInfo) 06:28:32 afc.c:39 afc_lock(): Locked 06:28:32 afc.c:198 afc_dispatch_packet(): doin things the old way 06:28:32 afc.c:199 afc_dispatch_packet(): packet length = 51 0000: 43 46 41 36 4c 50 41 41 33 00 00 00 00 00 00 00 | CFA6LPAA3....... 0010: 33 00 00 00 00 00 00 00 03 00 00 00 00 00 00 00 | 3............... 0020: 0a 00 00 00 00 00 00 00 | ........ 06:28:32 afc.c:213 afc_dispatch_packet(): packet data follows 0000: 2f 44 6f 77 6e 6c 6f 61 64 73 00 | /Downloads. 0000: 43 46 41 36 4c 50 41 41 78 00 00 00 00 00 00 00 | CFA6LPAAx....... 0010: 28 00 00 00 00 00 00 00 03 00 00 00 00 00 00 00 | (............... 0020: 02 00 00 00 00 00 00 00 | ........ received AFC packet, full len=120, this len=40, operation=0x2 06:28:32 afc.c:335 afc_receive_data(): packet data size = 80 06:28:32 afc.c:336 afc_receive_data(): packet data follows 0000: 73 74 5f 73 69 7a 65 00 31 30 32 00 73 74 5f 62 | st_size.102.st_b 0010: 6c 6f 63 6b 73 00 30 00 73 74 5f 6e 6c 69 6e 6b | locks.0.st_nlink 0020: 00 32 00 73 74 5f 69 66 6d 74 00 53 5f 49 46 44 | .2.st_ifmt.S_IFD 0030: 49 52 00 73 74 5f 6d 74 69 6d 65 00 31 32 36 38 | IR.st_mtime.1268 0040: 31 37 34 39 34 35 30 30 30 30 30 30 30 30 30 00 | 174945000000000. 06:28:32 afc.c:353 afc_receive_data(): got a data response 06:28:32 afc.c:49 afc_unlock(): Unlocked ********* The above buffer shows it is a directory (S_IFDIR) *********** send_reply(0x9ec7460), failed=0 () backend_dbus_handler org.gtk.vfs.Mount:OpenForRead Queued new job 0x9ec74b0 (GVfsJobOpenForRead) 06:28:32 afc.c:39 afc_lock(): Locked 06:28:32 afc.c:198 afc_dispatch_packet(): doin things the old way 06:28:32 afc.c:199 afc_dispatch_packet(): packet length = 59 0000: 43 46 41 36 4c 50 41 41 3b 00 00 00 00 00 00 00 | CFA6LPAA;....... 0010: 3b 00 00 00 00 00 00 00 04 00 00 00 00 00 00 00 | ;............... 0020: 0d 00 00 00 00 00 00 00 | ........ ***** ^^ 0xd = AFC_OP_FILE_OPEN !!! ************************************ 06:28:32 afc.c:213 afc_dispatch_packet(): packet data follows 0000: 01 00 00 00 00 00 00 00 2f 44 6f 77 6e 6c 6f 61 | ......../Downloa 0010: 64 73 00 | ds. 0000: 43 46 41 36 4c 50 41 41 30 00 00 00 00 00 00 00 | CFA6LPAA0....... 0010: 30 00 00 00 00 00 00 00 04 00 00 00 00 00 00 00 | 0............... 0020: 0e 00 00 00 00 00 00 00 | ........ received AFC packet, full len=48, this len=48, operation=0xe 06:28:32 afc.c:335 afc_receive_data(): packet data size = 8 06:28:32 afc.c:336 afc_receive_data(): packet data follows 0000: 01 00 00 00 00 00 00 00 | ........ 06:28:32 afc.c:356 afc_receive_data(): got a file handle response, handle=1 06:28:32 afc.c:49 afc_unlock(): Unlocked ********* The device even reports success and gives a file handle!! ********* send_reply(0x9ec74b0), failed=0 () Added new job source 0x9ecbc30 (GVfsReadChannel) Queued new job 0x9ecc400 (GVfsJobRead) 06:28:32 afc.c:776 afc_file_read(): called for length 65536 06:28:32 afc.c:39 afc_lock(): Locked 06:28:32 afc.c:783 afc_file_read(): current count is 0 but length is 65536 06:28:32 afc.c:198 afc_dispatch_packet(): doin things the old way 06:28:32 afc.c:199 afc_dispatch_packet(): packet length = 56 0000: 43 46 41 36 4c 50 41 41 38 00 00 00 00 00 00 00 | CFA6LPAA8....... 0010: 38 00 00 00 00 00 00 00 05 00 00 00 00 00 00 00 | 8............... 0020: 0f 00 00 00 00 00 00 00 | ........ 06:28:32 afc.c:213 afc_dispatch_packet(): packet data follows 0000: 01 00 00 00 00 00 00 00 00 00 01 00 00 00 00 00 | ................ 0000: 43 46 41 36 4c 50 41 41 27 00 00 00 01 00 00 00 | CFA6LPAA'....... 0010: 28 00 00 00 00 00 00 00 05 00 00 00 00 00 00 00 | (............... 0020: 02 00 00 00 00 00 00 00 | ........ ******************* This ^^^^ buffer kills the AFC operation. It is an invalid buffer sent by the device, this is NOT a libimobiledevice bug. The following lines show what happened: ****************** received AFC packet, full len=4294967335, this len=40, operation=0x2 afc_receive_data: entire_len is larger than MAXIMUM_PACKET_SIZE, (-1 > 65536)!06:28:37 afc.c:321 afc_receive_data(): Error receiving data (recv returned 0) 06:28:37 afc.c:327 afc_receive_data(): WARNING: could not receive full packet (read (null), size -1) 06:28:37 afc.c:335 afc_receive_data(): packet data size = 0 06:28:37 afc.c:336 afc_receive_data(): packet data follows 06:28:37 afc.c:353 afc_receive_data(): got a data response 06:28:37 afc.c:800 afc_file_read(): afc_receive_data returned error: 0 06:28:37 afc.c:801 afc_file_read(): bytes returned: 0 06:28:37 afc.c:49 afc_unlock(): Unlocked job_read send reply, 0 bytes Queued new job 0x9eaa700 (GVfsJobCloseRead)
Here the output of gvfs-info on the directory: $ gvfs-info afc://`idevice_id -l`/Downloads display name: Downloads edit name: Downloads name: Downloads type: directory size: 102 attributes: standard::type: 2 standard::is-hidden: FALSE standard::name: Downloads standard::display-name: Downloads standard::edit-name: Downloads standard::icon: folder standard::content-type: inode/directory standard::fast-content-type: inode/directory standard::size: 102 id::filesystem: afc:host=xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx time::modified: 1268174945 unix::nlink: 2 unix::uid: 1000 unix::gid: 1000 unix::blocks: 0 metadata::annotation:
Created attachment 156129 [details] [review] Fix g_vfs_backend_afc_open_for_read to only open regular files Fixes the bug.
Review of attachment 156129 [details] [review]: ::: daemon/gvfsbackendafc.c @@ +457,3 @@ + g_vfs_job_failed (G_VFS_JOB (job), G_IO_ERROR, + G_IO_ERROR_NOT_FOUND, + _("No such file")); Other backends have the string "File doesn't exist" which would be good to avoid adding new strings to the backend. @@ +763,2 @@ static void +fill_info_from_afcinfo (GFileInfo *info, char **afcinfo) Why the code reorganisation? This is not needed, especially at this late stage of the development. @@ +780,3 @@ else if (g_str_equal (afcinfo[i], "st_blocks")) { + g_file_info_set_attribute_uint64 (info, G_FILE_ATTRIBUTE_UNIX_BLOCKS, atoi(afcinfo[i+1])); And on all the lines below, what's the point of all the indentation changes?
OK, here's a reworked patch. The "No such file" string is from the gphoto2 backend, perhaps you want to change it too.
Created attachment 156160 [details] [review] Reworked fix for g_vfs_backend_afc_open_for_read to only open regular files
Any chance you could split that into 2? One commit for the is_directory() changes, and one for the g_vfs_backend_afc_set_info_from_afcinfo() changes.
Created attachment 156176 [details] [review] g_vfs_backend_afc_set_info_from_afcinfo: set content type even if matcher is NULL
Created attachment 156177 [details] [review] g_vfs_backend_afc_open_for_read: only open regular files
Attachment 156176 [details] pushed as 7900fd4 - g_vfs_backend_afc_set_info_from_afcinfo: set content type even if matcher is NULL Attachment 156177 [details] pushed as 27478c0 - g_vfs_backend_afc_open_for_read: only open regular files