Skip to content

Commit 676bf94

Browse files
author
Jason Yellick
committed
[FAB-1778] Add chain config to configtx.Manager
https://jira.hyperledger.org/browse/FAB-1778 This changeset finally adds the chainconfig.Descriptor to the common configtx.Manager path and utilizes the Hashing algorithm specified for chain creation. Change-Id: I184d6dc150544712ea87c283ad136079818ff820 Signed-off-by: Jason Yellick <[email protected]>
1 parent 2cdafd0 commit 676bf94

File tree

10 files changed

+74
-19
lines changed

10 files changed

+74
-19
lines changed

common/configtx/resources.go

+14
Original file line numberDiff line numberDiff line change
@@ -18,6 +18,7 @@ package configtx
1818

1919
import (
2020
"github.com/hyperledger/fabric/common/cauthdsl"
21+
"github.com/hyperledger/fabric/common/chainconfig"
2122
"github.com/hyperledger/fabric/common/policies"
2223
cb "github.com/hyperledger/fabric/protos/common"
2324
)
@@ -28,6 +29,9 @@ import (
2829
type Resources interface {
2930
// PolicyManager returns the policies.Manager for the chain
3031
PolicyManager() policies.Manager
32+
33+
// ChainConfig returns the chainconfig.Descriptor for the chain
34+
ChainConfig() chainconfig.Descriptor
3135
}
3236

3337
// Initializer is a structure which is only useful before a configtx.Manager
@@ -42,13 +46,19 @@ type Initializer interface {
4246
type resources struct {
4347
handlers map[cb.ConfigurationItem_ConfigurationType]Handler
4448
policyManager policies.Manager
49+
chainConfig chainconfig.Descriptor
4550
}
4651

4752
// PolicyManager returns the policies.Manager for the chain
4853
func (r *resources) PolicyManager() policies.Manager {
4954
return r.policyManager
5055
}
5156

57+
// ChainConfig returns the chainconfig.Descriptor for the chain
58+
func (r *resources) ChainConfig() chainconfig.Descriptor {
59+
return r.chainConfig
60+
}
61+
5262
// Handlers returns the handlers to be used when initializing the configtx.Manager
5363
func (r *resources) Handlers() map[cb.ConfigurationItem_ConfigurationType]Handler {
5464
return r.handlers
@@ -71,11 +81,14 @@ func NewInitializer() Initializer {
7181
}
7282

7383
policyManager := policies.NewManagerImpl(policyProviderMap)
84+
chainConfig := chainconfig.NewDescriptorImpl()
7485
handlers := make(map[cb.ConfigurationItem_ConfigurationType]Handler)
7586

7687
for ctype := range cb.ConfigurationItem_ConfigurationType_name {
7788
rtype := cb.ConfigurationItem_ConfigurationType(ctype)
7889
switch rtype {
90+
case cb.ConfigurationItem_Chain:
91+
handlers[rtype] = chainConfig
7992
case cb.ConfigurationItem_Policy:
8093
handlers[rtype] = policyManager
8194
default:
@@ -86,5 +99,6 @@ func NewInitializer() Initializer {
8699
return &resources{
87100
handlers: handlers,
88101
policyManager: policyManager,
102+
chainConfig: chainConfig,
89103
}
90104
}

common/configtx/template.go

+15-5
Original file line numberDiff line numberDiff line change
@@ -89,15 +89,17 @@ func (ct *compositeTemplate) Items(chainID string) ([]*cb.SignedConfigurationIte
8989

9090
type newChainTemplate struct {
9191
creationPolicy string
92+
hash func([]byte) []byte
9293
template Template
9394
}
9495

9596
// NewChainCreationTemplate takes a CreationPolicy and a Template to produce a Template which outputs an appropriately
9697
// constructed list of SignedConfigurationItem including an appropriate digest. Note, using this Template in
9798
// a CompositeTemplate will invalidate the CreationPolicy
98-
func NewChainCreationTemplate(creationPolicy string, template Template) Template {
99+
func NewChainCreationTemplate(creationPolicy string, hash func([]byte) []byte, template Template) Template {
99100
return &newChainTemplate{
100101
creationPolicy: creationPolicy,
102+
hash: hash,
101103
template: template,
102104
}
103105
}
@@ -116,7 +118,7 @@ func (nct *newChainTemplate) Items(chainID string) ([]*cb.SignedConfigurationIte
116118
Key: CreationPolicyKey,
117119
Value: utils.MarshalOrPanic(&ab.CreationPolicy{
118120
Policy: nct.creationPolicy,
119-
Digest: HashItems(items),
121+
Digest: HashItems(items, nct.hash),
120122
}),
121123
}),
122124
}
@@ -126,12 +128,12 @@ func (nct *newChainTemplate) Items(chainID string) ([]*cb.SignedConfigurationIte
126128

127129
// HashItems is a utility method for computing the hash of the concatenation of the marshaled ConfigurationItems
128130
// in a []*cb.SignedConfigurationItem
129-
func HashItems(items []*cb.SignedConfigurationItem) []byte {
131+
func HashItems(items []*cb.SignedConfigurationItem, hash func([]byte) []byte) []byte {
130132
sourceBytes := make([][]byte, len(items))
131133
for i := range items {
132134
sourceBytes[i] = items[i].ConfigurationItem
133135
}
134-
return util.ComputeCryptoHash(util.ConcatenateBytes(sourceBytes...))
136+
return hash(util.ConcatenateBytes(sourceBytes...))
135137
}
136138

137139
// join takes a number of SignedConfigurationItem slices and produces a single item
@@ -154,7 +156,15 @@ func join(sets ...[]*cb.SignedConfigurationItem) []*cb.SignedConfigurationItem {
154156

155157
// MakeChainCreationTransaction is a handy utility function for creating new chain transactions using the underlying Template framework
156158
func MakeChainCreationTransaction(creationPolicy string, chainID string, signer msp.SigningIdentity, templates ...Template) (*cb.Envelope, error) {
157-
newChainTemplate := NewChainCreationTemplate(creationPolicy, NewCompositeTemplate(templates...))
159+
composite := NewCompositeTemplate(templates...)
160+
items, err := composite.Items(chainID)
161+
if err != nil {
162+
return nil, err
163+
}
164+
165+
manager, err := NewManagerImpl(&cb.ConfigurationEnvelope{Items: items}, NewInitializer())
166+
167+
newChainTemplate := NewChainCreationTemplate(creationPolicy, manager.ChainConfig().HashingAlgorithm(), composite)
158168
signedConfigItems, err := newChainTemplate.Items(chainID)
159169
if err != nil {
160170
return nil, err

common/configtx/template_test.go

+2-1
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import (
2020
"fmt"
2121
"testing"
2222

23+
"github.com/hyperledger/fabric/common/util"
2324
cb "github.com/hyperledger/fabric/protos/common"
2425
"github.com/hyperledger/fabric/protos/utils"
2526
"github.com/stretchr/testify/assert"
@@ -79,7 +80,7 @@ func TestNewChainTemplate(t *testing.T) {
7980
)
8081

8182
creationPolicy := "Test"
82-
nct := NewChainCreationTemplate(creationPolicy, simple)
83+
nct := NewChainCreationTemplate(creationPolicy, util.ComputeCryptoHash, simple)
8384

8485
newChainID := "foo"
8586
items, err := nct.Items(newChainID)

common/configtx/test/orderer.template

-307 Bytes
Binary file not shown.

common/mocks/chainconfig/chainconfig.go

+6-3
Original file line numberDiff line numberDiff line change
@@ -19,21 +19,24 @@ package chainconfig
1919
import "github.com/hyperledger/fabric/common/util"
2020

2121
func nearIdentityHash(input []byte) []byte {
22-
return util.ConcatenateBytes([]byte("Hash("), input, []byte(""))
22+
return util.ConcatenateBytes([]byte("FakeHash("), input, []byte(""))
2323
}
2424

2525
// Descriptor is a mock implementation of sharedconfig.Descriptor
2626
type Descriptor struct {
27-
// HashingAlgorithmVal is returned as the result of HashingAlgorithm()
27+
// HashingAlgorithmVal is returned as the result of HashingAlgorithm() if set
2828
HashingAlgorithmVal func([]byte) []byte
2929
// BlockDataHashingStructureWidthVal is returned as the result of BlockDataHashingStructureWidth()
3030
BlockDataHashingStructureWidthVal uint32
3131
// OrdererAddressesVal is returned as the result of OrdererAddresses()
3232
OrdererAddressesVal []string
3333
}
3434

35-
// HashingAlgorithm returns the HashingAlgorithmVal
35+
// HashingAlgorithm returns the HashingAlgorithmVal if set, otherwise a fake simple hash function
3636
func (scm *Descriptor) HashingAlgorithm() func([]byte) []byte {
37+
if scm.HashingAlgorithmVal == nil {
38+
return nearIdentityHash
39+
}
3740
return scm.HashingAlgorithmVal
3841
}
3942

core/common/validation/config_test.go

+3-1
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ package validation
1919
import (
2020
"testing"
2121

22+
"github.com/hyperledger/fabric/common/chainconfig"
2223
"github.com/hyperledger/fabric/common/configtx"
2324
"github.com/hyperledger/fabric/common/configtx/test"
2425
"github.com/hyperledger/fabric/common/util"
@@ -29,7 +30,8 @@ func TestValidateConfigTx(t *testing.T) {
2930
chainID := util.GetTestChainID()
3031
oTemplate := test.GetOrdererTemplate()
3132
mspcfg := configtx.NewSimpleTemplate(utils.EncodeMSPUnsigned(chainID))
32-
chCrtTemp := configtx.NewCompositeTemplate(oTemplate, mspcfg)
33+
chainCfg := configtx.NewSimpleTemplate(chainconfig.DefaultHashingAlgorithm())
34+
chCrtTemp := configtx.NewCompositeTemplate(oTemplate, mspcfg, chainCfg)
3335
chCrtEnv, err := configtx.MakeChainCreationTransaction(test.AcceptAllPolicyKey, chainID, signer, chCrtTemp)
3436
if err != nil {
3537
t.Fatalf("MakeChainCreationTransaction failed, err %s", err)

orderer/common/bootstrap/provisional/provisional.go

+6
Original file line numberDiff line numberDiff line change
@@ -20,6 +20,7 @@ import (
2020
"fmt"
2121

2222
"github.com/hyperledger/fabric/common/cauthdsl"
23+
"github.com/hyperledger/fabric/common/chainconfig"
2324
"github.com/hyperledger/fabric/common/configtx"
2425
"github.com/hyperledger/fabric/common/genesis"
2526
"github.com/hyperledger/fabric/orderer/common/bootstrap"
@@ -67,6 +68,11 @@ type bootstrapper struct {
6768
func New(conf *config.TopLevel) Generator {
6869
bs := &bootstrapper{
6970
minimalItems: []*cb.ConfigurationItem{
71+
// Chain Config Types
72+
chainconfig.DefaultHashingAlgorithm(),
73+
chainconfig.DefaultBlockDataHashingStructure(),
74+
chainconfig.TemplateOrdererAddresses([]string{fmt.Sprintf("%s:%d", conf.General.ListenAddress, conf.General.ListenPort)}),
75+
7076
// Orderer Config Types
7177
sharedconfig.TemplateConsensusType(conf.Genesis.OrdererType),
7278
sharedconfig.TemplateBatchSize(&ab.BatchSize{

orderer/mocks/configtx/configtx.go

+9
Original file line numberDiff line numberDiff line change
@@ -17,6 +17,7 @@ limitations under the License.
1717
package configtx
1818

1919
import (
20+
"github.com/hyperledger/fabric/common/chainconfig"
2021
"github.com/hyperledger/fabric/common/configtx"
2122
"github.com/hyperledger/fabric/common/policies"
2223
cb "github.com/hyperledger/fabric/protos/common"
@@ -28,6 +29,9 @@ type Initializer struct {
2829

2930
// PolicyManagerVal is returned as the result of PolicyManager()
3031
PolicyManagerVal policies.Manager
32+
33+
// ChainConfigVal is returned as the result of ChainConfig()
34+
ChainConfigVal chainconfig.Descriptor
3135
}
3236

3337
// Returns the HandlersVal
@@ -40,6 +44,11 @@ func (i *Initializer) PolicyManager() policies.Manager {
4044
return i.PolicyManagerVal
4145
}
4246

47+
// Returns the ChainConfigVal
48+
func (i *Initializer) ChainConfig() chainconfig.Descriptor {
49+
return i.ChainConfigVal
50+
}
51+
4352
// Manager is a mock implementation of configtx.Manager
4453
type Manager struct {
4554
Initializer

orderer/multichain/systemchain.go

+3-1
Original file line numberDiff line numberDiff line change
@@ -19,6 +19,7 @@ package multichain
1919
import (
2020
"bytes"
2121

22+
"github.com/hyperledger/fabric/common/chainconfig"
2223
"github.com/hyperledger/fabric/common/configtx"
2324
"github.com/hyperledger/fabric/common/policies"
2425
"github.com/hyperledger/fabric/orderer/common/filter"
@@ -39,6 +40,7 @@ type limitedSupport interface {
3940
ChainID() string
4041
PolicyManager() policies.Manager
4142
SharedConfig() sharedconfig.Manager
43+
ChainConfig() chainconfig.Descriptor
4244
Enqueue(env *cb.Envelope) bool
4345
}
4446

@@ -193,7 +195,7 @@ func (sc *systemChain) authorize(configEnvelope *cb.ConfigurationEnvelope) cb.St
193195
// XXX actually do policy signature validation
194196
_ = policy
195197

196-
configHash := configtx.HashItems(configEnvelope.Items[1:])
198+
configHash := configtx.HashItems(configEnvelope.Items[1:], sc.support.ChainConfig().HashingAlgorithm())
197199

198200
if !bytes.Equal(configHash, creationPolicy.Digest) {
199201
logger.Debugf("Validly signed chain creation did not contain correct digest for remaining configuration %x vs. %x", configHash, creationPolicy.Digest)

orderer/multichain/systemchain_test.go

+16-8
Original file line numberDiff line numberDiff line change
@@ -20,7 +20,9 @@ import (
2020
"reflect"
2121
"testing"
2222

23+
"github.com/hyperledger/fabric/common/chainconfig"
2324
"github.com/hyperledger/fabric/common/configtx"
25+
mockchainconfig "github.com/hyperledger/fabric/common/mocks/chainconfig"
2426
"github.com/hyperledger/fabric/common/policies"
2527
coreutil "github.com/hyperledger/fabric/common/util"
2628
"github.com/hyperledger/fabric/orderer/common/bootstrap/provisional"
@@ -49,17 +51,19 @@ func (mpm *mockPolicyManager) GetPolicy(id string) (policies.Policy, bool) {
4951
}
5052

5153
type mockSupport struct {
52-
mpm *mockPolicyManager
53-
msc *mocksharedconfig.Manager
54-
chainID string
55-
queue []*cb.Envelope
54+
mpm *mockPolicyManager
55+
msc *mocksharedconfig.Manager
56+
chainID string
57+
queue []*cb.Envelope
58+
chainConfig *mockchainconfig.Descriptor
5659
}
5760

5861
func newMockSupport(chainID string) *mockSupport {
5962
return &mockSupport{
60-
mpm: &mockPolicyManager{},
61-
msc: &mocksharedconfig.Manager{},
62-
chainID: chainID,
63+
mpm: &mockPolicyManager{},
64+
msc: &mocksharedconfig.Manager{},
65+
chainID: chainID,
66+
chainConfig: &mockchainconfig.Descriptor{},
6367
}
6468
}
6569

@@ -80,6 +84,10 @@ func (ms *mockSupport) SharedConfig() sharedconfig.Manager {
8084
return ms.msc
8185
}
8286

87+
func (ms *mockSupport) ChainConfig() chainconfig.Descriptor {
88+
return ms.chainConfig
89+
}
90+
8391
type mockChainCreator struct {
8492
newChains []*cb.Envelope
8593
ms *mockSupport
@@ -118,7 +126,7 @@ func TestGoodProposal(t *testing.T) {
118126
Type: cb.ConfigurationItem_Orderer,
119127
Value: utils.MarshalOrPanic(&ab.CreationPolicy{
120128
Policy: provisional.AcceptAllPolicyKey,
121-
Digest: coreutil.ComputeCryptoHash([]byte{}),
129+
Digest: mcc.ms.ChainConfig().HashingAlgorithm()([]byte{}),
122130
}),
123131
}
124132
ingressTx := makeConfigTxWithItems(newChainID, chainCreateTx)

0 commit comments

Comments
 (0)