Example #1
0
 def validate_transaction(self, txn):
     # validate transactions signature
     header = TransactionHeader()
     header.ParseFromString(txn.header)
     valid = signing.verify(txn.header, txn.header_signature,
                            header.signer_pubkey)
     return valid
Example #2
0
    def verify_wait_certificate(cls, certificate, poet_public_key):
        # Reconstitute the PoET public key and check the signature over the
        # serialized wait certificate.
        decoded_poet_public_key = \
            signing.decode_pubkey(poet_public_key, 'hex')

        return \
            signing.verify(
                certificate.serialize(),
                certificate.signature,
                decoded_poet_public_key)
Example #3
0
    def deserialize_wait_timer(cls, serialized_timer, signature):
        with cls._lock:
            # Verify the signature before trying to deserialize
            if not signing.verify(serialized_timer, signature,
                                  cls._poet_public_key):
                return None

        return \
            EnclaveWaitTimer.wait_timer_from_serialized(
                serialized_timer=serialized_timer,
                signature=signature)
Example #4
0
    def verify_wait_certificate(cls, certificate, poet_public_key):
        # Reconstitute the PoET public key and check the signature over the
        # serialized wait certificate.
        decoded_poet_public_key = \
            signing.decode_pubkey(poet_public_key, 'hex')

        if not \
            signing.verify(
                certificate.serialize(),
                certificate.signature,
                decoded_poet_public_key):
            raise ValueError('Wait certificate signature does not match')
Example #5
0
    def validate_block(self, block):
        # validate block signature
        header = BlockHeader()
        header.ParseFromString(block.header)
        valid = signing.verify(block.header, block.header_signature,
                               header.signer_pubkey)

        # validate all batches in block. These are not all batches in the
        # batch_ids stored in the block header, only those sent with the block.
        total = len(block.batches)
        index = 0
        while valid and index < total:
            valid = self.validate_batch(block.batches[index])
            index += 1

        return valid
Example #6
0
    def validate_batch(self, batch):
        # validate batch signature
        header = BatchHeader()
        header.ParseFromString(batch.header)
        valid = signing.verify(batch.header, batch.header_signature,
                               header.signer_pubkey)

        # validate all transactions in batch
        total = len(batch.transactions)
        index = 0
        while valid and index < total:
            txn = batch.transactions[index]
            valid = self.validate_transaction(txn)
            if valid:
                txn_header = TransactionHeader()
                txn_header.ParseFromString(txn.header)
                if txn_header.batcher_pubkey != header.signer_pubkey:
                    valid = False
            index += 1

        return valid
Example #7
0
    def verify_signup_info(cls, signup_info, originator_public_key_hash,
                           most_recent_wait_certificate_id):
        # Verify the attestation verification report signature
        proof_data_dict = json2dict(signup_info.proof_data)
        verification_report = proof_data_dict.get('verification_report')
        if verification_report is None:
            raise \
                SignupInfoError(
                    'Verification report is missing from proof data')

        signature = proof_data_dict.get('signature')
        if signature is None:
            raise \
                SignupInfoError(
                    'Signature is missing from proof data')

        if not signing.verify(verification_report, signature,
                              cls._report_public_key):
            raise \
                SignupInfoError('Verification report signature is invalid')

        verification_report_dict = json2dict(verification_report)

        # Verify that the verification report contains a PSE manifest status
        # and it is OK
        pse_manifest_status = \
            verification_report_dict.get('pseManifestStatus')
        if pse_manifest_status is None:
            raise \
                SignupInfoError(
                    'Verification report does not contain a PSE manifest '
                    'status')
        if pse_manifest_status != 'OK':
            raise \
                SignupInfoError(
                    'PSE manifest status is {} (i.e., not OK)'.format(
                        pse_manifest_status))

        # Verify that the verification report contains a PSE manifest hash
        # and it is the value we expect
        pse_manifest_hash = \
            verification_report_dict.get('pseManifestHash')
        if pse_manifest_hash is None:
            raise \
                SignupInfoError(
                    'Verification report does not contain a PSE manifest '
                    'hash')

        expected_pse_manifest_hash = \
            base64.b64encode(
                hashlib.sha256(
                    b'Do you believe in manifest destiny?').hexdigest())

        if pse_manifest_hash != expected_pse_manifest_hash:
            raise \
                SignupInfoError(
                    'PSE manifest hash {0} does not match {1}'.format(
                        pse_manifest_hash,
                        expected_pse_manifest_hash))

        # Verify that the verification report contains an enclave quote and
        # that its status is OK
        enclave_quote_status = \
            verification_report_dict.get('isvEnclaveQuoteStatus')
        if enclave_quote_status is None:
            raise \
                SignupInfoError(
                    'Verification report does not contain an enclave quote '
                    'status')
        if enclave_quote_status != 'OK':
            raise \
                SignupInfoError(
                    'Enclave quote status is {} (i.e., not OK)'.format(
                        enclave_quote_status))

        enclave_quote = verification_report_dict.get('isvEnclaveQuoteBody')
        if enclave_quote is None:
            raise \
                SignupInfoError(
                    'Verification report does not contain an enclave quote')

        # Verify that the enclave quote contains a report body with the value
        # we expect (i.e., SHA256(SHA256(OPK)|PPK)
        report_data = '{0}{1}'.format(originator_public_key_hash.upper(),
                                      signup_info.poet_public_key.upper())
        expected_report_body = hashlib.sha256(
            dict2json(report_data)).hexdigest()

        enclave_quote_dict = \
            json2dict(base64.b64decode(enclave_quote))
        report_body = enclave_quote_dict.get('report_body')
        if report_body is None:
            raise \
                SignupInfoError(
                    'Enclave quote does not contain a report body')

        if report_body != expected_report_body:
            raise \
                SignupInfoError(
                    'Enclave quote report body {0} does not match {1}'.format(
                        report_body,
                        expected_report_body))

        # Verify that the wait certificate ID in the verification report
        # matches the provided wait certificate ID.  The wait certificate ID
        # is stored in the nonce field.
        nonce = verification_report_dict.get('nonce')
        if nonce is None:
            raise \
                SignupInfoError(
                    'Verification report does not have a nonce')