def hashData(elements, keys, algo, depco): """ Prepare the data and use them in a dep call I_ECI_HMAC_PCI_DATA. Returns the data hashed with pci algo and key. """ logger.debug('data to hash : %r', elements) logger.debug('key : %r', keys) logger.debug('algo-id : %r', algo) if isinstance(elements, str): elements = [elements] if isinstance(keys, int): keys = [keys] assert len(keys) == len(elements), 'The number of keys has to match the number of data to hash. (%d - %d)' % (len(keys), len(elements)) msg = ['FF'] for data, key in zip(elements, keys): msg.extend((dep.D_ECI_PCI_DATA, '%04X' % len(data), codecs.encode(data.encode(), 'hex').decode(), dep.D_ECI_KEY_SEL_PCI_HMAC, '%02X' % key, dep.D_ECI_PCI_HMAC_ALGO_ID, '%02s' % algo)) msg.append(dep.I_ECI_HMAC_PCI_DATA * len(elements)) msg.append(dep.D_ECI_PCI_HMAC * len(elements)) msg = ''.join(msg) result = depco.send(msg) logger.debug('returns : ' + result) if dep.D_ECI_PCI_HMAC not in result: raise ValueError('DEP returns error: ' + result) return zip(map(op.itemgetter(1), dep._dep_data_parser(result, result.find(dep.D_ECI_PCI_HMAC))), elements, keys)
def computeDDACertificate(keypair, pan, iss_privkey_index, iss_privkey_range, icc_sernum, icc_certexpdate, data2sign, pincert, deps, iss_privkey=None): pan_length = int(ceil(len(pan) / 2)) data_length = int(ceil(len(data2sign) / 2)) msg = 'FF' msg += dep.D_PKI_ENC_RSA_KEY + format(len(keypair) // 2, '04X') + keypair msg += dep.D_EMV_PAN + '%02X' % pan_length + pan.ljust(pan_length, 'F') msg += dep.D_EMV_CERT_EXP_DATE + icc_certexpdate msg += dep.D_EMV_CERT_SER_NUM + icc_sernum msg += dep.D_EMV_HASH_ALGO_ID + '01' msg += dep.D_EMV_ISS_KEY_INDEX + iss_privkey_index msg += dep.D_EMV_KEY_RANGE + iss_privkey_range msg += dep.D_EMV_STA_DATA_2_AUTH + '%04X' % data_length + data2sign if iss_privkey: msg += dep.D_STD_KEY_FROM_HOST + iss_privkey msg += dep.I_PKI_IMPORT_RSA_KEY if not pincert else dep.I_EMV_COMPUTE_ICC_PENC_PK_CERT msg += dep.I_EMV_COMPUTE_ICC_PK_CERT msg += dep.D_EMV_ICC_PK_CERT if not pincert else dep.D_EMV_ICC_PENC_PK_CERT msg += dep.D_EMV_ICC_PK_EXP msg += dep.D_EMV_ICC_PK_REM logger.debug('DEP call : %s', msg) depmsg = dep.DEPMessage(msg) result = depmsg.sendTo(deps).upper() logger.debug('returns : %s', result) if dep.D_EMV_ICC_PK_CERT not in result: raise ValueError('DEP returns error: ' + result) parser = dep._dep_data_parser(result, start_pos=result.find(dep.D_EMV_ICC_PK_CERT)) _, cert = next(parser) _, exp = next(parser) _, rem = next(parser) return cert, exp, rem