def fill(self, d):
     """
     """
     self._d = d
     idx = 0
     self.version, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
     self.alg, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
     self.s2k, idx = S2K.strcalc_s2k(d[idx:], idx)
Beispiel #2
0
    def fill(self, d):
        self._d = d
        idx = 0
        __version_d = d[idx:idx+1]
        self.version, idx = STN.strcalc(STN.str2int, __version_d, idx)

        if self.version in [2, 3, 4]:
            __created_d = d[idx:idx+4] 
            self.created, idx = STN.strcalc(STN.str2int, __created_d, idx)

            if self.version in [2, 3]:
                self.__expires_d = d[idx:idx+2]
                self.expires, idx = STN.strcalc(STN.str2int, self.__expires_d, idx)

            __alg_d = d[idx:idx+1]
            self.alg, idx = STN.strcalc(STN.str2int, __alg_d, idx)

            # resolve MPIs
            if self.alg in [ASYM_RSA_EOS, ASYM_RSA_E, ASYM_RSA_S]:
                self.RSA_n, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.RSA_e, idx = MPI.strcalc_mpi(d[idx:], idx)
                self._mpi_d = self.RSA_n._d + self.RSA_e._d
            elif ASYM_DSA == self.alg:
                self.DSA_p, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.DSA_q, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.DSA_g, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.DSA_y, idx = MPI.strcalc_mpi(d[idx:], idx)
                self._mpi_d = self.DSA_p._d + self.DSA_q._d + self.DSA_g._d + self.DSA_y._d
            elif self.alg in [ASYM_ELGAMAL_E, ASYM_ELGAMAL_EOS]:
                self.ELGAMAL_p, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.ELGAMAL_g, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.ELGAMAL_y, idx = MPI.strcalc_mpi(d[idx:], idx)
                self._mpi_d = self.ELGAMAL_p._d + self.ELGAMAL_g._d + self.ELGAMAL_y._d
            else:
                raise NotImplementedError("Unsupported key algorithm. Received alg->(%s)" % self.alg)

            # set fingerprint
            if self.version in [2, 3]:
                integer_data = self.RSA_n._int_d + self.RSA_e._int_d
                self.fingerprint = md5.new(integer_data).hexdigest().upper()
                # see fingerprint/id notes in doc/NOTES.txt
                self.id = STN.str2hex(self.RSA_n._int_d[-8:])
            elif 4 == self.version:
                f = ['\x99']
                f_data = ''.join([__version_d, __created_d, __alg_d, self._mpi_d])
                length = len(f_data)
                hi = (chr((0xffff & length) >> 8)) # high order packet length
                lo = (chr(0xff & length)) # low order packet length
                f.append(hi + lo) 
                f.append(f_data)
                self.fingerprint = sha.new(''.join(f)).hexdigest().upper()
                # see fingerprint/id notes in doc/NOTES.txt
                self.id = self.fingerprint[-16:]

        else: # unsupported packet version
            raise NotImplementedError("Unsupported key version: %s" % self.version)
        return idx
Beispiel #3
0
    def fill(self, d):
        self._d = d
        self.format = d[0:1]
        self.fnlen = STN.str2int(d[1:2])
        idx = 2

        if 0 < self.fnlen:
            self.filename, idx = STN.strcalc(None, d[idx:idx+self.fnlen], idx)
        else:
            self.filename = None

        self.modified, idx = STN.strcalc(STN.str2int, d[idx:idx+4], idx)
        self.data = d[idx:]
    def fill(self, d):
        self._d = d
        idx = 0
        self.version, idx = STN.strcalc(STN.str2int, d[idx:idx + 1], idx)
        self.keyid, idx = STN.strcalc(STN.str2hex, d[idx:idx + 8], idx)
        self.alg_pubkey, idx = STN.strcalc(STN.str2int, d[idx:idx + 1], idx)

        if self.alg_pubkey in [ASYM_RSA_EOS, ASYM_RSA_E, ASYM_RSA_S]:
            self.RSA_me_modn, idx = MPI.strcalc_mpi(d[idx:], idx)

        elif ASYM_ELGAMAL_E == self.alg_pubkey:
            self.ELGAMAL_gk_modp, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.ELGAMAL_myk_modp, idx = MPI.strcalc_mpi(d[idx:], idx)

        else:
            raise PGPValueError, "Unsupported public key algorithm. Received alg_pubkey->(%s)" % self.alg_pubkey
    def fill(self, d):
        self._d = d
        idx = 0
        self.version, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
        self.keyid, idx = STN.strcalc(STN.str2hex, d[idx:idx+8], idx) 
        self.alg_pubkey, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)

        if self.alg_pubkey in [ASYM_RSA_EOS, ASYM_RSA_E, ASYM_RSA_S]:
            self.RSA_me_modn, idx = MPI.strcalc_mpi(d[idx:], idx)

        elif ASYM_ELGAMAL_E == self.alg_pubkey:
            self.ELGAMAL_gk_modp, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.ELGAMAL_myk_modp, idx = MPI.strcalc_mpi(d[idx:], idx)

        else:
            raise PGPValueError, "Unsupported public key algorithm. Received alg_pubkey->(%s)" % self.alg_pubkey
