Skip to content

Commit 30cbdb4

Browse files
committed
Make sure slices are sorted
1 parent 7a74c73 commit 30cbdb4

File tree

2 files changed

+108
-76
lines changed

2 files changed

+108
-76
lines changed

fclient/crosssigning.go

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ package fclient
1717
import (
1818
"bytes"
1919
"encoding/json"
20+
"slices"
2021

2122
"github.com/matrix-org/gomatrixserverlib"
2223
"github.com/matrix-org/gomatrixserverlib/spec"
@@ -57,6 +58,14 @@ func (s *CrossSigningKey) Equal(other *CrossSigningKey) bool {
5758
if len(s.Usage) != len(other.Usage) {
5859
return false
5960
}
61+
62+
// Make sure the slices are sorted before we compare them.
63+
if !slices.IsSorted(s.Usage) {
64+
slices.Sort(s.Usage)
65+
}
66+
if !slices.IsSorted(other.Usage) {
67+
slices.Sort(other.Usage)
68+
}
6069
for i := range s.Usage {
6170
if s.Usage[i] != other.Usage[i] {
6271
return false

fclient/crosssigning_test.go

Lines changed: 99 additions & 76 deletions
Original file line numberDiff line numberDiff line change
@@ -7,85 +7,97 @@ import (
77
"github.com/matrix-org/gomatrixserverlib/spec"
88
)
99

10-
func TestCrossSigningKeyEqual(t *testing.T) {
11-
tests := []struct {
12-
name string
13-
s *CrossSigningKey
14-
other *CrossSigningKey
15-
expect bool
16-
}{
17-
{
18-
name: "NilReceiver_ReturnsFalse",
19-
s: nil,
20-
other: &CrossSigningKey{},
21-
expect: false,
22-
},
23-
{
24-
name: "NilOther_ReturnsFalse",
25-
s: &CrossSigningKey{},
26-
other: nil,
27-
expect: false,
28-
},
29-
{
30-
name: "DifferentUserID_ReturnsFalse",
31-
s: &CrossSigningKey{UserID: "user1"},
32-
other: &CrossSigningKey{UserID: "user2"},
33-
expect: false,
34-
},
35-
{
36-
name: "DifferentUsageLength_ReturnsFalse",
37-
s: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster}},
38-
other: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster, CrossSigningKeyPurposeSelfSigning}},
39-
expect: false,
40-
},
41-
{
42-
name: "DifferentUsageValues_ReturnsFalse",
43-
s: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster}},
44-
other: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeSelfSigning}},
45-
expect: false,
46-
},
47-
{
48-
name: "DifferentKeysLength_ReturnsFalse",
49-
s: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}}},
50-
other: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}, "key2": {}}},
51-
expect: false,
52-
},
53-
{
54-
name: "DifferentKeysValues_ReturnsFalse",
55-
s: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}}},
56-
other: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {1}}},
57-
expect: false,
58-
},
59-
{
60-
name: "DifferentSignaturesLength_ReturnsFalse",
61-
s: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}}},
62-
other: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}, "sig2": {"key2": {}}}},
63-
expect: false,
64-
},
65-
{
66-
name: "DifferentSignaturesValues_ReturnsFalse",
67-
s: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}}},
68-
other: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {1}}}},
69-
expect: false,
10+
var tests = []struct {
11+
name string
12+
s *CrossSigningKey
13+
other *CrossSigningKey
14+
expect bool
15+
}{
16+
{
17+
name: "NilReceiver_ReturnsFalse",
18+
s: nil,
19+
other: &CrossSigningKey{},
20+
expect: false,
21+
},
22+
{
23+
name: "NilOther_ReturnsFalse",
24+
s: &CrossSigningKey{},
25+
other: nil,
26+
expect: false,
27+
},
28+
{
29+
name: "DifferentUserID_ReturnsFalse",
30+
s: &CrossSigningKey{UserID: "user1"},
31+
other: &CrossSigningKey{UserID: "user2"},
32+
expect: false,
33+
},
34+
{
35+
name: "DifferentUsageLength_ReturnsFalse",
36+
s: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster}},
37+
other: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster, CrossSigningKeyPurposeSelfSigning}},
38+
expect: false,
39+
},
40+
{
41+
name: "UnsortedUsages_ReturnsTrue",
42+
s: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeSelfSigning, CrossSigningKeyPurposeMaster}},
43+
other: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster, CrossSigningKeyPurposeSelfSigning}},
44+
expect: true,
45+
},
46+
{
47+
name: "UnsortedUsages_ReturnsTrue",
48+
s: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeSelfSigning, CrossSigningKeyPurposeMaster}},
49+
other: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeSelfSigning, CrossSigningKeyPurposeMaster}},
50+
expect: true,
51+
},
52+
{
53+
name: "DifferentUsageValues_ReturnsFalse",
54+
s: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster}},
55+
other: &CrossSigningKey{Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeSelfSigning}},
56+
expect: false,
57+
},
58+
{
59+
name: "DifferentKeysLength_ReturnsFalse",
60+
s: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}}},
61+
other: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}, "key2": {}}},
62+
expect: false,
63+
},
64+
{
65+
name: "DifferentKeysValues_ReturnsFalse",
66+
s: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}}},
67+
other: &CrossSigningKey{Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {1}}},
68+
expect: false,
69+
},
70+
{
71+
name: "DifferentSignaturesLength_ReturnsFalse",
72+
s: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}}},
73+
other: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}, "sig2": {"key2": {}}}},
74+
expect: false,
75+
},
76+
{
77+
name: "DifferentSignaturesValues_ReturnsFalse",
78+
s: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}}},
79+
other: &CrossSigningKey{Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {1}}}},
80+
expect: false,
81+
},
82+
{
83+
name: "IdenticalKeys_ReturnsTrue",
84+
s: &CrossSigningKey{
85+
UserID: "user1",
86+
Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster},
87+
Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}},
88+
Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}},
7089
},
71-
{
72-
name: "IdenticalKeys_ReturnsTrue",
73-
s: &CrossSigningKey{
74-
UserID: "user1",
75-
Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster},
76-
Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}},
77-
Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}},
78-
},
79-
other: &CrossSigningKey{
80-
UserID: "user1",
81-
Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster},
82-
Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}},
83-
Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}},
84-
},
85-
expect: true,
90+
other: &CrossSigningKey{
91+
UserID: "user1",
92+
Usage: []CrossSigningKeyPurpose{CrossSigningKeyPurposeMaster},
93+
Keys: map[gomatrixserverlib.KeyID]spec.Base64Bytes{"key1": {}},
94+
Signatures: map[string]map[gomatrixserverlib.KeyID]spec.Base64Bytes{"sig1": {"key1": {}}},
8695
},
87-
}
96+
expect: true,
97+
},
98+
}
8899

100+
func TestCrossSigningKeyEqual(t *testing.T) {
89101
for _, tt := range tests {
90102
t.Run(tt.name, func(t *testing.T) {
91103
if got := tt.s.Equal(tt.other); got != tt.expect {
@@ -94,3 +106,14 @@ func TestCrossSigningKeyEqual(t *testing.T) {
94106
})
95107
}
96108
}
109+
110+
func BenchmarkEqual(b *testing.B) {
111+
112+
for i := 0; i < b.N; i++ {
113+
for _, tt := range tests {
114+
if !tt.s.Equal(tt.other) && tt.expect {
115+
b.Fatal(tt.name, tt.s)
116+
}
117+
}
118+
}
119+
}

0 commit comments

Comments
 (0)