|
30 | 30 | from saml2.extension.idpdisc import DiscoveryResponse
|
31 | 31 | from saml2.md import NAMESPACE as NS_MD
|
32 | 32 | from saml2.md import EntitiesDescriptor
|
| 33 | +from saml2.md import EntityDescriptor |
33 | 34 | from saml2.md import ArtifactResolutionService
|
34 | 35 | from saml2.md import NameIDMappingService
|
35 | 36 | from saml2.md import SingleSignOnService
|
|
44 | 45 | from saml2.time_util import before
|
45 | 46 | from saml2.time_util import str_to_time
|
46 | 47 | from saml2.validate import NotValid
|
| 48 | +from saml2.sigver import SignatureError |
47 | 49 | from saml2.sigver import security_context
|
48 | 50 | from saml2.extension.mdattr import NAMESPACE as NS_MDATTR
|
49 | 51 | from saml2.extension.mdattr import EntityAttributes
|
@@ -742,14 +744,50 @@ def parse_and_check_signature(self, txt):
|
742 | 744 | if not self.signed():
|
743 | 745 | return True
|
744 | 746 |
|
745 |
| - fallback_name = "{ns}:{tag}".format( |
746 |
| - ns=md.EntitiesDescriptor.c_namespace, tag=md.EntitiesDescriptor.c_tag |
747 |
| - ) |
748 |
| - node_name = self.node_name or fallback_name |
| 747 | + if self.node_name is not None: |
| 748 | + try: |
| 749 | + self.security.verify_signature( |
| 750 | + txt, node_name=self.node_name, cert_file=self.cert |
| 751 | + ) |
| 752 | + except SignatureError as e: |
| 753 | + error_context = { |
| 754 | + "message": "Failed to verify signature", |
| 755 | + "node_name": self.node_name, |
| 756 | + } |
| 757 | + raise SignatureError(error_context) from e |
| 758 | + else: |
| 759 | + return True |
| 760 | + |
| 761 | + def try_verify_signature(node_name): |
| 762 | + try: |
| 763 | + self.security.verify_signature( |
| 764 | + txt, node_name=node_name, cert_file=self.cert |
| 765 | + ) |
| 766 | + except SignatureError as e: |
| 767 | + return False |
| 768 | + else: |
| 769 | + return True |
| 770 | + |
| 771 | + descriptor_names = [ |
| 772 | + f"{ns}:{tag}" |
| 773 | + for ns, tag in [ |
| 774 | + (EntitiesDescriptor.c_namespace, EntitiesDescriptor.c_tag), |
| 775 | + (EntityDescriptor.c_namespace, EntityDescriptor.c_tag), |
| 776 | + ] |
| 777 | + ] |
749 | 778 |
|
750 |
| - return self.security.verify_signature( |
751 |
| - txt, node_name=node_name, cert_file=self.cert |
| 779 | + verified_w_descriptor_name = any( |
| 780 | + try_verify_signature(node_name) |
| 781 | + for node_name in descriptor_names |
752 | 782 | )
|
| 783 | + if not verified_w_descriptor_name: |
| 784 | + error_context = { |
| 785 | + "message": "Failed to verify signature", |
| 786 | + "descriptor_names": descriptor_names, |
| 787 | + } |
| 788 | + raise SignatureError(error_context) |
| 789 | + |
| 790 | + return verified_w_descriptor_name |
753 | 791 |
|
754 | 792 |
|
755 | 793 | class MetaDataFile(InMemoryMetaData):
|
@@ -926,7 +964,7 @@ def __init__(self, url=None, security=None, cert=None,
|
926 | 964 | # that use case since it is unlikely to be leveraged for most
|
927 | 965 | # flows.
|
928 | 966 | self.node_name = "{ns}:{tag}".format(
|
929 |
| - ns=md.EntityDescriptor.c_namespace, tag=md.EntityDescriptor.c_tag |
| 967 | + ns=EntityDescriptor.c_namespace, tag=EntityDescriptor.c_tag |
930 | 968 | )
|
931 | 969 |
|
932 | 970 | def load(self, *args, **kwargs):
|
|
0 commit comments