Beispiel #6
0
    def fill(self, d):
        """
        """
        idx = 0
        self.type, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
        self.alg_hash, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)

        if self.type in [0x01, 0x03]:
            self.salt, idx = STN.strcalc(None, d[idx:idx+8], idx)

            if 0x03 == self.type:
                c, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
                self.count_code = c
                self.count = (16 + (c & 15)) << ((c >> 4) + 6)

        self._d = d[0:idx]
        #hexify = lambda s: ''.join(['\\x%s' % hex(ord(c))[2:].zfill(2) for c in s])
        #print hexify(self._d)
        self.size = len(self._d)
Beispiel #7
0
    def fill(self, d):
        idx = PublicKeyBody.fill(self, d)
        self._private_idx = idx # marks start of private data

        self.s2k_usg, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)

        if 0 == self.s2k_usg: # unencrypted MPIs
            self.__resolve_secmpi(idx)

        else:

            if self.s2k_usg in [254, 255]: # encrypted MPIs
                self.alg_sym, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
                self.s2k, idx = S2K.strcalc_s2k(d[idx:], idx)

                if 0 == self.alg_sym: # plaintext or unencrypted data
                    self.__resolve_secmpi(idx)
                    return
                elif 1 == self.alg_sym: # IDEA [IDEA]
                    self.iv, idx = STN.strcalc(None, d[idx:idx+8], idx)
                elif 2 == self.alg_sym: # Triple-DES DES-EDE, 168 bit key derived from 192
                    raise NotImplementedError, "3DES"
                elif 3 == self.alg_sym: # CAST5 (128 bit key, as per RFC2144)
                    self.iv, idx = STN.strcalc(None, d[idx:idx+8], idx)
                elif 4 == self.alg_sym: # Blowfish (128 bit key, 16 rounds)
                    self.iv, idx = STN.strcalc(None, d[idx:idx+8], idx)
                elif self.alg_sym in [5, 6]: # Reserved
                    raise NotImplementedError, "Reserved"
                elif 7 == self.alg_sym: # AES with 128-bit key [AES]
                    raise NotImplementedError, "AES 128"
                elif 8 == self.alg_sym: # AES with 192-bit key
                    raise NotImplementedError, "AES 192"
                elif 9 == self.alg_sym: # AES with 256-bit key
                    raise NotImplementedError, "AES 256"
                elif 10 == self.alg_sym: # Twofish with 256-bit key [TWOFISH]
                    raise NotImplementedError, "Twofish"
                elif self.alg_sym in range(100, 111): #100-110 Private/Experimental
                    raise NotImplementedError, "Private/Experimental"
                else:
                    raise ValueError, "Unsupported symmetric encryption algorithm->(%s)" % (str(self.alg_sym))

            else: # s2k usage specifies the symmetric algorithm
                self.alg_sym = self.s2k_usg
                self.iv, idx = STN.strcalc(None, d[idx:idx+8], idx)

            # encrypted data: MPIs + chksum/hash
            if 3 == self.version and self.s2k_usg in [254, 255]:
                if 255 == self.s2k_usg: # checksum is stored in the clear
                    self._enc_d = d[:-2]
                    self.chksum = d[-2:]
                elif 254 == self.s2k_usg: # nothing was specifically mentioned
                    self._enc_d = d[:-20] # about SHA1 in v3/RSA keys, but this
                    self.chksum = d[-20:] # should make sense given the above
            else:
                self._enc_d = d[idx:]
Beispiel #8
0
    def fill(self, d):
        import struct
        idx = 0
        self._length_d, idx = STN.strcalc(None, d[idx:idx+2], idx)

        self.bit_length = STN.str2int(self._length_d)
        self.length = STN.mpilen2int(self._length_d)

        self._d = d[0:2+self.length]
        self._int_d = d[idx:idx+self.length]
        self.size = len(self._d) # explicitly..

        i = struct.unpack('>'+str(len(self._int_d))+'s', self._int_d)[0]
        self.value = STN.str2int(i) 

        if self.check():
            pass
        else:
            raise self.err[0], self.err[1]
