def treehash(self, secret_seed, s, z, public_seed, adrs: ADRS): if s % (1 << z) != 0: return -1 stack = [] for i in range(0, 2 ** z): adrs.set_type(ADRS.WOTS_HASH) adrs.set_key_pair_address(s + i) node = self.wots_pk_gen(secret_seed, public_seed, adrs.copy()) adrs.set_type(ADRS.TREE) adrs.set_tree_height(1) adrs.set_tree_index(s + i) if len(stack) > 0: while stack[len(stack) - 1]['height'] == adrs.get_tree_height(): adrs.set_tree_index((adrs.get_tree_index() - 1) // 2) node = hash(public_seed, adrs.copy(), stack.pop()['node'] + node, self._n) adrs.set_tree_height(adrs.get_tree_height() + 1) if len(stack) <= 0: break stack.append({'node': node, 'height': adrs.get_tree_height()}) return stack.pop()['node']
def fors_pk_from_sig(self, sig_fors, m, public_seed, adrs: ADRS): m_int = int.from_bytes(m, 'big') sigs = self.auths_from_sig_fors(sig_fors) root = bytes() for i in range(0, self._k): idx = (m_int >> (self._k - 1 - i) * self._a) % self._t sk = sigs[i][0] adrs.set_tree_height(0) adrs.set_tree_index(i * self._t + idx) node_0 = hash(public_seed, adrs.copy(), sk, self._n) node_1 = 0 auth = sigs[i][1] adrs.set_tree_index(i * self._t + idx) # Really Useful? for j in range(0, self._a): adrs.set_tree_height(j + 1) if math.floor(idx / 2**j) % 2 == 0: adrs.set_tree_index(adrs.get_tree_index() // 2) node_1 = hash(public_seed, adrs.copy(), node_0 + auth[j], self._n) else: adrs.set_tree_index((adrs.get_tree_index() - 1) // 2) node_1 = hash(public_seed, adrs.copy(), auth[j] + node_0, self._n) node_0 = node_1 root += node_0 fors_pk_adrs = adrs.copy() fors_pk_adrs.set_type(ADRS.FORS_ROOTS) fors_pk_adrs.set_key_pair_address(adrs.get_key_pair_address()) pk = hash(public_seed, fors_pk_adrs, root, self._n) return pk