1369ee090SLi-Wen Hsu#!/usr/local/bin/python2 208fca7a5SJohn-Mark Gurney# 308fca7a5SJohn-Mark Gurney# Copyright (c) 2014 The FreeBSD Foundation 408fca7a5SJohn-Mark Gurney# All rights reserved. 508fca7a5SJohn-Mark Gurney# 608fca7a5SJohn-Mark Gurney# This software was developed by John-Mark Gurney under 708fca7a5SJohn-Mark Gurney# the sponsorship from the FreeBSD Foundation. 808fca7a5SJohn-Mark Gurney# Redistribution and use in source and binary forms, with or without 908fca7a5SJohn-Mark Gurney# modification, are permitted provided that the following conditions 1008fca7a5SJohn-Mark Gurney# are met: 1108fca7a5SJohn-Mark Gurney# 1. Redistributions of source code must retain the above copyright 1208fca7a5SJohn-Mark Gurney# notice, this list of conditions and the following disclaimer. 1308fca7a5SJohn-Mark Gurney# 2. Redistributions in binary form must reproduce the above copyright 1408fca7a5SJohn-Mark Gurney# notice, this list of conditions and the following disclaimer in the 1508fca7a5SJohn-Mark Gurney# documentation and/or other materials provided with the distribution. 1608fca7a5SJohn-Mark Gurney# 1708fca7a5SJohn-Mark Gurney# THIS SOFTWARE IS PROVIDED BY THE AUTHOR AND CONTRIBUTORS ``AS IS'' AND 1808fca7a5SJohn-Mark Gurney# ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1908fca7a5SJohn-Mark Gurney# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 2008fca7a5SJohn-Mark Gurney# ARE DISCLAIMED. IN NO EVENT SHALL THE AUTHOR OR CONTRIBUTORS BE LIABLE 2108fca7a5SJohn-Mark Gurney# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL 2208fca7a5SJohn-Mark Gurney# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS 2308fca7a5SJohn-Mark Gurney# OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) 2408fca7a5SJohn-Mark Gurney# HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT 2508fca7a5SJohn-Mark Gurney# LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY 2608fca7a5SJohn-Mark Gurney# OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF 2708fca7a5SJohn-Mark Gurney# SUCH DAMAGE. 2808fca7a5SJohn-Mark Gurney# 2908fca7a5SJohn-Mark Gurney# $FreeBSD$ 3008fca7a5SJohn-Mark Gurney# 3108fca7a5SJohn-Mark Gurney 32d86680b0SEnji Cooperfrom __future__ import print_function 33a317fb03SConrad Meyerimport errno 3408fca7a5SJohn-Mark Gurneyimport cryptodev 3508fca7a5SJohn-Mark Gurneyimport itertools 3608fca7a5SJohn-Mark Gurneyimport os 3708fca7a5SJohn-Mark Gurneyimport struct 3808fca7a5SJohn-Mark Gurneyimport unittest 3908fca7a5SJohn-Mark Gurneyfrom cryptodev import * 4008fca7a5SJohn-Mark Gurneyfrom glob import iglob 4108fca7a5SJohn-Mark Gurney 4208fca7a5SJohn-Mark Gurneykatdir = '/usr/local/share/nist-kat' 4308fca7a5SJohn-Mark Gurney 4408fca7a5SJohn-Mark Gurneydef katg(base, glob): 45aeb5c8e6SJohn Baldwin assert os.path.exists(katdir), "Please 'pkg install nist-kat'" 46aeb5c8e6SJohn Baldwin if not os.path.exists(os.path.join(katdir, base)): 47aeb5c8e6SJohn Baldwin raise unittest.SkipTest("Missing %s test vectors" % (base)) 4808fca7a5SJohn-Mark Gurney return iglob(os.path.join(katdir, base, glob)) 4908fca7a5SJohn-Mark Gurney 50844d9543SConrad Meyeraesmodules = [ 'cryptosoft0', 'aesni0', 'ccr0', 'ccp0' ] 5108fca7a5SJohn-Mark Gurneydesmodules = [ 'cryptosoft0', ] 52844d9543SConrad Meyershamodules = [ 'cryptosoft0', 'aesni0', 'ccr0', 'ccp0' ] 5308fca7a5SJohn-Mark Gurney 5408fca7a5SJohn-Mark Gurneydef GenTestCase(cname): 5508fca7a5SJohn-Mark Gurney try: 5608fca7a5SJohn-Mark Gurney crid = cryptodev.Crypto.findcrid(cname) 5708fca7a5SJohn-Mark Gurney except IOError: 5808fca7a5SJohn-Mark Gurney return None 5908fca7a5SJohn-Mark Gurney 6008fca7a5SJohn-Mark Gurney class GendCryptoTestCase(unittest.TestCase): 6108fca7a5SJohn-Mark Gurney ############### 6208fca7a5SJohn-Mark Gurney ##### AES ##### 6308fca7a5SJohn-Mark Gurney ############### 64c091d0d9SJohn Baldwin @unittest.skipIf(cname not in aesmodules, 'skipping AES-XTS on %s' % (cname)) 6508fca7a5SJohn-Mark Gurney def test_xts(self): 6608fca7a5SJohn-Mark Gurney for i in katg('XTSTestVectors/format tweak value input - data unit seq no', '*.rsp'): 6708fca7a5SJohn-Mark Gurney self.runXTS(i, cryptodev.CRYPTO_AES_XTS) 6808fca7a5SJohn-Mark Gurney 69c091d0d9SJohn Baldwin @unittest.skipIf(cname not in aesmodules, 'skipping AES-CBC on %s' % (cname)) 7008fca7a5SJohn-Mark Gurney def test_cbc(self): 7108fca7a5SJohn-Mark Gurney for i in katg('KAT_AES', 'CBC[GKV]*.rsp'): 7208fca7a5SJohn-Mark Gurney self.runCBC(i) 7308fca7a5SJohn-Mark Gurney 74c091d0d9SJohn Baldwin @unittest.skipIf(cname not in aesmodules, 'skipping AES-GCM on %s' % (cname)) 7508fca7a5SJohn-Mark Gurney def test_gcm(self): 7608fca7a5SJohn-Mark Gurney for i in katg('gcmtestvectors', 'gcmEncrypt*'): 7708fca7a5SJohn-Mark Gurney self.runGCM(i, 'ENCRYPT') 7808fca7a5SJohn-Mark Gurney 7908fca7a5SJohn-Mark Gurney for i in katg('gcmtestvectors', 'gcmDecrypt*'): 8008fca7a5SJohn-Mark Gurney self.runGCM(i, 'DECRYPT') 8108fca7a5SJohn-Mark Gurney 8208fca7a5SJohn-Mark Gurney _gmacsizes = { 32: cryptodev.CRYPTO_AES_256_NIST_GMAC, 8308fca7a5SJohn-Mark Gurney 24: cryptodev.CRYPTO_AES_192_NIST_GMAC, 8408fca7a5SJohn-Mark Gurney 16: cryptodev.CRYPTO_AES_128_NIST_GMAC, 8508fca7a5SJohn-Mark Gurney } 8608fca7a5SJohn-Mark Gurney def runGCM(self, fname, mode): 8708fca7a5SJohn-Mark Gurney curfun = None 8808fca7a5SJohn-Mark Gurney if mode == 'ENCRYPT': 8908fca7a5SJohn-Mark Gurney swapptct = False 9008fca7a5SJohn-Mark Gurney curfun = Crypto.encrypt 9108fca7a5SJohn-Mark Gurney elif mode == 'DECRYPT': 9208fca7a5SJohn-Mark Gurney swapptct = True 9308fca7a5SJohn-Mark Gurney curfun = Crypto.decrypt 9408fca7a5SJohn-Mark Gurney else: 95d86680b0SEnji Cooper raise RuntimeError('unknown mode: %r' % repr(mode)) 9608fca7a5SJohn-Mark Gurney 9708fca7a5SJohn-Mark Gurney for bogusmode, lines in cryptodev.KATParser(fname, 9808fca7a5SJohn-Mark Gurney [ 'Count', 'Key', 'IV', 'CT', 'AAD', 'Tag', 'PT', ]): 9908fca7a5SJohn-Mark Gurney for data in lines: 10008fca7a5SJohn-Mark Gurney curcnt = int(data['Count']) 10108fca7a5SJohn-Mark Gurney cipherkey = data['Key'].decode('hex') 10208fca7a5SJohn-Mark Gurney iv = data['IV'].decode('hex') 10308fca7a5SJohn-Mark Gurney aad = data['AAD'].decode('hex') 10408fca7a5SJohn-Mark Gurney tag = data['Tag'].decode('hex') 10508fca7a5SJohn-Mark Gurney if 'FAIL' not in data: 10608fca7a5SJohn-Mark Gurney pt = data['PT'].decode('hex') 10708fca7a5SJohn-Mark Gurney ct = data['CT'].decode('hex') 10808fca7a5SJohn-Mark Gurney 10908fca7a5SJohn-Mark Gurney if len(iv) != 12: 11008fca7a5SJohn-Mark Gurney # XXX - isn't supported 11108fca7a5SJohn-Mark Gurney continue 11208fca7a5SJohn-Mark Gurney 113844d9543SConrad Meyer try: 11408fca7a5SJohn-Mark Gurney c = Crypto(cryptodev.CRYPTO_AES_NIST_GCM_16, 11508fca7a5SJohn-Mark Gurney cipherkey, 11608fca7a5SJohn-Mark Gurney mac=self._gmacsizes[len(cipherkey)], 117*de0f7dcaSJohn Baldwin mackey=cipherkey, crid=crid, 118*de0f7dcaSJohn Baldwin maclen=16) 119844d9543SConrad Meyer except EnvironmentError, e: 120844d9543SConrad Meyer # Can't test algorithms the driver does not support. 121844d9543SConrad Meyer if e.errno != errno.EOPNOTSUPP: 122844d9543SConrad Meyer raise 123844d9543SConrad Meyer continue 12408fca7a5SJohn-Mark Gurney 12508fca7a5SJohn-Mark Gurney if mode == 'ENCRYPT': 126844d9543SConrad Meyer try: 12708fca7a5SJohn-Mark Gurney rct, rtag = c.encrypt(pt, iv, aad) 128844d9543SConrad Meyer except EnvironmentError, e: 129844d9543SConrad Meyer # Can't test inputs the driver does not support. 130844d9543SConrad Meyer if e.errno != errno.EINVAL: 131844d9543SConrad Meyer raise 132844d9543SConrad Meyer continue 13308fca7a5SJohn-Mark Gurney rtag = rtag[:len(tag)] 13408fca7a5SJohn-Mark Gurney data['rct'] = rct.encode('hex') 13508fca7a5SJohn-Mark Gurney data['rtag'] = rtag.encode('hex') 136d86680b0SEnji Cooper self.assertEqual(rct, ct, repr(data)) 137d86680b0SEnji Cooper self.assertEqual(rtag, tag, repr(data)) 13808fca7a5SJohn-Mark Gurney else: 13908fca7a5SJohn-Mark Gurney if len(tag) != 16: 14008fca7a5SJohn-Mark Gurney continue 14108fca7a5SJohn-Mark Gurney args = (ct, iv, aad, tag) 14208fca7a5SJohn-Mark Gurney if 'FAIL' in data: 14308fca7a5SJohn-Mark Gurney self.assertRaises(IOError, 14408fca7a5SJohn-Mark Gurney c.decrypt, *args) 14508fca7a5SJohn-Mark Gurney else: 146844d9543SConrad Meyer try: 14708fca7a5SJohn-Mark Gurney rpt, rtag = c.decrypt(*args) 148844d9543SConrad Meyer except EnvironmentError, e: 149844d9543SConrad Meyer # Can't test inputs the driver does not support. 150844d9543SConrad Meyer if e.errno != errno.EINVAL: 151844d9543SConrad Meyer raise 152844d9543SConrad Meyer continue 15308fca7a5SJohn-Mark Gurney data['rpt'] = rpt.encode('hex') 15408fca7a5SJohn-Mark Gurney data['rtag'] = rtag.encode('hex') 15508fca7a5SJohn-Mark Gurney self.assertEqual(rpt, pt, 156d86680b0SEnji Cooper repr(data)) 15708fca7a5SJohn-Mark Gurney 15808fca7a5SJohn-Mark Gurney def runCBC(self, fname): 15908fca7a5SJohn-Mark Gurney curfun = None 16008fca7a5SJohn-Mark Gurney for mode, lines in cryptodev.KATParser(fname, 16108fca7a5SJohn-Mark Gurney [ 'COUNT', 'KEY', 'IV', 'PLAINTEXT', 'CIPHERTEXT', ]): 16208fca7a5SJohn-Mark Gurney if mode == 'ENCRYPT': 16308fca7a5SJohn-Mark Gurney swapptct = False 16408fca7a5SJohn-Mark Gurney curfun = Crypto.encrypt 16508fca7a5SJohn-Mark Gurney elif mode == 'DECRYPT': 16608fca7a5SJohn-Mark Gurney swapptct = True 16708fca7a5SJohn-Mark Gurney curfun = Crypto.decrypt 16808fca7a5SJohn-Mark Gurney else: 169d86680b0SEnji Cooper raise RuntimeError('unknown mode: %r' % repr(mode)) 17008fca7a5SJohn-Mark Gurney 17108fca7a5SJohn-Mark Gurney for data in lines: 17208fca7a5SJohn-Mark Gurney curcnt = int(data['COUNT']) 17308fca7a5SJohn-Mark Gurney cipherkey = data['KEY'].decode('hex') 17408fca7a5SJohn-Mark Gurney iv = data['IV'].decode('hex') 17508fca7a5SJohn-Mark Gurney pt = data['PLAINTEXT'].decode('hex') 17608fca7a5SJohn-Mark Gurney ct = data['CIPHERTEXT'].decode('hex') 17708fca7a5SJohn-Mark Gurney 17808fca7a5SJohn-Mark Gurney if swapptct: 17908fca7a5SJohn-Mark Gurney pt, ct = ct, pt 18008fca7a5SJohn-Mark Gurney # run the fun 18108fca7a5SJohn-Mark Gurney c = Crypto(cryptodev.CRYPTO_AES_CBC, cipherkey, crid=crid) 18208fca7a5SJohn-Mark Gurney r = curfun(c, pt, iv) 18308fca7a5SJohn-Mark Gurney self.assertEqual(r, ct) 18408fca7a5SJohn-Mark Gurney 18508fca7a5SJohn-Mark Gurney def runXTS(self, fname, meth): 18608fca7a5SJohn-Mark Gurney curfun = None 18708fca7a5SJohn-Mark Gurney for mode, lines in cryptodev.KATParser(fname, 18808fca7a5SJohn-Mark Gurney [ 'COUNT', 'DataUnitLen', 'Key', 'DataUnitSeqNumber', 'PT', 18908fca7a5SJohn-Mark Gurney 'CT' ]): 19008fca7a5SJohn-Mark Gurney if mode == 'ENCRYPT': 19108fca7a5SJohn-Mark Gurney swapptct = False 19208fca7a5SJohn-Mark Gurney curfun = Crypto.encrypt 19308fca7a5SJohn-Mark Gurney elif mode == 'DECRYPT': 19408fca7a5SJohn-Mark Gurney swapptct = True 19508fca7a5SJohn-Mark Gurney curfun = Crypto.decrypt 19608fca7a5SJohn-Mark Gurney else: 197d86680b0SEnji Cooper raise RuntimeError('unknown mode: %r' % repr(mode)) 19808fca7a5SJohn-Mark Gurney 19908fca7a5SJohn-Mark Gurney for data in lines: 20008fca7a5SJohn-Mark Gurney curcnt = int(data['COUNT']) 20108fca7a5SJohn-Mark Gurney nbits = int(data['DataUnitLen']) 20208fca7a5SJohn-Mark Gurney cipherkey = data['Key'].decode('hex') 20308fca7a5SJohn-Mark Gurney iv = struct.pack('QQ', int(data['DataUnitSeqNumber']), 0) 20408fca7a5SJohn-Mark Gurney pt = data['PT'].decode('hex') 20508fca7a5SJohn-Mark Gurney ct = data['CT'].decode('hex') 20608fca7a5SJohn-Mark Gurney 20708fca7a5SJohn-Mark Gurney if nbits % 128 != 0: 20808fca7a5SJohn-Mark Gurney # XXX - mark as skipped 20908fca7a5SJohn-Mark Gurney continue 21008fca7a5SJohn-Mark Gurney if swapptct: 21108fca7a5SJohn-Mark Gurney pt, ct = ct, pt 21208fca7a5SJohn-Mark Gurney # run the fun 213844d9543SConrad Meyer try: 21408fca7a5SJohn-Mark Gurney c = Crypto(meth, cipherkey, crid=crid) 21508fca7a5SJohn-Mark Gurney r = curfun(c, pt, iv) 216844d9543SConrad Meyer except EnvironmentError, e: 217844d9543SConrad Meyer # Can't test hashes the driver does not support. 218844d9543SConrad Meyer if e.errno != errno.EOPNOTSUPP: 219844d9543SConrad Meyer raise 220844d9543SConrad Meyer continue 22108fca7a5SJohn-Mark Gurney self.assertEqual(r, ct) 22208fca7a5SJohn-Mark Gurney 22308fca7a5SJohn-Mark Gurney ############### 22408fca7a5SJohn-Mark Gurney ##### DES ##### 22508fca7a5SJohn-Mark Gurney ############### 226d86680b0SEnji Cooper @unittest.skipIf(cname not in desmodules, 'skipping DES on %s' % (cname)) 22708fca7a5SJohn-Mark Gurney def test_tdes(self): 22808fca7a5SJohn-Mark Gurney for i in katg('KAT_TDES', 'TCBC[a-z]*.rsp'): 22908fca7a5SJohn-Mark Gurney self.runTDES(i) 23008fca7a5SJohn-Mark Gurney 23108fca7a5SJohn-Mark Gurney def runTDES(self, fname): 23208fca7a5SJohn-Mark Gurney curfun = None 23308fca7a5SJohn-Mark Gurney for mode, lines in cryptodev.KATParser(fname, 23408fca7a5SJohn-Mark Gurney [ 'COUNT', 'KEYs', 'IV', 'PLAINTEXT', 'CIPHERTEXT', ]): 23508fca7a5SJohn-Mark Gurney if mode == 'ENCRYPT': 23608fca7a5SJohn-Mark Gurney swapptct = False 23708fca7a5SJohn-Mark Gurney curfun = Crypto.encrypt 23808fca7a5SJohn-Mark Gurney elif mode == 'DECRYPT': 23908fca7a5SJohn-Mark Gurney swapptct = True 24008fca7a5SJohn-Mark Gurney curfun = Crypto.decrypt 24108fca7a5SJohn-Mark Gurney else: 242d86680b0SEnji Cooper raise RuntimeError('unknown mode: %r' % repr(mode)) 24308fca7a5SJohn-Mark Gurney 24408fca7a5SJohn-Mark Gurney for data in lines: 24508fca7a5SJohn-Mark Gurney curcnt = int(data['COUNT']) 24608fca7a5SJohn-Mark Gurney key = data['KEYs'] * 3 24708fca7a5SJohn-Mark Gurney cipherkey = key.decode('hex') 24808fca7a5SJohn-Mark Gurney iv = data['IV'].decode('hex') 24908fca7a5SJohn-Mark Gurney pt = data['PLAINTEXT'].decode('hex') 25008fca7a5SJohn-Mark Gurney ct = data['CIPHERTEXT'].decode('hex') 25108fca7a5SJohn-Mark Gurney 25208fca7a5SJohn-Mark Gurney if swapptct: 25308fca7a5SJohn-Mark Gurney pt, ct = ct, pt 25408fca7a5SJohn-Mark Gurney # run the fun 25508fca7a5SJohn-Mark Gurney c = Crypto(cryptodev.CRYPTO_3DES_CBC, cipherkey, crid=crid) 25608fca7a5SJohn-Mark Gurney r = curfun(c, pt, iv) 25708fca7a5SJohn-Mark Gurney self.assertEqual(r, ct) 25808fca7a5SJohn-Mark Gurney 25908fca7a5SJohn-Mark Gurney ############### 26008fca7a5SJohn-Mark Gurney ##### SHA ##### 26108fca7a5SJohn-Mark Gurney ############### 262d86680b0SEnji Cooper @unittest.skipIf(cname not in shamodules, 'skipping SHA on %s' % str(cname)) 26308fca7a5SJohn-Mark Gurney def test_sha(self): 264*de0f7dcaSJohn Baldwin for i in katg('shabytetestvectors', 'SHA*Msg.rsp'): 265*de0f7dcaSJohn Baldwin self.runSHA(i) 266*de0f7dcaSJohn Baldwin 267*de0f7dcaSJohn Baldwin def runSHA(self, fname): 268*de0f7dcaSJohn Baldwin # Skip SHA512_(224|256) tests 269*de0f7dcaSJohn Baldwin if fname.find('SHA512_') != -1: 270*de0f7dcaSJohn Baldwin return 271*de0f7dcaSJohn Baldwin 272*de0f7dcaSJohn Baldwin for hashlength, lines in cryptodev.KATParser(fname, 273*de0f7dcaSJohn Baldwin [ 'Len', 'Msg', 'MD' ]): 274*de0f7dcaSJohn Baldwin # E.g., hashlength will be "L=20" (bytes) 275*de0f7dcaSJohn Baldwin hashlen = int(hashlength.split("=")[1]) 276*de0f7dcaSJohn Baldwin 277*de0f7dcaSJohn Baldwin if hashlen == 20: 278*de0f7dcaSJohn Baldwin alg = cryptodev.CRYPTO_SHA1 279*de0f7dcaSJohn Baldwin elif hashlen == 28: 280*de0f7dcaSJohn Baldwin alg = cryptodev.CRYPTO_SHA2_224 281*de0f7dcaSJohn Baldwin elif hashlen == 32: 282*de0f7dcaSJohn Baldwin alg = cryptodev.CRYPTO_SHA2_256 283*de0f7dcaSJohn Baldwin elif hashlen == 48: 284*de0f7dcaSJohn Baldwin alg = cryptodev.CRYPTO_SHA2_384 285*de0f7dcaSJohn Baldwin elif hashlen == 64: 286*de0f7dcaSJohn Baldwin alg = cryptodev.CRYPTO_SHA2_512 287*de0f7dcaSJohn Baldwin else: 288*de0f7dcaSJohn Baldwin # Skip unsupported hashes 289*de0f7dcaSJohn Baldwin # Slurp remaining input in section 290*de0f7dcaSJohn Baldwin for data in lines: 291*de0f7dcaSJohn Baldwin continue 292*de0f7dcaSJohn Baldwin continue 293*de0f7dcaSJohn Baldwin 294*de0f7dcaSJohn Baldwin for data in lines: 295*de0f7dcaSJohn Baldwin msg = data['Msg'].decode('hex') 296*de0f7dcaSJohn Baldwin msg = msg[:int(data['Len'])] 297*de0f7dcaSJohn Baldwin md = data['MD'].decode('hex') 298*de0f7dcaSJohn Baldwin 299*de0f7dcaSJohn Baldwin try: 300*de0f7dcaSJohn Baldwin c = Crypto(mac=alg, crid=crid, 301*de0f7dcaSJohn Baldwin maclen=hashlen) 302*de0f7dcaSJohn Baldwin except EnvironmentError, e: 303*de0f7dcaSJohn Baldwin # Can't test hashes the driver does not support. 304*de0f7dcaSJohn Baldwin if e.errno != errno.EOPNOTSUPP: 305*de0f7dcaSJohn Baldwin raise 306*de0f7dcaSJohn Baldwin continue 307*de0f7dcaSJohn Baldwin 308*de0f7dcaSJohn Baldwin _, r = c.encrypt(msg, iv="") 309*de0f7dcaSJohn Baldwin 310*de0f7dcaSJohn Baldwin self.assertEqual(r, md, "Actual: " + \ 311*de0f7dcaSJohn Baldwin repr(r.encode("hex")) + " Expected: " + repr(data) + " on " + cname) 31208fca7a5SJohn-Mark Gurney 313c091d0d9SJohn Baldwin @unittest.skipIf(cname not in shamodules, 'skipping SHA-HMAC on %s' % str(cname)) 31408fca7a5SJohn-Mark Gurney def test_sha1hmac(self): 31508fca7a5SJohn-Mark Gurney for i in katg('hmactestvectors', 'HMAC.rsp'): 31608fca7a5SJohn-Mark Gurney self.runSHA1HMAC(i) 31708fca7a5SJohn-Mark Gurney 31808fca7a5SJohn-Mark Gurney def runSHA1HMAC(self, fname): 319005fdbbcSConrad Meyer for hashlength, lines in cryptodev.KATParser(fname, 32008fca7a5SJohn-Mark Gurney [ 'Count', 'Klen', 'Tlen', 'Key', 'Msg', 'Mac' ]): 321005fdbbcSConrad Meyer # E.g., hashlength will be "L=20" (bytes) 322005fdbbcSConrad Meyer hashlen = int(hashlength.split("=")[1]) 323005fdbbcSConrad Meyer 324005fdbbcSConrad Meyer blocksize = None 325005fdbbcSConrad Meyer if hashlen == 20: 326005fdbbcSConrad Meyer alg = cryptodev.CRYPTO_SHA1_HMAC 327005fdbbcSConrad Meyer blocksize = 64 328005fdbbcSConrad Meyer elif hashlen == 28: 329c87ada6aSJohn Baldwin alg = cryptodev.CRYPTO_SHA2_224_HMAC 330c87ada6aSJohn Baldwin blocksize = 64 331005fdbbcSConrad Meyer elif hashlen == 32: 332005fdbbcSConrad Meyer alg = cryptodev.CRYPTO_SHA2_256_HMAC 333005fdbbcSConrad Meyer blocksize = 64 334005fdbbcSConrad Meyer elif hashlen == 48: 335005fdbbcSConrad Meyer alg = cryptodev.CRYPTO_SHA2_384_HMAC 336005fdbbcSConrad Meyer blocksize = 128 337005fdbbcSConrad Meyer elif hashlen == 64: 338005fdbbcSConrad Meyer alg = cryptodev.CRYPTO_SHA2_512_HMAC 339005fdbbcSConrad Meyer blocksize = 128 340005fdbbcSConrad Meyer else: 341005fdbbcSConrad Meyer # Skip unsupported hashes 342005fdbbcSConrad Meyer # Slurp remaining input in section 343005fdbbcSConrad Meyer for data in lines: 344005fdbbcSConrad Meyer continue 345005fdbbcSConrad Meyer continue 346005fdbbcSConrad Meyer 34708fca7a5SJohn-Mark Gurney for data in lines: 34808fca7a5SJohn-Mark Gurney key = data['Key'].decode('hex') 34908fca7a5SJohn-Mark Gurney msg = data['Msg'].decode('hex') 35008fca7a5SJohn-Mark Gurney mac = data['Mac'].decode('hex') 351005fdbbcSConrad Meyer tlen = int(data['Tlen']) 35208fca7a5SJohn-Mark Gurney 353005fdbbcSConrad Meyer if len(key) > blocksize: 35408fca7a5SJohn-Mark Gurney continue 35508fca7a5SJohn-Mark Gurney 356a317fb03SConrad Meyer try: 357005fdbbcSConrad Meyer c = Crypto(mac=alg, mackey=key, 358*de0f7dcaSJohn Baldwin crid=crid, maclen=hashlen) 359a317fb03SConrad Meyer except EnvironmentError, e: 360a317fb03SConrad Meyer # Can't test hashes the driver does not support. 361a317fb03SConrad Meyer if e.errno != errno.EOPNOTSUPP: 362a317fb03SConrad Meyer raise 363a317fb03SConrad Meyer continue 36408fca7a5SJohn-Mark Gurney 365005fdbbcSConrad Meyer _, r = c.encrypt(msg, iv="") 366005fdbbcSConrad Meyer 367*de0f7dcaSJohn Baldwin self.assertEqual(r[:tlen], mac, "Actual: " + \ 368*de0f7dcaSJohn Baldwin repr(r.encode("hex")) + " Expected: " + repr(data)) 36908fca7a5SJohn-Mark Gurney 37008fca7a5SJohn-Mark Gurney return GendCryptoTestCase 37108fca7a5SJohn-Mark Gurney 37208fca7a5SJohn-Mark Gurneycryptosoft = GenTestCase('cryptosoft0') 37308fca7a5SJohn-Mark Gurneyaesni = GenTestCase('aesni0') 3746720b890SJohn Baldwinccr = GenTestCase('ccr0') 375844d9543SConrad Meyerccp = GenTestCase('ccp0') 37608fca7a5SJohn-Mark Gurney 37708fca7a5SJohn-Mark Gurneyif __name__ == '__main__': 37808fca7a5SJohn-Mark Gurney unittest.main() 379