Beispiel #9
0
    def fill(self, d):
        import struct
        idx = 0
        self._length_d, idx = STN.strcalc(None, d[idx:idx + 2], idx)

        self.bit_length = STN.str2int(self._length_d)
        self.length = STN.mpilen2int(self._length_d)

        self._d = d[0:2 + self.length]
        self._int_d = d[idx:idx + self.length]
        self.size = len(self._d)  # explicitly..

        i = struct.unpack('>' + str(len(self._int_d)) + 's', self._int_d)[0]
        self.value = STN.str2int(i)

        if self.check():
            pass
        else:
            raise self.err[0], self.err[1]
Beispiel #10
0
    def __resolve_secmpi(self, idx):
        d = self._d
        # 1:RSA (Encrypt or Sign), 2:RSA Encrypt-Only, 3:RSA Sign-Only
        if self.alg in [1, 2, 3]:
            self.RSA_d, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.RSA_p, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.RSA_q, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.RSA_u, idx = MPI.strcalc_mpi(d[idx:], idx)
            self._secmpi_d = self.RSA_d._d + self.RSA_p._d + self.RSA_q._d + self.RSA_u._d
        # 17:DSA (Digital Signature Algorithm)
        elif 17 == self.alg:
            self.DSA_x, idx = MPI.strcalc_mpi(d[idx:], idx)
            self._secmpi_d = self.DSA_x._d
        # 16:Elgamal (Encrypt-Only), 20:Elgamal (Encrypt or Sign)
        elif self.alg in [16, 20]:
            self.ELGAMAL_x, idx = MPI.strcalc_mpi(d[idx:], idx)
            self._secmpi_d = self.ELGAMAL_x._d
        else:
            self.err = (ValueError, "Unsupported key algorithm. Received alg->(%s)" % (str(self.alg)))

        if 255 == self.s2k_usg:
            self.chksum, idx = STN.strcalc(STN.str2int, d[idx:idx+2], idx)
        else:
            self.chksum = None
Beispiel #11
0
    def fill(self, d):
        self._d = d
        idx = 0
        __version_d = d[idx:idx + 1]
        self.version, idx = STN.strcalc(STN.str2int, __version_d, idx)

        if self.version in [2, 3, 4]:
            __created_d = d[idx:idx + 4]
            self.created, idx = STN.strcalc(STN.str2int, __created_d, idx)

            if self.version in [2, 3]:
                self.__expires_d = d[idx:idx + 2]
                self.expires, idx = STN.strcalc(STN.str2int, self.__expires_d,
                                                idx)

            __alg_d = d[idx:idx + 1]
            self.alg, idx = STN.strcalc(STN.str2int, __alg_d, idx)

            # resolve MPIs
            if self.alg in [ASYM_RSA_EOS, ASYM_RSA_E, ASYM_RSA_S]:
                self.RSA_n, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.RSA_e, idx = MPI.strcalc_mpi(d[idx:], idx)
                self._mpi_d = self.RSA_n._d + self.RSA_e._d
            elif ASYM_DSA == self.alg:
                self.DSA_p, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.DSA_q, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.DSA_g, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.DSA_y, idx = MPI.strcalc_mpi(d[idx:], idx)
                self._mpi_d = self.DSA_p._d + self.DSA_q._d + self.DSA_g._d + self.DSA_y._d
            elif self.alg in [ASYM_ELGAMAL_E, ASYM_ELGAMAL_EOS]:
                self.ELGAMAL_p, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.ELGAMAL_g, idx = MPI.strcalc_mpi(d[idx:], idx)
                self.ELGAMAL_y, idx = MPI.strcalc_mpi(d[idx:], idx)
                self._mpi_d = self.ELGAMAL_p._d + self.ELGAMAL_g._d + self.ELGAMAL_y._d
            else:
                raise NotImplementedError(
                    "Unsupported key algorithm. Received alg->(%s)" % self.alg)

            # set fingerprint
            if self.version in [2, 3]:
                integer_data = self.RSA_n._int_d + self.RSA_e._int_d
                self.fingerprint = md5.new(integer_data).hexdigest().upper()
                # see fingerprint/id notes in doc/NOTES.txt
                self.id = STN.str2hex(self.RSA_n._int_d[-8:])
            elif 4 == self.version:
                f = ['\x99']
                f_data = ''.join(
                    [__version_d, __created_d, __alg_d, self._mpi_d])
                length = len(f_data)
                hi = (chr((0xffff & length) >> 8))  # high order packet length
                lo = (chr(0xff & length))  # low order packet length
                f.append(hi + lo)
                f.append(f_data)
                self.fingerprint = sha.new(''.join(f)).hexdigest().upper()
                # see fingerprint/id notes in doc/NOTES.txt
                self.id = self.fingerprint[-16:]

        else:  # unsupported packet version
            raise NotImplementedError("Unsupported key version: %s" %
                                      self.version)
        return idx
