In my iOS app, I am using a serial DispatchQueue and create a background task to do some work. If this process is initiated while the app is in the foreground, it is very fast and efficient. Depending on the age of the device, the job takes from 4.5 - 12.2 seconds.
The app also utilizes backgroundFetch and content-available silent pushes to do this work in the background so that the user stays updated. The thing I'm struggling with is that iOS seems to be severely throttling the performance of the work being done, and it's worse on newer iPhone models -- it's up to 9X slower. In the background initiated case, the OS limits the time you have to complete this work (~30 seconds), which makes it impossible to complete in a single pass.
Unfortunately, the work involves some failry intensive I/O (either reading from a DB or file, both take about the same amount of time), and it doesn't lend itself to easily splitting the work into multiple passes.
Here are some examples of processing times:
iPhone SE
12.2 sec FG -> 23.3 sec BG (1.9X slower)
iPhone 7
9.0 sec FG -> 21.2 sec BG (2.3X slower)
iPhone 8
7.3 sec FG -> 61.2 sec BG (8.3X slower)
iPhone XS
4.5 sec FG -> 40.5 sec BG (9.0X slower)
I understand why the process might be slightly slower in the background, but does anyone know why is it so extreme on newer devices?
I've tried everything I can think of to increase the speed (including setting a higher priority on the DispatchQueue) to no avail. Is there a way to avoid the throttling? If not is there a reliable way to extend the process time in order to finish the processing?
Any other suggestions would be welcome.