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
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)
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)
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')
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
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
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')