Beispiel #12
0
    def fill(self, d):
        """Set the Packet instances's data, filling its attributes.

        :Parameters:
            - `d`: string of OpenPGP packet data

        :Returns: Nothing
 
        Tag data (d) must be a string of valid OpenPGP packet data
        (tag, length, body, and possibly partial length/body 
        interlacing).

        Example:

            >>> tag = chr(0xb4) # old version, user id (type 13), single octet length
            >>> length = chr(0x17) # body occupies next 23 octets
            >>> body = "Tester <*****@*****.**>"
            >>> pkt = Packet(tag+length+body)
            >>> pkt.tag.type, pkt.length.size, pkt.body.value
            13, 23, 'Tester <*****@*****.**>'
        """
        # Partial Length Mechanics (..elif 1 == self.tag.version..): Body
        # length is determined locally (with the help of str2int
        # functions) to accomodate a flow between partial body fragments,
        # concluding fragments, and complete packet bodies (append to
        # list, concatenate the list at the end). The actual length object
        # is determined after the fact and must match up with the body
        # data recovered in order to pass a selfcheck().
        # TODO see how much of the new length logic can use NewLength.data2size.
        self.tag = Tag(d[0:1])
        if 0 == self.tag.version: # old
            lo = [1, 2, 4, 0][self.tag.length_type] # [length octs][length type]
            idx = 1 + lo
            self.length = OldLength(d[1:idx])

            if 'UNDEFINED' == self.length.size:
                self.fill_body(d[idx:])
            else:
                self.fill_body(d[idx:idx+self.length.size])

        elif 1 == self.tag.version: # new
            idx = 1
            bodydata, lengthdata = [], []
            L1 = d[idx:idx+1]
            L1_ord = ord(L1)

            while 224 <= L1_ord <= 254: # catch partials
                size, idx = STN.strcalc(STN.partial2int, L1, idx)

                if 0 == len(lengthdata) and 512 > size:
                    raise PGPFormatError("First partial length MUST be at least 512 octets long. Received: length.size->(%s) length.data->(%s)" % (len(lengthdata), hex(L1_ord)))

                else:
                    lengthdata.append(L1)
                    bodydata.append(d[idx:idx+size])
                    idx = idx + size
                    L1 = d[idx:idx+1]
                    L1_ord = ord(L1)

            if L1_ord < 192:
                size, idx = STN.strcalc(STN.str2int, L1, idx)
                lengthdata.append(L1)
                bodydata.append(d[idx:idx+size])

            elif 192 <= L1_ord <= 223:
                lengthdata.append(d[idx:idx+2])
                size, idx = STN.strcalc(STN.doubleoct2int, d[idx:idx+2], idx)
                bodydata.append(d[idx:idx+size])

            elif 255 == L1_ord:
                lengthdata.append(d[idx:idx+5])
                size, idx = STN.strcalc(STN.pentoct2int, d[idx:idx+5], idx)
                bodydata.append(d[idx:idx+size])

            else:
                raise PGPError, "Extreme weirdness. Fix source."
            self.length = NewLength(''.join(lengthdata))
            self.fill_body(''.join(bodydata))

        self.size = len(self.tag._d) + len(self.length._d) + len(self.body._d)

        if self.check():
            return 1
        else:
            raise self.err[0], self.err[1]
