def wireEncode(self, wireFormat = None): """ Encode this Data for a particular wire format. If wireFormat is the default wire format, also set the defaultWireEncoding field to the encoded result. :param wireFormat: (optional) A WireFormat object used to encode this Data object. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: The encoded buffer in a SignedBlob object. :rtype: SignedBlob """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if (not self.getDefaultWireEncoding().isNull() and self.getDefaultWireEncodingFormat() == wireFormat): # We already have an encoding in the desired format. return self.getDefaultWireEncoding() (encoding, signedPortionBeginOffset, signedPortionEndOffset) = \ wireFormat.encodeData(self) wireEncoding = SignedBlob( encoding, signedPortionBeginOffset, signedPortionEndOffset) if wireFormat == WireFormat.getDefaultWireFormat(): # This is the default wire encoding. self._setDefaultWireEncoding( wireEncoding, WireFormat.getDefaultWireFormat()) return wireEncoding
def wireEncode(self, wireFormat=None): """ Encode this Interest for a particular wire format. If wireFormat is the default wire format, also set the defaultWireEncoding field to the encoded result. :param wireFormat: (optional) A WireFormat object used to encode this Interest. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: The encoded buffer. :rtype: SignedBlob """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if (not self.getDefaultWireEncoding().isNull() and self.getDefaultWireEncodingFormat() == wireFormat): # We already have an encoding in the desired format. return self.getDefaultWireEncoding() (encoding, signedPortionBeginOffset, signedPortionEndOffset) = \ wireFormat.encodeInterest(self) wireEncoding = SignedBlob(encoding, signedPortionBeginOffset, signedPortionEndOffset) if wireFormat == WireFormat.getDefaultWireFormat(): # This is the default wire encoding. self._setDefaultWireEncoding(wireEncoding, WireFormat.getDefaultWireFormat()) return wireEncoding
def wireDecode(self, input, wireFormat=None): """ Decode the input using a particular wire format and update this Interest. If wireFormat is the default wire format, also set the defaultWireEncoding to another pointer to the input. :param input: The array with the bytes to decode. If input is not a Blob, then copy the bytes to save the defaultWireEncoding (otherwise take another pointer to the same Blob). :type input: A Blob or an array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this Interest. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(input, Blob): # Input is a blob, so get its buf() and set copy False. result = wireFormat.decodeInterest(self, input.buf(), False) else: result = wireFormat.decodeInterest(self, input, True) (signedPortionBeginOffset, signedPortionEndOffset) = result if wireFormat == WireFormat.getDefaultWireFormat(): # This is the default wire encoding. In the Blob constructor, set # copy true, but if input is already a Blob, it won't copy. self._setDefaultWireEncoding( SignedBlob(Blob(input, True), signedPortionBeginOffset, signedPortionEndOffset), WireFormat.getDefaultWireFormat()) else: self._setDefaultWireEncoding(SignedBlob(), None)
def wireDecode(self, input, wireFormat = None): """ Decode the input using a particular wire format and update this Data. If wireFormat is the default wire format, also set the defaultWireEncoding to another pointer to the input. :param input: The array with the bytes to decode. If input is not a Blob, then copy the bytes to save the defaultWireEncoding (otherwise take another pointer to the same Blob). :type input: A Blob or an array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this Data object. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # If input is a blob, get its buf(). decodeBuffer = input.buf() if isinstance(input, Blob) else input (signedPortionBeginOffset, signedPortionEndOffset) = \ wireFormat.decodeData(self, decodeBuffer) if wireFormat == WireFormat.getDefaultWireFormat(): # This is the default wire encoding. In the Blob constructor, set # copy true, but if input is already a Blob, it won't copy. self._setDefaultWireEncoding(SignedBlob( Blob(input, True), signedPortionBeginOffset, signedPortionEndOffset), WireFormat.getDefaultWireFormat()) else: self._setDefaultWireEncoding(SignedBlob(), None)
def signInterestWithSha256(self, interest, wireFormat=None): """ Append a SignatureInfo for DigestSha256 to the Interest name, digest the name components and append a final name component with the signature bits (which is the digest). :param Interest interest: The Interest object to be signed. This appends name components of SignatureInfo and the signature bits. :param wireFormat: (optional) A WireFormat object used to encode the input. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() signature = DigestSha256Signature() # Append the encoded SignatureInfo. interest.getName().append(wireFormat.encodeSignatureInfo(signature)) # Append an empty signature so that the "signedPortion" is correct. interest.getName().append(Name.Component()) # Encode once to get the signed portion. encoding = interest.wireEncode(wireFormat) # Digest and set the signature. sha256 = hashes.Hash(hashes.SHA256(), backend=default_backend()) sha256.update(encoding.toSignedBytes()) signatureBits = sha256.finalize() signature.setSignature(Blob(bytearray(signatureBits), False)) # Remove the empty signature and append the real one. interest.setName(interest.getName().getPrefix(-1).append( wireFormat.encodeSignatureValue(signature)))
def _signInterest(self, interest, certificateName, wireFormat = None): """ Append a SignatureInfo to the Interest name, sign the name components and append a final name component with the signature bits. :param Interest interest: The Interest object to be signed. This appends name components of SignatureInfo and the signature bits. :param Name certificateName: The certificate name of the key to use for signing. :param wireFormat: (optional) A WireFormat object used to encode the input. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # TODO: Handle signature algorithms other than Sha256WithRsa. signature = Sha256WithRsaSignature() signature.getKeyLocator().setType(KeyLocatorType.KEYNAME) signature.getKeyLocator().setKeyName(certificateName.getPrefix(-1)) # Append the encoded SignatureInfo. interest.getName().append(wireFormat.encodeSignatureInfo(signature)) # Append an empty signature so that the "signedPortion" is correct. interest.getName().append(Name.Component()) # Encode once to get the signed portion. encoding = interest.wireEncode(wireFormat) signedSignature = self.sign(encoding.toSignedBuffer(), certificateName) # Remove the empty signature and append the real one. interest.setName(interest.getName().getPrefix(-1).append( wireFormat.encodeSignatureValue(signedSignature)))
def signWithSha256(self, data, wireFormat=None): """ Wire encode the Data object, digest it and set its SignatureInfo to a DigestSha256. :param Data data: The Data object to be signed. This updates its signature and wireEncoding. :param wireFormat: (optional) A WireFormat object used to encode the input. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() data.setSignature(DigestSha256Signature()) # Encode once to get the signed portion. encoding = data.wireEncode(wireFormat) # Digest and set the signature. sha256 = hashes.Hash(hashes.SHA256(), backend=default_backend()) sha256.update(encoding.toSignedBytes()) signatureBits = sha256.finalize() data.getSignature().setSignature(Blob(bytearray(signatureBits), False)) # Encode again to include the signature. data.wireEncode(wireFormat)
def signWithSha256(self, data, wireFormat = None): """ Wire encode the Data object, digest it and set its SignatureInfo to a DigestSha256. :param Data data: The Data object to be signed. This updates its signature and wireEncoding. :param wireFormat: (optional) A WireFormat object used to encode the input. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() data.setSignature(DigestSha256Signature()) # Encode once to get the signed portion. encoding = data.wireEncode(wireFormat) # Get the bytes to sign. signedPortion = encoding.toSignedBuffer() if sys.version_info[0] == 2: # In Python 2.x, we need a str. Use Blob to convert signedPortion. signedPortion = Blob(signedPortion, False).toRawStr() # Digest and set the signature. data.getSignature().setSignature(Blob(SHA256.new(signedPortion).digest())) # Encode again to include the signature. data.wireEncode(wireFormat)
def signWithSha256(self, data, wireFormat = None): """ Wire encode the Data object, digest it and set its SignatureInfo to a DigestSha256. :param Data data: The Data object to be signed. This updates its signature and wireEncoding. :param wireFormat: (optional) A WireFormat object used to encode the input. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() data.setSignature(DigestSha256Signature()) # Encode once to get the signed portion. encoding = data.wireEncode(wireFormat) # Digest and set the signature. sha256 = hashes.Hash(hashes.SHA256(), backend=default_backend()) sha256.update(encoding.toSignedBytes()) signatureBits = sha256.finalize() data.getSignature().setSignature(Blob(bytearray(signatureBits), False)) # Encode again to include the signature. data.wireEncode(wireFormat)
def getLinkWireEncoding(self, wireFormat=None): """ Get the wire encoding of the link object. If there is already a wire encoding then return it. Otherwise encode from the link object (if available). :param WireFormat wireFormat: (optional) A WireFormat object used to encode the Link. If omitted, use WireFormat.getDefaultWireFormat(). :return: The wire encoding, or an isNull Blob if the link is not specified. :rtype: Blob :deprecated: Use getForwardingHint. """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if (not self._linkWireEncoding.isNull() and self._linkWireEncodingFormat == wireFormat): return self._linkWireEncoding link = self.getLink() if link != None: return link.wireEncode(wireFormat) else: return Blob()
def signInterestWithSha256(self, interest, wireFormat = None): """ Append a SignatureInfo for DigestSha256 to the Interest name, digest the name components and append a final name component with the signature bits (which is the digest). :param Interest interest: The Interest object to be signed. This appends name components of SignatureInfo and the signature bits. :param wireFormat: (optional) A WireFormat object used to encode the input. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() signature = DigestSha256Signature() # Append the encoded SignatureInfo. interest.getName().append(wireFormat.encodeSignatureInfo(signature)) # Append an empty signature so that the "signedPortion" is correct. interest.getName().append(Name.Component()) # Encode once to get the signed portion. encoding = interest.wireEncode(wireFormat) # Digest and set the signature. sha256 = hashes.Hash(hashes.SHA256(), backend=default_backend()) sha256.update(encoding.toSignedBytes()) signatureBits = sha256.finalize() signature.setSignature(Blob(bytearray(signatureBits), False)) # Remove the empty signature and append the real one. interest.setName(interest.getName().getPrefix(-1).append( wireFormat.encodeSignatureValue(signature)))
def signWithHmacWithSha256(target, key, wireFormat = None): """ Wire encode the target, compute an HmacWithSha256 and update the signature value. Note: This method is an experimental feature. The API may change. :param target: If this is a Data object, update its signature and wire encoding. :type target: Data :param Blob key: The key for the HmacWithSha256. :param wireFormat: (optional) The WireFormat for calling encodeData, etc., or WireFormat.getDefaultWireFormat() if omitted. :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(target, Data): data = target # Encode once to get the signed portion. encoding = data.wireEncode(wireFormat) signer = hmac.HMAC(key.toBytes(), hashes.SHA256(), backend = default_backend()) signer.update(encoding.toSignedBytes()) data.getSignature().setSignature( Blob(bytearray(signer.finalize()), False)) else: raise SecurityException("signWithHmacWithSha256: Unrecognized target type")
def putData(self, data, wireFormat=None): """ The OnInterest callback calls this to put a Data packet which satisfies an Interest. :param Data data: The Data packet which satisfies the interest. :param WireFormat wireFormat: (optional) A WireFormat object used to encode the Data packet. If omitted, use WireFormat.getDefaultWireFormat(). :throws: RuntimeError If the encoded Data packet size exceeds getMaxNdnPacketSize(). """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # We get the encoding now before calling send because it may dispatch to # asyncio to be called later, and the caller may modify data before then. encoding = data.wireEncode(wireFormat) if encoding.size() > self.getMaxNdnPacketSize(): raise RuntimeError( "The encoded Data packet size exceeds the maximum limit getMaxNdnPacketSize()" ) self.send(encoding)
def setLinkWireEncoding(self, encoding, wireFormat = None): """ Set the link wire encoding bytes, without decoding them. If there is a link object, set it to null. If you later call getLink(), it will decode the wireEncoding to create the link object. :param Blob encoding: The Blob with the bytes of the link wire encoding. If no link is specified, set to an empty Blob() or call unsetLink(). :param WireFormat wireFormat: The wire format of the encoding, to be used later if necessary to decode. If omitted, use WireFormat.getDefaultWireFormat(). :return: This Interest so that you can chain calls to update values. :rtype: Interest """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self._linkWireEncoding = encoding self._linkWireEncodingFormat = wireFormat # Clear the link object, assuming that it has a different encoding. self._link.set(None) self._changeCount += 1 return self
def getLinkWireEncoding(self, wireFormat = None): """ Get the wire encoding of the link object. If there is already a wire encoding then return it. Otherwise encode from the link object (if available). :param WireFormat wireFormat: (optional) A WireFormat object used to encode the Link. If omitted, use WireFormat.getDefaultWireFormat(). :return: The wire encoding, or an isNull Blob if the link is not specified. :rtype: Blob """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if (not self._linkWireEncoding.isNull() and self._linkWireEncodingFormat == wireFormat): return self._linkWireEncoding link = self.getLink() if link != None: return link.wireEncode(wireFormat) else: return Blob()
def verifyDataWithHmacWithSha256(data, key, wireFormat = None): """ Compute a new HmacWithSha256 for the target and verify it against the signature value. Note: This method is an experimental feature. The API may change. :param target: The Data object to verify. :type target: Data :param Blob key: The key for the HmacWithSha256. :param wireFormat: (optional) The WireFormat for calling encodeData, etc., or WireFormat.getDefaultWireFormat() if omitted. :type wireFormat: A subclass of WireFormat :return: True if the signature verifies, otherwise False. :rtype: bool """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # wireEncode returns the cached encoding if available. encoding = data.wireEncode(wireFormat) signer = hmac.HMAC(key.toBytes(), hashes.SHA256(), backend = default_backend()) signer.update(encoding.toSignedBytes()) newSignatureBits = Blob(bytearray(signer.finalize()), False) # Use the flexible Blob.equals operator. return newSignatureBits == data.getSignature().getSignature()
def verifyInterest( self, interest, onVerified, onVerifyFailed, stepCount = 0, wireFormat = None): """ Check the signature on the signed interest and call either onVerify or onVerifyFailed. We use callback functions because verify may fetch information to check the signature. :param Interest interest: The interest with the signature to check. :param onVerified: If the signature is verified, this calls onVerified(interest). :type onVerified: function object :param onVerifyFailed: If the signature check fails or can't find the public key, this calls onVerifyFailed(interest). :type onVerifyFailed: function object :param int stepCount: (optional) The number of verification steps that have been done. If omitted, use 0. """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if self._policyManager.requireVerify(interest): nextStep = self._policyManager.checkVerificationPolicy( interest, stepCount, onVerified, onVerifyFailed, wireFormat) if nextStep != None: self._face.expressInterest( nextStep.interest, self._makeOnCertificateData(nextStep), self._makeOnCertificateInterestTimeout( nextStep.retry, onVerifyFailed, interest, nextStep)) elif self._policyManager.skipVerifyAndTrust(interest): onVerified(interest) else: onVerifyFailed(interest)
def generate(self, interest, keyChain, certificateName, wireFormat=None): """ Append a timestamp component and a random value component to interest's name. This ensures that the timestamp is greater than the timestamp used in the previous call. Then use keyChain to sign the interest which appends a SignatureInfo component and a component with the signature bits. If the interest lifetime is not set, this sets it. :param Interest interest: The interest whose name is append with components. :param KeyChain keyChain: The KeyChain for calling sign. :param Name certificateName: The certificate name of the key to use for signing. :param wireFormat: (optional) A WireFormat object used to encode the SignatureInfo and to encode interest name for signing. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self.prepareCommandInterestName(interest, wireFormat) keyChain.sign(interest, certificateName, wireFormat) if (interest.getInterestLifetimeMilliseconds() == None or interest.getInterestLifetimeMilliseconds() < 0): # The caller has not set the interest lifetime, so set it here. interest.setInterestLifetimeMilliseconds(1000.0)
def generate(self, interest, keyChain, certificateName, wireFormat = None): """ Append a timestamp component and a random value component to interest's name. This ensures that the timestamp is greater than the timestamp used in the previous call. Then use keyChain to sign the interest which appends a SignatureInfo component and a component with the signature bits. If the interest lifetime is not set, this sets it. :param Interest interest: The interest whose name is append with components. :param KeyChain keyChain: The KeyChain for calling sign. :param Name certificateName: The certificate name of the key to use for signing. :param wireFormat: (optional) A WireFormat object used to encode the SignatureInfo and to encode interest name for signing. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self.prepareCommandInterestName(interest, wireFormat) keyChain.sign(interest, certificateName, wireFormat) if (interest.getInterestLifetimeMilliseconds() == None or interest.getInterestLifetimeMilliseconds()< 0): # The caller has not set the interest lifetime, so set it here. interest.setInterestLifetimeMilliseconds(1000.0)
def registerPrefix( self, prefix, onInterest, onRegisterFailed, flags = None, wireFormat = None): """ Register prefix with the connected NDN hub and call onInterest when a matching interest is received. :param Name prefix: The Name for the prefix to register which is NOT copied for this internal Node method. The Face registerPrefix is reponsible for making a copy for Node to use.. :param onInterest: A function object to call when a matching interest is received. :type onInterest: function object :param onRegisterFailed: A function object to call if failed to retrieve the connected hub's ID or failed to register the prefix. :type onRegisterFailed: function object :param ForwardingFlags flags: The flags for finer control of which interests are forwardedto the application. :param wireFormat: A WireFormat object used to encode the message. :type wireFormat: a subclass of WireFormat """ if flags == None: flags = ForwardingFlags() if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # Node.expressInterest requires a copy of the prefix. self._node.registerPrefix( prefix, onInterest, onRegisterFailed, flags, wireFormat)
def setLinkWireEncoding(self, encoding, wireFormat=None): """ Set the link wire encoding bytes, without decoding them. If there is a link object, set it to None. If you later call getLink(), it will decode the wireEncoding to create the link object. :param Blob encoding: The Blob with the bytes of the link wire encoding. If no link is specified, set to an empty Blob() or call unsetLink(). :param WireFormat wireFormat: The wire format of the encoding, to be used later if necessary to decode. If omitted, use WireFormat.getDefaultWireFormat(). :return: This Interest so that you can chain calls to update values. :rtype: Interest :deprecated: Use setForwardingHint. """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self._linkWireEncoding = encoding self._linkWireEncodingFormat = wireFormat # Clear the link object, assuming that it has a different encoding. self._link.set(None) self._changeCount += 1 return self
def verifyInterestSignature(interest, publicKeyOrCertificate, digestAlgorithm=None, wireFormat=None): """ Verify the Interest packet using the public key, where the last two name components are the SignatureInfo and signature bytes. This does not check the type of public key or digest algorithm against the type of SignatureInfo such as Sha256WithRsaSignature. :param Interest interest: The Interest packet to verify. :param publicKeyOrCertificate: The object containing the public key, or the public key DER which is used to make the PublicKey object, or the certificate containing the public key. :type publicKeyOrCertificate: Blob, or an object which is the same as the bytes() operator, or CertificateV2 :param digestAlgorithm: (optional) The digest algorithm. If omitted, use DigestAlgorithm.SHA256. :param WireFormat wireFormat: (optional) A WireFormat object used to encode the Interest packet. If omitted, use WireFormat.getDefaultWireFormat(). :raises: ValueError for an invalid public key type or digestAlgorithm. """ arg3 = digestAlgorithm arg4 = wireFormat if type(arg3) is int: digestAlgorithm = arg3 else: digestAlgorithm = None if isinstance(arg3, WireFormat): wireFormat = arg3 elif isinstance(arg4, WireFormat): wireFormat = arg4 else: wireFormat = None if isinstance(publicKeyOrCertificate, CertificateV2): try: publicKey = publicKeyOrCertificate.getPublicKey() except: return False else: publicKey = publicKeyOrCertificate if wireFormat == None: wireFormat = WireFormat.getDefaultWireFormat() signature = VerificationHelpers._extractSignature(interest, wireFormat) if signature == None: return False encoding = interest.wireEncode(wireFormat) return VerificationHelpers.verifySignature(encoding.toSignedBytes(), signature.getSignature(), publicKey, digestAlgorithm)
def checkVerificationPolicy(self, dataOrInterest, stepCount, onVerified, onVerifyFailed, wireFormat=None): """ Look in the IdentityStorage for the public key with the name in the KeyLocator (if available) and use it to verify the data packet or signed interest. If the public key can't be found, call onVerifyFailed. :param dataOrInterest: The Data object or interest with the signature to check. :type dataOrInterest: Data or Interest :param int stepCount: The number of verification steps that have been done, used to track the verification progress. :param onVerified: If the signature is verified, this calls onVerified(dataOrInterest). :type onVerified: function object :param onVerifyFailed: If the signature check fails, this calls onVerifyFailed(dataOrInterest). :type onVerifyFailed: function object :return: None for no further step for looking up a certificate chain. :rtype: ValidationRequest """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(dataOrInterest, Data): data = dataOrInterest # wireEncode returns the cached encoding if available. if self._verify(data.getSignature(), data.wireEncode()): onVerified(data) else: onVerifyFailed(data) elif isinstance(dataOrInterest, Interest): interest = dataOrInterest # Decode the last two name components of the signed interest signature = wireFormat.decodeSignatureInfoAndValue( interest.getName().get(-2).getValue().buf(), interest.getName().get(-1).getValue().buf()) # wireEncode returns the cached encoding if available. if self._verify(signature, interest.wireEncode()): onVerified(interest) else: onVerifyFailed(interest) else: raise RuntimeError( "checkVerificationPolicy: unrecognized type for dataOrInterest" ) # No more steps, so return a None. return None
def verifyInterestSignature( interest, publicKeyOrCertificate, digestAlgorithm = None, wireFormat = None): """ Verify the Interest packet using the public key, where the last two name components are the SignatureInfo and signature bytes. This does not check the type of public key or digest algorithm against the type of SignatureInfo such as Sha256WithRsaSignature. :param Interest interest: The Interest packet to verify. :param publicKeyOrCertificate: The object containing the public key, or the public key DER which is used to make the PublicKey object, or the certificate containing the public key. :type publicKeyOrCertificate: Blob, or an object which is the same as the bytes() operator, or CertificateV2 :param digestAlgorithm: (optional) The digest algorithm. If omitted, use DigestAlgorithm.SHA256. :param WireFormat wireFormat: (optional) A WireFormat object used to encode the Interest packet. If omitted, use WireFormat.getDefaultWireFormat(). :raises: ValueError for an invalid public key type or digestAlgorithm. """ arg3 = digestAlgorithm arg4 = wireFormat if type(arg3) is int: digestAlgorithm = arg3 else: digestAlgorithm = None if isinstance(arg3, WireFormat): wireFormat = arg3 elif isinstance(arg4, WireFormat): wireFormat = arg4 else: wireFormat = None if isinstance(publicKeyOrCertificate, CertificateV2): try: publicKey = publicKeyOrCertificate.getPublicKey() except: return False else: publicKey = publicKeyOrCertificate; if wireFormat == None: wireFormat = WireFormat.getDefaultWireFormat() signature = VerificationHelpers._extractSignature(interest, wireFormat) if signature == None: return False encoding = interest.wireEncode(wireFormat) return VerificationHelpers.verifySignature( encoding.toSignedBytes(), signature.getSignature(), publicKey, digestAlgorithm)
def signByCertificate(self, target, certificateName, wireFormat=None): """ Sign the target based on the certificateName. If it is a Data object, set its signature. If it is an array, return a signature object. :param target: If this is a Data object, wire encode for signing, update its signature and key locator field and wireEncoding. If it is an array, sign it and return a Signature object. :param Name certificateName: The Name identifying the certificate which identifies the signing key. :param wireFormat: (optional) The WireFormat for calling encodeData, or WireFormat.getDefaultWireFormat() if omitted. :type wireFormat: A subclass of WireFormat :return: The Signature object (only if the target is an array). :rtype: An object of a subclass of Signature """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(target, Data): data = target digestAlgorithm = [0] signature = self._makeSignatureByCertificate( certificateName, digestAlgorithm) data.setSignature(signature) # Encode once to get the signed portion. encoding = data.wireEncode(wireFormat) data.getSignature().setSignature( self._privateKeyStorage.sign( encoding.toSignedBuffer(), IdentityCertificate.certificateNameToPublicKeyName( certificateName), digestAlgorithm[0])) # Encode again to include the signature. data.wireEncode(wireFormat) else: digestAlgorithm = [0] signature = self._makeSignatureByCertificate( certificateName, digestAlgorithm) signature.setSignature( self._privateKeyStorage.sign( target, IdentityCertificate.certificateNameToPublicKeyName( certificateName), digestAlgorithm[0])) return signature
def _registerPrefixHelper(self, registeredPrefixId, prefixCopy, onInterest, onRegisterFailed, arg5=None, arg6=None, arg7=None): """ This is a protected helper method to do the work of registerPrefix to resolve the different overloaded forms. The registeredPrefixId is from getNextEntryId(). This has no return value and can be used in a callback. """ # arg5, arg6, arg7 may be: # OnRegisterSuccess, ForwardingFlags, WireFormat # OnRegisterSuccess, ForwardingFlags, None # OnRegisterSuccess, WireFormat, None # OnRegisterSuccess, None, None # ForwardingFlags, WireFormat, None # ForwardingFlags, None, None # WireFormat, None, None # None, None, None if isinstance(arg5, collections.Callable): onRegisterSuccess = arg5 else: onRegisterSuccess = None if isinstance(arg5, ForwardingFlags): flags = arg5 elif isinstance(arg6, ForwardingFlags): flags = arg6 else: flags = ForwardingFlags() if isinstance(arg5, WireFormat): wireFormat = arg5 elif isinstance(arg6, WireFormat): wireFormat = arg6 elif isinstance(arg7, WireFormat): wireFormat = arg7 else: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() return self._node.registerPrefix(registeredPrefixId, prefixCopy, onInterest, onRegisterFailed, onRegisterSuccess, flags, wireFormat, self._commandKeyChain, self._commandCertificateName, self)
def verifyInterest(self, interest, onVerified, onVerifyFailed, stepCount=0, wireFormat=None): """ Check the signature on the signed interest and call either onVerify or onVerifyFailed. We use callback functions because verify may fetch information to check the signature. :param Interest interest: The interest with the signature to check. :param onVerified: If the signature is verified, this calls onVerified(interest). NOTE: The library will log any exceptions raised by this callback, but for better error handling the callback should catch and properly handle any exceptions. :type onVerified: function object :param onVerifyFailed: If the signature check fails or can't find the public key, this calls onVerifyFailed(interest). NOTE: The library will log any exceptions raised by this callback, but for better error handling the callback should catch and properly handle any exceptions. :type onVerifyFailed: function object :param int stepCount: (optional) The number of verification steps that have been done. If omitted, use 0. """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if self._policyManager.requireVerify(interest): nextStep = self._policyManager.checkVerificationPolicy( interest, stepCount, onVerified, onVerifyFailed, wireFormat) if nextStep != None: self._face.expressInterest( nextStep.interest, self._makeOnCertificateData(nextStep), self._makeOnCertificateInterestTimeout( nextStep.retry, onVerifyFailed, interest, nextStep)) elif self._policyManager.skipVerifyAndTrust(interest): try: onVerified(interest) except: logging.exception("Error in onVerified") else: try: onVerifyFailed(interest) except: logging.exception("Error in onVerifyFailed")
def signByCertificate(self, target, certificateName, wireFormat = None): """ Sign the target based on the certificateName. If it is a Data object, set its signature. If it is an array, return a signature object. :param target: If this is a Data object, wire encode for signing, update its signature and key locator field and wireEncoding. If it is an array, sign it and return a Signature object. :param Name certificateName: The Name identifying the certificate which identifies the signing key. :param wireFormat: (optional) The WireFormat for calling encodeData, or WireFormat.getDefaultWireFormat() if omitted. :type wireFormat: A subclass of WireFormat :return: The Signature object (only if the target is an array). :rtype: An object of a subclass of Signature """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(target, Data): data = target digestAlgorithm = [0] signature = self._makeSignatureByCertificate( certificateName, digestAlgorithm) data.setSignature(signature) # Encode once to get the signed portion. encoding = data.wireEncode(wireFormat) data.getSignature().setSignature(self._privateKeyStorage.sign (encoding.toSignedBuffer(), IdentityCertificate.certificateNameToPublicKeyName(certificateName), digestAlgorithm[0])) # Encode again to include the signature. data.wireEncode(wireFormat) else: digestAlgorithm = [0] signature = self._makeSignatureByCertificate( certificateName, digestAlgorithm) signature.setSignature( self._privateKeyStorage.sign( target, IdentityCertificate.certificateNameToPublicKeyName(certificateName), digestAlgorithm[0])) return signature
def wireEncode(self, wireFormat=None): """ Encode this EncryptedContent for a particular wire format. :param wireFormat: (optional) A WireFormat object used to encode this EncryptedContent. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: The encoded buffer. :rtype: Blob """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() return wireFormat.encodeEncryptedContent(self)
def wireEncodeV2(self, wireFormat = None): """ Encode this to an EncryptedContent v2 for a particular wire format. :param wireFormat: (optional) A WireFormat object used to encode this EncryptedContent. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: The encoded buffer. :rtype: Blob """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() return wireFormat.encodeEncryptedContentV2(self)
def getFullName(self, wireFormat=None): """ Get the Data packet's full name, which includes the final ImplicitSha256Digest component based on the wire encoding for a particular wire format. :param wireFormat: (optional) A WireFormat object used to encode this object. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: The full name. You must not change the Name object - if you need to change it then make a copy. :rtype: Name """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # The default full name depends on the default wire encoding. if (not self.getDefaultWireEncoding().isNull() and self._defaultFullName.size() > 0 and self.getDefaultWireEncodingFormat() == wireFormat): # We already have a full name. A non-null default wire encoding # means that the Data packet fields have not changed. return self._defaultFullName fullName = Name(self.getName()) sha256 = hashes.Hash(hashes.SHA256(), backend=default_backend()) sha256.update(self.wireEncode(wireFormat).toBytes()) fullName.appendImplicitSha256Digest( Blob(bytearray(sha256.finalize()), False)) if wireFormat == WireFormat.getDefaultWireFormat(): # wireEncode has already set defaultWireEncodingFormat_. self._defaultFullName = fullName return fullName
def getFullName(self, wireFormat = None): """ Get the Data packet's full name, which includes the final ImplicitSha256Digest component based on the wire encoding for a particular wire format. :param wireFormat: (optional) A WireFormat object used to encode this object. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: The full name. You must not change the Name object - if you need to change it then make a copy. :rtype: Name """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # The default full name depends on the default wire encoding. if (not self.getDefaultWireEncoding().isNull() and self._defaultFullName.size() > 0 and self.getDefaultWireEncodingFormat() == wireFormat): # We already have a full name. A non-null default wire encoding # means that the Data packet fields have not changed. return self._defaultFullName fullName = Name(self.getName()) sha256 = hashes.Hash(hashes.SHA256(), backend=default_backend()) sha256.update(self.wireEncode(wireFormat).toBytes()) fullName.appendImplicitSha256Digest( Blob(bytearray(sha256.finalize()), False)) if wireFormat == WireFormat.getDefaultWireFormat(): # wireEncode has already set defaultWireEncodingFormat_. self._defaultFullName = fullName return fullName
def wireEncode(self, wireFormat = None): """ Encode this ControlResponse for a particular wire format. :param wireFormat: (optional) A WireFormat object used to encode this ControlParameters. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: The encoded buffer. :rtype: Blob """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() return wireFormat.encodeControlResponse(self)
def checkVerificationPolicy(self, dataOrInterest, stepCount, onVerified, onVerifyFailed, wireFormat=None): """ Look in the IdentityStorage for the public key with the name in the KeyLocator (if available) and use it to verify the data packet or signed interest. If the public key can't be found, call onVerifyFailed. :param dataOrInterest: The Data object or interest with the signature to check. :type dataOrInterest: Data or Interest :param int stepCount: The number of verification steps that have been done, used to track the verification progress. :param onVerified: If the signature is verified, this calls onVerified(dataOrInterest). :type onVerified: function object :param onVerifyFailed: If the signature check fails, this calls onVerifyFailed(dataOrInterest). :type onVerifyFailed: function object :return: None for no further step for looking up a certificate chain. :rtype: ValidationRequest """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(dataOrInterest, Data): data = dataOrInterest # wireEncode returns the cached encoding if available. if self._verify(data.getSignature(), data.wireEncode()): onVerified(data) else: onVerifyFailed(data) elif isinstance(dataOrInterest, Interest): interest = dataOrInterest # Decode the last two name components of the signed interest signature = wireFormat.decodeSignatureInfoAndValue( interest.getName().get(-2).getValue().buf(), interest.getName().get(-1).getValue().buf() ) # wireEncode returns the cached encoding if available. if self._verify(signature, interest.wireEncode()): onVerified(interest) else: onVerifyFailed(interest) else: raise RuntimeError("checkVerificationPolicy: unrecognized type for dataOrInterest") # No more steps, so return a None. return None
def generate(self, interest, keyChain, certificateName, wireFormat = None): """ Append a timestamp component and a random value component to interest's name. This ensures that the timestamp is greater than the timestamp used in the previous call. Then use keyChain to sign the interest which appends a SignatureInfo component and a component with the signature bits. If the interest lifetime is not set, this sets it. :param Interest interest: The interest whose name is append with components. :param KeyChain keyChain: The KeyChain for calling sign. :param Name certificateName: The certificate name of the key to use for signing. :param wireFormat: (optional) A WireFormat object used to encode the SignatureInfo and to encode interest name for signing. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() timestamp = round(Common.getNowMilliseconds()) while timestamp <= self._lastTimestamp: timestamp += 1.0 # The timestamp is encoded as a TLV nonNegativeInteger. encoder = TlvEncoder(8) encoder.writeNonNegativeInteger(int(timestamp)) interest.getName().append(Blob(encoder.getOutput(), False)) # The random value is a TLV nonNegativeInteger too, but we know it is 8 # bytes, so we don't need to call the nonNegativeInteger encoder. randomBuffer = bytearray(8) for i in range(len(randomBuffer)): randomBuffer[i] = _systemRandom.randint(0, 0xff) interest.getName().append(Blob(randomBuffer, False)) keyChain.sign(interest, certificateName, wireFormat) if (interest.getInterestLifetimeMilliseconds() == None or interest.getInterestLifetimeMilliseconds()< 0): # The caller has not set the interest lifetime, so set it here. interest.setInterestLifetimeMilliseconds(1000.0) # We successfully signed the interest, so update the timestamp. self._lastTimestamp = timestamp
def generate(self, interest, keyChain, certificateName, wireFormat=None): """ Append a timestamp component and a random value component to interest's name. This ensures that the timestamp is greater than the timestamp used in the previous call. Then use keyChain to sign the interest which appends a SignatureInfo component and a component with the signature bits. If the interest lifetime is not set, this sets it. :param Interest interest: The interest whose name is append with components. :param KeyChain keyChain: The KeyChain for calling sign. :param Name certificateName: The certificate name of the key to use for signing. :param wireFormat: (optional) A WireFormat object used to encode the SignatureInfo and to encode interest name for signing. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() timestamp = round(Common.getNowMilliseconds()) while timestamp <= self._lastTimestamp: timestamp += 1.0 # The timestamp is encoded as a TLV nonNegativeInteger. encoder = TlvEncoder(8) encoder.writeNonNegativeInteger(int(timestamp)) interest.getName().append(Blob(encoder.getOutput(), False)) # The random value is a TLV nonNegativeInteger too, but we know it is 8 # bytes, so we don't need to call the nonNegativeInteger encoder. randomBuffer = bytearray(8) for i in range(len(randomBuffer)): randomBuffer[i] = _systemRandom.randint(0, 0xff) interest.getName().append(Blob(randomBuffer, False)) keyChain.sign(interest, certificateName, wireFormat) if (interest.getInterestLifetimeMilliseconds() == None or interest.getInterestLifetimeMilliseconds() < 0): # The caller has not set the interest lifetime, so set it here. interest.setInterestLifetimeMilliseconds(1000.0) # We successfully signed the interest, so update the timestamp. self._lastTimestamp = timestamp
def putData(self, data, wireFormat = None): """ The OnInterest callback calls this to put a Data packet which satisfies an Interest. :param Data data: The Data packet which satisfies the interest. :param WireFormat wireFormat: (optional) A WireFormat object used to encode the Data packet. If omitted, use WireFormat.getDefaultWireFormat(). :throws: RuntimeError If the encoded Data packet size exceeds getMaxNdnPacketSize(). """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self._node.putData(data, wireFormat)
def _registerPrefixHelper( self, registeredPrefixId, prefixCopy, onInterest, onRegisterFailed, flags = None, wireFormat = None): """ This is a protected helper method to do the work of registerPrefix to resolve the different overloaded forms. The registeredPrefixId is from getNextEntryId(). This has no return value and can be used in a callback. """ if flags == None: flags = ForwardingFlags() if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() return self._node.registerPrefix( registeredPrefixId, prefixCopy, onInterest, onRegisterFailed, flags, wireFormat, self._commandKeyChain, self._commandCertificateName, self)
def wireDecode(self, input, wireFormat=None): """ Decode the input using a particular wire format and update this ForwardingEntry. :param input: The array with the bytes to decode. :type input: An array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this ForwardingEntry. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # If input is a blob, get its buf(). decodeBuffer = input.buf() if isinstance(input, Blob) else input wireFormat.decodeForwardingEntry(self, decodeBuffer)
def wireDecode(self, input, wireFormat = None): """ Decode the input using a particular wire format and update this ControlResponse. :param input: The array with the bytes to decode. :type input: An array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this ControlParameters. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # If input is a blob, get its buf(). decodeBuffer = input.buf() if isinstance(input, Blob) else input wireFormat.decodeControlResponse(self, decodeBuffer)
def makeCommandInterest(self, name, params=None, wireFormat=None): """ Append the timestamp and nonce name components to the supplied name, create an Interest object and signs it with the KeyChain given to the constructor. This ensures that the timestamp is greater than the timestamp used in the previous call. :param Name name: The Name for the Interest, which is copied. :param SigningInfo params: (optional) The signing parameters. If omitted, use a default SigningInfo(). :param WireFormat wireFormat: (optional) A WireFormat object used to encode the SignatureInfo and to encode interest name for signing. If omitted, use WireFormat getDefaultWireFormat(). :return: The new command Interest object. :rtype: Interest """ arg2 = params arg3 = wireFormat if isinstance(arg2, SigningInfo): params = arg2 else: params = None if isinstance(arg2, WireFormat): wireFormat = arg2 elif isinstance(arg3, WireFormat): wireFormat = arg3 else: wireFormat = None if params == None: params = SigningInfo() if wireFormat == None: wireFormat = WireFormat.getDefaultWireFormat() # This copies the Name. commandInterest = Interest(name) self.prepareCommandInterestName(commandInterest, wireFormat) self._keyChain.sign(commandInterest, params, wireFormat) return commandInterest
def _registerPrefixHelper( self, registeredPrefixId, prefixCopy, onInterest, onRegisterFailed, arg5 = None, arg6 = None, arg7 = None): """ This is a protected helper method to do the work of registerPrefix to resolve the different overloaded forms. The registeredPrefixId is from getNextEntryId(). This has no return value and can be used in a callback. """ # arg5, arg6, arg7 may be: # OnRegisterSuccess, RegistrationOptions, WireFormat # OnRegisterSuccess, RegistrationOptions, None # OnRegisterSuccess, WireFormat, None # OnRegisterSuccess, None, None # RegistrationOptions, WireFormat, None # RegistrationOptions, None, None # WireFormat, None, None # None, None, None if isinstance(arg5, collections.Callable): onRegisterSuccess = arg5 else: onRegisterSuccess = None if isinstance(arg5, RegistrationOptions): registrationOptions = arg5 elif isinstance(arg6, RegistrationOptions): registrationOptions = arg6 else: registrationOptions = RegistrationOptions() if isinstance(arg5, WireFormat): wireFormat = arg5 elif isinstance(arg6, WireFormat): wireFormat = arg6 elif isinstance(arg7, WireFormat): wireFormat = arg7 else: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() return self._node.registerPrefix( registeredPrefixId, prefixCopy, onInterest, onRegisterFailed, onRegisterSuccess, registrationOptions, wireFormat, self._commandKeyChain, self._commandCertificateName, self)
def registerPrefix( self, prefix, onInterest, onRegisterFailed, flags = None, wireFormat = None): """ Register prefix with the connected NDN hub and call onInterest when a matching interest is received. If you have not called setCommandSigningInfo, this assumes you are connecting to NDNx. If you have called setCommandSigningInfo, this first sends an NFD registration request, and if that times out then this sends an NDNx registration request. If need to register a prefix with NFD, you must first call setCommandSigningInfo. :param Name prefix: The Name for the prefix to register which is NOT copied for this internal Node method. The Face registerPrefix is reponsible for making a copy for Node to use.. :param onInterest: When an interest is received which matches the name prefix, this calls onInterest(prefix, interest, transport, registeredPrefixId). NOTE: You must not change the prefix object - if you need to change it then make a copy. :type onInterest: function object :param onRegisterFailed: If register prefix fails for any reason, this calls onRegisterFailed(prefix). :type onRegisterFailed: function object :param ForwardingFlags flags: The flags for finer control of which interests are forwardedto the application. :param wireFormat: (optional) A WireFormat object used to encode this ControlParameters. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :raises: This raises an exception if setCommandSigningInfo has not been called to set the KeyChain, etc. for signing the command interest. """ if flags == None: flags = ForwardingFlags() if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() # Node.expressInterest requires a copy of the prefix. self._node.registerPrefix( prefix, onInterest, onRegisterFailed, flags, wireFormat, self._commandKeyChain, self._commandCertificateName)
def wireDecode(self, input, wireFormat=None): """ Decode the input using a particular wire format and update this EncryptedContent. :param input: The array with the bytes to decode. :type input: A Blob or an array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this EncryptedContent. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(input, Blob): # Input is a blob, so get its buf() and set copy False. wireFormat.decodeEncryptedContent(self, input.buf(), False) else: wireFormat.decodeEncryptedContent(self, input, True)
def wireDecode(self, input, wireFormat = None): """ Decode the input using a particular wire format and update this DelegationSet. :param input: The array with the bytes to decode. :type input: A Blob or an array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this DelegationSet. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() if isinstance(input, Blob): # Input is a blob, so get its buf() and set copy False. wireFormat.decodeDelegationSet(self, input.buf(), False) else: wireFormat.decodeDelegationSet(self, input, True)
def makeCommandInterest(self, interest, wireFormat = None): """ Append a timestamp component and a random value component to interest's name. Then use the keyChain and certificateName from setCommandSigningInfo to sign the interest. If the interest lifetime is not set, this sets it. :param Interest interest: The interest whose name is append with components. :param wireFormat: (optional) A WireFormat object used to encode the SignatureInfo and to encode interest name for signing. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self._node.makeCommandInterest( interest, self._commandKeyChain, self._commandCertificateName, wireFormat)
def __init__(self, arg1, privateKeyBag = None, publicKeyEncoding = None, password = None, digestAlgorithm = DigestAlgorithm.SHA256, wireFormat = None): if isinstance(arg1, Name): keyName = arg1 if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self._certificate = SafeBag._makeSelfSignedCertificate( keyName, privateKeyBag, publicKeyEncoding, password, digestAlgorithm, wireFormat) self._privateKeyBag = privateKeyBag elif isinstance(arg1, Data): # The certificate is supplied. self._certificate = Data(arg1) self._privateKeyBag = privateKeyBag else: # Assume the first argument is the encoded SafeBag. self.wireDecode(arg1)
def getKeyLocatorName(dataOrInterest, state): """ Extract the KeyLocator Name from a Data or signed Interest packet. The SignatureInfo in the packet must contain a KeyLocator of type KEYNAME. Otherwise, state.fail is invoked with INVALID_KEY_LOCATOR. :param dataOrInterest: The Data or Interest packet with the KeyLocator. :type dataOrInterest: Data or Interest :param ValidationState state: On error, this calls state.fail and returns an empty Name. :return: The KeyLocator name, or an empty Name for failure. :rtype: Name """ if isinstance(dataOrInterest, Data): data = dataOrInterest return ValidationPolicy._getKeyLocatorNameFromSignature( data.getSignature(), state) else: interest = dataOrInterest name = interest.getName() if name.size() < 2: state.fail( ValidationError(ValidationError.INVALID_KEY_LOCATOR, "Invalid signed Interest: name too short")) return Name() try: # TODO: Generalize the WireFormat. signatureInfo = WireFormat.getDefaultWireFormat( ).decodeSignatureInfoAndValue( interest.getName().get(-2).getValue().buf(), interest.getName().get(-1).getValue().buf()) except Exception as ex: state.fail( ValidationError(ValidationError.INVALID_KEY_LOCATOR, "Invalid signed Interest: " + repr(ex))) return Name() return ValidationPolicy._getKeyLocatorNameFromSignature( signatureInfo, state)
def __init__(self, keyNameOrCertificate, privateKeyBag, publicKeyEncoding=None, password=None, digestAlgorithm=DigestAlgorithm.SHA256, wireFormat=None): if isinstance(keyNameOrCertificate, Name): keyName = keyNameOrCertificate if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() self._certificate = SafeBag._makeSelfSignedCertificate( keyName, privateKeyBag, publicKeyEncoding, password, digestAlgorithm, wireFormat) self._privateKeyBag = privateKeyBag else: # The certificate is supplied. self._certificate = Data(keyNameOrCertificate) self._privateKeyBag = privateKeyBag
def wireDecode(self, input, wireFormat=None): """ Override to call the base class wireDecode then populate the list of delegations from the content. :param input: The array with the bytes to decode. :type input: A Blob or an array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this DelegationSet. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() Data.wireDecode(self, input, wireFormat) if self.getMetaInfo().getType() != ContentType.LINK: raise RuntimeError( "Link.wireDecode: MetaInfo ContentType is not LINK.") self._delegations.wireDecode(self.getContent())
def wireDecode(self, input, wireFormat = None): """ Override to call the base class wireDecode then populate the list of delegations from the content. :param input: The array with the bytes to decode. :type input: A Blob or an array type with int elements :param wireFormat: (optional) A WireFormat object used to decode this DelegationSet. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() Data.wireDecode(self, input, wireFormat) if self.getMetaInfo().getType() != ContentType.LINK: raise RuntimeError( "Link.wireDecode: MetaInfo ContentType is not LINK.") self._delegations.wireDecode(self.getContent())
def signInterestByCertificate(self, interest, certificateName, wireFormat=None): """ Append a SignatureInfo to the Interest name, sign the name components and append a final name component with the signature bits. :param Interest interest: The Interest object to be signed. This appends name components of SignatureInfo and the signature bits. :param Name certificateName: The certificate name of the key to use for signing. :param wireFormat: (optional) A WireFormat object used to encode the input. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() digestAlgorithm = [0] signature = self._makeSignatureByCertificate(certificateName, digestAlgorithm) # Append the encoded SignatureInfo. interest.getName().append(wireFormat.encodeSignatureInfo(signature)) # Append an empty signature so that the "signedPortion" is correct. interest.getName().append(Name.Component()) # Encode once to get the signed portion, and sign. encoding = interest.wireEncode(wireFormat) signature.setSignature( self._privateKeyStorage.sign( encoding.toSignedBuffer(), IdentityCertificate.certificateNameToPublicKeyName( certificateName), digestAlgorithm[0])) # Remove the empty signature and append the real one. interest.setName(interest.getName().getPrefix(-1).append( wireFormat.encodeSignatureValue(signature)))
def removeDelegation(self, name, wireFormat = None): """ Remove every delegation with the given name. Re-encode this object's content using the optional wireFormat. :param Name name: Then name to match the name of the delegation(s) to be removed. :param wireFormat: (optional) A WireFormat object used to encode the DelegationSet. If omitted, use WireFormat.getDefaultWireFormat(). :type wireFormat: A subclass of WireFormat :return: True if a delegation was removed, otherwise False. :rtype: bool """ if wireFormat == None: # Don't use a default argument since getDefaultWireFormat can change. wireFormat = WireFormat.getDefaultWireFormat() wasRemoved = self._delegations.remove(name) if wasRemoved: self.encodeContent(wireFormat) return wasRemoved