rewrite: Multi-threaded TileRendererLayer?

148 views
Skip to first unread message

Ludwig

unread,
May 11, 2013, 3:23:37 AM5/11/13
to mapsfo...@googlegroups.com
I am looking for something new to do.

The rendering process in the TileRendererLayer just runs one thread, which obviously limits performance.

Before I start looking into this in detail, I would like to know what is thought at the moment that the problems would be running this layer with multiple threads (like eg. the DownloadLayer)?

Ludwig

Thilo Mühlberg

unread,
May 13, 2013, 2:31:23 PM5/13/13
to mapsfo...@googlegroups.com
Hi Ludwig,

the actual map rendering has not been changed in the rewrite branch
(besides a very few small adjustments) so the drawn map tiles should
look more-or-less identical compared to the 0.3.0 version.

Reimplementing this whole package is also on my to-do list, allowing for
multi-threaded rendering would be one of the major benefits. But I think
that now is not the right moment to start this as it will detract our
energy from getting the 0.4.0 release out. Therefore we should first fix
the remaining issues with the rewrite branch (e.g View vs ViewGroup,
zoom buttons and map scale bar), write some new wiki articles for the
new API and make our Jenkins build green again.

If you have time you can also add a simple file chooser dialog to the
AWT/Swing based MapViewer. Currently the map file path is hard-coded
which means it provides very little benefit for non-developers. Having a
menu to pick a map file from the file system is trivial but an important
first step into the right direction.

Greetings,
Thilo
> --
> You received this message because you are subscribed to the Google
> Groups "mapsforge-dev" group.
> To unsubscribe from this group and stop receiving emails from it, send
> an email to mapsforge-de...@googlegroups.com.
> For more options, visit https://groups.google.com/groups/opt_out.
>
>


signature.asc

emux

unread,
May 14, 2013, 1:56:36 AM5/14/13
to mapsfo...@googlegroups.com
Hi Thilo, Ludwig

Among the issues that are to be fixed with the rewrite branch before its release, is the out of memory errors?
I'm referring to the changes at Ludwig's clone. Are they going to be at rewrite branch in the future?

Regards.

Ludwig

unread,
May 14, 2013, 6:54:43 AM5/14/13
to mapsfo...@googlegroups.com
Just a quick result from playing around with a multithreaded renderer.

The minimal changes to make it work are simply to give each mapworker their own MapDatabase and DatabaseRenderer (in TileRendererLayer). That of course means a pretty significant overhead as each worker has now their own RenderTheme and map file, but my initial goal was just to see what would need to change.

I then set the number of threads to the number of processors with Runtime.getRuntime().availableProcessors();  (There seems to be some discussion if this actually works, but on the physical devices I have the returned value was correct, but this is all Android 4.1+) and created as many mapworker threads as processors. The idea was that multiple mapworkers should be render the same amount of tiles faster than just one thread.

The first visual impression was that it was not really any faster than just running with one MapWorker thread.

To verify I added some time code that measured how long rendering a single tile took. It turned out that with a single MapWorker rendering a single tile took on average 75 milliseconds (just the rendering, not putting into cache or displaying), but with two threads it took on average 150 milliseconds, cancelling out any gain from having two threads working at once (this was measured on a Nexus 10).

So, it looks like simply putting the exisiting code on different threads will not improve the app speed as either the second processor is never used or, if it is used, there is some synchronization going on, maybe when opening the same file multiple times.

Ludwig





hannes....@googlemail.com

unread,
May 14, 2013, 6:12:36 PM5/14/13
to mapsfo...@googlegroups.com
On Tue, May 14, 2013 at 12:54 PM, Ludwig <ludwigbr...@gmail.com> wrote:
Just a quick result from playing around with a multithreaded renderer.

The minimal changes to make it work are simply to give each mapworker their own MapDatabase and DatabaseRenderer (in TileRendererLayer). That of course means a pretty significant overhead as each worker has now their own RenderTheme and map file, but my initial goal was just to see what would need to change.

I then set the number of threads to the number of processors with Runtime.getRuntime().availableProcessors();  (There seems to be some discussion if this actually works, but on the physical devices I have the returned value was correct, but this is all Android 4.1+) and created as many mapworker threads as processors. The idea was that multiple mapworkers should be render the same amount of tiles faster than just one thread.

The first visual impression was that it was not really any faster than just running with one MapWorker thread.

To verify I added some time code that measured how long rendering a single tile took. It turned out that with a single MapWorker rendering a single tile took on average 75 milliseconds (just the rendering, not putting into cache or displaying), but with two threads it took on average 150 milliseconds, cancelling out any gain from having two threads working at once (this was measured on a Nexus 10).

So, it looks like simply putting the exisiting code on different threads will not improve the app speed as either the second processor is never used or, if it is used, there is some synchronization going on, maybe when opening the same file multiple times.


Have you actually tried DDMS method profiling tool for android? It shows nicely which threads are running concurrently in a timeline, besides being useful for general profiling. In logcats log I see lots of garbage collection work. This could easily lead to blocking threads (i.e. WAIT_FOR_CONCURRENT_GC in logs).

Regards,
Hannes

Thilo Mühlberg

unread,
May 15, 2013, 1:43:48 AM5/15/13
to mapsfo...@googlegroups.com

That result does not surprise me. The whole tile renderer code is old, untested and not at all designed for multi-threading. Therefore I plan to rewrite it from scratch after the 0.4.0 release.

You also have to keep in mind that at least the labeling needs to be shared across all tile renderer threads safely. If you just start several threads, each will use its own labeling and thus names and icons will be cut off at tile borders very often.

Greetings,
Thilo

robvr

unread,
Jan 25, 2014, 10:31:42 PM1/25/14
to mapsfo...@googlegroups.com
Hi ludwig