Beispiel #13
0
    def fill(self, d):
        """Set the Packet instances's data, filling its attributes.

        :Parameters:
            - `d`: string of OpenPGP packet data

        :Returns: Nothing

        Tag data (d) must be a string of valid OpenPGP packet data
        (tag, length, body, and possibly partial length/body
        interlacing).

        Example:

            >>> tag = chr(0xb4) # old version, user id (type 13), single octet length
            >>> length = chr(0x17) # body occupies next 23 octets
            >>> body = "Tester <*****@*****.**>"
            >>> pkt = Packet(tag+length+body)
            >>> pkt.tag.type, pkt.length.size, pkt.body.value
            13, 23, 'Tester <*****@*****.**>'
        """
        # Partial Length Mechanics (..elif 1 == self.tag.version..): Body
        # length is determined locally (with the help of str2int
        # functions) to accomodate a flow between partial body fragments,
        # concluding fragments, and complete packet bodies (append to
        # list, concatenate the list at the end). The actual length object
        # is determined after the fact and must match up with the body
        # data recovered in order to pass a selfcheck().
        # TODO see how much of the new length logic can use NewLength.data2size.
        self.tag = Tag(d[0:1])
        if 0 == self.tag.version:  # old
            lo = [1, 2, 4,
                  0][self.tag.length_type]  # [length octs][length type]
            idx = 1 + lo
            self.length = OldLength(d[1:idx])

            if 'UNDEFINED' == self.length.size:
                self.fill_body(d[idx:])
            else:
                self.fill_body(d[idx:idx + self.length.size])

        elif 1 == self.tag.version:  # new
            idx = 1
            bodydata, lengthdata = [], []
            L1 = d[idx:idx + 1]
            L1_ord = ord(L1)

            while 224 <= L1_ord <= 254:  # catch partials
                size, idx = STN.strcalc(STN.partial2int, L1, idx)

                if 0 == len(lengthdata) and 512 > size:
                    raise PGPFormatError(
                        "First partial length MUST be at least 512 octets long. Received: length.size->(%s) length.data->(%s)"
                        % (len(lengthdata), hex(L1_ord)))

                else:
                    lengthdata.append(L1)
                    bodydata.append(d[idx:idx + size])
                    idx = idx + size
                    L1 = d[idx:idx + 1]
                    L1_ord = ord(L1)

            if L1_ord < 192:
                size, idx = STN.strcalc(STN.str2int, L1, idx)
                lengthdata.append(L1)
                bodydata.append(d[idx:idx + size])

            elif 192 <= L1_ord <= 223:
                lengthdata.append(d[idx:idx + 2])
                size, idx = STN.strcalc(STN.doubleoct2int, d[idx:idx + 2], idx)
                bodydata.append(d[idx:idx + size])

            elif 255 == L1_ord:
                lengthdata.append(d[idx:idx + 5])
                size, idx = STN.strcalc(STN.pentoct2int, d[idx:idx + 5], idx)
                bodydata.append(d[idx:idx + size])

            else:
                raise PGPError, "Extreme weirdness. Fix source."
            self.length = NewLength(''.join(lengthdata))
            self.fill_body(''.join(bodydata))

        self.size = len(self.tag._d) + len(self.length._d) + len(self.body._d)

        if self.check():
            return 1
        else:
            raise self.err[0], self.err[1]
Beispiel #14
0
    def fill(self, d):
        self._d = d
        version_d = d[0]
        self.version, idx = STN.strcalc(STN.str2int, d[0], 0)

        if self.version in [2, 3]:
            hash_len, idx = STN.strcalc(STN.str2int, d[idx:idx + 1], idx)
            self.type, idx = STN.strcalc(STN.str2int, d[idx:idx + 1], idx)
            self.created, idx = STN.strcalc(STN.str2int, d[idx:idx + 4], idx)
            self.hashed_data = d[2:idx]
            self.keyid, idx = STN.strcalc(STN.str2hex, d[idx:idx + 8], idx)
            self.alg_pubkey, idx = STN.strcalc(STN.str2int, d[idx:idx + 1],
                                               idx)
            self.alg_hash, idx = STN.strcalc(STN.str2int, d[idx:idx + 1], idx)
            self.hashed_subpkts = []  # dummy settings to make searches easier
            self.unhashed_subpkts = []  #

        elif 4 == self.version:
            import struct
            _type_d, idx = STN.strcalc(None, d[idx:idx + 1], idx)
            self.type = STN.str2int(_type_d)
            self.alg_pubkey, idx = STN.strcalc(STN.str2int, d[idx:idx + 1],
                                               idx)
            self.alg_hash, idx = STN.strcalc(STN.str2int, d[idx:idx + 1], idx)
            # hashed subpackets
            subpkts_len, idx = STN.strcalc(STN.str2int, d[idx:idx + 2], idx)
            self.hashed_subpkts = self.__resolve_subpkts(d[idx:idx +
                                                           subpkts_len])
            # hashed data & trailer - should '>i' ever return more than 4 chars?
            hashed_data = d[0:idx + subpkts_len]
            bigend = struct.pack('>i', len(hashed_data))[-4:]
            self.hashed_data = ''.join(
                [hashed_data, version_d, '\xff', bigend])
            idx = idx + subpkts_len
            # unhashed subpackets
            subpkts_len, idx = STN.strcalc(STN.str2int, d[idx:idx + 2], idx)
            self.unhashed_subpkts = self.__resolve_subpkts(d[idx:idx +
                                                             subpkts_len])
            idx = idx + subpkts_len
            # attribute convenience
            self.keyid = self.__set_subpkt_attr(SIGSUB_SIGNERID) or ''
            self.created = self.__set_subpkt_attr(SIGSUB_CREATED) or 0

        else:
            raise PGPValueError(
                "Unsupported signature version. Received->(%s)" %
                str(self.version))

        self.hash_frag, idx = STN.strcalc(None, d[idx:idx + 2], idx)

        if self.alg_pubkey in [ASYM_RSA_S, ASYM_RSA_EOS]:
            self.RSA, idx = MPI.strcalc_mpi(d[idx:], idx)

        elif ASYM_DSA == self.alg_pubkey:
            self.DSA_r, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.DSA_s, idx = MPI.strcalc_mpi(d[idx:], idx)

        elif self.alg_pubkey in [ASYM_ELGAMAL_EOS]:
            self.ELGAMAL_a, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.ELGAMAL_b, idx = MPI.strcalc_mpi(d[idx:], idx)

        else:
            raise PGPValueError("Unsupported public-key algorithm (%d)." %
                                self.alg_pubkey)
