Bug 462059 - Folder access times out on folders containing a high amount of files (> 10000)
Summary: Folder access times out on folders containing a high amount of files (> 10000)
Status: RESOLVED FIXED
Alias: None
Product: kio-extras
Classification: Frameworks and Libraries
Component: MTP (show other bugs)
Version: 21.12.3
Platform: Ubuntu Linux
: NOR normal
Target Milestone: ---
Assignee: Unassigned bugs mailing-list
URL:
Keywords:
Depends on:
Blocks:
 
Reported: 2022-11-20 12:57 UTC by Christoph Thielecke
Modified: 2023-03-21 15:09 UTC (History)
2 users (show)

See Also:
Latest Commit:
Version Fixed In:


Attachments

Note You need to log in before you can comment on or make changes to this bug.
Description Christoph Thielecke 2022-11-20 12:57:20 UTC
SUMMARY
Listing mtp foldr with high amount of files leas to timeout


STEPS TO REPRODUCE
1. Connect android mobile in mtp mode with high amount of files in a folder (e.g. DCIM folder, > 10000)
2. Access the folder with high amount of files


OBSERVED RESULT
1. On access there is a message like "Accessing folder"
2. After serveral minutes, dolphin reports that folder can't be opend

EXPECTED RESULT
1. On access there is a message like "Accessing folder"
2. After serveral minutes, dolphin lists the files

Additional information:
I think there all information fetched for the files at once.
Only the file names should be fetched first and this should be done asynchronously.

The detailed information (like timestamps, size) could be fetched later in background.