Somehow 'write your own navigationsystem from scratch' got on my Bucketlist.
I started with mapsforge as à tileprovider to get me started, and now am implementing my own tilefactory.
I have a multithreaded renderer and it does speed things up.
It is à multi producer, one consumer model, implemented with queues.
Disadvantage is THE app is marked as a battery intensive app by android, so it Will scare of users.
Advantage of queues is That you can manipulate THE inputqueue, eg delete render requests when scrolling very fast.
Code is prototype but i Will send it to you if you want

Rob

Ludwig

unread,
Jan 25, 2014, 10:44:42 PM1/25/14
to mapsfo...@googlegroups.com
Hi there, 

multi-threading the renderer is on my list for 0.5, so input is welcome. 

You do not say on which code-base you implemented your changes, but if you have a patch based on the current rescue or rescue-exp that would be the easiest to start a discussion. 

Ludwig


--
You received this message because you are subscribed to the Google Groups "mapsforge-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mapsforge-de...@googlegroups.com.

robvr

unread,
Jan 26, 2014, 4:39:02 AM1/26/14
to mapsfo...@googlegroups.com
Hi Ludwig

You do not sleep much too I see :)
It is not based on mapsforge at all, so i can't make à patch off it.
It is à OpenGL ES based app, closed source for now, as it is à prototype and not as clean coded as
Mapsforge. I am impressed by the high quality of your code, but i want to make my own.
Allthough i did borrow your vbeint i must confess.
I Will clean up à little and try to send you THE relvevant sources.

Grts
Rob

Ludwig

unread,
Jan 28, 2014, 10:57:22 PM1/28/14
to mapsfo...@googlegroups.com
Thanks,

I had put only a bit of effort in once to see how much work it would overall be to make the renderer multi-thread safe. The problem I encountered was that I somehow could not get a real device to actually run the code on different cores at the same time, despite technically multi-threaded, I could see that everything was just time-sharing the same core, resulting in not much improvement. I did not investigate this enough to find if there is a secret to make a device activate on more than one core.

Lots of mapsforge based apps are classed as battery-intensive, one of problems is the use of location polling. 

Ludwig




Rob

--
You received this message because you are subscribed to the Google Groups "mapsforge-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mapsforge-de...@googlegroups.com.

hannes....@googlemail.com

unread,
Jan 29, 2014, 12:02:43 AM1/29/14
to mapsfo...@googlegroups.com
On Wed, Jan 29, 2014 at 4:57 AM, Ludwig <ludwigbr...@gmail.com> wrote:
Thanks,

I had put only a bit of effort in once to see how much work it would overall be to make the renderer multi-thread safe. The problem I encountered was that I somehow could not get a real device to actually run the code on different cores at the same time, despite technically multi-threaded, I could see that everything was just time-sharing the same core, resulting in not much improvement. I did not investigate this enough to find if there is a secret to make a device activate on more than one core.


I did look into the ddms trace for Locus as I've heard that their mapsforge rendering is faster than that of competing products. It turns out they already split up the tile creation into two threads. One that reads the data and does theme matching and another one that does draw the bitmap tile. Unfortunately they scrambled methods names in their compiled packages. Maybe you could ask them to provide their modifications :)

On the second row is the reader+theme, 5.,8. do draw the tile

With the current architecture it should be not too difficult to split tile creation into three threads without synchronization on shared resources as all data in these steps is pretty much self-contained:
1. MapDatabase(read tile data) > queue >
2. DatabaseRenderer(Rendertheme matching + coordinate transformation) > queue >
3. DatabaseRenderer(drawing layers to Bitmap)


Regards,
Hannes

 
Lots of mapsforge based apps are classed as battery-intensive, one of problems is the use of location polling. 

Ludwig




On 26 January 2014 17:39, robvr <r.van...@gmail.com> wrote:
Hi Ludwig

You do not sleep much too I see :)
It is not based on mapsforge at all, so i can't make à patch off it.
It is à OpenGL ES based app, closed source for now, as it is à prototype and not as clean coded as
Mapsforge. I am impressed by the high quality of your code, but i want to make my own.
Allthough i did borrow your vbeint i must confess.
I Will clean up à little and try to send you THE relvevant sources.

Grts
Rob

--
You received this message because you are subscribed to the Google Groups "mapsforge-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mapsforge-de...@googlegroups.com.
To view this discussion on the web visit https://groups.google.com/d/msgid/mapsforge-dev/c9b2534d-2d3d-4b4c-83e7-14a25a0a12b9%40googlegroups.com.

--
You received this message because you are subscribed to the Google Groups "mapsforge-dev" group.
To unsubscribe from this group and stop receiving emails from it, send an email to mapsforge-de...@googlegroups.com.

Ludwig

unread,
Jan 29, 2014, 12:56:07 AM1/29/14
to mapsfo...@googlegroups.com
Hi Hannes, 

thanks for the hints. When I was trying it, I was splitting the whole process into multiple threads, each doing a read on the map file, matching and drawing (it seemed the easiest way to do it). Maybe that was the wrong approach as it is probably inefficient in the disk read operations. I will think this through a bit more.

Ludwig


fzk

unread,
Jan 29, 2014, 2:48:32 AM1/29/14
to mapsfo...@googlegroups.com
Yes that's true, the app "Locus Map" (with a performance optimized library) is significant faster than any other app using the standard mapsforge library. You can see and feel this especially with the Freizeitkarte maps, where a lot of data modifications were applied in order to reduce the number of objects to draw with in a zoom level. My recommendation: Ask the main developer of "Locus Map" (menion) for the sources. His approach is working for a long time on a wide range of devices and brings a significant performance boost ... maybe a good start (but probably not the "end of the flag pole").

Klaus
Reply all
Reply to author
Forward
0 new messages