Source code for hsslms.utils

#!/usr/bin/env python3
# -*- coding: utf-8 -*-
"""
Created on Sat Jan  1 11:48:07 2022

@author: mvr
"""
from enum import Enum
from hashlib import sha256

[docs]class INVALID(Exception): """Exception for an invalid signature.""" pass
[docs]class FAILURE(Exception): """Exception for general technical failures , e.g. if no private key is left to sign.""" pass
[docs]def u32str(i): return i.to_bytes(4, 'big')
[docs]def u16str(i): return i.to_bytes(2, 'big')
[docs]def u8str(i): return i.to_bytes(1, 'big')
[docs]def strTou32(S): return int.from_bytes(S, 'big')
[docs]def coef(S, i, w): return (2**w - 1) & (S[(i*w) >> 3] >> (8 - (w * (i % (8 // w)) + w)))
[docs]def cksm(S, w, n, ls): return u16str(((2**w - 1)*((n*8)//w) - sum([coef(S,i,w) for i in range((n*8)//w)])) << ls)
D_PBLC = u16str(0x8080) D_MESG = u16str(0x8181) D_LEAF = u16str(0x8282) D_INTR = u16str(0x8383)
[docs]class LMOTS_ALGORITHM_TYPE(Enum): """Enumeration of Leighton-Micali One-Time-Signatures (LMOTS) algorithm types, see rfc8554. Attributes: H: Hashfunction n (int): Outputlength of the hashfunction w (int): number of simultanious signes bits p (int): internal dependent parameter ls (int): internal dependent parameter """ LMOTS_SHA256_N32_W1 = 1 LMOTS_SHA256_N32_W2 = 2 LMOTS_SHA256_N32_W4 = 3 LMOTS_SHA256_N32_W8 = 4 LMOTS_SHA256_N24_W1 = 5 LMOTS_SHA256_N24_W2 = 6 LMOTS_SHA256_N24_W4 = 7 LMOTS_SHA256_N24_W8 = 8 @property def H(self): return sha256 @property def n(self): if 'N32' in self.name: return 32 else: return 24 @property def w(self): return {1:1, 2:2, 3:4, 4:8, 5:1, 6:2, 7:4, 8:8}[self.value] @property def p(self): return {1:265, 2:133, 3:67, 4:34, 5:200, 6:101, 7:51, 8:26}[self.value] @property def ls(self): return {1:7, 2:6, 3:4, 4:0, 5:8, 6:6, 7:4, 8:0}[self.value]
[docs]class LMS_ALGORITHM_TYPE(Enum): """Enumeration of Leighton-Micali Signatures (LMS) algorithm types, see rfc8554. Attributes: H: Hashfunction m (int): Outputlength of the hashfunction h (int): height of the tree """ LMS_SHA256_M32_H5 = 5 LMS_SHA256_M32_H10 = 6 LMS_SHA256_M32_H15 = 7 LMS_SHA256_M32_H20 = 8 LMS_SHA256_M32_H25 = 9 LMS_SHA256_M24_H5 = 10 LMS_SHA256_M24_H10 = 11 LMS_SHA256_M24_H15 = 12 LMS_SHA256_M24_H20 = 13 LMS_SHA256_M24_H25 = 14 @property def H(self): return sha256 @property def m(self): if 'M32' in self.name: return 32 else: return 24 @property def h(self): return {5:5, 6:10, 7:15, 8:20, 9:25, 10:5, 11:10, 12:15, 13:20, 14:25}[self.value]