Skip to content

Commit

Permalink
Deduplicate orderer server TLS root CAs (#2030)
Browse files Browse the repository at this point in the history
When the orderer TLS root CAs are updated, an aggregation of all root TLS CA certificates over all channels is injected into the PredicateDialer.
Then, upon client TLS handshake, a fresh TLS config object is built (for orthogonal purposes), however the operation entails parsing of all
root CAs all over again.

In case the orderer is part of too many channels, this induces a high and unnecessary processing overhead.

This commit simply performs a deduplication of the bespoken TLS root CA certificates prior to updating the root CAs.

Change-Id: I21b2ed483afc9595c2ccd7fbe9ec0cf475cc5f62
Signed-off-by: yacovm <[email protected]>
  • Loading branch information
yacovm authored Oct 20, 2020
1 parent cf344b5 commit 56d7b84
Show file tree
Hide file tree
Showing 2 changed files with 47 additions and 4 deletions.
20 changes: 16 additions & 4 deletions orderer/common/server/main.go
Original file line number Diff line number Diff line change
Expand Up @@ -877,16 +877,28 @@ func updateClusterDialer(rootCASupport *comm.CredentialSupport, clusterDialer *c

// Iterate over all orderer root CAs for all chains and add them
// to the root CAs
var clusterRootCAs [][]byte
clusterRootCAs := make(cluster.StringSet)
for _, orgRootCAs := range rootCASupport.OrdererRootCAsByChainAndOrg {
for _, roots := range orgRootCAs {
clusterRootCAs = append(clusterRootCAs, roots...)
for _, root := range roots {
clusterRootCAs[string(root)] = struct{}{}
}
}
}

// Add the local root CAs too
clusterRootCAs = append(clusterRootCAs, localClusterRootCAs...)
for _, localRoot := range localClusterRootCAs {
clusterRootCAs[string(localRoot)] = struct{}{}
}

var clusterRootCAsBytes [][]byte
// Convert the StringSet back to a byte slice
for root := range clusterRootCAs {
clusterRootCAsBytes = append(clusterRootCAsBytes, []byte(root))
}

// Update the cluster config with the new root CAs
clusterDialer.UpdateRootCAs(clusterRootCAs)
clusterDialer.UpdateRootCAs(clusterRootCAsBytes)
}

func prettyPrintStruct(i interface{}) {
Expand Down
31 changes: 31 additions & 0 deletions orderer/common/server/main_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -472,6 +472,37 @@ func TestUpdateTrustedRoots(t *testing.T) {
grpcServer.Listener().Close()
}

func TestRootServerCertAggregation(t *testing.T) {
credSupport := &comm.CredentialSupport{
OrdererRootCAsByChainAndOrg: make(comm.OrgRootCAs),
}

predDialer := &cluster.PredicateDialer{
ClientConfig: comm.ClientConfig{
SecOpts: &comm.SecureOptions{},
},
}

ca1, err := tlsgen.NewCA()
require.NoError(t, err)

ca2, err := tlsgen.NewCA()
require.NoError(t, err)

credSupport.OrdererRootCAsByChainAndOrg["foo"] = map[string]comm.CertificateBundle{
"Org1": [][]byte{ca1.CertBytes()},
}
credSupport.OrdererRootCAsByChainAndOrg["bar"] = map[string]comm.CertificateBundle{
"Org1": [][]byte{ca1.CertBytes()},
}

updateClusterDialer(credSupport, predDialer, [][]byte{ca2.CertBytes(), ca2.CertBytes(), ca2.CertBytes()})

require.Len(t, predDialer.ClientConfig.SecOpts.ServerRootCAs, 2)
require.Contains(t, predDialer.ClientConfig.SecOpts.ServerRootCAs, ca1.CertBytes())
require.Contains(t, predDialer.ClientConfig.SecOpts.ServerRootCAs, ca2.CertBytes())
}

func TestConfigureClusterListener(t *testing.T) {
logEntries := make(chan string, 100)

Expand Down

0 comments on commit 56d7b84

Please sign in to comment.