Android file transfer (https://github.com/whoozle/android-file-transfer-linux) works fine but this needs to setup manually and requires to no access the mtp device using kio-mtp.
It could be helpful to look how it access the device and fix the kio module.

Please make mtp really useable/stable for heavy usage.

SOFTWARE/OS VERSIONS
Operating System: Kubuntu 22.04
KDE Plasma Version: 5.24.6
KDE Frameworks Version: 5.92.0
Qt Version: 5.15.3
Kernel Version: 5.17.0-1021-oem (64-bit)
Graphics Platform: X11
Processors: 8 × Intel® Core™ i7 CPU Q 840 @ 1.87GHz
Memory: 19.5 GiB of RAM
Graphics Processor: NV92
Comment 1 Christoph Thielecke 2022-11-20 12:58:44 UTC
Note the folder I tried to access contain ~26800 files.
Comment 2 Harald Sitter 2022-12-27 19:24:07 UTC
Can you still reproduce this with 22.12? 21.12 is no longer supported.

I've tried listing some 14k files and that seems to succeed.
Comment 3 Christoph Thielecke 2022-12-28 18:49:33 UTC
(In reply to Harald Sitter from comment #2)
> Can you still reproduce this with 22.12? 21.12 is no longer supported.
This is strange, as 21.12 is used on Ubuntu Jammy (22.04LTS) and 22.08 is used on Ubuntu Kinetic (22.10).

Both are not old.

I'll try with Kubuntu Kinetic (22.10, uses 22.08) and KDE neon (neon-user-20221222-0714.iso) and report the feedback.

> I've tried listing some 14k files and that seems to succeed.

Have you tried with an amount of 50k? I have ~26800 files.

Interesting is, that on Windows machine I saw that the file list will be dynamically updated.
Maybe it would be interesting what commands are done there.
Comment 4 Harald Sitter 2022-12-28 20:00:12 UTC
22.08 is also out of support. 

I haven't tried with more than 14k since I don't actually know how to synthesize that many files and transfering them over mtp takes ages because of how the protocol works.
Comment 5 Christoph Thielecke 2022-12-29 13:01:32 UTC
(In reply to Harald Sitter from comment #4)
> 22.08 is also out of support. 
> 
> I haven't tried with more than 14k since I don't actually know how to
> synthesize that many files and transfering them over mtp takes ages because
> of how the protocol works.

Use an external sd card and copy the file structure with an adapter on a local computer or use kde-connect.
Comment 6 Harald Sitter 2022-12-30 12:07:09 UTC
Found it!

>    m_dbusInterface->setTimeout(std::chrono::milliseconds(5min).count()); // TODO: listing folders with a huge amount of files may take a while

What really needs to happen is rewriting the listing portion of the dbus interface. It currently runs a blocking list operation that is subject to timeouts. What should happen instead is that listing gives out a dbusobjectpath under which it will issue listing status signals. This would then also allow more atomic listing where entries are emitted as they arrive rather than having to load the entire file list into memory and only once that is done emitting the result all at once.

ListingObject {
Q_INVOKABLE void start();
Q_SIGNAL void file(file);
Q_SIGNAL void done();
Q_SIGNAL void error(msg);
}
Comment 7 Christoph Thielecke 2022-12-31 13:14:41 UTC
(In reply to Harald Sitter from comment #6)
> Found it!
> 
> >    m_dbusInterface->setTimeout(std::chrono::milliseconds(5min).count()); // TODO: listing folders with a huge amount of files may take a while
> 
> What really needs to happen is rewriting the listing portion of the dbus
> interface. It currently runs a blocking list operation that is subject to
> timeouts. What should happen instead is that listing gives out a
> dbusobjectpath under which it will issue listing status signals. This would
> then also allow more atomic listing where entries are emitted as they arrive
> rather than having to load the entire file list into memory and only once
> that is done emitting the result all at once.
> 
> ListingObject {
> Q_INVOKABLE void start();
> Q_SIGNAL void file(file);
> Q_SIGNAL void done();
> Q_SIGNAL void error(msg);
> }

Nice!
Do you have a patch that I can test it?
It would be nice to have a patch for 21.12.3 to, that would make things easy.
Comment 8 Christoph Thielecke 2022-12-31 13:15:47 UTC
(In reply to Christoph Thielecke from comment #3)
> (In reply to Harald Sitter from comment #2)
> > Can you still reproduce this with 22.12? 21.12 is no longer supported.
> This is strange, as 21.12 is used on Ubuntu Jammy (22.04LTS) and 22.08 is
> used on Ubuntu Kinetic (22.10).
> 
> Both are not old.
> 
> I'll try with Kubuntu Kinetic (22.10, uses 22.08) and KDE neon
> (neon-user-20221222-0714.iso) and report the feedback.

I tested both and they have same behavior.
Comment 9 Harald Sitter 2023-01-01 10:52:07 UTC
(In reply to Christoph Thielecke from comment #7)
> Nice!
> Do you have a patch that I can test it?

Nope, that will be a fair amount of work.

> It would be nice to have a patch for 21.12.3 to, that would make things easy.

You can just patch that line I've referenced to use a larger value. That way it won't time out after 5 minutes.
Comment 10 Harald Sitter 2023-02-24 13:35:48 UTC
As it turns out we don't actually have the necessary facilities in libmtp. We'll need better handling there. I'll bump the timeout as a stop gap measure, but that will also not be enough given a large enough number of files :(
Comment 11 Harald Sitter 2023-02-24 13:36:08 UTC
https://github.com/libmtp/libmtp/issues/144
Comment 12 Harald Sitter 2023-02-24 13:42:30 UTC
Git commit 5821c30d1f6be18e0993f03db08ec41602e5dc82 by Harald Sitter.
Committed on 24/02/2023 at 13:41.
Pushed by sitter into branch 'release/22.12'.

mtp: bump dbus timeout to 60 minutes

to prevent timeouts when listing tens of thousands of files.
(cherry picked from commit ec022fb86947765b18cdccaae0853bb1c163d2f5)

M  +4    -1    mtp/shared/kmtpstorageinterface.cpp

https://invent.kde.org/network/kio-extras/commit/5821c30d1f6be18e0993f03db08ec41602e5dc82
Comment 13 Harald Sitter 2023-02-24 13:42:39 UTC
Git commit ec022fb86947765b18cdccaae0853bb1c163d2f5 by Harald Sitter.
Committed on 24/02/2023 at 13:41.
Pushed by sitter into branch 'master'.

mtp: bump dbus timeout to 60 minutes

to prevent timeouts when listing tens of thousands of files.

M  +4    -1    mtp/shared/kmtpstorageinterface.cpp

https://invent.kde.org/network/kio-extras/commit/ec022fb86947765b18cdccaae0853bb1c163d2f5
Comment 14 Bug Janitor Service 2023-03-13 21:07:33 UTC
A possibly relevant merge request was started @ https://invent.kde.org/network/kio-extras/-/merge_requests/230
Comment 15 Harald Sitter 2023-03-21 15:09:29 UTC
Git commit 87aeb0d9a61cd8a7e7041dc430395ed2cbf01c66 by Harald Sitter.
Committed on 21/03/2023 at 15:03.
Pushed by sitter into branch 'master'.

mtp: use LIBMTP_Get_Children to implement async listing

LIBMTP_Get_Children returns a list of object ids within a folder, which
returns loads faster than the existing files listing API. once we have
the list of ids we can asynchronously resolve the actual file entries
for them and emit them as they appear. this allows us to enumerate
entries as they appear rather than all at once.

to facilitate this behavior a new function getFilesAndFolders2 was
introduced that returns a qdbusobjectpath. under this path a new
MTPLister object is registered that emits the listing.

M  +3    -0    CMakeLists.txt
M  +6    -0    mtp/CMakeLists.txt
M  +30   -2    mtp/kio_mtp.cpp
M  +2    -0    mtp/kiod_module/CMakeLists.txt
A  +20   -0    mtp/kiod_module/memory.h     [License: LGPL(3+eV) LGPL(v3.0) LGPL(v2.1)]
A  +110  -0    mtp/kiod_module/mtpfile.h     [License: GPL(v2.0+)]
A  +42   -0    mtp/kiod_module/mtplister.cpp     [License: LGPL(3+eV) LGPL(v3.0) LGPL(v2.1)]
A  +36   -0    mtp/kiod_module/mtplister.h     [License: LGPL(3+eV) LGPL(v3.0) LGPL(v2.1)]
M  +103  -139  mtp/kiod_module/mtpstorage.cpp
M  +17   -2    mtp/kiod_module/mtpstorage.h
M  +8    -0    mtp/shared/CMakeLists.txt
A  +4    -0    mtp/shared/config-mtp.h.cmake
M  +10   -0    mtp/shared/kmtpstorageinterface.cpp
M  +1    -0    mtp/shared/kmtpstorageinterface.h
A  +22   -0    mtp/shared/org.kde.kmtp.Lister.xml
M  +5    -0    mtp/shared/org.kde.kmtp.storage.xml

https://invent.kde.org/network/kio-extras/commit/87aeb0d9a61cd8a7e7041dc430395ed2cbf01c66