aboutsummaryrefslogtreecommitdiff
path: root/roomserver
diff options
context:
space:
mode:
authorNeil Alexander <neilalexander@users.noreply.github.com>2022-02-24 11:09:01 +0000
committerGitHub <noreply@github.com>2022-02-24 11:09:01 +0000
commit4b01f1cd122ed155ff8b05aa848f4daf2aa60c34 (patch)
tree24a061f35629bdd88c54ad16593953615e4613a3 /roomserver
parentfea8d152e7d81a9cbd387108d263950d8ec6ddc7 (diff)
State resolution v2 micro-optimisations (#2226)
* Don't populate duplicates into auth events * Only append the single event * Potentially reduce number of iterations in `isInAllAuthLists
Diffstat (limited to 'roomserver')
-rw-r--r--roomserver/state/state.go23
1 files changed, 19 insertions, 4 deletions
diff --git a/roomserver/state/state.go b/roomserver/state/state.go
index e5f69521..187b996c 100644
--- a/roomserver/state/state.go
+++ b/roomserver/state/state.go
@@ -814,6 +814,7 @@ func (v *StateResolution) resolveConflictsV2(
// events may be duplicated across these sets but that's OK.
authSets := make(map[string][]*gomatrixserverlib.Event, len(conflicted))
authEvents := make([]*gomatrixserverlib.Event, 0, estimate*3)
+ gotAuthEvents := make(map[string]struct{}, estimate*3)
authDifference := make([]*gomatrixserverlib.Event, 0, estimate)
// For each conflicted event, let's try and get the needed auth events.
@@ -850,9 +851,22 @@ func (v *StateResolution) resolveConflictsV2(
if err != nil {
return nil, err
}
- authEvents = append(authEvents, authSets[key]...)
+
+ // Only add auth events into the authEvents slice once, otherwise the
+ // check for the auth difference can become expensive and produce
+ // duplicate entries, which just waste memory and CPU time.
+ for _, event := range authSets[key] {
+ if _, ok := gotAuthEvents[event.EventID()]; !ok {
+ authEvents = append(authEvents, event)
+ gotAuthEvents[event.EventID()] = struct{}{}
+ }
+ }
}
+ // Kill the reference to this so that the GC may pick it up, since we no
+ // longer need this after this point.
+ gotAuthEvents = nil // nolint:ineffassign
+
// This function helps us to work out whether an event exists in one of the
// auth sets.
isInAuthList := func(k string, event *gomatrixserverlib.Event) bool {
@@ -866,11 +880,12 @@ func (v *StateResolution) resolveConflictsV2(
// This function works out if an event exists in all of the auth sets.
isInAllAuthLists := func(event *gomatrixserverlib.Event) bool {
- found := true
for k := range authSets {
- found = found && isInAuthList(k, event)
+ if !isInAuthList(k, event) {
+ return false
+ }
}
- return found
+ return true
}
// Look through all of the auth events that we've been given and work out if