Beispiel #15
0
    def fill(self, d):
        self._d = d
        version_d = d[0]
        self.version, idx = STN.strcalc(STN.str2int, d[0], 0)

        if self.version in [2, 3]:
            hash_len, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
            self.type, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
            self.created, idx = STN.strcalc(STN.str2int, d[idx:idx+4], idx)
            self.hashed_data = d[2:idx]
            self.keyid, idx = STN.strcalc(STN.str2hex, d[idx:idx+8], idx)
            self.alg_pubkey, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
            self.alg_hash, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
            self.hashed_subpkts = [] # dummy settings to make searches easier
            self.unhashed_subpkts = [] #

        elif 4 == self.version:
            import struct
            _type_d, idx = STN.strcalc(None, d[idx:idx+1], idx)
            self.type = STN.str2int(_type_d)
            self.alg_pubkey, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
            self.alg_hash, idx = STN.strcalc(STN.str2int, d[idx:idx+1], idx)
            # hashed subpackets
            subpkts_len, idx = STN.strcalc(STN.str2int, d[idx:idx+2], idx)
            self.hashed_subpkts = self.__resolve_subpkts(d[idx:idx+subpkts_len])
            # hashed data & trailer - should '>i' ever return more than 4 chars?
            hashed_data = d[0:idx+subpkts_len]
            bigend = struct.pack('>i', len(hashed_data))[-4:] 
            self.hashed_data = ''.join([hashed_data, version_d, '\xff', bigend])
            idx = idx + subpkts_len
            # unhashed subpackets
            subpkts_len, idx = STN.strcalc(STN.str2int, d[idx:idx+2], idx)
            self.unhashed_subpkts = self.__resolve_subpkts(d[idx:idx+subpkts_len])
            idx = idx + subpkts_len
            # attribute convenience
            self.keyid = self.__set_subpkt_attr(SIGSUB_SIGNERID) or ''
            self.created = self.__set_subpkt_attr(SIGSUB_CREATED) or 0

        else:
            raise PGPValueError("Unsupported signature version. Received->(%s)" % str(self.version))

        self.hash_frag, idx = STN.strcalc(None, d[idx:idx+2], idx)

        if self.alg_pubkey in [ASYM_RSA_S, ASYM_RSA_EOS]:
            self.RSA, idx = MPI.strcalc_mpi(d[idx:], idx)

        elif ASYM_DSA == self.alg_pubkey:
            self.DSA_r, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.DSA_s, idx = MPI.strcalc_mpi(d[idx:], idx)

        elif self.alg_pubkey in [ASYM_ELGAMAL_EOS]:
            self.ELGAMAL_a, idx = MPI.strcalc_mpi(d[idx:], idx)
            self.ELGAMAL_b, idx = MPI.strcalc_mpi(d[idx:], idx)

        else:
            raise PGPValueError("Unsupported public-key algorithm (%d)." % self.alg_pubkey)