github.com/ewagmig/fabric@v2.1.1+incompatible/msp/mspimpl.go (about) 1 /* 2 Copyright IBM Corp. All Rights Reserved. 3 4 SPDX-License-Identifier: Apache-2.0 5 */ 6 7 package msp 8 9 import ( 10 "bytes" 11 "crypto/x509" 12 "crypto/x509/pkix" 13 "encoding/hex" 14 "encoding/pem" 15 16 "github.com/golang/protobuf/proto" 17 m "github.com/hyperledger/fabric-protos-go/msp" 18 "github.com/hyperledger/fabric/bccsp" 19 "github.com/hyperledger/fabric/bccsp/factory" 20 "github.com/hyperledger/fabric/bccsp/signer" 21 "github.com/hyperledger/fabric/bccsp/sw" 22 "github.com/pkg/errors" 23 ) 24 25 // mspSetupFuncType is the prototype of the setup function 26 type mspSetupFuncType func(config *m.FabricMSPConfig) error 27 28 // validateIdentityOUsFuncType is the prototype of the function to validate identity's OUs 29 type validateIdentityOUsFuncType func(id *identity) error 30 31 // satisfiesPrincipalInternalFuncType is the prototype of the function to check if principals are satisfied 32 type satisfiesPrincipalInternalFuncType func(id Identity, principal *m.MSPPrincipal) error 33 34 //setupAdminInternalFuncType is a prototype of the function to setup the admins 35 type setupAdminInternalFuncType func(conf *m.FabricMSPConfig) error 36 37 // This is an instantiation of an MSP that 38 // uses BCCSP for its cryptographic primitives. 39 type bccspmsp struct { 40 // version specifies the behaviour of this msp 41 version MSPVersion 42 // The following function pointers are used to change the behaviour 43 // of this MSP depending on its version. 44 // internalSetupFunc is the pointer to the setup function 45 internalSetupFunc mspSetupFuncType 46 47 // internalValidateIdentityOusFunc is the pointer to the function to validate identity's OUs 48 internalValidateIdentityOusFunc validateIdentityOUsFuncType 49 50 // internalSatisfiesPrincipalInternalFunc is the pointer to the function to check if principals are satisfied 51 internalSatisfiesPrincipalInternalFunc satisfiesPrincipalInternalFuncType 52 53 // internalSetupAdmin is the pointer to the function that setup the administrators of this msp 54 internalSetupAdmin setupAdminInternalFuncType 55 56 // list of CA certs we trust 57 rootCerts []Identity 58 59 // list of intermediate certs we trust 60 intermediateCerts []Identity 61 62 // list of CA TLS certs we trust 63 tlsRootCerts [][]byte 64 65 // list of intermediate TLS certs we trust 66 tlsIntermediateCerts [][]byte 67 68 // certificationTreeInternalNodesMap whose keys correspond to the raw material 69 // (DER representation) of a certificate casted to a string, and whose values 70 // are boolean. True means that the certificate is an internal node of the certification tree. 71 // False means that the certificate corresponds to a leaf of the certification tree. 72 certificationTreeInternalNodesMap map[string]bool 73 74 // list of signing identities 75 signer SigningIdentity 76 77 // list of admin identities 78 admins []Identity 79 80 // the crypto provider 81 bccsp bccsp.BCCSP 82 83 // the provider identifier for this MSP 84 name string 85 86 // verification options for MSP members 87 opts *x509.VerifyOptions 88 89 // list of certificate revocation lists 90 CRL []*pkix.CertificateList 91 92 // list of OUs 93 ouIdentifiers map[string][][]byte 94 95 // cryptoConfig contains 96 cryptoConfig *m.FabricCryptoConfig 97 98 // NodeOUs configuration 99 ouEnforcement bool 100 // These are the OUIdentifiers of the clients, peers, admins and orderers. 101 // They are used to tell apart these entities 102 clientOU, peerOU, adminOU, ordererOU *OUIdentifier 103 } 104 105 // newBccspMsp returns an MSP instance backed up by a BCCSP 106 // crypto provider. It handles x.509 certificates and can 107 // generate identities and signing identities backed by 108 // certificates and keypairs 109 func newBccspMsp(version MSPVersion, defaultBCCSP bccsp.BCCSP) (MSP, error) { 110 mspLogger.Debugf("Creating BCCSP-based MSP instance") 111 112 theMsp := &bccspmsp{} 113 theMsp.version = version 114 theMsp.bccsp = defaultBCCSP 115 switch version { 116 case MSPv1_0: 117 theMsp.internalSetupFunc = theMsp.setupV1 118 theMsp.internalValidateIdentityOusFunc = theMsp.validateIdentityOUsV1 119 theMsp.internalSatisfiesPrincipalInternalFunc = theMsp.satisfiesPrincipalInternalPreV13 120 theMsp.internalSetupAdmin = theMsp.setupAdminsPreV142 121 case MSPv1_1: 122 theMsp.internalSetupFunc = theMsp.setupV11 123 theMsp.internalValidateIdentityOusFunc = theMsp.validateIdentityOUsV11 124 theMsp.internalSatisfiesPrincipalInternalFunc = theMsp.satisfiesPrincipalInternalPreV13 125 theMsp.internalSetupAdmin = theMsp.setupAdminsPreV142 126 case MSPv1_3: 127 theMsp.internalSetupFunc = theMsp.setupV11 128 theMsp.internalValidateIdentityOusFunc = theMsp.validateIdentityOUsV11 129 theMsp.internalSatisfiesPrincipalInternalFunc = theMsp.satisfiesPrincipalInternalV13 130 theMsp.internalSetupAdmin = theMsp.setupAdminsPreV142 131 case MSPv1_4_3: 132 theMsp.internalSetupFunc = theMsp.setupV142 133 theMsp.internalValidateIdentityOusFunc = theMsp.validateIdentityOUsV142 134 theMsp.internalSatisfiesPrincipalInternalFunc = theMsp.satisfiesPrincipalInternalV142 135 theMsp.internalSetupAdmin = theMsp.setupAdminsV142 136 default: 137 return nil, errors.Errorf("Invalid MSP version [%v]", version) 138 } 139 140 return theMsp, nil 141 } 142 143 // NewBccspMspWithKeyStore allows to create a BCCSP-based MSP whose underlying 144 // crypto material is available through the passed keystore 145 func NewBccspMspWithKeyStore(version MSPVersion, keyStore bccsp.KeyStore, bccsp bccsp.BCCSP) (MSP, error) { 146 thisMSP, err := newBccspMsp(version, bccsp) 147 if err != nil { 148 return nil, err 149 } 150 151 csp, err := sw.NewWithParams( 152 factory.GetDefaultOpts().SwOpts.SecLevel, 153 factory.GetDefaultOpts().SwOpts.HashFamily, 154 keyStore) 155 if err != nil { 156 return nil, err 157 } 158 thisMSP.(*bccspmsp).bccsp = csp 159 160 return thisMSP, nil 161 } 162 163 func (msp *bccspmsp) getCertFromPem(idBytes []byte) (*x509.Certificate, error) { 164 if idBytes == nil { 165 return nil, errors.New("getCertFromPem error: nil idBytes") 166 } 167 168 // Decode the pem bytes 169 pemCert, _ := pem.Decode(idBytes) 170 if pemCert == nil { 171 return nil, errors.Errorf("getCertFromPem error: could not decode pem bytes [%v]", idBytes) 172 } 173 174 // get a cert 175 var cert *x509.Certificate 176 cert, err := x509.ParseCertificate(pemCert.Bytes) 177 if err != nil { 178 return nil, errors.Wrap(err, "getCertFromPem error: failed to parse x509 cert") 179 } 180 181 return cert, nil 182 } 183 184 func (msp *bccspmsp) getIdentityFromConf(idBytes []byte) (Identity, bccsp.Key, error) { 185 // get a cert 186 cert, err := msp.getCertFromPem(idBytes) 187 if err != nil { 188 return nil, nil, err 189 } 190 191 // get the public key in the right format 192 certPubK, err := msp.bccsp.KeyImport(cert, &bccsp.X509PublicKeyImportOpts{Temporary: true}) 193 if err != nil { 194 return nil, nil, err 195 } 196 197 mspId, err := newIdentity(cert, certPubK, msp) 198 if err != nil { 199 return nil, nil, err 200 } 201 202 return mspId, certPubK, nil 203 } 204 205 func (msp *bccspmsp) getSigningIdentityFromConf(sidInfo *m.SigningIdentityInfo) (SigningIdentity, error) { 206 if sidInfo == nil { 207 return nil, errors.New("getIdentityFromBytes error: nil sidInfo") 208 } 209 210 // Extract the public part of the identity 211 idPub, pubKey, err := msp.getIdentityFromConf(sidInfo.PublicSigner) 212 if err != nil { 213 return nil, err 214 } 215 216 // Find the matching private key in the BCCSP keystore 217 privKey, err := msp.bccsp.GetKey(pubKey.SKI()) 218 // Less Secure: Attempt to import Private Key from KeyInfo, if BCCSP was not able to find the key 219 if err != nil { 220 mspLogger.Debugf("Could not find SKI [%s], trying KeyMaterial field: %+v\n", hex.EncodeToString(pubKey.SKI()), err) 221 if sidInfo.PrivateSigner == nil || sidInfo.PrivateSigner.KeyMaterial == nil { 222 return nil, errors.New("KeyMaterial not found in SigningIdentityInfo") 223 } 224 225 pemKey, _ := pem.Decode(sidInfo.PrivateSigner.KeyMaterial) 226 if pemKey == nil { 227 return nil, errors.Errorf("%s: wrong PEM encoding", sidInfo.PrivateSigner.KeyIdentifier) 228 } 229 privKey, err = msp.bccsp.KeyImport(pemKey.Bytes, &bccsp.ECDSAPrivateKeyImportOpts{Temporary: true}) 230 if err != nil { 231 return nil, errors.WithMessage(err, "getIdentityFromBytes error: Failed to import EC private key") 232 } 233 } 234 235 // get the peer signer 236 peerSigner, err := signer.New(msp.bccsp, privKey) 237 if err != nil { 238 return nil, errors.WithMessage(err, "getIdentityFromBytes error: Failed initializing bccspCryptoSigner") 239 } 240 241 return newSigningIdentity(idPub.(*identity).cert, idPub.(*identity).pk, peerSigner, msp) 242 } 243 244 // Setup sets up the internal data structures 245 // for this MSP, given an MSPConfig ref; it 246 // returns nil in case of success or an error otherwise 247 func (msp *bccspmsp) Setup(conf1 *m.MSPConfig) error { 248 if conf1 == nil { 249 return errors.New("Setup error: nil conf reference") 250 } 251 252 // given that it's an msp of type fabric, extract the MSPConfig instance 253 conf := &m.FabricMSPConfig{} 254 err := proto.Unmarshal(conf1.Config, conf) 255 if err != nil { 256 return errors.Wrap(err, "failed unmarshalling fabric msp config") 257 } 258 259 // set the name for this msp 260 msp.name = conf.Name 261 mspLogger.Debugf("Setting up MSP instance %s", msp.name) 262 263 // setup 264 return msp.internalSetupFunc(conf) 265 } 266 267 // GetVersion returns the version of this MSP 268 func (msp *bccspmsp) GetVersion() MSPVersion { 269 return msp.version 270 } 271 272 // GetType returns the type for this MSP 273 func (msp *bccspmsp) GetType() ProviderType { 274 return FABRIC 275 } 276 277 // GetIdentifier returns the MSP identifier for this instance 278 func (msp *bccspmsp) GetIdentifier() (string, error) { 279 return msp.name, nil 280 } 281 282 // GetTLSRootCerts returns the root certificates for this MSP 283 func (msp *bccspmsp) GetTLSRootCerts() [][]byte { 284 return msp.tlsRootCerts 285 } 286 287 // GetTLSIntermediateCerts returns the intermediate root certificates for this MSP 288 func (msp *bccspmsp) GetTLSIntermediateCerts() [][]byte { 289 return msp.tlsIntermediateCerts 290 } 291 292 // GetDefaultSigningIdentity returns the 293 // default signing identity for this MSP (if any) 294 func (msp *bccspmsp) GetDefaultSigningIdentity() (SigningIdentity, error) { 295 mspLogger.Debugf("Obtaining default signing identity") 296 297 if msp.signer == nil { 298 return nil, errors.New("this MSP does not possess a valid default signing identity") 299 } 300 301 return msp.signer, nil 302 } 303 304 // GetSigningIdentity returns a specific signing 305 // identity identified by the supplied identifier 306 func (msp *bccspmsp) GetSigningIdentity(identifier *IdentityIdentifier) (SigningIdentity, error) { 307 // TODO 308 return nil, errors.Errorf("no signing identity for %#v", identifier) 309 } 310 311 // Validate attempts to determine whether 312 // the supplied identity is valid according 313 // to this MSP's roots of trust; it returns 314 // nil in case the identity is valid or an 315 // error otherwise 316 func (msp *bccspmsp) Validate(id Identity) error { 317 mspLogger.Debugf("MSP %s validating identity", msp.name) 318 319 switch id := id.(type) { 320 // If this identity is of this specific type, 321 // this is how I can validate it given the 322 // root of trust this MSP has 323 case *identity: 324 return msp.validateIdentity(id) 325 default: 326 return errors.New("identity type not recognized") 327 } 328 } 329 330 // hasOURole checks that the identity belongs to the organizational unit 331 // associated to the specified MSPRole. 332 // This function does not check the certifiers identifier. 333 // Appropriate validation needs to be enforced before. 334 func (msp *bccspmsp) hasOURole(id Identity, mspRole m.MSPRole_MSPRoleType) error { 335 // Check NodeOUs 336 if !msp.ouEnforcement { 337 return errors.New("NodeOUs not activated. Cannot tell apart identities.") 338 } 339 340 mspLogger.Debugf("MSP %s checking if the identity is a client", msp.name) 341 342 switch id := id.(type) { 343 // If this identity is of this specific type, 344 // this is how I can validate it given the 345 // root of trust this MSP has 346 case *identity: 347 return msp.hasOURoleInternal(id, mspRole) 348 default: 349 return errors.New("Identity type not recognized") 350 } 351 } 352 353 func (msp *bccspmsp) hasOURoleInternal(id *identity, mspRole m.MSPRole_MSPRoleType) error { 354 var nodeOU *OUIdentifier 355 switch mspRole { 356 case m.MSPRole_CLIENT: 357 nodeOU = msp.clientOU 358 case m.MSPRole_PEER: 359 nodeOU = msp.peerOU 360 case m.MSPRole_ADMIN: 361 nodeOU = msp.adminOU 362 case m.MSPRole_ORDERER: 363 nodeOU = msp.ordererOU 364 default: 365 return errors.New("Invalid MSPRoleType. It must be CLIENT, PEER, ADMIN or ORDERER") 366 } 367 368 if nodeOU == nil { 369 return errors.Errorf("cannot test for classification, node ou for type [%s], not defined, msp: [%s]", mspRole, msp.name) 370 } 371 372 for _, OU := range id.GetOrganizationalUnits() { 373 if OU.OrganizationalUnitIdentifier == nodeOU.OrganizationalUnitIdentifier { 374 return nil 375 } 376 } 377 378 return errors.Errorf("The identity does not contain OU [%s], MSP: [%s]", mspRole, msp.name) 379 } 380 381 // DeserializeIdentity returns an Identity given the byte-level 382 // representation of a SerializedIdentity struct 383 func (msp *bccspmsp) DeserializeIdentity(serializedID []byte) (Identity, error) { 384 mspLogger.Debug("Obtaining identity") 385 386 // We first deserialize to a SerializedIdentity to get the MSP ID 387 sId := &m.SerializedIdentity{} 388 err := proto.Unmarshal(serializedID, sId) 389 if err != nil { 390 return nil, errors.Wrap(err, "could not deserialize a SerializedIdentity") 391 } 392 393 if sId.Mspid != msp.name { 394 return nil, errors.Errorf("expected MSP ID %s, received %s", msp.name, sId.Mspid) 395 } 396 397 return msp.deserializeIdentityInternal(sId.IdBytes) 398 } 399 400 // deserializeIdentityInternal returns an identity given its byte-level representation 401 func (msp *bccspmsp) deserializeIdentityInternal(serializedIdentity []byte) (Identity, error) { 402 // This MSP will always deserialize certs this way 403 bl, _ := pem.Decode(serializedIdentity) 404 if bl == nil { 405 return nil, errors.New("could not decode the PEM structure") 406 } 407 cert, err := x509.ParseCertificate(bl.Bytes) 408 if err != nil { 409 return nil, errors.Wrap(err, "parseCertificate failed") 410 } 411 412 // Now we have the certificate; make sure that its fields 413 // (e.g. the Issuer.OU or the Subject.OU) match with the 414 // MSP id that this MSP has; otherwise it might be an attack 415 // TODO! 416 // We can't do it yet because there is no standardized way 417 // (yet) to encode the MSP ID into the x.509 body of a cert 418 419 pub, err := msp.bccsp.KeyImport(cert, &bccsp.X509PublicKeyImportOpts{Temporary: true}) 420 if err != nil { 421 return nil, errors.WithMessage(err, "failed to import certificate's public key") 422 } 423 424 return newIdentity(cert, pub, msp) 425 } 426 427 // SatisfiesPrincipal returns nil if the identity matches the principal or an error otherwise 428 func (msp *bccspmsp) SatisfiesPrincipal(id Identity, principal *m.MSPPrincipal) error { 429 principals, err := collectPrincipals(principal, msp.GetVersion()) 430 if err != nil { 431 return err 432 } 433 for _, principal := range principals { 434 err = msp.internalSatisfiesPrincipalInternalFunc(id, principal) 435 if err != nil { 436 return err 437 } 438 } 439 return nil 440 } 441 442 // collectPrincipals collects principals from combined principals into a single MSPPrincipal slice. 443 func collectPrincipals(principal *m.MSPPrincipal, mspVersion MSPVersion) ([]*m.MSPPrincipal, error) { 444 switch principal.PrincipalClassification { 445 case m.MSPPrincipal_COMBINED: 446 // Combined principals are not supported in MSP v1.0 or v1.1 447 if mspVersion <= MSPv1_1 { 448 return nil, errors.Errorf("invalid principal type %d", int32(principal.PrincipalClassification)) 449 } 450 // Principal is a combination of multiple principals. 451 principals := &m.CombinedPrincipal{} 452 err := proto.Unmarshal(principal.Principal, principals) 453 if err != nil { 454 return nil, errors.Wrap(err, "could not unmarshal CombinedPrincipal from principal") 455 } 456 // Return an error if there are no principals in the combined principal. 457 if len(principals.Principals) == 0 { 458 return nil, errors.New("No principals in CombinedPrincipal") 459 } 460 // Recursively call msp.collectPrincipals for all combined principals. 461 // There is no limit for the levels of nesting for the combined principals. 462 var principalsSlice []*m.MSPPrincipal 463 for _, cp := range principals.Principals { 464 internalSlice, err := collectPrincipals(cp, mspVersion) 465 if err != nil { 466 return nil, err 467 } 468 principalsSlice = append(principalsSlice, internalSlice...) 469 } 470 // All the combined principals have been collected into principalsSlice 471 return principalsSlice, nil 472 default: 473 return []*m.MSPPrincipal{principal}, nil 474 } 475 } 476 477 // satisfiesPrincipalInternalPreV13 takes as arguments the identity and the principal. 478 // The function returns an error if one occurred. 479 // The function implements the behavior of an MSP up to and including v1.1. 480 func (msp *bccspmsp) satisfiesPrincipalInternalPreV13(id Identity, principal *m.MSPPrincipal) error { 481 switch principal.PrincipalClassification { 482 // in this case, we have to check whether the 483 // identity has a role in the msp - member or admin 484 case m.MSPPrincipal_ROLE: 485 // Principal contains the msp role 486 mspRole := &m.MSPRole{} 487 err := proto.Unmarshal(principal.Principal, mspRole) 488 if err != nil { 489 return errors.Wrap(err, "could not unmarshal MSPRole from principal") 490 } 491 492 // at first, we check whether the MSP 493 // identifier is the same as that of the identity 494 if mspRole.MspIdentifier != msp.name { 495 return errors.Errorf("the identity is a member of a different MSP (expected %s, got %s)", mspRole.MspIdentifier, id.GetMSPIdentifier()) 496 } 497 498 // now we validate the different msp roles 499 switch mspRole.Role { 500 case m.MSPRole_MEMBER: 501 // in the case of member, we simply check 502 // whether this identity is valid for the MSP 503 mspLogger.Debugf("Checking if identity satisfies MEMBER role for %s", msp.name) 504 return msp.Validate(id) 505 case m.MSPRole_ADMIN: 506 mspLogger.Debugf("Checking if identity satisfies ADMIN role for %s", msp.name) 507 // in the case of admin, we check that the 508 // id is exactly one of our admins 509 if msp.isInAdmins(id.(*identity)) { 510 return nil 511 } 512 return errors.New("This identity is not an admin") 513 case m.MSPRole_CLIENT: 514 fallthrough 515 case m.MSPRole_PEER: 516 mspLogger.Debugf("Checking if identity satisfies role [%s] for %s", m.MSPRole_MSPRoleType_name[int32(mspRole.Role)], msp.name) 517 if err := msp.Validate(id); err != nil { 518 return errors.Wrapf(err, "The identity is not valid under this MSP [%s]", msp.name) 519 } 520 521 if err := msp.hasOURole(id, mspRole.Role); err != nil { 522 return errors.Wrapf(err, "The identity is not a [%s] under this MSP [%s]", m.MSPRole_MSPRoleType_name[int32(mspRole.Role)], msp.name) 523 } 524 return nil 525 default: 526 return errors.Errorf("invalid MSP role type %d", int32(mspRole.Role)) 527 } 528 case m.MSPPrincipal_IDENTITY: 529 // in this case we have to deserialize the principal's identity 530 // and compare it byte-by-byte with our cert 531 principalId, err := msp.DeserializeIdentity(principal.Principal) 532 if err != nil { 533 return errors.WithMessage(err, "invalid identity principal, not a certificate") 534 } 535 536 if bytes.Equal(id.(*identity).cert.Raw, principalId.(*identity).cert.Raw) { 537 return principalId.Validate() 538 } 539 540 return errors.New("The identities do not match") 541 case m.MSPPrincipal_ORGANIZATION_UNIT: 542 // Principal contains the OrganizationUnit 543 OU := &m.OrganizationUnit{} 544 err := proto.Unmarshal(principal.Principal, OU) 545 if err != nil { 546 return errors.Wrap(err, "could not unmarshal OrganizationUnit from principal") 547 } 548 549 // at first, we check whether the MSP 550 // identifier is the same as that of the identity 551 if OU.MspIdentifier != msp.name { 552 return errors.Errorf("the identity is a member of a different MSP (expected %s, got %s)", OU.MspIdentifier, id.GetMSPIdentifier()) 553 } 554 555 // we then check if the identity is valid with this MSP 556 // and fail if it is not 557 err = msp.Validate(id) 558 if err != nil { 559 return err 560 } 561 562 // now we check whether any of this identity's OUs match the requested one 563 for _, ou := range id.GetOrganizationalUnits() { 564 if ou.OrganizationalUnitIdentifier == OU.OrganizationalUnitIdentifier && 565 bytes.Equal(ou.CertifiersIdentifier, OU.CertifiersIdentifier) { 566 return nil 567 } 568 } 569 570 // if we are here, no match was found, return an error 571 return errors.New("The identities do not match") 572 default: 573 return errors.Errorf("invalid principal type %d", int32(principal.PrincipalClassification)) 574 } 575 } 576 577 // satisfiesPrincipalInternalV13 takes as arguments the identity and the principal. 578 // The function returns an error if one occurred. 579 // The function implements the additional behavior expected of an MSP starting from v1.3. 580 // For pre-v1.3 functionality, the function calls the satisfiesPrincipalInternalPreV13. 581 func (msp *bccspmsp) satisfiesPrincipalInternalV13(id Identity, principal *m.MSPPrincipal) error { 582 switch principal.PrincipalClassification { 583 case m.MSPPrincipal_COMBINED: 584 return errors.New("SatisfiesPrincipalInternal shall not be called with a CombinedPrincipal") 585 case m.MSPPrincipal_ANONYMITY: 586 anon := &m.MSPIdentityAnonymity{} 587 err := proto.Unmarshal(principal.Principal, anon) 588 if err != nil { 589 return errors.Wrap(err, "could not unmarshal MSPIdentityAnonymity from principal") 590 } 591 switch anon.AnonymityType { 592 case m.MSPIdentityAnonymity_ANONYMOUS: 593 return errors.New("Principal is anonymous, but X.509 MSP does not support anonymous identities") 594 case m.MSPIdentityAnonymity_NOMINAL: 595 return nil 596 default: 597 return errors.Errorf("Unknown principal anonymity type: %d", anon.AnonymityType) 598 } 599 600 default: 601 // Use the pre-v1.3 function to check other principal types 602 return msp.satisfiesPrincipalInternalPreV13(id, principal) 603 } 604 } 605 606 // satisfiesPrincipalInternalV142 takes as arguments the identity and the principal. 607 // The function returns an error if one occurred. 608 // The function implements the additional behavior expected of an MSP starting from v2.0. 609 // For v1.3 functionality, the function calls the satisfiesPrincipalInternalPreV13. 610 func (msp *bccspmsp) satisfiesPrincipalInternalV142(id Identity, principal *m.MSPPrincipal) error { 611 _, okay := id.(*identity) 612 if !okay { 613 return errors.New("invalid identity type, expected *identity") 614 } 615 616 switch principal.PrincipalClassification { 617 case m.MSPPrincipal_ROLE: 618 if !msp.ouEnforcement { 619 break 620 } 621 622 // Principal contains the msp role 623 mspRole := &m.MSPRole{} 624 err := proto.Unmarshal(principal.Principal, mspRole) 625 if err != nil { 626 return errors.Wrap(err, "could not unmarshal MSPRole from principal") 627 } 628 629 // at first, we check whether the MSP 630 // identifier is the same as that of the identity 631 if mspRole.MspIdentifier != msp.name { 632 return errors.Errorf("the identity is a member of a different MSP (expected %s, got %s)", mspRole.MspIdentifier, id.GetMSPIdentifier()) 633 } 634 635 // now we validate the admin role only, the other roles are left to the v1.3 function 636 switch mspRole.Role { 637 case m.MSPRole_ADMIN: 638 mspLogger.Debugf("Checking if identity has been named explicitly as an admin for %s", msp.name) 639 // in the case of admin, we check that the 640 // id is exactly one of our admins 641 if msp.isInAdmins(id.(*identity)) { 642 return nil 643 } 644 645 // or it carries the Admin OU, in this case check that the identity is valid as well. 646 mspLogger.Debugf("Checking if identity carries the admin ou for %s", msp.name) 647 if err := msp.Validate(id); err != nil { 648 return errors.Wrapf(err, "The identity is not valid under this MSP [%s]", msp.name) 649 } 650 651 if err := msp.hasOURole(id, m.MSPRole_ADMIN); err != nil { 652 return errors.Wrapf(err, "The identity is not an admin under this MSP [%s]", msp.name) 653 } 654 655 return nil 656 case m.MSPRole_ORDERER: 657 mspLogger.Debugf("Checking if identity satisfies role [%s] for %s", m.MSPRole_MSPRoleType_name[int32(mspRole.Role)], msp.name) 658 if err := msp.Validate(id); err != nil { 659 return errors.Wrapf(err, "The identity is not valid under this MSP [%s]", msp.name) 660 } 661 662 if err := msp.hasOURole(id, mspRole.Role); err != nil { 663 return errors.Wrapf(err, "The identity is not a [%s] under this MSP [%s]", m.MSPRole_MSPRoleType_name[int32(mspRole.Role)], msp.name) 664 } 665 return nil 666 } 667 } 668 669 // Use the v1.3 function to check other principal types 670 return msp.satisfiesPrincipalInternalV13(id, principal) 671 } 672 673 func (msp *bccspmsp) isInAdmins(id *identity) bool { 674 for _, admincert := range msp.admins { 675 if bytes.Equal(id.cert.Raw, admincert.(*identity).cert.Raw) { 676 // we do not need to check whether the admin is a valid identity 677 // according to this MSP, since we already check this at Setup time 678 // if there is a match, we can just return 679 return true 680 } 681 } 682 return false 683 } 684 685 // getCertificationChain returns the certification chain of the passed identity within this msp 686 func (msp *bccspmsp) getCertificationChain(id Identity) ([]*x509.Certificate, error) { 687 mspLogger.Debugf("MSP %s getting certification chain", msp.name) 688 689 switch id := id.(type) { 690 // If this identity is of this specific type, 691 // this is how I can validate it given the 692 // root of trust this MSP has 693 case *identity: 694 return msp.getCertificationChainForBCCSPIdentity(id) 695 default: 696 return nil, errors.New("identity type not recognized") 697 } 698 } 699 700 // getCertificationChainForBCCSPIdentity returns the certification chain of the passed bccsp identity within this msp 701 func (msp *bccspmsp) getCertificationChainForBCCSPIdentity(id *identity) ([]*x509.Certificate, error) { 702 if id == nil { 703 return nil, errors.New("Invalid bccsp identity. Must be different from nil.") 704 } 705 706 // we expect to have a valid VerifyOptions instance 707 if msp.opts == nil { 708 return nil, errors.New("Invalid msp instance") 709 } 710 711 // CAs cannot be directly used as identities.. 712 if id.cert.IsCA { 713 return nil, errors.New("An X509 certificate with Basic Constraint: " + 714 "Certificate Authority equals true cannot be used as an identity") 715 } 716 717 return msp.getValidationChain(id.cert, false) 718 } 719 720 func (msp *bccspmsp) getUniqueValidationChain(cert *x509.Certificate, opts x509.VerifyOptions) ([]*x509.Certificate, error) { 721 // ask golang to validate the cert for us based on the options that we've built at setup time 722 if msp.opts == nil { 723 return nil, errors.New("the supplied identity has no verify options") 724 } 725 validationChains, err := cert.Verify(opts) 726 if err != nil { 727 return nil, errors.WithMessage(err, "the supplied identity is not valid") 728 } 729 730 // we only support a single validation chain; 731 // if there's more than one then there might 732 // be unclarity about who owns the identity 733 if len(validationChains) != 1 { 734 return nil, errors.Errorf("this MSP only supports a single validation chain, got %d", len(validationChains)) 735 } 736 737 return validationChains[0], nil 738 } 739 740 func (msp *bccspmsp) getValidationChain(cert *x509.Certificate, isIntermediateChain bool) ([]*x509.Certificate, error) { 741 validationChain, err := msp.getUniqueValidationChain(cert, msp.getValidityOptsForCert(cert)) 742 if err != nil { 743 return nil, errors.WithMessage(err, "failed getting validation chain") 744 } 745 746 // we expect a chain of length at least 2 747 if len(validationChain) < 2 { 748 return nil, errors.Errorf("expected a chain of length at least 2, got %d", len(validationChain)) 749 } 750 751 // check that the parent is a leaf of the certification tree 752 // if validating an intermediate chain, the first certificate will the parent 753 parentPosition := 1 754 if isIntermediateChain { 755 parentPosition = 0 756 } 757 if msp.certificationTreeInternalNodesMap[string(validationChain[parentPosition].Raw)] { 758 return nil, errors.Errorf("invalid validation chain. Parent certificate should be a leaf of the certification tree [%v]", cert.Raw) 759 } 760 return validationChain, nil 761 } 762 763 // getCertificationChainIdentifier returns the certification chain identifier of the passed identity within this msp. 764 // The identifier is computes as the SHA256 of the concatenation of the certificates in the chain. 765 func (msp *bccspmsp) getCertificationChainIdentifier(id Identity) ([]byte, error) { 766 chain, err := msp.getCertificationChain(id) 767 if err != nil { 768 return nil, errors.WithMessagef(err, "failed getting certification chain for [%v]", id) 769 } 770 771 // chain[0] is the certificate representing the identity. 772 // It will be discarded 773 return msp.getCertificationChainIdentifierFromChain(chain[1:]) 774 } 775 776 func (msp *bccspmsp) getCertificationChainIdentifierFromChain(chain []*x509.Certificate) ([]byte, error) { 777 // Hash the chain 778 // Use the hash of the identity's certificate as id in the IdentityIdentifier 779 hashOpt, err := bccsp.GetHashOpt(msp.cryptoConfig.IdentityIdentifierHashFunction) 780 if err != nil { 781 return nil, errors.WithMessage(err, "failed getting hash function options") 782 } 783 784 hf, err := msp.bccsp.GetHash(hashOpt) 785 if err != nil { 786 return nil, errors.WithMessage(err, "failed getting hash function when computing certification chain identifier") 787 } 788 for i := 0; i < len(chain); i++ { 789 hf.Write(chain[i].Raw) 790 } 791 return hf.Sum(nil), nil 792 } 793 794 // sanitizeCert ensures that x509 certificates signed using ECDSA 795 // do have signatures in Low-S. If this is not the case, the certificate 796 // is regenerated to have a Low-S signature. 797 func (msp *bccspmsp) sanitizeCert(cert *x509.Certificate) (*x509.Certificate, error) { 798 if isECDSASignedCert(cert) { 799 // Lookup for a parent certificate to perform the sanitization 800 var parentCert *x509.Certificate 801 chain, err := msp.getUniqueValidationChain(cert, msp.getValidityOptsForCert(cert)) 802 if err != nil { 803 return nil, err 804 } 805 806 // at this point, cert might be a root CA certificate 807 // or an intermediate CA certificate 808 if cert.IsCA && len(chain) == 1 { 809 // cert is a root CA certificate 810 parentCert = cert 811 } else { 812 parentCert = chain[1] 813 } 814 815 // Sanitize 816 cert, err = sanitizeECDSASignedCert(cert, parentCert) 817 if err != nil { 818 return nil, err 819 } 820 } 821 return cert, nil 822 } 823 824 // IsWellFormed checks if the given identity can be deserialized into its provider-specific form. 825 // In this MSP implementation, well formed means that the PEM has a Type which is either 826 // the string 'CERTIFICATE' or the Type is missing altogether. 827 func (msp *bccspmsp) IsWellFormed(identity *m.SerializedIdentity) error { 828 bl, _ := pem.Decode(identity.IdBytes) 829 if bl == nil { 830 return errors.New("PEM decoding resulted in an empty block") 831 } 832 // Important: This method looks very similar to getCertFromPem(idBytes []byte) (*x509.Certificate, error) 833 // But we: 834 // 1) Must ensure PEM block is of type CERTIFICATE or is empty 835 // 2) Must not replace getCertFromPem with this method otherwise we will introduce 836 // a change in validation logic which will result in a chain fork. 837 if bl.Type != "CERTIFICATE" && bl.Type != "" { 838 return errors.Errorf("pem type is %s, should be 'CERTIFICATE' or missing", bl.Type) 839 } 840 _, err := x509.ParseCertificate(bl.Bytes) 841 return err 842 }