Lorawan-stack: Optimize device matching

Created on 5 Jun 2020  ·  5Comments  ·  Source: TheThingsNetwork/lorawan-stack

Summary

Optimize device matching in Network Server

Why do we need this?

For Redis I/O, memory usage and overall compute performance when we increasing DevAddr reuse and increasing DevAddr size.

What is already there? What do you see now?

Currently, NS ranges over devices by DevAddr, and decodes the proto. The protos are big, containing the mac state and recent uplink and downlink messages, plus there can be many protos (hundreds) of duplicate DevAddr.

What is missing? What do you want to see?

We need a materialized view in Redis for matching uplinks to devices by UID, before loading the matched device.

How do you propose to implement this?

Store relevant information for matching in dedicated keys, so basically DevAddr, FCnt, NwkSIntKeys and UID.

A sorted set and/or hash map would be useful as this enables Redis sorting and from-querying by FCnt, getting the integrity keys and UID.

Update this materialized view on each uplink and join-accept.

We can have a rolling migration with fallback to the existing matching scheme.

How do you propose to test this?

Unit tests, potentially with asserting the Redis keys and their values in the test.

Can you do this yourself and submit a Pull Request?

Can review

network server performance in progress scalability

All 5 comments

I think a better approach would be to tackle this in another way, which also increases performance in general case - split out the space-consuming data out of the protos and store those separately - i.e. recent_uplinks, recent_downlinks etc., it also makes way more sense to store these in lists instead of marshaled protos - that means we wouldn't actually need to query the existing messages, but would just append a new one, which is way more efficient, but let's start with just the proto and go from there.
Given that we have fieldmasks, splitting the proto would be quite straightforward and completely handled by Redis registry implementations.

So the suggestion is to have:

  • ns:devices:uid:foo:bar:recent_uplinks
  • ns:devices:uid:foo:bar:recent_downlinks
  • ns:devices:uid:foo:bar:mac_state:recent_uplinks
  • ns:devices:uid:foo:bar:mac_state:recent_downlinks
  • ns:devices:uid:foo:bar:pending_mac_state:recent_uplinks
  • ns:devices:uid:foo:bar:pending_mac_state:recent_downlinks
    ...
  • ns:devices:uid:foo:bar - rest of the proto

Migration would happen automatically, similarly how deprecated fields are handled in registries already.

What is the status here?

I expect this to be ready for merge by the end of next week.
The implementation is done for weeks, working on refactoring and then adapting tests ever since

Please consider making the returned error more clear if the device can't be matched. See for example https://github.com/TheThingsNetwork/lorawan-stack/issues/2394.

We can't provide a whole lot of information, but device_not_found implies that the device can't be found, while it could be that the DevAddr is not found at all, that the MIC mismatches with found entries and/or that the FCnt reset while that is not allowed with found entries.

Good suggestion, but I think it's best to do it as a next step, because it will be a huge PR to review with a lot of relatively complex functionality

Was this page helpful?
0 / 5 - 0 ratings